Database Sampel untuk OLTP Dalam Memori
Berlaku untuk: SQL ServerAzure SQL Database
Gambaran Umum
Sampel ini menampilkan fitur OLTP Dalam Memori. Ini menunjukkan tabel yang dioptimalkan memori dan prosedur tersimpan yang dikompilasi secara asli, dan dapat digunakan untuk menunjukkan manfaat performa OLTP Dalam Memori.
Catatan
Untuk melihat topik ini untuk SQL Server 2014 (12.x), lihat Ekstensi ke AdventureWorks untuk Menunjukkan OLTP Dalam Memori.
Sampel memigrasikan lima tabel dalam database ke memori yang dioptimalkan AdventureWorks2022
, dan mencakup beban kerja demo untuk pemrosesan pesanan penjualan. Anda dapat menggunakan beban kerja demo ini untuk melihat manfaat performa menggunakan OLTP Dalam Memori di server Anda.
Dalam deskripsi sampel, kita membahas tradeoff yang dibuat dalam memigrasikan tabel ke OLTP Dalam Memori untuk memperhitungkan fitur yang belum (belum) didukung untuk tabel yang dioptimalkan memori.
Dokumentasi sampel ini disusun sebagai berikut:
Prasyarat untuk menginstal sampel dan menjalankan beban kerja demo.
Petunjuk untuk Menginstal sampel OLTP Dalam Memori berdasarkan AdventureWorks.
Deskripsi tabel dan prosedur sampel - mencakup deskripsi tabel dan prosedur yang ditambahkan oleh
AdventureWorks2022
sampel OLTP Dalam Memori, serta pertimbangan untuk memigrasikan beberapa tabel asliAdventureWorks2022
agar dioptimalkan memori.Petunjuk untuk melakukan Pengukuran Performa menggunakan Beban Kerja Demo - mencakup instruksi untuk menginstal dan menjalankan ostress, alat yang menggunakan untuk mendorong beban kerja, serta menjalankan beban kerja demo itu sendiri.
Prasyarat
-
SQL Server 2016 (13.x)
Untuk pengujian performa, server dengan spesifikasi yang mirip dengan lingkungan produksi Anda. Untuk sampel khusus ini, Anda harus memiliki setidaknya 16 GB memori yang tersedia untuk SQL Server. Untuk panduan umum tentang perangkat keras untuk OLTP Dalam Memori, lihat posting blog berikut: Pertimbangan perangkat keras untuk OLTP Dalam Memori di SQL Server 2014
Menginstal sampel OLTP Dalam Memori berdasarkan AdventureWorks
Ikuti langkah-langkah berikut untuk menginstal sampel:
Unduh
AdventureWorks2016_EXT.bak
danSQLServer2016Samples.zip
dari: https://github.com/microsoft/sql-server-samples/releases/tag/adventureworks ke folder lokal, misalnyaC:\Temp
.Pulihkan cadangan database menggunakan Transact-SQL atau SQL Server Management Studio:
Identifikasi folder target dan nama file untuk file data, misalnya
'h:\DATA\AdventureWorks2022_Data.mdf'
Identifikasi folder target dan nama file untuk file log, misalnya
'i:\DATA\AdventureWorks2022_log.ldf'
- File log harus ditempatkan pada drive yang berbeda dari file data, idealnya drive latensi rendah seperti penyimpanan SSD atau PCIe, untuk performa maksimum.
Contoh skrip T-SQL:
RESTORE DATABASE [AdventureWorks2022] FROM DISK = N'C:\temp\AdventureWorks2022.bak' WITH FILE = 1, MOVE N'AdventureWorks2022_Data' TO N'h:\DATA\AdventureWorks2022_Data.mdf', MOVE N'AdventureWorks2022_Log' TO N'i:\DATA\AdventureWorks2022_log.ldf', MOVE N'AdventureWorks2022_mod' TO N'h:\data\AdventureWorks2022_mod' GO
Untuk melihat contoh skrip dan beban kerja, bongkar file SQLServer2016Samples.zip ke folder lokal. Lihat file OLTP\readme.txt dalam memori untuk petunjuk tentang menjalankan beban kerja.
Deskripsi tabel dan prosedur sampel
Sampel membuat tabel baru untuk produk dan pesanan penjualan, berdasarkan tabel yang ada di AdventureWorks2022
. Skema tabel baru mirip dengan tabel yang ada, dengan beberapa perbedaan, seperti yang dijelaskan di bawah ini.
Tabel baru yang dioptimalkan memori membawa akhiran '_inmem'. Sampel ini juga mencakup tabel terkait yang membawa akhiran '_ondisk' - tabel ini dapat digunakan untuk membuat perbandingan satu-ke-satu antara performa tabel yang dioptimalkan memori dan tabel berbasis disk pada sistem Anda.
Tabel yang dioptimalkan memori yang digunakan dalam beban kerja untuk perbandingan performa sepenuhnya tahan lama dan sepenuhnya dicatat. Mereka tidak mengorbankan durabilitas atau keandalan untuk mencapai perolehan performa.
Beban kerja target untuk sampel ini adalah pemrosesan pesanan penjualan, di mana kami mempertimbangkan juga informasi tentang produk dan diskon. Untuk akhir ini, kita menggunakan tabel SalesOrderHeader
, , SalesOrderDetail
, Product
SpecialOffer
, dan SpecialOfferProduct
.
Dua prosedur tersimpan baru, Sales.usp_InsertSalesOrder_inmem
dan Sales.usp_UpdateSalesOrderShipInfo_inmem
, digunakan untuk menyisipkan pesanan penjualan dan untuk memperbarui informasi pengiriman pesanan penjualan tertentu.
Skema Demo
baru berisi tabel pembantu dan prosedur tersimpan untuk menjalankan beban kerja demo.
Secara konkret, sampel OLTP Dalam Memori menambahkan objek berikut ke AdventureWorks2022
:
Tabel ditambahkan oleh sampel
Tabel baru
Sales.SalesOrderHeader_inmem
- Informasi header tentang pesanan penjualan. Setiap pesanan penjualan memiliki satu baris dalam tabel ini.
Sales.SalesOrderDetail_inmem
- Detail pesanan penjualan. Setiap item baris pesanan penjualan memiliki satu baris dalam tabel ini.
Sales.SpecialOffer_inmem
- Informasi tentang penawaran khusus, termasuk persentase diskon yang terkait dengan setiap penawaran khusus.
Sales.SpecialOfferProduct_inmem
- Tabel referensi antara penawaran khusus dan produk. Setiap penawaran khusus dapat menampilkan nol atau lebih produk, dan setiap produk dapat ditampilkan dalam nol atau lebih penawaran khusus.
Production.Product_inmem
- Informasi tentang produk, termasuk harga daftar mereka.
Demo.DemoSalesOrderDetailSeed
- Digunakan dalam beban kerja demo untuk membuat pesanan penjualan sampel.
Variasi tabel berbasis disk:
Sales.SalesOrderHeader_ondisk
Sales.SalesOrderDetail_ondisk
Sales.SpecialOffer_ondisk
Sales.SpecialOfferProduct_ondisk
Production.Product_ondisk
Perbedaan antara tabel berbasis disk asli dan yang dioptimalkan memori baru
Sebagian besar, tabel baru yang diperkenalkan oleh sampel ini menggunakan kolom yang sama dan jenis data yang sama dengan tabel asli. Namun, ada beberapa perbedaan. Kami mencantumkan perbedaan di bawah ini, bersama dengan alasan untuk perubahan.
Sales.SalesOrderHeader_inmem
Batasan default didukung untuk tabel yang dioptimalkan memori, dan sebagian besar batasan default yang kami migrasikan apa adanya. Namun, tabel
Sales.SalesOrderHeader
asli berisi dua batasan default yang mengambil tanggal saat ini, untuk kolomOrderDate
danModifiedDate
. Dalam beban kerja pemrosesan pesanan throughput tinggi dengan banyak konkurensi, sumber daya global apa pun dapat menjadi titik ketidakcocokan. Waktu sistem adalah sumber daya global seperti itu, dan kami telah mengamati bahwa itu dapat menjadi hambatan saat menjalankan beban kerja OLTP Dalam Memori yang menyisipkan pesanan penjualan, khususnya jika waktu sistem perlu diambil untuk beberapa kolom di header pesanan penjualan, serta detail pesanan penjualan. Masalah ditangani dalam sampel ini dengan mengambil waktu sistem hanya sekali untuk setiap pesanan penjualan yang dimasukkan, dan menggunakan nilai tersebut untuk kolom tanggalwaktu diSalesOrderHeader_inmem
danSalesOrderDetail_inmem
, dalam prosedurSales.usp_InsertSalesOrder_inmem
tersimpan .Jenis data yang ditentukan pengguna alias (UDT) - Tabel asli menggunakan dua UDT
dbo.OrderNumber
alias dandbo.AccountNumber
, untuk kolomPurchaseOrderNumber
danAccountNumber
, masing-masing. SQL Server 2016 (13.x) tidak mendukung alias UDT untuk tabel yang dioptimalkan memori, sehingga tabel baru menggunakan jenis data sistem nvarchar(25) dan nvarchar(15), masing-masing.Kolom yang dapat diubah ke null dalam kunci indeks - Dalam tabel asli, kolom
SalesPersonID
dapat diubah ke null, sementara dalam tabel baru kolom tidak dapat diubah ke null dan memiliki batasan default dengan nilai (-1). Keadaan ini karena indeks pada tabel yang dioptimalkan memori tidak dapat memiliki kolom null di kunci indeks; -1 adalah pengganti null dalam hal ini.Kolom komputasi - Kolom
SalesOrderNumber
komputasi danTotalDue
dihilangkan, karena SQL Server 2016 (13.x) tidak mendukung kolom komputasi dalam tabel yang dioptimalkan memori. TampilanSales.vSalesOrderHeader_extended_inmem
baru mencerminkan kolomSalesOrderNumber
danTotalDue
. Oleh karena itu, Anda dapat menggunakan tampilan ini jika kolom ini diperlukan.- Berlaku untuk: SQL Server 2017 (14.x) CTP 1.1.
Dimulai dengan SQL Server 2017 (14.x) CTP 1.1, kolom komputasi didukung dalam tabel dan indeks yang dioptimalkan memori.
- Berlaku untuk: SQL Server 2017 (14.x) CTP 1.1.
Batasan kunci asing didukung untuk tabel yang dioptimalkan memori di SQL Server 2016 (13.x), tetapi hanya jika tabel yang dirujuk juga dioptimalkan memori. Kunci asing yang mereferensikan tabel yang juga dimigrasikan ke memori yang dioptimalkan disimpan dalam tabel yang dimigrasikan, sementara kunci asing lainnya dihilangkan. Selain itu,
SalesOrderHeader_inmem
adalah tabel panas dalam contoh beban kerja, dan batasan kunci asing memerlukan pemrosesan tambahan untuk semua operasi DML, karena memerlukan pencarian di semua tabel lain yang dirujuk dalam batasan ini. Oleh karena itu, asumsinya adalah bahwa aplikasi memastikan integritas referensial untukSales.SalesOrderHeader_inmem
tabel, dan integritas referensial tidak divalidasi saat baris dimasukkan.Rowguid - Kolom rowguid dihilangkan. Meskipun uniqueidentifier didukung untuk tabel yang dioptimalkan memori, opsi ROWGUIDCOL tidak didukung di SQL Server 2016 (13.x). Kolom semacam ini biasanya digunakan untuk menggabungkan replikasi atau tabel yang memiliki kolom aliran file. Sampel ini tidak mencakup keduanya.
Sales.SalesOrderDetail
Batasan default - mirip
SalesOrderHeader
dengan , batasan default yang memerlukan tanggal/waktu sistem tidak dimigrasikan, sebaliknya prosedur tersimpan yang menyisipkan pesanan penjualan mengurus memasukkan tanggal/waktu sistem saat ini pada sisipan pertama.Kolom komputasi - kolom
LineTotal
komputasi tidak dimigrasikan karena kolom komputasi tidak didukung dengan tabel yang dioptimalkan memori di SQL Server 2016 (13.x). Untuk mengakses kolom ini, gunakan tampilanSales.vSalesOrderDetail_extended_inmem
.Rowguid - Kolom
rowguid
dihilangkan. Untuk detailnya, lihat deskripsi untuk tabelSalesOrderHeader
.
Production.Product
UDT alias - tabel asli menggunakan jenis
dbo.Flag
data yang ditentukan pengguna , yang setara dengan jenis data sistem bit. Tabel yang dimigrasikan menggunakan jenis data bit sebagai gantinya.Rowguid - Kolom
rowguid
dihilangkan. Untuk detailnya, lihat deskripsi untuk tabelSalesOrderHeader
.
Sales.SpecialOffer
- Rowguid - Kolom
rowguid
dihilangkan. Untuk detailnya, lihat deskripsi untuk tabelSalesOrderHeader
.
Sales.SpecialOfferProduct
- Rowguid - Kolom
rowguid
dihilangkan. Untuk detailnya, lihat deskripsi untuk tabelSalesOrderHeader
.
Pertimbangan untuk indeks pada tabel yang dioptimalkan memori
Indeks garis besar untuk tabel yang dioptimalkan memori adalah indeks NONCLUSTERED, yang mendukung pencarian titik (pencarian indeks pada predikat kesetaraan), pemindaian rentang (pencarian indeks dalam predikat ketidaksetaraan), pemindaian indeks penuh, dan pemindaian yang diurutkan. Selain itu, indeks NONCLUSTERED mendukung pencarian pada kolom utama kunci indeks. Bahkan indeks NONCLUSTERED yang dioptimalkan memori mendukung semua operasi yang didukung oleh indeks NONCLUSTERED berbasis disk, dengan satu-satunya pengecualian adalah pemindaian mundur. Oleh karena itu, menggunakan indeks NONCLUSTERED adalah pilihan yang aman untuk indeks Anda.
Indeks HASH dapat digunakan untuk mengoptimalkan beban kerja lebih lanjut. Mereka dioptimalkan untuk pencarian titik dan sisipan baris. Namun, seseorang harus mempertimbangkan bahwa mereka tidak mendukung pemindaian rentang, pemindaian yang diurutkan, atau pencarian pada kolom kunci indeks terkemuka. Oleh karena itu, perawatan perlu dilakukan saat menggunakan indeks ini. Selain itu, perlu untuk menentukan bucket_count
pada waktu pembuatan. Biasanya harus diatur di antara satu dan dua kali jumlah nilai kunci indeks, tetapi menilai berlebihan biasanya bukan masalah.
Untuk informasi selengkapnya:
Indeks pada tabel yang dimigrasikan telah disetel untuk beban kerja pemrosesan pesanan penjualan demo. Beban kerja bergantung pada sisipan dan pencarian titik dalam tabel Sales.SalesOrderHeader_inmem
dan Sales
.SalesOrderDetail_inmem
, dan juga bergantung pada pencarian titik pada kolom kunci utama dalam tabel Production.Product_inmem
dan Sales.SpecialOffer_inmem
.
Sales.SalesOrderHeader_inmem
memiliki tiga indeks, yang semuanya merupakan indeks HASH karena alasan performa, dan karena tidak ada pemindaian yang diurutkan atau rentang yang diperlukan untuk beban kerja.
Indeks HASH pada (
SalesOrderID
): bucket_count berukuran 10 juta (dibulatkan hingga 16 juta), karena jumlah pesanan penjualan yang diharapkan adalah 10 jutaIndeks HASH pada (
SalesPersonID
): bucket_count adalah 1 juta. Himpunan data yang disediakan tidak memiliki banyak orang penjualan. Tetapi bucket_count besar ini memungkinkan pertumbuhan di masa depan. Selain itu, Anda tidak membayar penalti performa untuk pencarian titik jika bucket_count terlalu besar.Indeks HASH pada (
CustomerID
): bucket_count adalah 1 juta. Himpunan data yang disediakan tidak memiliki banyak pelanggan, tetapi ini memungkinkan pertumbuhan di masa depan.
Sales.SalesOrderDetail_inmem
memiliki tiga indeks, yang semuanya merupakan indeks HASH karena alasan performa, dan karena tidak ada pemindaian yang diurutkan atau rentang yang diperlukan untuk beban kerja.
Indeks HASH pada (
SalesOrderID
,SalesOrderDetailID
): ini adalah indeks kunci utama, dan meskipun pencarian pada (SalesOrderID
,SalesOrderDetailID
) jarang, menggunakan indeks hash untuk kunci mempercepat sisipan baris. bucket_count berukuran 50 juta (dibulatkan hingga 67 juta): jumlah pesanan penjualan yang diharapkan adalah 10 juta, dan ini berukuran rata-rata lima item per pesananIndeks HASH pada (
SalesOrderID
): pencarian berdasarkan pesanan penjualan sering: Anda akan ingin menemukan semua item baris yang sesuai dengan satu pesanan. bucket_count berukuran 10 juta (dibulatkan hingga 16 juta), karena jumlah pesanan penjualan yang diharapkan adalah 10 jutaIndeks HASH pada (
ProductID
): bucket_count adalah 1 juta. Himpunan data yang disediakan tidak memiliki banyak produk, tetapi ini memungkinkan pertumbuhan di masa mendatang.
Production.Product_inmem
memiliki tiga indeks
Indeks HASH pada (
ProductID
): pencarian beradaProductID
di jalur penting untuk beban kerja demo, oleh karena itu ini adalah indeks hashIndeks NONCLUSTERED pada (
Name
): ini akan memungkinkan pemindaian nama produk yang diurutkanIndeks NONCLUSTERED pada (
ProductNumber
): ini akan memungkinkan pemindaian nomor produk yang diurutkan
Sales.SpecialOffer_inmem
memiliki satu indeks HASH pada (SpecialOfferID
): pencarian titik penawaran khusus berada di bagian penting dari beban kerja demo. Ini bucket_count
berukuran 1 juta untuk memungkinkan pertumbuhan di masa depan.
Sales.SpecialOfferProduct_inmem
tidak direferensikan dalam beban kerja demo, dan dengan demikian tidak ada kebutuhan yang jelas untuk menggunakan indeks hash pada tabel ini untuk mengoptimalkan beban kerja - indeks pada (SpecialOfferID
, ProductID
) dan (ProductID
) adalah NONCLUSTERED.
Perhatikan bahwa dalam beberapa jumlah wadah di atas terlalu besar, tetapi tidak jumlah wadah untuk indeks SalesOrderHeader_inmem
dan SalesOrderDetail_inmem
: mereka berukuran hanya untuk 10 juta pesanan penjualan. Ini dilakukan untuk memungkinkan penginstalan sampel pada sistem dengan ketersediaan memori rendah, meskipun dalam kasus tersebut beban kerja demo akan gagal dengan kehabisan memori. Jika Anda ingin menskalakan jauh lebih dari 10 juta pesanan penjualan, jangan ragu untuk meningkatkan jumlah wadah yang sesuai.
Pertimbangan untuk pemanfaatan memori
Pemanfaatan memori dalam database sampel, baik sebelum dan sesudah menjalankan beban kerja demo, dibahas dalam pemanfaatan Memori Bagian untuk tabel yang dioptimalkan memori.
Prosedur Tersimpan ditambahkan oleh sampel
Dua prosedur tersimpan utama untuk menyisipkan pesanan penjualan dan memperbarui detail pengiriman adalah sebagai berikut:
Sales.usp_InsertSalesOrder_inmem
Menyisipkan pesanan penjualan baru dalam database dan menghasilkan untuk pesanan penjualan tersebut
SalesOrderID
. Sebagai parameter input, dibutuhkan detail untuk header pesanan penjualan, serta item baris dalam pesanan.Parameter output:
- @SalesOrderID int -
SalesOrderID
untuk pesanan penjualan yang baru saja dimasukkan
- @SalesOrderID int -
Parameter input (diperlukan):
@DueDate datetime2
@CustomerID Int
@BillToAddressID [int]
@ShipToAddressID [int]
@ShipMethodID [int]
@SalesOrderDetails
Sales.SalesOrderDetailType_inmem
- parameter bernilai tabel (TVP) yang berisi item baris pesanan
Parameter input (opsional):
@Status [ tinyint ]
@OnlineOrderFlag [bit]
@PurchaseOrderNumber [nvarchar] (25)
@AccountNumber [nvarchar] (15)
@SalesPersonID [int]
@TerritoryID [int]
@CreditCardID [int]
@CreditCardApprovalCode [varchar] (15)
@CurrencyRateID [int]
@Comment nvarchar(128)
Sales.usp_UpdateSalesOrderShipInfo_inmem
Perbarui informasi pengiriman untuk pesanan penjualan tertentu. Ini juga akan memperbarui informasi pengiriman untuk semua item baris pesanan penjualan.
Ini adalah prosedur pembungkus
Sales.usp_UpdateSalesOrderShipInfo_native
untuk prosedur tersimpan yang dikompilasi secara asli dengan logika coba lagi untuk menangani potensi konflik (tidak terduga) dengan transaksi bersamaan yang memperbarui urutan yang sama. Untuk informasi selengkapnya, lihat logika coba lagi.
Sales.usp_UpdateSalesOrderShipInfo_native
- Ini adalah prosedur tersimpan yang dikompilasi secara asli yang benar-benar memproses pembaruan untuk informasi pengiriman. Ini berarti dipanggil dari prosedur
Sales.usp_UpdateSalesOrderShipInfo_inmem
tersimpan pembungkus . Jika klien dapat menangani kegagalan dan menerapkan logika coba lagi, Anda dapat memanggil prosedur ini secara langsung, daripada menggunakan prosedur tersimpan pembungkus.
- Ini adalah prosedur tersimpan yang dikompilasi secara asli yang benar-benar memproses pembaruan untuk informasi pengiriman. Ini berarti dipanggil dari prosedur
Prosedur tersimpan berikut digunakan untuk beban kerja demo.
Demo.usp_DemoReset
- Mengatur ulang demo dengan mengosongkan dan menyetel
SalesOrderHeader
ulang tabel danSalesOrderDetail
.
- Mengatur ulang demo dengan mengosongkan dan menyetel
Prosedur tersimpan berikut digunakan untuk menyisipkan dan menghapus dari tabel yang dioptimalkan memori sambil menjamin domain dan integritas referensial.
Production.usp_InsertProduct_inmem
Production.usp_DeleteProduct_inmem
Sales.usp_InsertSpecialOffer_inmem
Sales.usp_DeleteSpecialOffer_inmem
Sales.usp_InsertSpecialOfferProduct_inmem
Akhirnya prosedur tersimpan berikut digunakan untuk memverifikasi domain dan integritas referensial.
dbo.usp_ValidateIntegrity
Parameter opsional: @object_id - ID objek untuk memvalidasi integritas untuk
Prosedur ini bergantung pada tabel
dbo.DomainIntegrity
, ,dbo.ReferentialIntegrity
dandbo.UniqueIntegrity
untuk aturan integritas yang perlu diverifikasi - sampel mengisi tabel ini berdasarkan pemeriksaan, kunci asing, dan batasan unik yang ada untuk tabel asli dalamAdventureWorks2022
database.Ini bergantung pada prosedur
dbo.usp_GenerateCKCheck
pembantu , ,dbo.usp_GenerateFKCheck
dandbo.GenerateUQCheck
untuk menghasilkan T-SQL yang diperlukan untuk melakukan pemeriksaan integritas.
Pengukuran Performa menggunakan Beban Kerja Demo
Ostress adalah alat baris perintah yang dikembangkan oleh tim dukungan Microsoft CSS SQL Server. Alat ini dapat digunakan untuk menjalankan kueri atau menjalankan prosedur tersimpan secara paralel. Anda dapat mengonfigurasi jumlah utas untuk menjalankan pernyataan T-SQL tertentu secara paralel, dan Anda dapat menentukan berapa kali pernyataan harus dijalankan pada utas ini; ostress akan memutar utas dan menjalankan pernyataan pada semua utas secara paralel. Setelah eksekusi selesai untuk semua utas, ostress akan melaporkan waktu yang diperlukan untuk semua utas untuk menyelesaikan eksekusi.
Menginstal ostress
Ostress diinstal sebagai bagian dari Utilitas Report Markup Language (RML) ; tidak ada instalasi mandiri untuk ostress.
Langkah-langkah penginstalan:
Unduh dan jalankan paket penginstalan x64 untuk utilitas RML dari halaman berikut: Unduh RML untuk SQL Server
Jika ada kotak dialog yang mengatakan file tertentu sedang digunakan, pilih 'Lanjutkan'
Menjalankan ostress
Ostress dijalankan dari prompt baris perintah. Paling nyaman untuk menjalankan alat dari "RML Cmd Prompt", yang diinstal sebagai bagian dari Utilitas RML.
Untuk membuka Prompt Cmd RML, ikuti instruksi berikut:
Di Windows, buka menu mulai dengan memilih kunci Windows, dan ketik rml
. Pilih "RML Cmd Prompt", yang akan berada dalam daftar hasil pencarian.
Pastikan bahwa prompt perintah terletak di folder penginstalan Utilitas RML.
Opsi baris perintah untuk ostress dapat dilihat saat hanya menjalankan ostress.exe tanpa opsi baris perintah apa pun. Opsi utama yang perlu dipertimbangkan untuk menjalankan ostress dengan sampel ini adalah:
-S nama instans Microsoft SQL Server untuk disambungkan
-E gunakan autentikasi Windows untuk menyambungkan (default); jika Anda menggunakan autentikasi SQL Server, gunakan opsi -Anda dan -P untuk menentukan nama pengguna dan kata sandi, masing-masing
-d nama database, untuk contoh ini
AdventureWorks2022
-Q pernyataan T-SQL yang akan dijalankan
-n jumlah koneksi yang memproses setiap file/kueri input
-adalah jumlah iterasi untuk setiap koneksi untuk menjalankan setiap file/kueri input
Beban Kerja Demo
Prosedur tersimpan utama yang digunakan dalam beban kerja demo adalah Sales.usp_InsertSalesOrder_inmem/ondisk
. Skrip di bawah ini membuat parameter bernilai tabel (TVP) dengan data sampel, dan memanggil prosedur untuk menyisipkan pesanan penjualan dengan lima item baris.
Alat ostress digunakan untuk menjalankan panggilan prosedur tersimpan secara paralel, untuk mensimulasikan klien yang menyisipkan pesanan penjualan secara bersamaan.
Reset demo setelah setiap stres menjalankan eksekusi Demo.usp_DemoReset
. Prosedur ini menghapus baris dalam tabel yang dioptimalkan memori, memotong tabel berbasis disk, dan menjalankan titik pemeriksaan database.
Skrip berikut dijalankan secara bersamaan untuk mensimulasikan beban kerja pemrosesan pesanan penjualan:
DECLARE
@i int = 0,
@od Sales.SalesOrderDetailType_inmem,
@SalesOrderID int,
@DueDate datetime2 = sysdatetime(),
@CustomerID int = rand() * 8000,
@BillToAddressID int = rand() * 10000,
@ShipToAddressID int = rand() * 10000,
@ShipMethodID int = (rand() * 5) + 1;
INSERT INTO @od
SELECT OrderQty, ProductID, SpecialOfferID
FROM Demo.DemoSalesOrderDetailSeed
WHERE OrderID= cast((rand()*106) + 1 as int);
WHILE (@i < 20)
BEGIN;
EXEC Sales.usp_InsertSalesOrder_inmem @SalesOrderID OUTPUT, @DueDate, @CustomerID, @BillToAddressID, @ShipToAddressID, @ShipMethodID, @od;
SET @i += 1
END
Dengan skrip ini, setiap urutan sampel yang dibangun dimasukkan 20 kali, melalui 20 prosedur tersimpan yang dijalankan dalam perulangan WHILE. Perulangan digunakan untuk memperhitungkan fakta bahwa database digunakan untuk membuat urutan sampel. Di lingkungan produksi yang khas, aplikasi tingkat menengah akan membangun pesanan penjualan yang akan dimasukkan.
Skrip di atas menyisipkan pesanan penjualan ke dalam tabel yang dioptimalkan memori. Skrip untuk memasukkan pesanan penjualan ke dalam tabel berbasis disk diturunkan dengan mengganti dua kemunculan '_inmem' dengan '_ondisk'.
Kami akan menggunakan alat ostress untuk menjalankan skrip menggunakan beberapa koneksi bersamaan. Kami akan menggunakan parameter '-n' untuk mengontrol jumlah koneksi, dan parameter 'r' untuk mengontrol berapa kali skrip dijalankan pada setiap koneksi.
Menjalankan Beban Kerja
Untuk menguji dalam skala besar, kami menyisipkan 10 juta pesanan penjualan, menggunakan 100 koneksi. Pengujian ini dilakukan secara wajar pada server sederhana (misalnya, 8 fisik, 16 inti logis), dan penyimpanan SSD dasar untuk log. Jika pengujian tidak berkinerja baik pada perangkat keras Anda, lihat Bagian Pemecahan masalah pengujian yang berjalan lambat. Jika Anda ingin mengurangi tingkat stres untuk pengujian ini, turunkan jumlah koneksi dengan mengubah parameter '-n'. Misalnya untuk menurunkan jumlah koneksi menjadi 40, ubah parameter '-n100' menjadi '-n40'.
Sebagai ukuran performa untuk beban kerja, kami menggunakan waktu yang berlalu seperti yang dilaporkan oleh ostress.exe setelah menjalankan beban kerja.
Instruksi dan pengukuran di bawah ini menggunakan beban kerja yang menyisipkan 10 juta pesanan penjualan. Untuk instruksi menjalankan beban kerja yang diperkecil yang menyisipkan 1 juta pesanan penjualan, lihat instruksi di 'OLTP\readme.txt Dalam Memori' yang merupakan bagian dari arsip SQLServer2016Samples.zip.
Tabel yang dioptimalkan memori
Kita akan mulai dengan menjalankan beban kerja pada tabel yang dioptimalkan memori. Perintah berikut membuka 100 utas, masing-masing berjalan untuk 5.000 iterasi. Setiap iterasi menyisipkan 20 pesanan penjualan dalam transaksi terpisah. Ada 20 sisipan per iterasi untuk mengimbangi fakta bahwa database digunakan untuk menghasilkan data yang akan dimasukkan. Hasil ini menghasilkan total 20 * 5.000 * 100 = 10.000.000 sisipan pesanan penjualan.
Buka Prompt Cmd RML, dan jalankan perintah berikut:
Pilih tombol Salin untuk menyalin perintah, dan tempelkan ke prompt perintah Utilitas RML.
ostress.exe -n100 -r5000 -S. -E -dAdventureWorks2022 -q -Q"DECLARE @i int = 0, @od Sales.SalesOrderDetailType_inmem, @SalesOrderID int, @DueDate datetime2 = sysdatetime(), @CustomerID int = rand() * 8000, @BillToAddressID int = rand() * 10000, @ShipToAddressID int = rand() * 10000, @ShipMethodID int = (rand() * 5) + 1; INSERT INTO @od SELECT OrderQty, ProductID, SpecialOfferID FROM Demo.DemoSalesOrderDetailSeed WHERE OrderID= cast((rand()*106) + 1 as int); while (@i < 20) begin; EXEC Sales.usp_InsertSalesOrder_inmem @SalesOrderID OUTPUT, @DueDate, @CustomerID, @BillToAddressID, @ShipToAddressID, @ShipMethodID, @od; set @i += 1 end"
Pada satu server pengujian dengan jumlah total 8 inti fisik (16 logis), ini membutuhkan waktu 2 menit dan 5 detik. Pada server pengujian kedua dengan 24 inti fisik (48 logis), ini membutuhkan waktu 1 menit dan 0 detik.
Amati pemanfaatan CPU saat beban kerja berjalan, misalnya menggunakan task manager. Anda akan melihat bahwa pemanfaatan CPU mendekati 100%. Jika tidak demikian, Anda memiliki hambatan IO log, lihat juga Memecahkan masalah pengujian yang berjalan lambat.
Tabel berbasis disk
Perintah berikut akan menjalankan beban kerja pada tabel berbasis disk. Beban kerja ini mungkin memakan waktu cukup lama untuk dijalankan, yang sebagian besar disebabkan oleh ketidakcocokan kait dalam sistem. Tabel yang dioptimalkan memori bebas kait dan dengan demikian tidak menderita masalah ini.
Buka Prompt Cmd RML, dan jalankan perintah berikut:
Pilih tombol Salin untuk menyalin perintah, dan tempelkan ke prompt perintah Utilitas RML.
ostress.exe -n100 -r5000 -S. -E -dAdventureWorks2022 -q -Q"DECLARE @i int = 0, @od Sales.SalesOrderDetailType_ondisk, @SalesOrderID int, @DueDate datetime2 = sysdatetime(), @CustomerID int = rand() * 8000, @BillToAddressID int = rand() * 10000, @ShipToAddressID int = rand() * 10000, @ShipMethodID int = (rand() * 5) + 1; INSERT INTO @od SELECT OrderQty, ProductID, SpecialOfferID FROM Demo.DemoSalesOrderDetailSeed WHERE OrderID= cast((rand()*106) + 1 as int); while (@i < 20) begin; EXEC Sales.usp_InsertSalesOrder_ondisk @SalesOrderID OUTPUT, @DueDate, @CustomerID, @BillToAddressID, @ShipToAddressID, @ShipMethodID, @od; set @i += 1 end"
Pada satu server pengujian dengan jumlah total 8 inti fisik (16 logis), ini membutuhkan waktu 41 menit dan 25 detik. Pada server pengujian kedua dengan 24 inti fisik (48 logis), ini membutuhkan waktu 52 menit dan 16 detik.
Faktor utama dalam perbedaan performa antara tabel yang dioptimalkan memori dan tabel berbasis disk dalam pengujian ini adalah fakta bahwa saat menggunakan tabel berbasis disk, SQL Server tidak dapat sepenuhnya menggunakan CPU. Alasannya adalah ketidakcocokan kait: transaksi bersamaan mencoba menulis ke halaman data yang sama; kait digunakan untuk memastikan hanya satu transaksi pada satu waktu yang dapat menulis ke halaman. Mesin OLTP Dalam Memori bebas kait, dan baris data tidak diatur dalam halaman. Dengan demikian, transaksi bersamaan tidak memblokir sisipan satu sama lain, sehingga memungkinkan SQL Server untuk sepenuhnya menggunakan CPU.
Anda dapat mengamati pemanfaatan CPU saat beban kerja berjalan, misalnya menggunakan task manager. Anda akan melihat dengan tabel berbasis disk, pemanfaatan CPU jauh dari 100%. Pada konfigurasi pengujian dengan 16 prosesor logis, pemanfaatan akan melayang di sekitar 24%.
Secara opsional, Anda dapat melihat jumlah tunggu kait per detik menggunakan Monitor Performa, dengan penghitung \SQL Server:Latches\Latch Waits/sec
kinerja .
Mereset demo
Untuk mengatur ulang demo, buka Perintah Cmd RML, dan jalankan perintah berikut:
ostress.exe -S. -E -dAdventureWorks2022 -Q"EXEC Demo.usp_DemoReset"
Bergantung pada perangkat keras, mungkin perlu waktu beberapa menit untuk dijalankan.
Kami merekomendasikan reset setelah setiap demo berjalan. Karena beban kerja ini hanya sisipan, setiap eksekusi akan mengonsumsi lebih banyak memori, dan dengan demikian diperlukan reset untuk mencegah kehabisan memori. Jumlah memori yang digunakan setelah eksekusi dibahas dalam pemanfaatan Memori Bagian setelah menjalankan beban kerja.
Pemecahan masalah pengujian yang berjalan lambat
Hasil pengujian biasanya akan bervariasi menurut perangkat keras, dan juga tingkat konkurensi yang digunakan dalam eksekusi pengujian. Beberapa hal yang perlu dicari jika hasilnya tidak seperti yang diharapkan:
Jumlah transaksi bersamaan: Saat menjalankan beban kerja pada satu utas, perolehan performa dengan OLTP Dalam Memori kemungkinan akan kurang dari 2X. Ketidakcocokan kait hanya masalah yang signifikan jika ada tingkat konkurensi yang tinggi.
Jumlah inti rendah yang tersedia untuk SQL Server: Ini berarti akan ada tingkat konkurensi rendah dalam sistem, karena hanya ada sebanyak mungkin transaksi yang dijalankan secara bersamaan karena ada inti yang tersedia untuk SQL.
- Gejala: jika pemanfaatan CPU tinggi saat menjalankan beban kerja pada tabel berbasis disk, ini berarti tidak ada banyak ketidakcocokan, menunjuk ke kurangnya konkurensi.
Kecepatan drive log: Jika drive log tidak dapat mengikuti tingkat throughput transaksi dalam sistem, beban kerja menjadi tersempitan pada IO log. Meskipun pengelogan lebih efisien dengan OLTP Dalam Memori, jika IO log adalah hambatan, potensi perolehan performa terbatas.
- Gejala: jika pemanfaatan CPU tidak mendekati 100% atau sangat lonjakan saat menjalankan beban kerja pada tabel yang dioptimalkan memori, ada kemungkinan ada hambatan IO log. Ini dapat dikonfirmasi dengan membuka Resource Monitor dan melihat panjang antrean untuk drive log.
Pemanfaatan Ruang Memori dan Disk dalam Sampel
Di bawah ini kami menjelaskan apa yang diharapkan dalam hal pemanfaatan memori dan ruang disk untuk database sampel. Kami juga menunjukkan hasil yang telah kami lihat di server pengujian dengan 16 inti logis.
Pemanfaatan memori untuk tabel yang dioptimalkan memori
Pemanfaatan database secara keseluruhan
Kueri berikut dapat digunakan untuk mendapatkan total pemanfaatan memori untuk OLTP Dalam Memori dalam sistem.
SELECT type
, name
, pages_kb/1024 AS pages_MB
FROM sys.dm_os_memory_clerks WHERE type LIKE '%xtp%'
Rekam jepret setelah database baru saja dibuat:
jenis | nama | pages_MB |
---|---|---|
MEMORYCLERK_XTP | Default | 94 |
MEMORYCLERK_XTP | DB_ID_5 | 877 |
MEMORYCLERK_XTP | Default | 0 |
MEMORYCLERK_XTP | Default | 0 |
Petugas memori default berisi struktur memori di seluruh sistem dan relatif kecil. Petugas memori untuk database pengguna, dalam hal ini database dengan ID 5 ( database_id
mungkin berbeda dalam instans Anda), adalah sekitar 900 MB.
Pemanfaatan memori per tabel
Kueri berikut dapat digunakan untuk menelusuri paling detail pemanfaatan memori tabel individual dan indeksnya:
SELECT object_name(t.object_id) AS [Table Name]
, memory_allocated_for_table_kb
, memory_allocated_for_indexes_kb
FROM sys.dm_db_xtp_table_memory_stats dms JOIN sys.tables t
ON dms.object_id=t.object_id
WHERE t.type='U';
Tabel berikut ini menampilkan hasil kueri ini untuk penginstalan sampel baru:
Nama Tabel | memory_allocated_for_table_kb | memory_allocated_for_indexes_kb |
---|---|---|
SpecialOfferProduct_inmem | 64 | 3840 |
DemoSalesOrderHeaderSeed | 1984 | 5504 |
SalesOrderDetail_inmem | 15316 | 663552 |
DemoSalesOrderDetailSeed | 64 | 10432 |
SpecialOffer_inmem | 3 | 8192 |
SalesOrderHeader_inmem | 7168 | 147456 |
Product_inmem | 124 | 12352 |
Seperti yang Anda lihat tabelnya cukup kecil: SalesOrderHeader_inmem
berukuran sekitar 7 MB, dan SalesOrderDetail_inmem
berukuran sekitar 15 MB.
Apa yang mencolok di sini adalah ukuran memori yang dialokasikan untuk indeks, dibandingkan dengan ukuran data tabel. Itu karena indeks hash dalam sampel telah diukur sebelumnya untuk ukuran data yang lebih besar. Perhatikan bahwa indeks hash memiliki ukuran tetap, dan dengan demikian ukurannya tidak akan tumbuh dengan ukuran data dalam tabel.
Pemanfaatan memori setelah menjalankan beban kerja
Setelah menyisipkan 10 juta pesanan penjualan, pemanfaatan memori all-up terlihat mirip dengan yang berikut ini:
SELECT type
, name
, pages_kb/1024 AS pages_MB
FROM sys.dm_os_memory_clerks WHERE type LIKE '%xtp%'
jenis | nama | pages_MB |
---|---|---|
MEMORYCLERK_XTP | Default | 146 |
MEMORYCLERK_XTP | DB_ID_5 | 7374 |
MEMORYCLERK_XTP | Default | 0 |
MEMORYCLERK_XTP | Default | 0 |
Seperti yang Anda lihat, SQL Server menggunakan sedikit di bawah 8 GB untuk tabel dan indeks yang dioptimalkan memori dalam database sampel.
Melihat penggunaan memori terperinci per tabel setelah satu contoh dijalankan:
SELECT object_name(t.object_id) AS [Table Name]
, memory_allocated_for_table_kb
, memory_allocated_for_indexes_kb
FROM sys.dm_db_xtp_table_memory_stats dms JOIN sys.tables t
ON dms.object_id=t.object_id
WHERE t.type='U'
Nama Tabel | memory_allocated_for_table_kb | memory_allocated_for_indexes_kb |
---|---|---|
SalesOrderDetail_inmem | 5113761 | 663552 |
DemoSalesOrderDetailSeed | 64 | 10368 |
SpecialOffer_inmem | 2 | 8192 |
SalesOrderHeader_inmem | 1575679 | 147456 |
Product_inmem | 111 | 12032 |
SpecialOfferProduct_inmem | 64 | 3712 |
DemoSalesOrderHeaderSeed | 1984 | 5504 |
Kita dapat melihat total sekitar 6,5 GB data. Perhatikan bahwa ukuran indeks pada tabel SalesOrderHeader_inmem
dan SalesOrderDetail_inmem
sama dengan ukuran indeks sebelum menyisipkan pesanan penjualan. Ukuran indeks tidak berubah karena kedua tabel menggunakan indeks hash, dan indeks hash statis.
Setelah reset demo
Prosedur Demo.usp_DemoReset
tersimpan dapat digunakan untuk mengatur ulang demo. Ini menghapus data dalam tabel SalesOrderHeader_inmem
dan SalesOrderDetail_inmem
, dan menyemai ulang data dari tabel SalesOrderHeader
asli dan SalesOrderDetail
.
Sekarang, meskipun baris dalam tabel telah dihapus, ini tidak berarti bahwa memori segera diklaim kembali. SQL Server mengklaim kembali memori dari baris yang dihapus dalam tabel yang dioptimalkan memori di latar belakang, sesuai kebutuhan. Anda akan melihat bahwa segera setelah reset demo, tanpa beban kerja transaksional pada sistem, memori dari baris yang dihapus belum diklaim kembali:
SELECT type
, name
, pages_kb/1024 AS pages_MB
FROM sys.dm_os_memory_clerks WHERE type LIKE '%xtp%';
jenis | nama | pages_MB |
---|---|---|
MEMORYCLERK_XTP | Default | 2261 |
MEMORYCLERK_XTP | DB_ID_5 | 7396 |
MEMORYCLERK_XTP | Default | 0 |
MEMORYCLERK_XTP | Default | 0 |
Ini diharapkan: memori akan diklaim kembali ketika beban kerja transaksi berjalan.
Jika Anda memulai eksekusi kedua beban kerja demo, Anda akan melihat pemanfaatan memori berkurang pada awalnya, karena baris yang dihapus sebelumnya dibersihkan. Pada titik tertentu ukuran memori akan meningkat lagi, sampai beban kerja selesai. Setelah memasukkan 10 juta baris setelah reset demo, pemanfaatan memori akan sangat mirip dengan pemanfaatan setelah eksekusi pertama. Contohnya:
SELECT type
, name
, pages_kb/1024 AS pages_MB
FROM sys.dm_os_memory_clerks WHERE type LIKE '%xtp%';
jenis | nama | pages_MB |
---|---|---|
MEMORYCLERK_XTP | Default | 1863 |
MEMORYCLERK_XTP | DB_ID_5 | 7390 |
MEMORYCLERK_XTP | Default | 0 |
MEMORYCLERK_XTP | Default | 0 |
Pemanfaatan disk untuk tabel yang dioptimalkan memori
Ukuran on-disk secara keseluruhan untuk file titik pemeriksaan database pada waktu tertentu dapat ditemukan menggunakan kueri:
SELECT SUM(df.size) * 8 / 1024 AS [On-disk size in MB]
FROM sys.filegroups f JOIN sys.database_files df
ON f.data_space_id=df.data_space_id
WHERE f.type=N'FX';
Status awal
Ketika sampel grup file dan sampel tabel yang dioptimalkan memori dibuat pada awalnya, sejumlah file titik pemeriksaan telah dibuat sebelumnya dan sistem mulai mengisi file - jumlah file titik pemeriksaan yang telah dibuat sebelumnya tergantung pada jumlah prosesor logis dalam sistem. Karena sampel awalnya sangat kecil, file yang telah dibuat sebelumnya sebagian besar akan kosong setelah pembuatan awal.
Kode berikut menunjukkan ukuran awal pada disk untuk sampel pada komputer dengan 16 prosesor logis:
SELECT SUM(df.size) * 8 / 1024 AS [On-disk size in MB]
FROM sys.filegroups f JOIN sys.database_files df
ON f.data_space_id=df.data_space_id
WHERE f.type=N'FX';
Ukuran pada disk dalam MB |
---|
2312 |
Seperti yang Anda lihat, ada perbedaan besar antara ukuran pada disk file titik pemeriksaan, yaitu 2,3 GB, dan ukuran data aktual, yang lebih dekat ke 30 MB.
Melihat lebih dekat dari asal pemanfaatan ruang disk, Anda bisa menggunakan kueri berikut. Ukuran pada disk yang dikembalikan oleh kueri ini adalah perkiraan untuk file dengan status dalam 5 (DIPERLUKAN UNTUK BACKUP/HA), 6 (DALAM TRANSISI KE TOMBSTONE), atau 7 (TOMBSTONE).
SELECT state_desc
, file_type_desc
, COUNT(*) AS [count]
, SUM(CASE
WHEN state = 5 AND file_type=0 THEN 128*1024*1024
WHEN state = 5 AND file_type=1 THEN 8*1024*1024
WHEN state IN (6,7) THEN 68*1024*1024
ELSE file_size_in_bytes
END) / 1024 / 1024 AS [on-disk size MB]
FROM sys.dm_db_xtp_checkpoint_files
GROUP BY state, state_desc, file_type, file_type_desc
ORDER BY state, file_type;
Untuk status awal sampel, hasilnya akan terlihat seperti untuk server dengan 16 prosesor logis:
state_desc | file_type_desc | jumlah | ukuran pada disk MB |
---|---|---|---|
DIBUAT SEBELUMNYA | DATA | 16 | 2048 |
DIBUAT SEBELUMNYA | DELTA | 16 | 128 |
SEDANG DIBANGUN | DATA | 1 | 128 |
SEDANG DIBANGUN | DELTA | 1 | 8 |
Seperti yang Anda lihat, sebagian besar ruang digunakan oleh data dan file delta yang dibuat sebelumnya. SQL Server telah membuat satu pasang file (data, delta) per prosesor logis. Selain itu, file data telah diukur sebelumnya pada 128 MB, dan file delta pada 8 MB, untuk membuat penyisipan data ke dalam file-file ini lebih efisien.
Data aktual dalam tabel yang dioptimalkan memori ada dalam satu file data.
Setelah menjalankan beban kerja
Setelah satu eksekusi pengujian yang menyisipkan 10 juta pesanan penjualan, ukuran on-disk keseluruhan terlihat seperti ini (untuk server pengujian 16-core):
SELECT SUM(df.size) * 8 / 1024 AS [On-disk size in MB]
FROM sys.filegroups f JOIN sys.database_files df
ON f.data_space_id=df.data_space_id
WHERE f.type=N'FX';
Ukuran pada disk dalam MB |
---|
8828 |
Ukuran pada disk mendekati 9 GB, yang mendekati ukuran dalam memori data.
Melihat lebih dekat ukuran file titik pemeriksaan di berbagai status:
SELECT state_desc
, file_type_desc
, COUNT(*) AS [count]
, SUM(CASE
WHEN state = 5 AND file_type=0 THEN 128*1024*1024
WHEN state = 5 AND file_type=1 THEN 8*1024*1024
WHEN state IN (6,7) THEN 68*1024*1024
ELSE file_size_in_bytes
END) / 1024 / 1024 AS [on-disk size MB]
FROM sys.dm_db_xtp_checkpoint_files
GROUP BY state, state_desc, file_type, file_type_desc
ORDER BY state, file_type;
state_desc | file_type_desc | jumlah | ukuran pada disk MB |
---|---|---|---|
DIBUAT SEBELUMNYA | DATA | 16 | 2048 |
DIBUAT SEBELUMNYA | DELTA | 16 | 128 |
SEDANG DIBANGUN | DATA | 1 | 128 |
SEDANG DIBANGUN | DELTA | 1 | 8 |
Kami masih memiliki 16 pasang file yang telah dibuat sebelumnya, siap untuk pergi karena titik pemeriksaan ditutup.
Ada satu pasangan yang sedang dibangun, yang digunakan sampai titik pemeriksaan saat ini ditutup. Seiring dengan file titik pemeriksaan aktif, ini memberikan sekitar 6,5 GB pemanfaatan disk untuk 6,5 GB data dalam memori. Ingat bahwa indeks tidak bertahan pada disk, dan dengan demikian ukuran keseluruhan pada disk lebih kecil dari ukuran dalam memori dalam kasus ini.
Setelah reset demo
Setelah reset demo, ruang disk tidak segera diklaim kembali jika tidak ada beban kerja transaksional pada sistem, dan tidak ada titik pemeriksaan database. Agar file titik pemeriksaan dipindahkan melalui berbagai tahap mereka dan akhirnya dibuang, sejumlah titik pemeriksaan dan peristiwa pemotongan log perlu terjadi, untuk memulai penggabungan file titik pemeriksaan, serta untuk memulai pengumpulan sampah. Ini akan terjadi secara otomatis jika Anda memiliki beban kerja transaksional dalam sistem (dan mengambil cadangan log reguler, jika Anda menggunakan model pemulihan PENUH), tetapi tidak ketika sistem menganggur, seperti dalam skenario demo.
Dalam contoh, setelah reset demo, Anda mungkin melihat sesuatu seperti:
SELECT SUM(df.size) * 8 / 1024 AS [On-disk size in MB]
FROM sys.filegroups f JOIN sys.database_files df
ON f.data_space_id=df.data_space_id
WHERE f.type=N'FX';
Ukuran pada disk dalam MB |
---|
11839 |
Pada hampir 12 GB, ini secara signifikan lebih dari 9 GB yang kami miliki sebelum reset demo. Ini karena beberapa penggabungan file titik pemeriksaan telah dimulai, tetapi beberapa target penggabungan belum diinstal, dan beberapa file sumber gabungan belum dibersihkan, seperti yang dapat dilihat dari berikut ini:
SELECT state_desc
, file_type_desc
, COUNT(*) AS [count]
, SUM(CASE
WHEN state = 5 AND file_type=0 THEN 128*1024*1024
WHEN state = 5 AND file_type=1 THEN 8*1024*1024
WHEN state IN (6,7) THEN 68*1024*1024
ELSE file_size_in_bytes
END) / 1024 / 1024 AS [on-disk size MB]
FROM sys.dm_db_xtp_checkpoint_files
GROUP BY state, state_desc, file_type, file_type_desc
ORDER BY state, file_type;
state_desc | file_type_desc | jumlah | ukuran pada disk MB |
---|---|---|---|
DIBUAT SEBELUMNYA | DATA | 16 | 2048 |
DIBUAT SEBELUMNYA | DELTA | 16 | 128 |
AKTIF | DATA | 38 | 5152 |
AKTIF | DELTA | 38 | 1331 |
GABUNGKAN TARGET | DATA | 7 | 896 |
GABUNGKAN TARGET | DELTA | 7 | 56 |
SUMBER GABUNGAN | DATA | 13 | 1772 |
SUMBER GABUNGAN | DELTA | 13 | 455 |
Target penggabungan diinstal dan sumber gabungan dibersihkan saat aktivitas transaksi terjadi dalam sistem.
Setelah menjalankan beban kerja demo kedua, memasukkan 10 juta pesanan penjualan setelah reset demo, Anda akan melihat bahwa file yang dibangun selama eksekusi pertama beban kerja telah dibersihkan. Jika Anda menjalankan kueri di atas beberapa kali saat beban kerja berjalan, Anda dapat melihat file titik pemeriksaan melewati berbagai tahap.
Setelah eksekusi kedua dari beban kerja masukkan 10 juta pesanan penjualan, Anda akan melihat pemanfaatan disk sangat mirip dengan, meskipun belum tentu sama seperti setelah eksekusi pertama, karena sistem bersifat dinamis. Contohnya:
SELECT state_desc
, file_type_desc
, COUNT(*) AS [count]
, SUM(CASE
WHEN state = 5 AND file_type=0 THEN 128*1024*1024
WHEN state = 5 AND file_type=1 THEN 8*1024*1024
WHEN state IN (6,7) THEN 68*1024*1024
ELSE file_size_in_bytes
END) / 1024 / 1024 AS [on-disk size MB]
FROM sys.dm_db_xtp_checkpoint_files
GROUP BY state, state_desc, file_type, file_type_desc
ORDER BY state, file_type;
state_desc | file_type_desc | jumlah | ukuran pada disk MB |
---|---|---|---|
DIBUAT SEBELUMNYA | DATA | 16 | 2048 |
DIBUAT SEBELUMNYA | DELTA | 16 | 128 |
SEDANG DIBANGUN | DATA | 2 | 268 |
SEDANG DIBANGUN | DELTA | 2 | 16 |
AKTIF | DATA | 41 | 5608 |
AKTIF | DELTA | 41 | 328 |
Dalam hal ini, ada dua pasangan file titik pemeriksaan dalam status 'sedang dibangun', yang berarti beberapa pasangan file dipindahkan ke status 'under construction', kemungkinan karena tingkat konkurensi yang tinggi dalam beban kerja. Beberapa utas bersamaan memerlukan pasangan file baru pada saat yang sama, dan dengan demikian memindahkan pasangan dari 'dibuat sebelumnya' ke 'dalam konstruksi'.