Membandingkan transaksi dan kumpulan

Selesai

Sangat membantu untuk membandingkan perilaku batch T-SQL, yang diapit dalam blok TRY/CATCH, dengan perilaku transaksi.

Pertimbangkan kode berikut yang menyisipkan dua pesanan pelanggan, memerlukan baris dalam tabel SalesLT.SalesOrderHeader , dan satu atau beberapa baris dalam tabel SalesLT.SalesOrderDetail . Semua pernyataan INSERT diapit dalam blok TRY.

  • Jika penyisipan pertama gagal, eksekusi akan diteruskan ke blok CATCH dan tidak ada kode lebih lanjut yang dijalankan.
  • Jika sisipan kedua gagal, eksekusi akan diteruskan ke blok CATCH dan tidak ada kode lebih lanjut yang dijalankan. Namun, sisipan pertama berhasil, dan tidak digulung kembali, sehingga meninggalkan database dalam status yang tidak konsisten. Baris untuk pesanan telah disisipkan, tetapi tidak ada baris yang disisipkan untuk detail pesanan.
BEGIN TRY
	INSERT INTO dbo.Orders(custid, empid, orderdate) 
		VALUES (68, 9, '2021-07-12');
	INSERT INTO dbo.Orders(custid, empid, orderdate) 
		VALUES (88, 3, '2021-07-15');
	INSERT INTO dbo.OrderDetails(orderid,productid,unitprice,qty) 
		VALUES (1, 2, 15.20, 20);
	INSERT INTO dbo.OrderDetails(orderid,productid,unitprice,qty) 
		VALUES (999, 77, 26.20, 15);
END TRY
BEGIN CATCH
	SELECT ERROR_NUMBER() AS ErrNum, ERROR_MESSAGE() AS ErrMsg;
END CATCH;

Bandingkan ini dengan menerapkan kode dalam transaksi. Blok TRY/CATCH masih digunakan untuk penanganan kesalahan, namun pernyataan INSERT untuk tabel Orders dan OrderDetails diapit dalam kata kunci BEGIN TRANSACTION/COMMIT TRANSACTION. Ini memastikan bahwa semua pernyataan diperlakukan sebagai satu transaksi, yang berhasil atau gagal. Salah satu baris ditulis ke tabel Orders dan OrderDetails, atau tidak ada baris yang disisipkan. Dengan cara ini, database tidak pernah dalam keadaan tidak konsisten.

BEGIN TRY
 BEGIN TRANSACTION;
	INSERT INTO dbo.Orders(custid, empid, orderdate) 
		VALUES (68,9,'2006-07-15');
	INSERT INTO dbo.OrderDetails(orderid,productid,unitprice,qty) 
		VALUES (99, 2,15.20,20);
	COMMIT TRANSACTION;
END TRY
BEGIN CATCH
 SELECT ERROR_NUMBER() AS ErrNum, ERROR_MESSAGE() AS ErrMsg;
 ROLLBACK TRANSACTION;
END CATCH;