Bagikan melalui


Pemadatan indeks otomatis (pratinjau)

Berlaku untuk:Azure SQL DatabaseAzure SQL Managed InstanceAUTDDatabase SQL di Microsoft Fabric

Pemadatan indeks otomatis membantu Anda mengurangi konsumsi ruang penyimpanan, I/O disk, CPU, memori, dan meningkatkan performa beban kerja tanpa menginvestasikan waktu dan upaya ke dalam pekerjaan pemeliharaan indeks. Pemadatan indeks dilakukan terus menerus dan dengan overhead rendah saat data dalam database berubah.

Nota

Pemadatan indeks otomatis saat ini dalam pratinjau di Azure SQL Database, Azure SQL Managed Instance dengan kebijakan pembaruan yang selalu terbaru, dan database SQL di Fabric.

Untuk jawaban atas pertanyaan umum, lihat Tanya jawab umum (FAQ).

Mengaktifkan dan menonaktifkan

Pemadatan indeks otomatis dinonaktifkan secara default. Anda bisa mengaktifkan atau menonaktifkannya untuk database dengan menjalankan pernyataan Transact-SQL berikut.

  • Aktifkan pemadatan indeks otomatis:

    ALTER DATABASE [database-name-placeholder]
    SET AUTOMATIC_INDEX_COMPACTION = ON;
    
  • Nonaktifkan pemadatan indeks otomatis:

    ALTER DATABASE [database-name-placeholder]
    SET AUTOMATIC_INDEX_COMPACTION = OFF;
    

Untuk melihat apakah pemadatan indeks otomatis diaktifkan, gunakan tampilan katalog sys.databases . Misalnya, untuk melihat database mana yang mengaktifkan pemadatan indeks otomatis, jalankan kueri berikut:

SELECT database_id,
       name,
       is_automatic_index_compaction_on
FROM sys.databases;

Anda juga dapat menggunakan fungsi DATABASEPROPERTYEX untuk memeriksa IsAutomaticIndexCompactionOn properti .

Manfaat dan pertimbangan

Pemadatan indeks otomatis memberikan manfaat berikut:

  • Anda tidak perlu menyiapkan dan memelihara pekerjaan pemeliharaan indeks.
  • Ini menghindari konsumsi sumber daya yang tinggi dengan pekerjaan pemeliharaan indeks.
  • Ini mengurangi pertumbuhan ruang yang dapat terjadi ketika data dalam database dimodifikasi.
  • Ini meningkatkan performa kueri.
    • Kueri yang membaca indeks ringkas membaca lebih sedikit halaman dan karenanya memerlukan lebih sedikit disk I/O, CPU, dan memori.
    • Indeks ringkas lebih mungkin dipilih untuk meningkatkan rencana kueri.

Penting

Pemadatan otomatis hanya bertindak pada halaman yang baru saja dimodifikasi. Akibatnya, overhead kompaksi minimal dibandingkan dengan pembangunan indeks ulang atau reorganisasi indeks, yang memproses setiap halaman.

Meskipun overhead proses pemadatan minimal, itu bukan nol. Saat Anda mengaktifkan pemadatan indeks otomatis, pertimbangkan:

  • Jika proses pemadatan memindahkan banyak baris, Anda mungkin melihat peningkatan jumlah I/O tulis log transaksi dan ukuran cadangan log transaksi.
  • Anda mungkin melihat peningkatan kecil dalam pemanfaatan CPU ketika pemadatan terjadi, dalam rentang persen satu digit rendah. Peningkatan ini tidak umum.
  • Mirip dengan reorganisasi indeks, proses pemadatan memperoleh kunci halaman eksklusif jangka pendek (X) untuk memindahkan baris dari satu halaman ke halaman lainnya.
    • Dampak keserentakan adalah minimal. Jika kunci pada halaman tidak dapat segera diperoleh, halaman dilewati untuk menghindari pemblokiran kueri dan proses lain.
      • Kueri terkadang mungkin mengalami pemblokiran jangka pendek (milidetik). Pemblokiran ini terjadi jika kueri mencoba memperoleh kunci halaman atau baris setelah proses pemadatan telah terlebih dahulu mengambil kunci jangka pendek eksklusif di halaman, dan jarang terjadi.

Cara kerjanya

Pemadatan indeks otomatis adalah bagian dari proses pembersih penyimpanan versi persisten latar belakang (PVS ). Proses ini secara berkala menghapus versi baris usang dari halaman data. Jika Anda mengaktifkan pemadatan indeks otomatis untuk database, pembersih PVS juga memadatkan indeks.

Saat pembersih mengunjungi setiap halaman yang memiliki baris yang baru saja disisipkan, diperbarui, atau dihapus, ia memeriksa ruang kosong pada halaman tersebut dan ruang terpakai di beberapa halaman berikutnya. Jika ada cukup ruang kosong di halaman saat ini, pembersih memindahkan baris dari halaman berikut ke halaman saat ini jika tindakan tersebut membuat setidaknya salah satu halaman berikut kosong.

Halaman kosong didealokasi. Akibatnya, jumlah total halaman yang digunakan dalam database berkurang, kepadatan halaman meningkat, dan konsumsi ruang penyimpanan, I/O disk, CPU, dan memori kumpulan buffer berkurang.

Diagram berikut menunjukkan tampilan konseptual halaman data dalam indeks sebelum dan sesudah pemadatan.

Diagram memperlihatkan tampilan konseptual halaman data sebelum dan sesudah pemadatan indeks otomatis.

Proses pemadatan berlanjut di latar belakang saat data dimodifikasi dan versi baris usang dibersihkan.

Proses pemadatan mungkin melewati beberapa halaman karena aktivitas bersamaan, seperti:

  • Transaksi aktif menggunakan halaman .
  • Pembangunan atau reorganisasi indeks sedang berlangsung.
  • Operasi penyusutan sedang berlangsung.
  • Ukuran PVS yang besar atau banyaknya transaksi yang dibatalkan untuk dibersihkan dari PVS.
    • Pembersihan PVS diprioritaskan daripada pemadatan otomatis. Pemadatan ditangguhkan jika ukuran PVS melebihi 150 GB, atau jika jumlah transaksi yang dibatalkan melebihi 1.000.

Untuk alasan yang kurang umum mengapa proses pemadatan mungkin melewati halaman, lihat Menggunakan peristiwa yang diperluas untuk memantau statistik pemadatan.

Jika sebuah halaman dilewati, halaman tersebut akan dipertimbangkan untuk pemadatan saat diproses berikutnya oleh pembersih PVS.

Pemadatan indeks otomatis tidak tersedia untuk tabel sistem dan untuk database sistem selain msdb. Indeks dengan kunci halaman yang dinonaktifkan tidak memenuhi syarat untuk pemadatan otomatis.

Untuk informasi selengkapnya tentang halaman data, lihat Panduan arsitektur halaman dan ekstensi.

Untuk informasi selengkapnya tentang indeks, lihat Arsitektur indeks dan panduan desain.

Perbandingan dengan reorganisasi indeks dan pembangunan ulang indeks

Pertimbangkan perbedaan berikut antara operasi pemeliharaan indeks tradisional (reorganisasi indeks, pembangunan ulang indeks) dan pemadatan indeks otomatis:

Pertimbangan Recommendations
Pemadatan terjadi terus menerus dan dengan overhead minimal selama data dalam database dimodifikasi. Anda tidak perlu menyiapkan, memantau, dan memelihara pekerjaan pemeliharaan indeks untuk mendapatkan manfaat yang mungkin diberikan pekerjaan ini.
Tidak seperti reorganisasi indeks dan membangun kembali yang memproses semua halaman, proses pemadatan hanya mempertimbangkan halaman yang dimodifikasi setelah Anda mengaktifkan pemadatan indeks otomatis. Jika kepadatan halaman untuk indeks sudah rendah, pertimbangkan untuk menjalankan reorganisasi indeks satu kali atau pembangunan ulang indeks untuk meningkatkannya. Operasi satu kali ini adalah pengoptimalan ekstra untuk meningkatkan kepadatan halaman segera. Sejak saat itu, pemadatan otomatis membuat indeks tetap ringkas tanpa tindakan pengguna.
Setiap operasi pembangunan ulang indeks memerlukan ruang kosong yang substansial dalam file data, biasanya sama dengan ukuran indeks atau partisi yang sedang dibangun kembali. Anda tidak perlu mengalokasikan ruang kosong dalam file data untuk pemadatan indeks otomatis atau untuk reorganisasi indeks.
Tidak seperti pembangunan ulang indeks atau reorganisasi indeks, pemadatan tidak mengurangi fragmentasi indeks. Peningkatan kepadatan halaman setelah pemadatan lebih penting daripada fragmentasi indeks. Untuk sebagian besar beban kerja, fragmentasi indeks yang lebih tinggi tidak memengaruhi performa kueri atau konsumsi sumber daya.
Ketika faktor pengisian untuk indeks kurang dari 100 persen tetapi jumlah data pada halaman melebihi faktor pengisian, pemadatan indeks atau reorganisasi tidak memindahkan baris menjauh dari halaman. Pembangunan ulang indeks membuat halaman baru dan mengisinya sesuai dengan faktor pengisian. Untuk sebagian besar beban kerja, kepadatan halaman yang lebih tinggi lebih disukai. Beban kerja yang memerlukan faktor pengisian yang lebih rendah untuk mengurangi pemisahan halaman mungkin mendapat manfaat dari pembangunan ulang indeks sesekali. Pembangunan ulang membuat halaman dengan kepadatan halaman yang lebih rendah yang cocok dengan faktor pengisian.
Tidak seperti pembangunan ulang indeks, pemadatan tidak memperbarui statistik pada indeks. Jika pembaruan statistik otomatis tidak mencukupi untuk beban kerja Anda dan Anda mengandalkan pembangunan ulang indeks untuk memperbarui statistik, pertimbangkan untuk menggunakan pemadatan otomatis dalam kombinasi dengan pekerjaan pembaruan statistik.

Untuk informasi selengkapnya tentang reorganisasi dan pembangunan ulang indeks, lihat Mengoptimalkan pemeliharaan indeks untuk meningkatkan performa kueri dan mengurangi konsumsi sumber daya.

Kepadatan halaman dan fragmentasi indeks

Kepadatan halaman dan fragmentasi indeks adalah dua metrik yang mencerminkan konsumsi ruang oleh indeks dan dapat memengaruhi performa kueri. Fungsi manajemen dinamis (DMF) sys.dm_db_index_physical_stats melaporkan metrik ini di avg_page_space_used_in_percent kolom dan avg_fragmentation_in_percent masing-masing.

Pemadatan meningkatkan kepadatan halaman dengan menyimpan lebih banyak baris di halaman yang sama, yang meningkatkan performa dan mengurangi konsumsi sumber daya.

Anda mungkin mengamati bahwa fragmentasi indeks lebih tinggi saat Anda mengaktifkan pemadatan indeks otomatis. Jika kondisi ini terjadi, pertimbangkan:

Pertimbangan Recommendations
Dalam beberapa beban kerja intensif penulisan, halaman mungkin dibagi lagi segera setelah pemadatan. Pemisahan halaman meningkatkan fragmentasi indeks. Jika performa beban kerja terpengaruh sebagai hasilnya, gunakan pembangunan ulang indeks satu kali dengan faktor pengisian yang sedikit berkurang untuk mengurangi pemisahan halaman setelah pemadatan.

Misalnya, atur faktor pengisian dalam rentang 70-95 persen. Namun, jangan mengurangi faktor pengisian secara tidak perlu atau mengaturnya terlalu rendah. Sebagian besar beban kerja mencapai performa optimal dan pemanfaatan sumber daya dengan fill factor yang diatur pada nilai default 100 persen.
Dealokasi halaman kosong selama pemadatan dapat menciptakan kesenjangan dalam urutan nomor halaman dalam suatu extent. Kesenjangan dalam jangkauan meningkatkan fragmentasi indeks, berpotensi mengurangi ukuran I/O read-ahead . Bahkan untuk beban kerja yang mendapat manfaat dari pembacaan awal, pengaruh kinerja akibat fragmentasi yang lebih tinggi diminimalkan karena kueri membaca lebih sedikit halaman setelah pemadatan.

Petunjuk / Saran

Untuk sebagian besar beban kerja, manfaat kepadatan halaman yang lebih tinggi melebihi dampak performa apa pun dari fragmentasi indeks yang lebih tinggi.

Memantau pemadatan indeks otomatis

Untuk melihat efektivitas pemadatan indeks otomatis, Anda dapat memantau metrik indeks utama seperti jumlah halaman, kepadatan halaman rata-rata, dan fragmentasi indeks rata-rata dari waktu ke waktu. Untuk informasi selengkapnya, lihat contoh Menentukan metrik indeks kunci .

Anda juga dapat memantau statistik pemadatan terperinci menggunakan Extended Events. Untuk informasi selengkapnya, lihat contoh Menggunakan peristiwa yang diperluas untuk memantau statistik pemadatan .

Keterbatasan

Proses pemadatan indeks otomatis hanya mempertimbangkan halaman pada tingkat daun dari indeks pohon-B yang terkandung dalam unit alokasi IN_ROW_DATA. Hal ini termasuk halaman dalam:

  • Indeks dan batasan berkluster.
  • Indeks dan batasan yang tidak terkendali.
  • Indeks pohon B pada tabel internal yang menyimpan jenis indeks khusus seperti XML, teks lengkap, spasial, dan kumpulan baris internal penyimpan kolom.

Jenis halaman berikut tidak memenuhi syarat untuk pemadatan indeks otomatis:

  • Halaman dalam tabel tumpuk.
  • Halaman dalam unit alokasi ROW_OVERFLOW_DATA atau LOB_DATA.
  • Halaman dalam grup baris yang terkompresi pada indeks kolom penyimpan.
  • Halaman pada tabel yang dioptimalkan untuk memori.

Tanya jawab umum (FAQ)

Bagian ini menjawab pertanyaan umum tentang pemadatan indeks otomatis.

Apakah menghidupkan ulang atau akses database eksklusif diperlukan untuk mengaktifkan atau menonaktifkan pemadatan otomatis?

Tidak. Pemadatan dimulai atau berhenti dalam beberapa menit setelah menjalankan ALTER DATABASE ... SET AUTOMATIC_INDEX_COMPACTION = ... perintah.

Bagaimana hal itu mempengaruhi kinerja kueri?

Kueri cenderung berjalan lebih cepat dan menggunakan lebih sedikit I/O disk, memori, dan CPU. Perbaikan ini terutama terlihat pada beban kerja dengan aktivitas penulisan signifikan yang dapat menyebabkan pembengkakan indeks.

Bagaimana cara mengubah konsumsi ruang penyimpanan?

Pemadatan mengurangi pertumbuhan ruang yang digunakan dalam file data. Namun, tidak seperti penyusutan database, itu tidak mengurangi ukuran file data yang dialokasikan.

Apakah ada overhead?

Untuk sebagian besar beban kerja, overhead tidak terlihat. Untuk beban kerja dengan intensitas penulisan tinggi, Anda mungkin melihat peningkatan I/O log transaksi serta ukuran cadangan log transaksi.

Bisakah itu menyebabkan pemblokiran?

Pemblokiran karena pemadatan otomatis tidak mungkin terjadi. Jika ada pemblokiran terjadi, pemblokiran bersifat jangka pendek dan sementara (milidetik).

Jika kueri diblokir, periksa perintah pemblokir kepala di sys.dm_exec_requests. Pemadatan otomatis mungkin memblokir kueri jika perintah adalah VERSION_CLEANER_MAIN atau VERSION_CLEANER_WORKER.

Apakah itu menghormati faktor pengisian?

Pemadatan otomatis tidak pernah mengisi halaman melebihi faktor isian. Namun, jika halaman sudah diisi di atas faktor pengisian oleh pernyataan DML sebelumnya, pemadatan tidak mengurangi kepadatan halaman. Halaman mungkin tetap diisi di atas faktor pengisian setelah pemadatan.

Apakah berfungsi jika indeks menggunakan kompresi baris atau halaman?

Ya. Pemadatan otomatis menghapus ruang kosong dari halaman dalam indeks. Tidak masalah apakah data pada halaman dikompresi atau tidak.

Apa bedanya dengan pembersihan hantu?

Pembersihan hantu menghapus baris yang dihapus sementara dari halaman, yang meninggalkan ruang kosong di halaman. Pemadatan otomatis menghapus ruang kosong pada halaman dengan mengonsolidasikan data pada lebih sedikit halaman.

Apa yang terjadi jika saya menjalankan pembangunan ulang indeks atau reorganisasi indeks saat pemadatan otomatis diaktifkan?

Pemadatan otomatis mengabaikan indeks yang sedang dibangun kembali atau diatur ulang, termasuk indeks dalam operasi indeks yang dapat dilanjutkan setelah dijeda.

Examples

Jalankan contoh T-SQL berikut dalam database pengguna, bukan di master database.

Menentukan metrik indeks kunci

Kueri berikut mengembalikan jumlah halaman dalam tingkat daun indeks, kepadatan halaman rata-rata dan fragmentasi di page_countkolom , , avg_page_space_used_in_percentdan avg_fragmentation_in_percent masing-masing, untuk indeks yang memenuhi syarat untuk pemadatan otomatis. Kueri juga mengembalikan baris total yang berisi metrik ini secara agregat untuk semua indeks dalam database.

SELECT COALESCE (OBJECT_SCHEMA_NAME(ips.object_id), '<Total>') AS schema_name,
       COALESCE (OBJECT_NAME(ips.object_id), '<Total>') AS object_name,
       COALESCE (i.name, '<Total>') AS index_name,
       COALESCE (i.type_desc, '<Total>') AS index_type,
       COALESCE (ips.partition_number, NULL) AS partition_number,
       AVG(ips.avg_page_space_used_in_percent) AS avg_page_space_used_in_percent,
       AVG(ips.avg_fragmentation_in_percent) AS avg_fragmentation_in_percent,
       SUM(ips.record_count) AS record_count,
       SUM(ips.page_count) AS page_count
FROM sys.dm_db_index_physical_stats(DB_ID(), DEFAULT, DEFAULT, DEFAULT, 'SAMPLED') AS ips
     INNER JOIN sys.indexes AS i
         ON ips.object_id = i.object_id
        AND ips.index_id = i.index_id
WHERE i.type_desc IN ('CLUSTERED', 'NONCLUSTERED', 'XML', 'SPATIAL')
      AND ips.index_level = 0
      AND ips.page_count > 0
      AND ips.alloc_unit_type_desc = 'IN_ROW_DATA'
GROUP BY ROLLUP(ips.object_id, i.name, i.type_desc, ips.partition_number)
HAVING ips.object_id IS NULL
       AND ips.object_id IS NULL
       AND i.name IS NULL
       AND i.type_desc IS NULL
       AND ips.partition_number IS NULL
       OR ips.object_id IS NOT NULL
          AND ips.object_id IS NOT NULL
          AND i.name IS NOT NULL
          AND i.type_desc IS NOT NULL
          AND ips.partition_number IS NOT NULL
ORDER BY IIF (ips.object_id IS NULL, 0, 1), page_count DESC;

Kueri mengembalikan perkiraan hasil dengan mengambil sampel subset halaman. Ubah SAMPLED menjadi DETAILED untuk mendapatkan hasil yang lebih tepat. Penggunaan DETAILED untuk database besar dapat memakan waktu lebih lama karena semua indeks yang memenuhi syarat dalam database sepenuhnya dipindai. Untuk informasi selengkapnya, lihat sys.dm_db_index_physical_stats.

Menggunakan peristiwa yang diperluas untuk memantau statistik pemadatan

Anda dapat menggunakan peristiwa diperpanjang auto_index_compaction_stats untuk memantau statistik pemadatan untuk basis data. Peristiwa ini terjadi setiap 10 menit. Ini berisi data seperti jumlah baris yang dipindahkan antar halaman untuk memampatkan indeks, jumlah halaman yang dialokasikan kembali, dan jumlah upaya pemadatan yang dilewati karena beragam alasan. Statistik yang dilaporkan oleh setiap peristiwa bersifat kumulatif sejak startup mesin database.

Contoh T-SQL berikut membuat dan memulai sesi peristiwa yang mengumpulkan auto_index_compaction_stats data peristiwa dalam target ring_buffer . Kueri membandingkan peristiwa saat ini dan sebelumnya untuk mengembalikan statistik pemadatan untuk setiap interval 10 menit. Karena kueri memerlukan setidaknya dua peristiwa untuk menghitung statistik untuk interval waktu, kueri mungkin tidak mengembalikan data apa pun hingga 20 menit setelah sesi peristiwa dimulai.

/*
Create and start an event session collecting the auto_index_compaction_stats event
into a ring_buffer target
*/
IF NOT EXISTS (SELECT 1
               FROM sys.dm_xe_database_sessions
               WHERE name = N'automatic_index_compaction')
BEGIN
    CREATE EVENT SESSION automatic_index_compaction ON DATABASE
    ADD EVENT sqlserver.auto_index_compaction_stats
    ADD TARGET package0.ring_buffer (SET MAX_MEMORY = 1024);

    ALTER EVENT SESSION automatic_index_compaction ON DATABASE STATE = START;
END;

/* Get event data from the ring_buffer target */
DECLARE @EventData AS XML = (SELECT CAST (xst.target_data AS XML) AS TargetData
                             FROM sys.dm_xe_database_session_targets AS xst
                                  INNER JOIN sys.dm_xe_database_sessions AS xs
                                      ON xst.event_session_address = xs.address
                             WHERE xs.name = N'automatic_index_compaction');

/* Return statistics for each 10-minute interval */
WITH compaction_stats_event AS (
    SELECT d.value('@timestamp', 'datetimeoffset') AS timestamp,
           d.value('(data[@name = "database_id"]/value/text())[1]', 'smallint') AS database_id,
           d.value('(data[@name = "compact_attempts"]/value/text())[1]', 'bigint') AS compact_attempts,
           d.value('(data[@name = "compact_completed"]/value/text())[1]', 'bigint') AS compact_completed,
           d.value('(data[@name = "pages_deallocated_compaction"]/value/text())[1]', 'bigint') AS pages_deallocated_compaction,
           d.value('(data[@name = "rows_moved"]/value/text())[1]', 'bigint') AS rows_moved
    FROM @EventData.nodes('/RingBufferTarget/event') AS e(d)
    WHERE e.d.value('@name', 'sysname') = 'auto_index_compaction_stats'
),
timestamp_map AS (
    SELECT database_id,
           timestamp,
           LAG(timestamp) OVER (PARTITION BY database_id ORDER BY timestamp) AS previous_timestamp
    FROM compaction_stats_event
)
SELECT c.timestamp,
       c.database_id,
       c.compact_attempts - p.compact_attempts AS compact_attempts,
       c.compact_completed - p.compact_completed AS compact_completed,
       c.pages_deallocated_compaction - p.pages_deallocated_compaction AS pages_deallocated_compaction,
       c.rows_moved - p.rows_moved AS rows_moved
FROM compaction_stats_event AS c
     INNER JOIN timestamp_map AS tm
         ON c.timestamp = tm.timestamp
        AND c.database_id = tm.database_id
     INNER JOIN compaction_stats_event AS p
         ON tm.previous_timestamp = p.timestamp
        AND tm.database_id = p.database_id
ORDER BY timestamp DESC;

Anda dapat mengubah kueri sebelumnya untuk menyertakan bidang acara lainnya dan mengembalikan lebih banyak statistik, seperti jumlah percobaan pemadatan yang dilewatkan karena berbagai alasan. Gunakan kueri berikut untuk melihat semua bidang auto_index_compaction_stats peristiwa dan deskripsinya.

SELECT name,
       type_name,
       description
FROM sys.dm_xe_object_columns
WHERE object_name = N'auto_index_compaction_stats'
      AND column_type = N'data';

Kirim tanggapan

Microsoft sangat ingin mendengar umpan balik Anda mengenai pemadatan indeks otomatis. Kirim umpan balik produk dengan memposting ide baru di forum umpan balik SQL. Anggota komunitas lain dapat memberi suara positif dan mengomentari ide dan saran Anda. Suara dan komentar komunitas membantu Microsoft merencanakan dan memprioritaskan peningkatan produk.