Menerima kenyamanan menggunakan tes unit pada C ++ favorit saya, saya mencoba untuk mentransfer pengalaman saya ke TSQL, terutama karena majikan baru suka inisiatif yang berguna di lapangan dan mendistribusikan roti untuk itu.
Saya melihat melalui beberapa
kerangka kerja terkenal, saya sampai pada kesimpulan bahwa, sebagai aturan, mereka besar dan membawa sintaks tambahan yang perlu dipelajari tambahan.
Beberapa kerangka kerja bekerja dengan indah dan menyenangkan mata manajer, kepada siapa mereka ditampilkan, tetapi memiliki sejumlah keterbatasan yang saya tidak suka.
Saya ingin mengimplementasikan semuanya pada TSQL halal-halal-Orthodox murni.
Dari waktu ke waktu, mengalihkan perhatian dari pengembangan utama selama beberapa tahun karena mengasah struktur skrip, saya memutuskan untuk membagikannya kepada Anda (tetapi masih berhasil menghasilkan skrip 3,5 Mb).
Persyaratan dasar saya sederhana - Saya harus melakukan uji unit dalam file tanpa perlu gerakan dan perangkat lunak khusus - hanya hardcore: sqlcmd atau MSSMS.
Tidak ada perubahan yang dilakukan pada database di mana tes dilakukan - semuanya digulung kembali ke awal skrip.
Hanya satu batasan yang ditetapkan - tes harus bekerja dalam database kosong (data awal mungkin), jika tidak Anda bosan membongkar semua opsi.
Tugas utama adalah menguji logika dan menjaga integritas logika.
Untuk ini, saya letakkan judul berikut di awal tes:
SET QUOTED_IDENTIFIER ON GO PRINT '-------------------------------- CLR Unit tests for Habr Logic ---------------------------------' IF 0 < ( SELECT count(*) FROM device) begin RAISERROR ('FAILED: database must be empty for this unit test', 16, -1 ) end GO
Saya mencoba untuk tidak membuat tes unit lebih lama dari beberapa layar, meskipun ini tidak mudah, dalam kasus logika yang kompleks.
Tes unit tipikal terlihat seperti ini dan memiliki 3 bagian utama:
BEGIN TRAN TestClr2 declare @test_name sysname = (select TOP 1 name from sys.dm_tran_active_transactions WHERE transaction_type = 1 ORDER BY transaction_begin_time DESC) + ' [fn_calculate_dev_status] record for device has wrong range' BEGIN TRY SET NOCOUNT ON;
- 1. menyiapkan data untuk unit testDi sini kita bisa mengisi tabel yang diperlukan dengan data dan menyiapkan beberapa variabel sementara atau tabel agar tidak mengacaukan kode di bagian pengujian.
- 2. jalankan unit testDi sini, sebagai aturan, ia dapat berfungsi, panggilan fungsi, atau prosedur, atau perubahan tabel, jika kami menguji logika pemicu.
- 3. verifikasi hasilDi bagian pengujian ini, kami memeriksa bagaimana keadaan objek database telah berubah, atau hasil dari fungsi-prosedur yang diuji.
Jika fungsi prosedur mengembalikan catatan, maka kami memasukkannya ke tabel sementara dan menganalisisnya.
Hasil agregat dan disiapkan dibandingkan dengan standar dan melemparkan pengecualian jika semuanya gagal.
Dengan Oracle, semuanya sedikit lebih rumit - saya tidak bisa melakukan penulisan dan menjalankan tes dalam bentuk itu dan dalam ideologi yang sama, bukan dari sedikit pengalaman - kami berhenti mendukung Oracle untuk produk kami.
Setiap unit tes dikeluarkan sebagai prosedur:
CREATE OR REPLACE PROCEDURE UnitTest9_TRG_JOBLOGDETAIL AS v_message VARCHAR2(255) := 'UnitTest9_TRG_JOBLOGDETAIL: INSERT joblogdetail]- joblogdetail_result not Failed and joblogdetail_endtime is null '; v_maxdate date := '2014/01/01'; v_cnt NUMBER := 0; BEGIN savepoint my_savepoint; <b>
Pada file tes yang sama di akhir, Anda harus melakukan pembersihan database dari tes yang dibuat dan dijalankan.
commit; / set serveroutput on; SET FEEDBACK OFF; spool C:\dist\test.spl; exec UnitTest_empty_database; exec UnitTest3297_TRGBFR_UDEVICE(1); exec UnitTest5_TRG_BF_UDEVICE; exec UnitTest_3062a; ... spool off; / DROP PROCEDURE UnitTest_3062; DROP PROCEDURE UnitTest_BIRDIESEC_3344; DROP PROCEDURE UnitTest_empty_database; ... SET FEEDBACK ON; commit;
Itu saja.
Kemudian Anda hanya menghasilkan file, dibagi ke dalam kategori jenis: pemicu, fungsi, prosedur, laporan, objek besar dan khusus dari logika bisnis, dan tentu saja, untuk setiap objek basis data.
Hampir semua pengembang basis data mengerutkan kening dan berkata - mengapa saya harus, biarkan penguji melakukan ini. Jika database tidak memiliki logika dari kata sama sekali, maka saya setuju dengan mereka, tetapi jika ada banyak, maka mereka secara alami menyelamatkan saraf, reputasi dan uang.
Sebuah contoh
Kami memiliki pohon antarmuka web koneksi logis antara objek pohon seperti Amerika -> Kanada -> Ontario -> Waterloo, Asia -> Jepang -> Tokyo -> Ebina, yaitu, seluruh bola kantor geografis.
Setiap node tersebut memiliki aturan yang sangat kompleks, pengguna atau aturan atau generator menetapkan perangkat.
Akibatnya, bahkan instruksi yang dijelaskan secara rinci dalam langkah-langkah menghancurkan semua orang, bahkan mereka yang berpartisipasi dalam diskusi dan pengembangan logika ini.
Lebih dari lima puluh langkah instruksi dengan set data yang berbeda - semuanya didokumentasikan secara rinci.
Setiap perubahan atau penambahan pada logika adalah jam verifikasi manual yang tidak ada yang rusak.
Refactoring kematian serupa.
Setelah saya membahas logika dengan unit test, semuanya diperiksa oleh sutra dan saya yakin semuanya berfungsi sebagaimana mestinya.
Setiap pengembang java menggunakan saya, melemparkan guntur dan kilat (berpikir sendiri tentang tangan saya yang bengkok) dengan mudah dilakukan dengan menjalankan tes yang sesuai.
Beberapa menit dan semua orang puas. Setiap perubahan kode fatal dalam ketidakhadiran saya akan cepat dilaporkan kepada saya melalui surat.
Secara alami, sebagai orang yang malas, saya memutuskan untuk mengotomatisasi segalanya untuk Continuous Automation dan menulis bubur dari batch dan python.
Saya meminta Anda untuk mengeksekusi sedikit, dalam pengembangan sehari-hari hampir selusin bahasa dan lingkungan di mana Anda harus melompat, ada kekurangan waktu untuk menjilat semuanya dan menempatkannya dalam tampilan profesional.
Saya tidak ingin melakukan segalanya di Windows PowerShell - melompat kami masih berjalan di sana-sini pada Windows95 tertanam.
Saya ingin membuat semua panggilan dengan Python, tetapi ternyata beberapa konstruksi sql (XML-parsing dalam cte) tidak didukung tidak hanya di pustaka python, tetapi juga dalam .NET, jadi saya melakukan scripting melalui sqlcmd.
Kode diposting di
sini .
Untuk menjalankan contoh yang berfungsi, cukup edit 2 file: smtppart.py dan config.ini - nama server SMTP, port dan email tempat pesan kesalahan akan dihapus.
Skrip pertama kali mencoba untuk mendapatkan pembaruan terbaru dari svn (ganti dengan milik Anda - git, terpaksa, ...).
Kemudian basis bersih dibuat dari skrip dengan nama acak, tes unit diluncurkan di dalamnya, kemudian basis dihapus.
Membuat database skrip 80 Mb dan tes 3,5 Mb (bagian utama dari skema sudah dilakukan sebelum saya bergabung dengan perusahaan, jadi saya menguji hanya bagian saya) dilakukan pada mesin saya dalam waktu sekitar 15 menit. Saya hanya punya waktu untuk minum secangkir kopi sebelum komit terakhir.
Jika ada kesalahan, maka hasil kesalahan akan dikirim ke email.
Instalasi ketergantungan dijelaskan dalam file: readme.txt
Setelah setiap perubahan kode, Anda harus secara manual mengatur kode hash (akan terlihat di baris perintah) di file config.ini - pesan akan datang bahkan jika kode diubah dan tidak ada yang rusak - jadi saya dapat mengontrol perubahan dalam kode sehingga saya dapat memeriksa perubahan tanpa Keterlibatan saya sebelumnya.

Peluncuran semua tes unit dalam file autorun.bat dapat ditempatkan di
Penjadwal Tugas Windows untuk berjalan 1-2 hari sebelum perusahaan membangun atau setelah meninggalkan rumah - jika ada yang rusak di malam hari - Anda dapat melihat apa yang terjadi di depan TV dan dengan cepat memperbaikinya.
Saya tahu bahwa dalam unit test itu yang paling sulit untuk mengatur semuanya, dan kemudian itu mudah dan menyenangkan untuk menulis tes, meskipun itu bisa sulit dan sulit, tetapi perlu. Semoga sukses dalam pengujian, saya harap saran saya akan membantu seseorang.
Saya akan dengan senang hati menerima saran jika sesuatu dapat ditingkatkan di suatu tempat dan menyisir kode, jangan menilai dengan ketat.