it-swarm.com.de

Richtlinien für die Pflege des Volltextindex

Welche Richtlinien sollten für die Pflege von Volltextindizes beachtet werden?

Sollte ich den Volltextkatalog neu erstellen oder neu organisieren (siehe BOL )? Was ist eine angemessene Wartungskadenz? Welche Heuristiken (ähnlich den Fragmentierungsschwellen von 10% und 30%) können verwendet werden, um zu bestimmen, wann eine Wartung erforderlich ist?

(Alles unten sind lediglich zusätzliche Informationen, die auf die Frage eingehen und zeigen, worüber ich bisher nachgedacht habe.)



Zusätzliche Informationen: meine erste Recherche

Es gibt viele Ressourcen zur Pflege des B-Tree-Index (z. B. diese Frage , Ola Hallengrens Skripte und zahlreiche Blog-Beiträge zu diesem Thema von anderen Websites). Ich habe jedoch festgestellt, dass keine dieser Ressourcen Empfehlungen oder Skripte zur Verwaltung von Volltextindizes enthält.

Es gibt Microsoft-Dokumentation , die erwähnt, dass das Defragmentieren des B-Tree-Index der Basistabelle und das anschließende Ausführen einer REORGANISIERUNG für den Volltextkatalog die Leistung verbessern kann, jedoch keine spezifischeren Empfehlungen berührt .

Ich habe auch diese Frage gefunden, aber es konzentriert sich hauptsächlich auf die Änderungsverfolgung (wie Datenaktualisierungen der zugrunde liegenden Tabelle in den Volltextindex übertragen werden) und nicht auf die Art der regelmäßig geplanten Wartung, die die Effizienz maximieren könnte des Index.

Zusätzliche Informationen: Grundlegende Leistungstests

Diese SQL Fiddle enthält Code, mit dem ein Volltextindex mit AUTO Änderungsverfolgung erstellt und sowohl die Größe als auch die Abfrageleistung des Index überprüft werden können, wenn die Daten in der Tabelle geändert werden . Wenn ich die Logik des Skripts auf einer Kopie meiner Produktionsdaten ausführe (im Gegensatz zu den künstlich hergestellten Daten in der Geige), finden Sie hier eine Zusammenfassung der Ergebnisse, die ich nach jedem Datenänderungsschritt sehe:

(enter image description here

Obwohl die Update-Anweisungen in diesem Skript ziemlich erfunden waren, scheinen diese Daten zu zeigen, dass durch regelmäßige Wartung viel gewonnen werden kann.

Zusätzliche Informationen: Erste Ideen

Ich denke darüber nach, eine nächtliche oder wöchentliche Aufgabe zu erstellen. Es scheint, dass diese Aufgabe entweder REBUILD oder REORGANIZE ausführen könnte.

Da die Volltextindizes sehr groß sein können (zig oder Hunderte Millionen Zeilen), möchte ich feststellen können, wann die Indizes im Katalog ausreichend fragmentiert sind, sodass ein REBUILD/REORGANIZE erforderlich ist. Ich bin mir ein bisschen unklar, welche Heuristiken dafür sinnvoll sein könnten.

30
Geoff Patterson

Ich konnte online keine guten Ressourcen finden, daher habe ich weitere praktische Nachforschungen angestellt und dachte, es wäre nützlich, den resultierenden Volltext-Wartungsplan zu veröffentlichen, den wir basierend auf diesen Nachforschungen implementieren.


Unsere Heuristik, um festzustellen, wann Wartung erforderlich ist

(enter image description here

Unser primäres Ziel ist es, eine konsistente Volltextabfrageleistung beizubehalten, wenn sich Daten in den zugrunde liegenden Tabellen entwickeln. Aus verschiedenen Gründen wäre es für uns jedoch schwierig, jede Nacht eine repräsentative Suite von Volltextabfragen für jede unserer Datenbanken zu starten und anhand der Leistung dieser Abfragen zu bestimmen, wann eine Wartung erforderlich ist. Aus diesem Grund wollten wir Faustregeln erstellen, die sehr schnell berechnet und als Heuristik verwendet werden können, um anzuzeigen, dass die Pflege des Volltextindex möglicherweise gerechtfertigt ist.

Im Verlauf dieser Untersuchung haben wir festgestellt, dass der Systemkatalog viele Informationen darüber enthält, wie ein bestimmter Volltextindex in Fragmente unterteilt ist. Es wird jedoch keine offizielle "Fragmentierung%" berechnet (wie bei B-Tree-Indizes über sys.dm_db_index_physical_stats ). Basierend auf den Volltextfragmentinformationen haben wir beschlossen, unsere eigene "Volltextfragmentierung%" zu berechnen. Wir haben dann einen Entwicklungsserver verwendet, um wiederholt zufällige Aktualisierungen von 100 bis 25.000 Zeilen gleichzeitig für eine 10-Millionen-Zeilen-Kopie der Produktionsdaten durchzuführen, die Volltextfragmentierung aufzuzeichnen und eine Benchmark-Volltextabfrage mit CONTAINSTABLE.

Die Ergebnisse, wie in den obigen und unteren Diagrammen zu sehen, waren sehr aufschlussreich und zeigten, dass das von uns erstellte Fragmentierungsmaß sehr stark mit der beobachteten Leistung korreliert. Da dies auch mit unseren qualitativen Beobachtungen in der Produktion zusammenhängt, reicht dies aus, um die Fragmentierung% als Heuristik für die Entscheidung zu verwenden, wann unsere Volltextindizes gewartet werden müssen.

(enter image description here


Der Wartungsplan

Wir haben uns entschieden, den folgenden Code zu verwenden, um eine Fragmentierung% für jeden Volltextindex zu berechnen. Alle nicht trivialen Volltextindizes mit einer Fragmentierung von mindestens 10% werden als neu erstellt gekennzeichnet, um von unserer nächtlichen Wartung neu erstellt zu werden.

-- Compute fragmentation information for all full-text indexes on the database
SELECT c.fulltext_catalog_id, c.name AS fulltext_catalog_name, i.change_tracking_state,
    i.object_id, OBJECT_SCHEMA_NAME(i.object_id) + '.' + OBJECT_NAME(i.object_id) AS object_name,
    f.num_fragments, f.fulltext_mb, f.largest_fragment_mb,
    100.0 * (f.fulltext_mb - f.largest_fragment_mb) / NULLIF(f.fulltext_mb, 0) AS fulltext_fragmentation_in_percent
INTO #fulltextFragmentationDetails
FROM sys.fulltext_catalogs c
JOIN sys.fulltext_indexes i
    ON i.fulltext_catalog_id = c.fulltext_catalog_id
JOIN (
    -- Compute fragment data for each table with a full-text index
    SELECT table_id,
        COUNT(*) AS num_fragments,
        CONVERT(DECIMAL(9,2), SUM(data_size/(1024.*1024.))) AS fulltext_mb,
        CONVERT(DECIMAL(9,2), MAX(data_size/(1024.*1024.))) AS largest_fragment_mb
    FROM sys.fulltext_index_fragments
    GROUP BY table_id
) f
    ON f.table_id = i.object_id

-- Apply a basic heuristic to determine any full-text indexes that are "too fragmented"
-- We have chosen the 10% threshold based on performance benchmarking on our own data
-- Our over-night maintenance will then drop and re-create any such indexes
SELECT *
FROM #fulltextFragmentationDetails
WHERE fulltext_fragmentation_in_percent >= 10
    AND fulltext_mb >= 1 -- No need to bother with indexes of trivial size

Diese Abfragen führen zu Ergebnissen wie den folgenden. In diesem Fall werden die Zeilen 1, 6 und 9 als zu fragmentiert für eine optimale Leistung markiert, da der Volltextindex über 1 MB liegt und mindestens 10% fragmentiert ist.

(enter image description here


Wartungskadenz

Wir haben bereits ein nächtliches Wartungsfenster und die Berechnung der Fragmentierung ist sehr billig zu berechnen. Wir werden diese Prüfung also jede Nacht durchführen und dann nur dann den teureren Vorgang ausführen, einen Volltextindex tatsächlich neu zu erstellen, wenn dies auf der Grundlage des 10% -Fragmentierungsschwellenwerts erforderlich ist.


REBUILD vs. REORGANIZE vs. DROP/CREATE

SQL Server bietet die Optionen REBUILD und REORGANIZE, sie sind jedoch nur für einen Volltextkatalog (der eine beliebige Anzahl von Volltextindizes enthalten kann) in seiner Gesamtheit verfügbar. Aus früheren Gründen haben wir einen einzigen Volltextkatalog, der alle unsere Volltextindizes enthält. Deshalb haben wir uns entschieden zu fallen (DROP FULLTEXT INDEX) und dann neu erstellen (CREATE FULLTEXT INDEX) stattdessen auf einer einzelnen Volltext-Indexebene.

Es ist vielleicht idealer, Volltextindizes auf logische Weise in separate Kataloge aufzuteilen und stattdessen ein REBUILD auszuführen, aber die Drop/Create-Lösung funktioniert in der Zwischenzeit für uns.

37
Geoff Patterson