I have the following structure:
PROCEDURE A
BEGIN TRANSACTION
WHILE <loops 20 times>
BEGIN
--10 minute script
--INSERT a single record into table X
END
COMMIT TRANSACTION
PROCEDURE B - This is run via the agent every 10 minutes it scans table X for any new entries and if it finds any it sends an e-mail
If everything runs ok 20 new records will be added to table X – will these records only get added to X if all 20 loops have been successful? If the loop gets to it’s 5th iteration and then errors will the first 4 records be committed ?
Well, holding a transaction open for 10 minutes is evil. Holding a transaction open 20 times for 10 minutes is … well, 20 times more evil. Long lived transactions are very very very damaging and they cause serious problems in locking and blocking, log use and growth, recovery problems. Never design anything that has transactions longer than seconds. Time for you to revisit the fundamental issue you’re trying to solve and come up with a radically different solution.
As for the core question: transactions can use savepoints in such iterations, so that iteration 1-4 are saved (committed) even if iteration 5 hits an issue and has to rollback. The trick is to rollback up to a savepoint, not completely. Follow the same pattern as in Exception Handling and Nested Transactions. Note that not every error is recoverable, some errors will force a complete rollback (eg. deadlock is a typical example).