An EXIT handler terminates the current compound statement when the specified condition occurs. When a condition occurs and an exit handler is invoked, control is passed to the handler. When the handler completes, control returns to the caller of the compound statement.
In IBM DB2, the DECLARE EXIT HANDLER statement is used to define actions that should be taken when specific SQL conditions or errors occur during procedure execution. Unlike CONTINUE handlers, EXIT handlers terminate the execution of the current block and return control to the caller.
When migrating from DB2 to Snowflake, SnowConvert AI transforms EXIT HANDLER declarations into equivalent Snowflake Scripting exception handling using EXCEPTION blocks with WHEN OTHER EXIT THEN or specific exception types.
DECLAREEXITHANDLERFOR condition_value [,...]
handler_action_statement;-- Where condition_value can be:-- SQLSTATE [VALUE] sqlstate_value-- condition_name-- SQLWARNING-- SQLEXCEPTION-- NOT FOUND
CREATEPROCEDURE error_exit_handler()LANGUAGESQLBEGINDECLAREEXITHANDLERFOR SQLEXCEPTION
BEGININSERTINTO error_log VALUES(CURRENT_TIMESTAMP,'Error occurred, exiting');END;-- These statements may cause errorsINSERTINTO table1 VALUES(1/0);UPDATE table2 SET status ='completed'WHERE id =-1;-- This will NOT execute if an error occurred aboveINSERTINTO success_log VALUES('All operations completed');END;
CREATEORREPLACEPROCEDURE error_exit_handler()RETURNSVARCHARLANGUAGESQLCOMMENT='{ "origin": "sf_sc", "name": "snowconvert", "version": { "major": 0, "minor": 0, "patch": "0" }, "attributes": { "component": "db2", "convertedOn": "01/15/2025" }}'AS$$
BEGIN
-- These statements may cause errors
INSERT INTO table1 VALUES (1/0);
UPDATE table2 SET status = 'completed' WHERE id = -1;
-- This will NOT execute if an error occurred above
INSERT INTO success_log VALUES ('All operations completed');
EXCEPTION
WHEN OTHER THEN
BEGIN
INSERT INTO error_log VALUES (CURRENT_TIMESTAMP(), 'Error occurred, exiting');
END;
END;
$$;
CREATEORREPLACEPROCEDURE sqlstate_exit_handler()RETURNSVARCHARLANGUAGESQLCOMMENT='{ "origin": "sf_sc", "name": "snowconvert", "version": { "major": 0, "minor": 0, "patch": "0" }, "attributes": { "component": "db2", "convertedOn": "01/15/2025" }}'AS$$
BEGIN
-- Attempt to insert records
INSERT INTO users VALUES (1, 'John');
INSERT INTO users VALUES (1, 'Jane'); -- Duplicate key - will trigger handler
INSERT INTO users VALUES (2, 'Bob'); -- Will NOT execute
EXCEPTION
WHEN OTHER EXIT THEN
CASE
WHEN (SQLSTATE = '23505') THEN
BEGIN
INSERT INTO error_log VALUES ('Duplicate key error, exiting procedure');
ROLLBACK;
END;
END;
END;
$$;
CREATEPROCEDURE cursor_exit_handler()LANGUAGESQLBEGINDECLARE v_id INT;DECLARE v_name VARCHAR(100);DECLAREEXITHANDLERFORNOT FOUND
INSERTINTO log_table VALUES('No data found, exiting');-- This will trigger the handler if no rows foundSELECT id,nameINTO v_id, v_name
FROM employees
WHERE department ='NonExistent';-- This will NOT execute if no rows were foundINSERTINTO results VALUES(v_id, v_name);END;
CREATEORREPLACEPROCEDURE cursor_exit_handler()RETURNSVARCHARLANGUAGESQLCOMMENT='{ "origin": "sf_sc", "name": "snowconvert", "version": { "major": 0, "minor": 0, "patch": "0" }, "attributes": { "component": "db2", "convertedOn": "01/15/2025" }}'AS$$
DECLARE
v_id INT;
v_name VARCHAR(100);
BEGIN
-- This will trigger the handler if no rows found
SELECT id, name INTO v_id, v_name
FROM employees
WHERE department = 'NonExistent';
-- This will NOT execute if no rows were found
INSERT INTO results VALUES (v_id, v_name);
EXCEPTION
WHEN NO_DATA_FOUND THEN
INSERT INTO log_table VALUES ('No data found, exiting');
END;
$$;
DB2 allows multiple EXIT HANDLERs with different priorities. In Snowflake, handler precedence must be managed through explicit conditional logic using CASE statements.
EXIT HANDLER in DB2 terminates the current compound statement and returns control to the caller. In Snowflake, this is achieved using the EXCEPTION block, which automatically exits the current BEGIN…END block when an exception occurs.
The main behavioral differences are:
Execution Termination: Both DB2 and Snowflake exit the current block when an EXIT handler is triggered.
Statement-level Control: In DB2, the EXIT handler activates at the statement that causes the error. In Snowflake, the entire remaining block is skipped.
Nested Blocks: Exit behavior in nested blocks is consistent between DB2 and Snowflake.
DB2 allows declaring both CONTINUE and EXIT handlers in the same procedure block. However, Snowflake Scripting does not support mixing CONTINUE and EXIT handlers in the same EXCEPTION block. When this pattern is encountered, SnowConvert AI generates separate EXCEPTION blocks with an EWI warning.
CREATEORREPLACEPROCEDURE with_continueAndExit()RETURNSVARCHARLANGUAGESQLCOMMENT='{ "origin": "sf_sc", "name": "snowconvert", "version": { "major": 0, "minor": 0, "patch": "0" }, "attributes": { "component": "db2", "convertedOn": "01/15/2025" }}'AS$$
DECLARE
test_1 INTEGER DEFAULT 10;
BEGIN
test_1 := 1 / 0;
INSERT INTO error_test VALUES ('COMPLETED');
EXCEPTION
WHEN OTHER CONTINUE THEN
INSERT INTO error_test VALUES ('EXCEPTION')
!!!RESOLVE EWI!!! /*** SSC-EWI-0114 - MIXED CONTINUE AND EXIT EXCEPTION HANDLERS IN THE SAME BLOCK ARE NOT SUPPORTED BY SNOWFLAKE SCRIPTING ***/!!!
EXCEPTION
WHEN OTHER EXIT THEN
CASE
WHEN (SQLSTATE = '20000') THEN
INSERT INTO error_test VALUES ('ERROR 2000')
END
END;
$$;