하나의 트리거안에 여러가지 작업을 실행시키는것보다 작업들을 각각의 프로시저로 만든다음 전체를 실행시켜주는 프로시저로 나누었다.
이렇게 한 이유에는 한 트리거안에 복잡한 작업들이 여러개 실행된다면 성능저하가 우려되고, 또한 그 중 한가지 작업이라도 에러가 발생한다면 모두 롤백되기 때문이다.
이를 프로시저로 바꾼다면 성능저하도 해결할 수 있고, 또한 트랜잭션을 관리해줌으로써 중간에 에러가 발생하더라도 꼭 필요한 데이터에 대한 작업은 실행이 될것이다.
delimiter //
DROP procedure if EXISTS insert_delivery_processing;
CREATE PROCEDURE insert_delivery_processing(in updated_order_id BIGINT)
BEGIN
DECLARE selected_dv_order_id BIGINT;
DECLARE exit handler FOR SQLEXCEPTION
BEGIN
ROLLBACK;
INSERT INTO transaction_log(
message,
order_id
) VALUES(
'insert_delivery_processing 프로시저 에러 발생',
updated_order_id
);
END;
START TRANSACTION;
CALL insert_delivery_order(updated_order_id, selected_dv_order_id); -- 트랜잭션 관리를 어떻게 할것인가
COMMIT;
START TRANSACTION;
CALL insert_chat_channel(selected_dv_order_id);
COMMIT;
START TRANSACTION;
CALL insert_delivery_insurance(selected_dv_order_id);
COMMIT;
END //
delimiter ;
drop procedure insert_delivery_processing;
exit handler를 이용해서 이 통합 프로시저에 에러가 발생할 경우 로그가 테이블에 생성되게했다.
이 과정에서 에러가 발생되어 롤백이 되는데도 계속 로그테이블에 기록이 생성되지않는 문제가 발생했는데,
문제는 에러테이블의 INSERT문과 핸들러의 ROLLBACK의 위치가 잘못되어서였다..
DECLARE exit handler FOR SQLEXCEPTION
BEGIN
INSERT INTO transaction_log(
message,
order_id
) VALUES(
'insert_delivery_processing 프로시저 에러 발생',
updated_order_id
);
ROLLBACK;
END;
이렇게 될 경우 insert문이 실행되어도 이후에 ROLLBACK이 실행되어 INSERT문이 롤백되어버린다.