Sqlserver
 sql >> Datenbank >  >> RDS >> Sqlserver

SQL Server – Untersuchen Sie die Interna von sp_spaceused

Dieser Artikel ist ein Versuch, die Ausgabe von sp_spaceused zu analysieren gespeicherte Prozedur.

Einführung

Das Verständnis der Interna der Datenbanknutzung und der Wachstumstrends spielt eine entscheidende Rolle bei der Definition der richtigen Größe der Datenbank. sp_spaceused ist wahrscheinlich die am häufigsten ausgeführte gespeicherte Systemprozedur eines Administrators, um den von einer Datenbank belegten Speicherplatz zu ermitteln. Dies hilft, einen schnellen Überblick über die Datenbanknutzung zu erhalten. Statistiken. sp_spaceused wird verwendet, um die Anzahl der Zeilen, die Datengröße, die Indexgröße, die Menge des belegten Speicherplatzes, den ungenutzten Speicherplatz jedes Objekts und die nicht zugeordnete Größe der Datenbank anzuzeigen. Obwohl man sich die von sp_spaceused angegebenen Werte ansieht, sollte man nicht daran denken, die Datenbank, die Datendatei oder die Protokolldatei zu verkleinern. Oft sind wir uns dessen nicht bewusst, was wir tun. Oft wissen wir nicht, welche Nachwirkungen solche ressourcenintrinsischen Operationen haben würden. Die Ausgabe von sp_spaceused sagt viel über die aktuelle Leistung der Datenbank aus. Die nicht zugewiesenen Spalte und dieunbenutzte Spalte teilen uns den freien Speicherplatz mit, der auf der Datenbank- und Tabellenebene verbleibt.

Dieser Artikel berücksichtigt:

  1. Ein Blick in sp_spaceused
  2. Auswirkung der Einstellung für automatisches Wachstum auf die Spalten, nicht zugeordnet und nicht verwendet
  3. Ermitteln der Details zur Speicherplatznutzung auf Datenbank- und Instanzebene
  4. Messung der Autowachstumsereignisse
  5. Ermitteln der mdf- und ldf-Dateigrößen
  6. Faktoren, die die Leistung der Datenbank bestimmen
  7. Und mehr...

Interna von sp_spaceused

Erfassen Sie Details zur Speicherplatznutzung aller Tische

Im folgenden T-SQL wird die undokumentierte gespeicherte Prozedur sp_MSforeachtable verwendet, um alle Tabellen innerhalb des Bereichs des aktuellen Datenbankkontexts zu durchlaufen, um die Speicherplatznutzungsmetriken aller Tabellen im Kontext abzurufen.

Declare @tbl_sp_spaceused table(
    name varchar(100) NULL,
    rows bigint NULL,
    reserved varchar(20) NULL,
    data varchar(20) NULL,
    index_size varchar(20) NULL,
    unused varchar(20) NULL
    )

-- insert output of sp_spaceused to table variable

INSERT INTO @tbl_sp_spaceused ( name, rows, reserved, data, index_size, unused )
EXEC sp_MSforeachtable @command1 = 'EXEC sp_spaceused [?]'

SELECT *
FROM @tbl_sp_spaceused
order by rows desc

Erfassen Sie Details zur Speicherplatznutzung aller Datenbanken

Die undokumentierte gespeicherte Prozedur sp_MSforeachDB wird verwendet, um die gesamte Datenbank innerhalb des Bereichs der aktuellen SQL-Instanz zu durchlaufen, um die Speicherplatznutzungsinformationen aller Datenbanken abzurufen.

declare @tbl_sp_spaceusedDBs table(
    database_name varchar(100) NOT NULL,
    database_size varchar(50) NULL,
    unallocated varchar(30) NULL,
    reserved varchar(20) NULL,
    data varchar(20) NULL,
    index_size varchar(20) NULL,
    unused varchar(20) NULL
    )
INSERT INTO @tbl_sp_spaceusedDBs ( database_name, database_size, unallocated, reserved, data, index_size, unused )
EXEC sp_msforeachdb @command1="use ? exec sp_spaceused @oneresultset = 1"

SELECT *
FROM @tbl_sp_spaceusedDBs
ORDER BY database_name, database_size

Hier, Datenbankname ist der Name der Datenbank; in diesem Fall PythonSample . Datenbankgröße ist Uallokiert+Reserviert+Daten+Index+Unbenutzt =MDF +LDF (=in diesem Fall 848 MB). Die nicht zugewiesenen Platz hier ist 51,94 MB.

Dies ist in Wirklichkeit die Festplattengrenze, die für die Datenbank markiert wurde. Der sp_spaceused gibt eine nicht zugeordnete Spalte aus, die auf Datenbankebene definiert ist, und sie ist nicht für eine Tabelle reserviert und kann vom ersten Objekt belegt werden, das mehr Platz zum Wachsen beansprucht.

Die nicht zugeordnete Speicherplatz ist der freie Speicherplatz in der Datendatei, damit er nicht bei jeder Abfrage automatisch vergrößert werden muss; Normalerweise verwaltet die SQL Server-Speicher-Engine die automatische Vergrößerung mithilfe eines Mechanismus, der als Proportional Fill Algorithm bekannt ist. Die Verwaltung der Extents erfolgt effektiv basierend auf der Anzahl der Schreibvorgänge auf den Dateien. Und gleichzeitig wird, wenn der verwendete Speicherplatz einen Schwellenwert erreicht, ein Ereignis für weiteres automatisches Wachstum ausgelöst. Das Festlegen des richtigen Werts für nicht zugeordneten Speicherplatz hängt von den Anforderungen und Situationen sowie der Art der Verwendung der Datenbank ab. Nicht zugeordneter Speicherplatz ist der Speicherplatz, der noch nicht verwendet wird und „zu haben“ ist. Im Wesentlichen sind diese Extents mit Bit 1 auf der GAM-Seite gekennzeichnet. Wenn Sie das Konzept des automatischen Wachstums von oben verstehen, kann jede Art von Wachstum weitere nicht zugeordnete Extents generieren.

Mit der folgenden SQL-Abfrage können wir sehen, wie oft das Autowachstumsereignis generiert wurde, zusammen mit der Zeit, die die Datenbank für den Prozess angehalten hat.

DECLARE @fname NVARCHAR(1000);

-- Get the name of the current default trace
SELECT @fname = CAST(value AS VARCHAR(MAX))
FROM ::fn_trace_getinfo(DEFAULT)
WHERE traceid = 1 AND property = 2;


SELECT 
	 ft.StartTime [Start Time]
	,t.name [Event Name]
	,DB_NAME(ft.databaseid) [Database Name]
	,ft.Filename [File Name]
	,(ft.IntegerData*8)/1024.0 [Growth MB]
	,(ft.duration/1000) [Duration MS]
FROM ::fn_trace_gettable(@fname, DEFAULT) AS ft 
INNER JOIN sys.trace_events AS t ON ft.EventClass = t.trace_event_id  
WHERE (ft.EventClass = 92  -- DateFile Auto-growth
    OR ft.EventClass = 93) -- LogFile Auto-growth
ORDER BY ft.StartTime

Sehen wir uns an, was die einzelnen Begriffe bedeuten:

Reserviert :Der für die Verwendung durch Datenbankobjekte reservierte Speicherplatz =(Daten +Index + Nicht verwendet ) =476704 + 1280 + 1312 =479296 KB. Dies zeigt an, wie voll die Objekte sind; Idealerweise werden 10 % des ungenutzten Speicherplatzes für Transaktionstabellen erwartet.

Daten :Die tatsächliche Größe der Daten. Dies ist die Summe aller Datendateien der Datenbank.

Index :Der Speicherplatz, der vom Index verwendet wird.

Hinweis:In einigen Fällen habe ich gesehen, dass die Größe des Index größer ist als die Größe der tatsächlichen Daten. Was Indizes angeht, hängt der Bedarf des Systems immer von der Leistungsfähigkeit der Datenbank ab. Oftmals sind die Leseoperationen wichtiger als die Schreiboperationen. Und in einigen anderen Fällen sind Schreibvorgänge wichtiger als Lesevorgänge. In Fällen, in denen das Unternehmen entschieden hat, dass Lesevorgänge weitaus wichtiger sind als Schreibvorgänge, benötigt dieses System möglicherweise Tonnen von Indizes, um die Leistungsanforderungen des Unternehmens und der Benutzer zu erfüllen.

Unbenutzt :Ein Teil des reservierten Speicherplatzes, der noch nicht verwendet wird

Unbenutzt sind Seiten auf zugewiesenen Extents, die aber noch von keinem Objekt verwendet werden. Sobald ein Extent zugewiesen wird (entweder als einheitlicher oder gemeinsam genutzter Extent), erhalten wir acht reservierte Seiten auf diesem Extent. Einige Seiten sind gebraucht, andere unbenutzt.

Die unbenutzte und nicht zugeordnet Spalten in der Ausgabe können verwirrend sein. Zur Verdeutlichung die unused Spaltenausgabe zeigt nicht die Menge an freiem Speicherplatz, der in der gesamten Datenbank verbleibt. Es ist stattdessen die Gesamtmenge an Speicherplatz, die für Tabellen reserviert, aber nicht mit Daten gefüllt ist. In vielen Fällen kann der ungenutzte Speicherplatz zurückgewonnen werden, indem ein gruppierter Index erstellt oder die vorhandenen Indizes verwaltet werden.

Die Ausgabe von sp_spaceused kann weiter vereinfacht werden, um die Größe der .mdf-Datei und der .log-Dateien zu finden. Die Summe aus reserviertem Speicherplatz und nicht zugewiesenem Speicherplatz entspricht mehr oder weniger der Größe der Daten- oder MDF-Datei. Außerdem ergibt das Subtrahieren der MDF-Dateigröße von der Datenbankgröße die Protokolldateigröße.

Hier sind also zwei Formeln:

Größe der MDF-Datei =reservierter + nicht zugeordneter Speicherplatz

Größe der Protokolldatei =Database_Size – Größe der MDF-Datei

SELECT 476704+ 1280+ 1312 'Reserved KB', (479296/1024.00)+51.94 'MDFSizeMB', 848.00 - ((479296/1024.00)+51.94) 'LogSizeMB'

Die oben genannten Punkte sagen uns, wie jede der Spalten in der Ausgabe von sp_spaceused interpretiert, berechnet und analysiert wird.

Auswirkung der Einstellung für automatisches Wachstum

Die Anfangsgrößen und die Auto-Growth-Konfiguration haben einen erheblichen Einfluss auf den ungenutzten Speicherplatz. Hier die richtigen Werte festzulegen, ist eine Herausforderung. Ich habe viele Fälle gesehen, in denen das automatische Wachstum prozentual steigen sollte. Nehmen wir an, dass das automatische Wachstum bei einer Datendateigröße von 100 GB auf 25 % eingestellt ist. Es sind nur 4 Auto-Growth-Ereignisse erforderlich, um das Laufwerk zu füllen.

Der andere Fall besteht darin, die Indizes neu zu erstellen. Dieser Vorgang wirkt sich direkt auf den ungenutzten Speicherplatz der Tabelle aus, da die Daten zwischen den einheitlichen und gemischten Extents neu gemischt werden. In einigen Fällen kann der Vorgang beim Neumischen der Seiten aufgrund der Einstellung für automatisches Wachstum der Datendatei zu nicht zugeordnetem Speicherplatz führen.

Betrachten wir ein Szenario, in dem die Einstellung für die automatische Vergrößerung nicht richtig in der Datenbank festgelegt ist. Dies ist wieder ein Problem:Wenn die automatische Vergrößerung in der Datenbank aktiviert ist, bedeutet dies, dass die Laufwerkserweiterung während eines Ereignisses automatisch stattfindet, selbst wenn die Daten nicht den gesamten Speicherplatz belegen.

Es empfiehlt sich immer, die entsprechende Einstellung für die automatische Vergrößerung für die Datendatei festzulegen. Manchmal kann die falsche Einstellung der Datendatei zu einer physischen Fragmentierung führen, was zu einer schwerwiegenden Leistungsminderung des Systems führt. Mit anderen Worten, wenn Sie keinen nicht zugeordneten Speicherplatz haben, werden die neuen Daten versuchen, sich an leeren Orten zu befinden, die möglicherweise verstreut sind. Dies gilt auch für die Protokolldatei. Der nicht zugeordnete Speicherplatz in der Datenbank beeinflusst indirekt die Einstellung für die automatische Vergrößerung der Datendatei und der Protokolldatei und wirkt sich direkt auf die Leistung aus. Der Schlüssel liegt darin, die richtige Balance zu finden.

Abschluss

  1. Im Prozess der Datenbankerstellung ist die definierte Größe (d. h. die Anfangsgröße) nichts anderes als die tatsächliche Größe der Datenbank. Diese Anfangsgröße wird im Seitenkopf aufgezeichnet. Während eines Datenbankverkleinerungsprozesses verwendet der Prozess die Mindestgröße -Eigenschaft als Referenz, nur wenn die tatsächliche Datengröße kleiner als die Mindestgröße ist – die Mindestgröße wird auch im Seitenkopf gefunden und kann mit dem DBCC PAGE-Befehl angezeigt werden. Derselbe Prozess gilt auch für DBCC SHRINKFILE, das Dateien auf weniger als ihre ursprüngliche Größe verkleinert.
  2. Es wird nicht empfohlen, die Datenbank zu verkleinern, um Speicherplatz freizugeben, obwohl die Entscheidung vom Szenario abhängt – ungewöhnliche Szenarien können eine unkonventionelle Vorgehensweise rechtfertigen. Man muss jedoch bedenken, dass das Verkleinern einer Datenbank zu einer Fragmentierung in der Datenbank führt. Es empfiehlt sich immer, die Grundursache des nicht zugeordneten Speicherplatzes zu analysieren und ungenutzter Speicherplatz der Objekte. In vielen Fällen wäre die Erweiterung der Festplatte zur Bewältigung des Datenwachstums eine praktikable/empfohlene Option.
  3. Auto-Growth-Konfiguration:Wenn SQL Server einen Auto-Grow-Vorgang durchführt, muss die Transaktion, die das Auto-Grow-Ereignis ausgelöst hat, warten, bis das Auto-Grow-Ereignis abgeschlossen ist. Erst dann kann die Transaktion selbst abgeschlossen werden.
  4. Es wird immer empfohlen, die Optionen für das automatische Wachstum in Zahlen statt in Prozenten einzustellen.
  5. Die Einführung von ungenutztem Platz in der Tabelle kann folgende Gründe haben:
    • Fragmentierung
      Wenn Daten aufgrund ihrer Art und Art der Definition fragmentiert werden, wird ungenutzter Speicherplatz generiert. Außerdem führt eine häufige Änderung der Daten (alle UPDATE-, INSERT- ODER DELETE-Operationen) zu mehr Seitenteilungen, was eher ungenutzten Platz in der Tabelle erzeugt.
    • Kein geclusterter Index in der Tabelle
      Um die Fragmentierung in einem Heap zu reduzieren, kann man daran denken, einen geclusterten Index zu erstellen auf dem Tisch. Um die Indexfragmentierung zu reduzieren, führen Sie eine Indexwartung durch, indem Sie den Wert avg_fragmentation_in_percent ermitteln.
    • Größe der Daten
      In einigen Fällen führt die Verwendung geeigneter Datentypen zu kleineren Datenzeilen, wodurch wiederum mehr Zeilen auf einer Seite platziert werden können. Es reduziert nicht nur den internen ungenutzten Speicherplatz, sondern wirkt sich auch auf die Leistung aus, indem es die Anzahl der Seitenteilungen reduziert.
  6. Der ungenutzte Speicherplatz kann auch das Ergebnis des Löschens der Spalte mit variabler Länge sein. Verwenden Sie DBCC CLEANTABLE, nachdem Sie wesentliche Änderungen an den Spalten mit variabler Länge in einer Tabelle oder indizierten Sicht vorgenommen haben, um den ungenutzten Speicherplatz sofort zurückzugewinnen. Alternativ können Sie die Indizes für die Tabelle oder Sicht neu erstellen; Dies ist jedoch ein ressourcenintensiverer Vorgang.
  7. Der ungenutzte Speicherplatz ist relativ größer, wenn wir am Ende relativ größere Daten (>8 KB) laden. In solchen Fällen haben wir große Mengen ungenutzten Speicherplatzes auf den Datenseiten.
  8. Nach einer SharePoint-Migration kann man einen erheblichen Teil des ungenutzten Speicherplatzes sehen, der in die Datenbanken eingeführt wurde. Die Wiederherstellung ist ein langsamerer Prozess, der Ghost-Cleanup-Prozess entfernt diese Seiten und die Freigabe erfolgt über einen bestimmten Zeitraum.
  9. In einigen Fällen sind die Werte von sp_spaceused möglicherweise nicht korrekt. Obwohl sp_spaceused seine Informationen vom Systemobjekt erhält, das alle Schätzungen enthält, können sie manchmal ungenau sein. Einer der Gründe dafür ist, dass während einer Datenbankmigration oder im Falle veralteter Statistiken oder wenn das System häufigen DDL-Änderungen unterzogen wird oder nach der Durchführung umfangreicher Massenkopiervorgänge. Verwenden Sie zum Synchronisieren von Systemobjekten die Anweisungen DBCC updateusage(0) oder DBCC CHECKTABLE, um sicherzustellen, dass sp_spaceused aktuelle, genaue Daten zurückgibt. Denken Sie jedoch daran, dass DBCC-Befehle ressourcenintensiv sind; ein gutes Verständnis für die Auswirkungen seiner Verwendung haben. Wenn wir den Befehl DBCC updateusage ausführen, scannt die SQL Server-Datenbank-Engine die Datenseiten in der Datenbank und nimmt die erforderlichen Korrekturen an sys.allocation_units vor und sys.partitions Katalogansichten bezüglich des von jeder Tabelle verwendeten Speicherplatzes.

Referenzen

  • https://msdn.microsoft.com/en-us/library/cc280360.aspx
  • https://docs.microsoft.com/en-us/sql/t-sql/database-console-commands/dbcc-cleantable-transact-sql
  • https://docs.microsoft.com/en-us/sql/relational-databases/system-catalog-views/sys-database-files-transact-sql