Catatan
Akses ke halaman ini memerlukan otorisasi. Anda dapat mencoba masuk atau mengubah direktori.
Akses ke halaman ini memerlukan otorisasi. Anda dapat mencoba mengubah direktori.
Berlaku untuk:SQL Server
Azure SQL Database
Azure SQL Managed Instance
Azure Synapse Analytics
Sistem Platform Analitik (PDW)
Titik akhir analitik SQL di Microsoft Fabric
Gudang di Microsoft Fabric
Database SQL di Microsoft Fabric
Menerapkan penanganan kesalahan untuk Transact-SQL yang mirip dengan penanganan pengecualian dalam bahasa C# dan Visual C++. Sekelompok pernyataan Transact-SQL dapat diapit dalam TRY blok. Jika terjadi kesalahan di blok, kontrol biasanya diteruskan TRY ke grup pernyataan lain yang diapit dalam CATCH blok.
Syntax
BEGIN TRY
{ sql_statement | statement_block }
END TRY
BEGIN CATCH
[ { sql_statement | statement_block } ]
END CATCH
[ ; ]
Arguments
sql_statement
Setiap pernyataan T-SQL.
statement_block
Setiap grup pernyataan Transact-SQL dalam batch atau diapit dalam BEGIN...END blok.
Remarks
Konstruksi TRY...CATCH menangkap semua kesalahan eksekusi yang memiliki tingkat keparahan lebih tinggi dari 10 yang tidak menutup koneksi database.
Blok TRY harus segera diikuti oleh blok terkait CATCH . Menyertakan pernyataan lain antara END TRY pernyataan dan BEGIN CATCH menghasilkan kesalahan sintaks.
Konstruksi TRY...CATCH tidak dapat mencakup beberapa batch. Konstruksi TRY...CATCH tidak dapat mencakup beberapa blok pernyataan Transact-SQL. Misalnya, TRY...CATCH konstruksi tidak dapat mencakup dua BEGIN...END blok pernyataan Transact-SQL, dan tidak dapat menjangkau IF...ELSE konstruksi.
Jika tidak ada kesalahan dalam kode yang diapit dalam TRY blok, ketika pernyataan terakhir dalam TRY blok selesai, kontrol meneruskan ke pernyataan segera setelah pernyataan terkait END CATCH .
Jika ada kesalahan dalam kode yang diapit dalam TRY blok, kontrol akan meneruskan ke pernyataan pertama di blok terkait CATCH . Ketika kode di CATCH blok selesai, kontrol meneruskan ke pernyataan segera setelah END CATCH pernyataan.
Note
END CATCH Jika pernyataan adalah pernyataan terakhir dalam prosedur atau pemicu yang disimpan, kontrol diteruskan kembali ke pernyataan yang disebut prosedur tersimpan atau menembakkan pemicu.
Kesalahan yang CATCH terperangkap oleh blok tidak dikembalikan ke aplikasi panggilan. Jika ada bagian dari informasi kesalahan yang harus dikembalikan ke aplikasi, kode dalam CATCH blok harus melakukannya dengan menggunakan mekanisme seperti SELECT tataan hasil atau RAISERROR pernyataan dan PRINT .
TRY...CATCH konstruksi dapat ditumpuk.
TRY Blok atau CATCH blok dapat berisi konstruksi berlapisTRY...CATCH. Misalnya, CATCH blok dapat berisi konstruksi yang disematkan TRY...CATCH untuk menangani kesalahan yang ditemui oleh CATCH kode.
Kesalahan yang ditemui dalam CATCH blok diperlakukan seperti kesalahan yang dihasilkan di tempat lain.
CATCH Jika blok berisi konstruksi berlapisTRY...CATCH, kesalahan apa pun di blok berlapis meneruskan TRY kontrol ke blok berlapisCATCH. Jika tidak ada konstruksi berlapis TRY...CATCH , kesalahan akan diteruskan kembali ke pemanggil.
TRY...CATCH konstruksi menangkap kesalahan yang tidak tertangani dari prosedur tersimpan atau pemicu yang dijalankan oleh kode di TRY blok. Atau, prosedur atau pemicu yang disimpan dapat berisi konstruksi mereka sendiri TRY...CATCH untuk menangani kesalahan yang dihasilkan oleh kode mereka. Misalnya, ketika TRY blok menjalankan prosedur tersimpan dan kesalahan terjadi dalam prosedur tersimpan, kesalahan dapat ditangani dengan cara berikut:
Jika prosedur tersimpan tidak berisi konstruksinya sendiri
TRY...CATCH, kesalahan mengembalikan kontrol keCATCHblok yang terkait denganTRYblok yang berisiEXECUTEpernyataan.Jika prosedur tersimpan berisi
TRY...CATCHkonstruksi, kesalahan mentransfer kontrol keCATCHblok dalam prosedur tersimpan.CATCHKetika kode blok selesai, kontrol diteruskan kembali ke pernyataan segera setelahEXECUTEpernyataan yang memanggil prosedur tersimpan.
GOTO pernyataan tidak dapat digunakan untuk memasukkan TRY atau CATCH memblokir.
GOTOpernyataan dapat digunakan untuk melompat ke label di dalam blok atau TRY yang sama CATCH atau untuk meninggalkan atau TRYCATCH memblokir.
Konstruksi TRY...CATCH tidak dapat digunakan dalam fungsi yang ditentukan pengguna.
Mengambil informasi kesalahan
Dalam cakupan CATCH blok, fungsi sistem berikut dapat digunakan untuk mendapatkan informasi tentang kesalahan yang menyebabkan CATCH blok dijalankan:
| Function | Description |
|---|---|
| ERROR_NUMBER | Mengembalikan jumlah kesalahan. |
| ERROR_SEVERITY | Mengembalikan tingkat keparahan. |
| ERROR_STATE | Mengembalikan nomor status kesalahan. |
| ERROR_PROCEDURE | Mengembalikan nama prosedur tersimpan atau pemicu tempat kesalahan terjadi. |
| ERROR_LINE | Mengembalikan nomor baris di dalam rutinitas yang menyebabkan kesalahan. |
| ERROR_MESSAGE | Mengembalikan teks lengkap pesan kesalahan. Teks mencakup nilai yang disediakan untuk parameter yang dapat diganti, seperti panjang, nama objek, atau waktu. |
Fungsi-fungsi ini kembali NULL jika dipanggil di luar cakupan CATCH blok. Informasi kesalahan dapat diambil dengan menggunakan fungsi-fungsi ini dari mana saja dalam cakupan CATCH blok. Misalnya, skrip berikut menunjukkan prosedur tersimpan yang berisi fungsi penanganan kesalahan.
CATCH Di blok TRY...CATCH konstruksi, prosedur tersimpan dipanggil dan informasi tentang kesalahan dikembalikan.
-- Verify that the stored procedure does not already exist.
IF OBJECT_ID('usp_GetErrorInfo', 'P') IS NOT NULL
DROP PROCEDURE usp_GetErrorInfo;
GO
-- Create procedure to retrieve error information.
CREATE PROCEDURE usp_GetErrorInfo
AS
SELECT ERROR_NUMBER() AS ErrorNumber,
ERROR_SEVERITY() AS ErrorSeverity,
ERROR_STATE() AS ErrorState,
ERROR_PROCEDURE() AS ErrorProcedure,
ERROR_LINE() AS ErrorLine,
ERROR_MESSAGE() AS ErrorMessage;
GO
BEGIN TRY
-- Generate divide-by-zero error.
SELECT 1 / 0;
END TRY
BEGIN CATCH
-- Execute error retrieval routine.
EXECUTE usp_GetErrorInfo;
END CATCH;
Fungsi ini ERROR_* juga berfungsi di CATCH blok di dalam prosedur tersimpan yang dikompilasi secara asli.
Kesalahan tidak terpengaruh oleh TRY... Konstruksi CATCH
TRY...CATCH konstruksi tidak menjebak kondisi berikut:
Peringatan atau pesan informasi yang memiliki tingkat keparahan 10 atau lebih rendah.
Kesalahan yang memiliki tingkat keparahan 20 atau lebih tinggi yang menghentikan pemrosesan tugas Mesin Database SQL Server untuk sesi tersebut. Jika terjadi kesalahan yang memiliki tingkat keparahan 20 atau lebih tinggi dan koneksi database tidak terganggu,
TRY...CATCHmenangani kesalahan.Perhatian, seperti permintaan yang mengganggu klien atau koneksi klien yang rusak.
Ketika administrator sistem menggunakan
KILLpernyataan untuk mengakhiri sesi.
Jenis kesalahan berikut tidak ditangani oleh CATCH blok ketika terjadi pada tingkat eksekusi yang sama dengan TRY...CATCH konstruksi:
Kompilasi kesalahan, seperti kesalahan sintaksis, yang mencegah batch berjalan.
Kesalahan yang terjadi selama kompilasi ulang tingkat pernyataan, seperti kesalahan resolusi nama objek yang terjadi setelah kompilasi karena resolusi nama yang ditangguhkan.
Kesalahan resolusi nama objek
Kesalahan ini dikembalikan ke tingkat yang menjalankan batch, prosedur tersimpan, atau pemicu.
Jika terjadi kesalahan selama kompilasi atau kompilasi ulang tingkat pernyataan pada tingkat eksekusi yang lebih rendah (misalnya, saat mengeksekusi sp_executesql atau prosedur tersimpan yang ditentukan pengguna) di dalam TRY blok, kesalahan terjadi pada tingkat yang lebih rendah dari TRY...CATCH konstruksi dan akan ditangani oleh blok terkait CATCH .
Contoh berikut menunjukkan bagaimana kesalahan resolusi nama objek yang SELECT dihasilkan oleh pernyataan tidak ditangkap oleh TRY...CATCH konstruksi, tetapi ditangkap oleh CATCH blok ketika pernyataan yang sama dijalankan di dalam prosedur tersimpan SELECT .
BEGIN TRY
-- Table does not exist; object name resolution
-- error not caught.
SELECT *
FROM NonexistentTable;
END TRY
BEGIN CATCH
SELECT ERROR_NUMBER() AS ErrorNumber,
ERROR_MESSAGE() AS ErrorMessage;
END CATCH
Kesalahan tidak tertangkap dan kontrol keluar dari TRY...CATCH konstruksi ke tingkat yang lebih tinggi berikutnya.
Menjalankan pernyataan di SELECT dalam prosedur tersimpan menyebabkan kesalahan terjadi pada tingkat yang lebih rendah dari TRY blok. Kesalahan ditangani oleh TRY...CATCH konstruksi.
-- Verify that the stored procedure does not exist.
IF OBJECT_ID(N'usp_ExampleProc', N'P') IS NOT NULL
DROP PROCEDURE usp_ExampleProc;
GO
-- Create a stored procedure that will cause an
-- object resolution error.
CREATE PROCEDURE usp_ExampleProc
AS
SELECT *
FROM NonexistentTable;
GO
BEGIN TRY
EXECUTE usp_ExampleProc;
END TRY
BEGIN CATCH
SELECT ERROR_NUMBER() AS ErrorNumber,
ERROR_MESSAGE() AS ErrorMessage;
END CATCH;
Transaksi dan XACT_STATE yang tidak dapat diterapkan
Jika kesalahan yang dihasilkan dalam TRY blok menyebabkan status transaksi saat ini tidak valid, transaksi diklasifikasikan sebagai transaksi yang tidak dapat diterapkan. Kesalahan yang biasanya mengakhiri transaksi di luar TRY blok menyebabkan transaksi memasuki status tidak dapat diterapkan ketika kesalahan terjadi di dalam TRY blok. Transaksi yang tidak dapat diterapkan hanya dapat melakukan operasi baca atau ROLLBACK TRANSACTION. Transaksi tidak dapat menjalankan pernyataan Transact-SQL apa pun yang akan menghasilkan operasi tulis atau COMMIT TRANSACTION. Fungsi XACT_STATE mengembalikan nilai -1 jika transaksi telah diklasifikasikan sebagai transaksi yang tidak dapat diterapkan. Ketika batch selesai, Mesin Database mengembalikan transaksi aktif yang tidak dapat diterapkan. Jika tidak ada pesan kesalahan yang dikirim ketika transaksi memasuki status yang tidak dapat diterapkan, ketika batch selesai, pesan kesalahan dikirim ke aplikasi klien. Ini menunjukkan bahwa transaksi yang tidak dapat diterapkan terdeteksi dan digulung balik.
Untuk informasi selengkapnya tentang transaksi dan fungsi yang XACT_STATE tidak dapat diterapkan, lihat XACT_STATE.
Examples
A. Gunakan TRY... MENANGKAP
Contoh berikut menunjukkan SELECT pernyataan yang menghasilkan kesalahan dibagi berdasarkan nol. Kesalahan menyebabkan eksekusi melompat ke blok terkait CATCH .
BEGIN TRY
-- Generate a divide-by-zero error.
SELECT 1 / 0;
END TRY
BEGIN CATCH
SELECT ERROR_NUMBER() AS ErrorNumber,
ERROR_SEVERITY() AS ErrorSeverity,
ERROR_STATE() AS ErrorState,
ERROR_PROCEDURE() AS ErrorProcedure,
ERROR_LINE() AS ErrorLine,
ERROR_MESSAGE() AS ErrorMessage;
END CATCH;
GO
B. Gunakan TRY... CATCH dalam transaksi
Contoh berikut menunjukkan cara TRY...CATCH kerja blok di dalam transaksi. Pernyataan di TRY dalam blok menghasilkan kesalahan pelanggaran batasan.
BEGIN TRANSACTION;
BEGIN TRY
-- Generate a constraint violation error.
DELETE
FROM Production.Product
WHERE ProductID = 980;
END TRY
BEGIN CATCH
SELECT ERROR_NUMBER() AS ErrorNumber,
ERROR_SEVERITY() AS ErrorSeverity,
ERROR_STATE() AS ErrorState,
ERROR_PROCEDURE() AS ErrorProcedure,
ERROR_LINE() AS ErrorLine,
ERROR_MESSAGE() AS ErrorMessage;
IF @@TRANCOUNT > 0
ROLLBACK TRANSACTION;
END CATCH;
IF @@TRANCOUNT > 0
COMMIT TRANSACTION;
GO
C. Gunakan TRY... CATCH dengan XACT_STATE
Contoh berikut menunjukkan cara menggunakan TRY...CATCH konstruksi untuk menangani kesalahan yang terjadi di dalam transaksi. Fungsi menentukan XACT_STATE apakah transaksi harus dilakukan atau digulung balik. Dalam contoh ini, SET XACT_ABORT adalah ON. Ini membuat transaksi tidak dapat diterapkan ketika kesalahan pelanggaran batasan terjadi.
-- Check to see whether this stored procedure exists.
IF OBJECT_ID(N'usp_GetErrorInfo', N'P') IS NOT NULL
DROP PROCEDURE usp_GetErrorInfo;
GO
-- Create procedure to retrieve error information.
CREATE PROCEDURE usp_GetErrorInfo
AS
SELECT ERROR_NUMBER() AS ErrorNumber,
ERROR_SEVERITY() AS ErrorSeverity,
ERROR_STATE() AS ErrorState,
ERROR_LINE() AS ErrorLine,
ERROR_PROCEDURE() AS ErrorProcedure,
ERROR_MESSAGE() AS ErrorMessage;
GO
-- SET XACT_ABORT ON will cause the transaction to be uncommittable
-- when the constraint violation occurs.
SET XACT_ABORT ON;
BEGIN TRY
BEGIN TRANSACTION;
-- A FOREIGN KEY constraint exists on this table. This
-- statement will generate a constraint violation error.
DELETE
FROM Production.Product
WHERE ProductID = 980;
-- If the DELETE statement succeeds, commit the transaction.
COMMIT TRANSACTION;
END TRY
BEGIN CATCH
-- Execute error retrieval routine.
EXECUTE usp_GetErrorInfo;
-- Test XACT_STATE:
-- If 1, the transaction is committable.
-- If -1, the transaction is uncommittable and should
-- be rolled back.
-- XACT_STATE = 0 means that there is no transaction and
-- a commit or rollback operation would generate an error.
-- Test whether the transaction is uncommittable.
IF (XACT_STATE()) = -1
BEGIN
PRINT N'The transaction is in an uncommittable state. Rolling back transaction.'
ROLLBACK TRANSACTION;
END;
-- Test whether the transaction is committable.
-- You may want to commit a transaction in a catch block if you want to commit changes to statements that ran prior to the error.
IF (XACT_STATE()) = 1
BEGIN
PRINT N'The transaction is committable. Committing transaction.'
COMMIT TRANSACTION;
END;
END CATCH;
GO
Konten terkait
- LEMPAR (Transact-SQL)
- Tingkat keparahan kesalahan Mesin Database
- ERROR_LINE (T-SQL)
- ERROR_MESSAGE (T-SQL)
- ERROR_NUMBER (T-SQL)
- ERROR_PROCEDURE (T-SQL)
- ERROR_SEVERITY (T-SQL)
- ERROR_STATE (T-SQL)
- RAISERROR (Transact-SQL)
- @@ERROR (T-SQL)
- GOTO (Transact-SQL)
- MULAI... AKHIR (Transact-SQL)
- XACT_STATE (Transact-SQL)
- SET XACT_ABORT (Transact-SQL)