

Die vorliegende Übersetzung wurde maschinell erstellt. Im Falle eines Konflikts oder eines Widerspruchs zwischen dieser übersetzten Fassung und der englischen Fassung (einschließlich infolge von Verzögerungen bei der Übersetzung) ist die englische Fassung maßgeblich.

# Optimierung mit Warteereignissen für Aurora PostgreSQL
<a name="AuroraPostgreSQL.Tuning"></a>

Warteereignisse sind ein wichtiges Optimierungs-Tool für Aurora PostgreSQL. Wenn Sie herausfinden können, warum Sitzungen auf Ressourcen warten und was sie tun, können Sie Engpässe besser reduzieren. Anhand der Informationen in diesem Abschnitt können Sie mögliche Ursachen und Abhilfemaßnahmen ermitteln. Bevor Sie sich mit diesem Abschnitt befassen, empfehlen wir Ihnen dringend, die grundlegenden Aurora-Konzepte zu verstehen, insbesondere die folgenden Themen:
+ [Amazon Aurora-Speicher](Aurora.Overview.StorageReliability.md)
+ [Verwalten von Performance und Skalierung für einen Aurora-DB-Cluster](Aurora.Managing.Performance.md) 

**Wichtig**  
Die Warteereignisse in diesem Abschnitt gelten speziell für Aurora PostgreSQL. Verwenden Sie die Informationen in diesem Abschnitt, um nur Amazon Aurora zu optimieren, nicht RDS für PostgreSQL.  
Einige Warteereignisse in diesem Abschnitt haben keine Entsprechungen in den Open-Source-Versionen dieser Datenbank-Engines. Andere Warteereignisse haben dieselben Namen wie Ereignisse in Open-Source-Engines, verhalten sich jedoch anders. Beispielsweise funktioniert Amazon-Aurora-Speicher anders als Open-Source-Speicher, sodass speicherbezogene Warteereignisse auf unterschiedliche Ressourcenbedingungen hinweisen.

**Topics**
+ [Grundlegende Konzepte für Aurora PostgreSQL-Optimierung](AuroraPostgreSQL.Tuning.concepts.md)
+ [Aurora PostgreSQL-Warteereignisse](AuroraPostgreSQL.Tuning.concepts.summary.md)
+ [Kunde: ClientRead](apg-waits.clientread.md)
+ [Kunde: ClientWrite](apg-waits.clientwrite.md)
+ [CPU](apg-waits.cpu.md)
+ [IO: BufFileRead und IO: BufFileWrite](apg-waits.iobuffile.md)
+ [IO: DataFileRead](apg-waits.iodatafileread.md)
+ [IO:XactSync](apg-waits.xactsync.md)
+ [IPC:DamRecordTxAck](apg-waits.ipcdamrecordtxac.md)
+ [IPC:parallel-Warteereignisse](apg-ipc-parallel.md)
+ [IPC: ProcArrayGroupUpdate](apg-rpg-ipcprocarraygroup.md)
+ [Lock:advisory](apg-waits.lockadvisory.md)
+ [Lock:extend](apg-waits.lockextend.md)
+ [Lock:Relation](apg-waits.lockrelation.md)
+ [Lock:transactionid](apg-waits.locktransactionid.md)
+ [Lock:tuple](apg-waits.locktuple.md)
+ [LWLock:buffer\$1content () BufferContent](apg-waits.lockbuffercontent.md)
+ [LWLock:buffer\$1mapping](apg-waits.lwl-buffer-mapping.md)
+ [LWLock:BufferIO (IPC:BufferIO)](apg-waits.lwlockbufferio.md)
+ [LWLock:lock\$1manager](apg-waits.lw-lock-manager.md)
+ [LWLock:MultiXact](apg-waits.lwlockmultixact.md)
+ [LWLock:pg\$1stat\$1statements](apg-rpg-lwlockpgstat.md)
+ [Timeout:PgSleep](apg-waits.timeoutpgsleep.md)

# Grundlegende Konzepte für Aurora PostgreSQL-Optimierung
<a name="AuroraPostgreSQL.Tuning.concepts"></a>

Bevor Sie Ihre Aurora PostgreSQL-Datenbank optimieren, sollten Sie wissen, was Warteereignisse sind und warum sie auftreten. Sehen Sie sich auch die grundlegende Speicher- und Festplattenarchitektur von Aurora PostgreSQL an. Ein hilfreiches Architekturdiagramm finden Sie im [PostgreSQL](https://en.wikibooks.org/wiki/PostgreSQL/Architecture)-Wikibook.

**Topics**
+ [Aurora PostgreSQL-Warteereignisse](#AuroraPostgreSQL.Tuning.concepts.waits)
+ [Aurora PostgreSQL-Speicher](#AuroraPostgreSQL.Tuning.concepts.memory)
+ [Aurora PostgreSQL-Prozesse](#AuroraPostgreSQL.Tuning.concepts.processes)

## Aurora PostgreSQL-Warteereignisse
<a name="AuroraPostgreSQL.Tuning.concepts.waits"></a>

Ein *Warteereignis* zeigt eine Ressource an, auf die eine Sitzung wartet. Das Warteereignis `Client:ClientRead` tritt beispielsweise ein, wenn Aurora PostgreSQL darauf wartet, Daten von der client.emory- und Festplattenarchitektur von Aurora PostgreSQL zu empfangen. Zu den typischen Ressourcen, auf die eine Sitzung wartet, gehören die folgenden:
+ Singlethread-Zugriff auf einen Puffer, beispielsweise wenn eine Sitzung versucht, einen Puffer zu ändern
+ Eine Zeile, die derzeit von einer anderen Sitzung gesperrt ist
+ Eine gelesene Datendatei
+ Eine geschriebene Protokolldatei

Um beispielsweise eine Abfrage zu erfüllen, kann die Sitzung einen vollständigen Tabellenscan durchführen. Wenn sich die Daten noch nicht im Arbeitsspeicher befinden, wartet die Sitzung, I/O bis die Festplatte abgeschlossen ist. Wenn die Puffer in den Speicher gelesen werden, muss die Sitzung möglicherweise warten, da andere Sitzungen auf dieselben Puffer zugreifen. Die Datenbank zeichnet die Wartezeiten unter Verwendung eines vordefinierten Warteereignisses auf. Diese Ereignisse sind in Kategorien eingeteilt.

Ein Wait-Ereignis allein zeigt kein Leistungsproblem an. Wenn sich beispielsweise die angeforderten Daten nicht im Speicher befinden, müssen die Daten von der Festplatte gelesen werden. Wenn eine Sitzung eine Zeile für eine Aktualisierung sperrt, wartet eine andere Sitzung darauf, dass die Zeile entsperrt wird, damit sie sie aktualisieren kann. Bei einem Commit muss gewartet werden, bis der Schreibvorgang in eine Protokolldatei abgeschlossen ist. Wartezeiten sind ein wesentlicher Bestandteil des normalen Funktionierens einer Datenbank. 

Eine große Anzahl von Warteereignissen weist normalerweise auf ein Leistungsproblem hin. In solchen Fällen können Sie Warteereignisdaten verwenden, um zu bestimmen, wo die Sitzungen Zeit verbringen. Wenn beispielsweise ein Bericht, der normalerweise in Minuten ausgeführt wird, jetzt stundenlang ausgeführt wird, können Sie die Warteereignisse identifizieren, die am meisten zur Gesamtwartezeit beitragen. Wenn Sie die Ursachen für die häufigsten Warteereignisse ermitteln können, können Sie manchmal Änderungen vornehmen, die die Leistung verbessern. Wenn Ihre Sitzung beispielsweise auf eine Zeile wartet, die von einer anderen Sitzung gesperrt wurde, können Sie die Sperrsitzung beenden. 

## Aurora PostgreSQL-Speicher
<a name="AuroraPostgreSQL.Tuning.concepts.memory"></a>

Aurora PostgreSQL-Speicher ist in freigegeben und lokal unterteilt.

**Topics**
+ [Gemeinsamer Speicher in Aurora PostgreSQL](#AuroraPostgreSQL.Tuning.concepts.shared)
+ [Lokaler Speicher in Aurora PostgreSQL](#AuroraPostgreSQL.Tuning.concepts.local)

### Gemeinsamer Speicher in Aurora PostgreSQL
<a name="AuroraPostgreSQL.Tuning.concepts.shared"></a>

Aurora PostgreSQL weist beim Start der Instance gemeinsam genutzten Speicher zu. Shared Memory ist in mehrere Teilbereiche unterteilt. Nachfolgend finden Sie eine Beschreibung der wichtigsten.

**Topics**
+ [Freigegebene Puffer](#AuroraPostgreSQL.Tuning.concepts.buffer-pool)
+ [Write-Ahead-Protokoll (WAL)-Puffer](#AuroraPostgreSQL.Tuning.concepts.WAL)

#### Freigegebene Puffer
<a name="AuroraPostgreSQL.Tuning.concepts.buffer-pool"></a>

Der *freigegebene Pufferpool* ist ein Aurora PostgreSQL-Speicherbereich, der alle Seiten enthält, die von Anwendungsverbindungen verwendet werden oder verwendet wurden. Eine *Seite* ist die Speicherversion eines Plattenblocks. Der gemeinsam genutzte Pufferpool zwischenspeichert die von der Platte gelesenen Datenblöcke. Der Pool reduziert die Notwendigkeit, Daten erneut von der Festplatte zu lesen, wodurch die Datenbank effizienter arbeitet.

Jede Tabelle und jeder Index wird als Array von Seiten einer festen Größe gespeichert. Jeder Block enthält mehrere Tupel, die Zeilen entsprechen. Ein Tupel kann auf jeglicher Seite gespeichert werden.

Der gemeinsam genutzte Pufferpool hat endlichen Speicher. Wenn eine neue Anforderung eine Seite erfordert, die sich nicht im Speicher befindet und kein Speicher mehr vorhanden ist, entfernt Aurora PostgreSQL eine weniger häufig verwendete Seite, um die Anforderung aufzunehmen. Die Räumungsrichtlinie wird durch einen Takt-Sweep-Algorithmus implementiert.

Der Parameter `shared_buffers` bestimmt, wie viel Speicher der Server für das Caching von Daten bereitstellt.

#### Write-Ahead-Protokoll (WAL)-Puffer
<a name="AuroraPostgreSQL.Tuning.concepts.WAL"></a>

Ein *Write-Ahead-Protokoll(WAL)-Puffer* enthält Transaktionsdaten, die Aurora PostgreSQL später in den persistenten Speicher schreibt. Mithilfe des WAL-Mechanismus kann Aurora PostgreSQL Folgendes tun:
+ Daten nach einem Fehler wiederherstellen
+ Reduzieren Sie die I/O Festplattenkapazität, indem Sie häufige Schreibvorgänge auf die Festplatte vermeiden

Wenn ein Client Daten ändert, schreibt Aurora PostgreSQL die Änderungen in den WAL-Puffer. Wenn der Client einen `COMMIT` ausgibt, schreibt der WAL-Writerprozess Transaktionsdaten in die WAL-Datei.

Der Parameter `wal_level` bestimmt, wie viele Informationen in das WAL geschrieben werden.

### Lokaler Speicher in Aurora PostgreSQL
<a name="AuroraPostgreSQL.Tuning.concepts.local"></a>

Jeder Backend-Prozess weist lokalen Speicher für die Abfrageverarbeitung zu.

**Topics**
+ [Arbeitsspeicherbereich](#AuroraPostgreSQL.Tuning.concepts.local.work_mem)
+ [Wartungs-Arbeitsspeicherbereich](#AuroraPostgreSQL.Tuning.concepts.local.maintenance_work_mem)
+ [Temporärer Pufferbereich](#AuroraPostgreSQL.Tuning.concepts.temp)

#### Arbeitsspeicherbereich
<a name="AuroraPostgreSQL.Tuning.concepts.local.work_mem"></a>

Der *Arbeitsspeicherbereich* enthält temporäre Daten für Abfragen, die Sortierungen und Hashes durchführen. Beispielsweise führt eine Abfrage mit einer `ORDER BY`-Klausel eine Sortierung durch. Abfragen verwenden Hash-Tabellen in Hash-Joins und Aggregationen.

Der `work_mem`-Parameter die Speichermenge, die von internen Sortiervorgängen und Hash-Tabellen verwendet werden soll, bevor in temporäre Plattendateien geschrieben wird. Der Standardwert lautet 4 MB. Mehrere Sitzungen können gleichzeitig ausgeführt werden, und jede Sitzung kann Wartungsvorgänge parallel ausführen. Aus diesem Grund kann der gesamte verwendete Arbeitsspeicher ein Vielfaches der Einstellung `work_mem` betragen. 

#### Wartungs-Arbeitsspeicherbereich
<a name="AuroraPostgreSQL.Tuning.concepts.local.maintenance_work_mem"></a>

Der *Wartungsarbeitsspeicherbereich* speichert Daten für Wartungsvorgänge zwischen. Zu diesen Vorgängen gehören das Vakuumieren, das Erstellen eines Index und das Hinzufügen von Fremdschlüsseln.

Der Parameter `maintenance_work_mem` gibt die maximale Speichermenge an, die von Wartungsvorgängen verwendet werden soll. Der Standardwert lautet 64 MB. In einer Datenbanksitzung kann jeweils nur ein Wartungsvorgang ausgeführt werden.

#### Temporärer Pufferbereich
<a name="AuroraPostgreSQL.Tuning.concepts.temp"></a>

Der *temporäre Pufferbereich* speichert temporäre Tabellen für jede Datenbanksitzung zwischen.

Jede Sitzung weist temporäre Puffer nach Bedarf bis zu dem von Ihnen angegebenen Limit zu. Wenn die Sitzung endet, löscht der Server die Puffer.

Der Parameter `temp_buffers` legt die maximale Anzahl temporärer Puffer fest, die von jeder Sitzung verwendet werden. Vor der ersten Verwendung temporärer Tabellen innerhalb einer Sitzung können Sie den `temp_buffers`-Wert ändern.

## Aurora PostgreSQL-Prozesse
<a name="AuroraPostgreSQL.Tuning.concepts.processes"></a>

Aurora PostgreSQL verwendet mehrere Prozesse.

**Topics**
+ [Postmaster-Prozess](#AuroraPostgreSQL.Tuning.concepts.postmaster)
+ [Backend-Prozesse](#AuroraPostgreSQL.Tuning.concepts.backend)
+ [Hintergrundprozesse](#AuroraPostgreSQL.Tuning.concepts.vacuum)

### Postmaster-Prozess
<a name="AuroraPostgreSQL.Tuning.concepts.postmaster"></a>

Der *Postmaster-Prozess* ist der erste Prozess, der beim Starten von Aurora PostgreSQL gestartet wird. Der Postmaster-Prozess hat die folgenden Hauptaufgaben:
+ Hintergrundprozesse teilen und überwachen
+ Empfangen Sie Authentifizierungsanfragen von Clientprozessen und authentifizieren Sie sie, bevor Sie der Datenbank erlauben, Anfragen zu bearbeiten

### Backend-Prozesse
<a name="AuroraPostgreSQL.Tuning.concepts.backend"></a>

Wenn der Postmaster eine Client-Anfrage authentifiziert, forkisiert der Postmaster einen neuen Backend-Prozess, auch Postgres-Prozess genannt. Ein Client-Prozess verbindet sich mit genau einem Backend-Prozess. Der Client-Prozess und der Backend-Prozess kommunizieren direkt ohne Eingriff des Postmaster-Prozesses.

### Hintergrundprozesse
<a name="AuroraPostgreSQL.Tuning.concepts.vacuum"></a>

Der Postmaster-Prozess teilt mehrere Prozesse, die unterschiedliche Backend-Aufgaben ausführen. Einige der wichtigeren sind die folgenden:
+ WAL-Writer

  Aurora PostgreSQL schreibt Daten im WAL-Puffer (Write Ahead Logging) in die Protokolldateien. Das Prinzip der Write-Ahead-Protokollierung besteht darin, dass die Datenbank keine Änderungen in die Datendateien schreiben kann, bis die Datenbank Protokolldatensätze geschrieben hat, die diese Änderungen auf die Festplatte beschreiben. Der WAL-Mechanismus reduziert Festplatten-I/O und ermöglicht Aurora PostgreSQL, die Protokolle zu verwenden, um die Datenbank nach einem Fehler wiederherzustellen.
+ Hintergrund-Autor

  Dieser Prozess schreibt regelmäßig schmutzige (modifizierte) Seiten aus den Speicherpuffern in die Datendateien. Eine Seite wird schmutzig, wenn ein Backend-Prozess sie im Speicher ändert.
+ Autovacuum-Daemon

  Der Daemon besteht aus Folgendem:
  + Der Autovacuum-Launcher
  + Die Autovacuum-Worker-Prozesse

  Wenn Autovacuum aktiviert ist, sucht es nach Tabellen mit einer großen Anzahl eingefügter, aktualisierter oder gelöschter Tupel. Der Daemon hat folgende Aufgaben:
  + Wiederherstellen oder Wiederverwenden von Speicherplatz, der von aktualisierten oder gelöschten Zeilen belegt ist
  + Vom Planer verwendete Statistiken aktualisieren
  + Schutz vor Verlust alter Daten durch Transaktions-ID-Wraparound

  Die Autovacuum-Funktion automatisiert die Ausführung von `VACUUM`- und `ANALYZE`-Befehlen. `VACUUM` hat folgende Varianten: Standard und Voll. Standardvakuum läuft parallel zu anderen Datenbankvorgängen. `VACUUM FULL` erfordert eine exklusive Sperre für die Tabelle, an der es arbeitet. Daher kann es nicht parallel zu Vorgängen ausgeführt werden, die auf dieselbe Tabelle zugreifen. `VACUUM`erzeugt eine beträchtliche Menge an I/O Datenverkehr, was zu Leistungseinbußen bei anderen aktiven Sitzungen führen kann.

# Aurora PostgreSQL-Warteereignisse
<a name="AuroraPostgreSQL.Tuning.concepts.summary"></a>

Die folgende Tabelle listet die Warteereignisse für Aurora PostgreSQL auf, die am häufigsten auf Leistungsprobleme hinweisen, und fasst die häufigsten Ursachen und Korrekturmaßnahmen zusammen. Die folgenden Warteereignisse sind eine Teilmenge der Liste in [Amazon-Aurora-PostgreSQL-Warteereignisse](AuroraPostgreSQL.Reference.Waitevents.md).


| Warteereignis | Definition | 
| --- | --- | 
|  [Kunde: ClientRead](apg-waits.clientread.md)  |  Dieses Ereignis tritt ein, wenn Aurora PostgreSQL darauf wartet, Daten vom Client zu empfangen.  | 
|  [Kunde: ClientWrite](apg-waits.clientwrite.md)  |  Dieses Ereignis tritt ein, wenn Aurora PostgreSQL darauf wartet, Daten an den Client zu schreiben.  | 
|  [CPU](apg-waits.cpu.md)  |  Dieses Ereignis tritt auf, wenn ein Thread in der CPU aktiv ist oder auf die CPU wartet.  | 
|  [IO: BufFileRead und IO: BufFileWrite](apg-waits.iobuffile.md)  |  Diese Ereignisse treten auf, wenn Aurora PostgreSQL temporäre Dateien erstellt.  | 
|  [IO: DataFileRead](apg-waits.iodatafileread.md)  |  Dieses Ereignis tritt auf, wenn eine Verbindung darauf wartet, dass ein Backend-Prozess eine erforderliche Seite aus dem Speicher liest, da die Seite nicht im gemeinsam genutzten Speicher verfügbar ist.   | 
|  [IO:XactSync](apg-waits.xactsync.md)  |  Dieses Ereignis tritt ein, wenn die Datenbank darauf wartet, dass das Aurora-Storage-Subsystem den Commit einer regulären Transaktion bzw. den Commit oder Rollback einer vorbereiteten Transaktion ausführt.   | 
|  [IPC:DamRecordTxAck](apg-waits.ipcdamrecordtxac.md)  |  Dieses Ereignis tritt auf, wenn Aurora PostgreSQL in einer Sitzung, die Datenbank-Aktivitätsstreams verwendet, ein Aktivitätsstream-Ereignis erzeugt und dann wartet, bis dieses Ereignis dauerhaft wird  | 
|  [Lock:advisory](apg-waits.lockadvisory.md)  |  Dieses Ereignis tritt auf, wenn eine PostgreSQL-Anwendung eine Sperre verwendet, um Aktivitäten über mehrere Sitzungen hinweg zu koordinieren.  | 
|  [Lock:extend](apg-waits.lockextend.md) |  Dieses Ereignis tritt ein, wenn ein Backend-Prozess darauf wartet, eine Beziehung zu sperren, um sie zu erweitern, während ein anderer Prozess diese Beziehung für denselben Zweck gesperrt hat.  | 
|  [Lock:Relation](apg-waits.lockrelation.md)  |  Dieses Ereignis tritt ein, wenn eine Abfrage darauf wartet, eine Sperre für eine Tabelle oder Ansicht zu erhalten, die derzeit von einer anderen Transaktion gesperrt ist.  | 
|  [Lock:transactionid](apg-waits.locktransactionid.md)  | Dieses Ereignis tritt ein, wenn eine Transaktion auf eine Sperre auf Zeilenebene wartet. | 
|  [Lock:tuple](apg-waits.locktuple.md)  |  Dieses Ereignis tritt ein, wenn ein Backend-Prozess darauf wartet, eine Sperre für ein Tupel zu erlangen.  | 
|  [LWLock:buffer\$1content () BufferContent](apg-waits.lockbuffercontent.md)  |  Dieses Ereignis tritt ein, wenn eine Sitzung darauf wartet, eine Datenseite im Speicher zu lesen oder zu schreiben, während eine andere Sitzung diese Seite zum Schreiben gesperrt hat.  | 
|  [LWLock:buffer\$1mapping](apg-waits.lwl-buffer-mapping.md)  |  Dieses Ereignis tritt ein, wenn eine Sitzung darauf wartet, einen Datenblock einem Puffer im gemeinsam genutzten Pufferpool zuzuordnen.  | 
|  [LWLock:BufferIO (IPC:BufferIO)](apg-waits.lwlockbufferio.md)  |  Dieses Ereignis tritt auf, wenn Aurora PostgreSQL oder RDS for PostgreSQL darauf wartet, dass andere Prozesse ihre input/output (I/O-) Operationen beenden, wenn gleichzeitig versucht wird, auf eine Seite zuzugreifen.  | 
|  [LWLock:lock\$1manager](apg-waits.lw-lock-manager.md)  | Dieses Ereignis tritt ein, wenn die Aurora PostgreSQL-Engine den Speicherbereich der gemeinsam genutzten Sperre verwaltet, um eine Sperre zuzuweisen, zu überprüfen und aufzuheben, wenn eine Fast-Path-Sperre nicht möglich ist. | 
| [LWLock:MultiXact](apg-waits.lwlockmultixact.md)  | Diese Art von Ereignis tritt auf, wenn Aurora PostgreSQL eine Sitzung offen hält, um mehrere Transaktionen abzuschließen, die dieselbe Zeile in einer Tabelle betreffen. Das Warte-Ereignis gibt an, welcher Aspekt der Verarbeitung mehrerer Transaktionen das Warte-Ereignis generiert, d. h.: SLRU, LWLock:,: MultiXactOffset SLRU oder LWLock:MultiXactOffsetBuffer. LWLock MultiXactMember LWLock MultiXactMemberBuffer | 
|  [Timeout:PgSleep](apg-waits.timeoutpgsleep.md)  |  Dieses Ereignis tritt ein, wenn ein Serverprozess die Funktion `pg_sleep` aufgerufen hat und darauf wartet, dass das Sleep-Timeout abläuft.   | 

# Kunde: ClientRead
<a name="apg-waits.clientread"></a>

Das Ereignis `Client:ClientRead` tritt ein, wenn Aurora PostgreSQL darauf wartet, Daten vom Client zu empfangen.

**Topics**
+ [Unterstützte Engine-Versionen](#apg-waits.clientread.context.supported)
+ [Kontext](#apg-waits.clientread.context)
+ [Wahrscheinliche Ursachen für erhöhte Wartezeiten](#apg-waits.clientread.causes)
+ [Aktionen](#apg-waits.clientread.actions)

## Unterstützte Engine-Versionen
<a name="apg-waits.clientread.context.supported"></a>

Diese Warteereignisinformationen werden für Aurora PostgreSQL Version 10 und höher unterstützt.

## Kontext
<a name="apg-waits.clientread.context"></a>

Ein Aurora PostgreSQL DB-Cluster wartet darauf, Daten vom Client zu empfangen. Der Aurora PostgreSQL-DB-Cluster muss die Daten vom Client empfangen, bevor er weitere Daten an den Client senden kann. Die Zeit, die der Cluster wartet, bevor er Daten vom Client empfängt, ist ein `Client:ClientRead`-Ereignis.

## Wahrscheinliche Ursachen für erhöhte Wartezeiten
<a name="apg-waits.clientread.causes"></a>

Häufige Gründe dafür, dass das `Client:ClientRead`-Ereignis in den Top-Wartezeiten angezeigt wird, sind die folgenden: 

**Erhöhte Netzwerklatenz**  
Es kann zu einer erhöhten Netzwerklatenz zwischen dem Aurora PostgreSQL-DB-Cluster und dem Client kommen. Eine höhere Netzwerklatenz erhöht die Zeit, die der DB-Cluster benötigt, um Daten vom Client zu empfangen.

**Erhöhte Belastung des Clients**  
Auf dem Client kann es zu CPU-Druck oder Netzwerksättigung kommen. Eine Zunahme der Last auf dem Client kann die Übertragung von Daten vom Client zum Aurora PostgreSQL-DB-Cluster verzögern.

**Übermäßige Netzwerkrundfahrten**  
Eine große Anzahl von Netzwerk-Roundtrips zwischen dem Aurora PostgreSQL-DB-Cluster und dem Client kann die Datenübertragung vom Client zum Aurora PostgreSQL-DB-Cluster verzögern.

**Großer Kopiervorgang**  
Während eines Kopiervorgangs werden die Daten vom Dateisystem des Clients in den Aurora PostgreSQL DB-Cluster übertragen. Das Senden einer großen Datenmenge an den DB-Cluster kann die Übertragung von Daten vom Client zum DB-Cluster verzögern.

**Verbindung von Clients im Leerlauf**  
Eine Verbindung mit einer DB-Instance von Aurora PostgreSQL befindet sich im Transaktionsstatus im Leerlauf und wartet darauf, dass ein Client weitere Daten sendet oder einen Befehl ausgibt. Dieser Status kann zu einer Zunahme von `Client:ClientRead`-Ereignissen führen.

**PgBouncer wird für das Verbindungspooling verwendet**  
PgBouncer hat eine Netzwerkkonfigurationseinstellung auf niedriger Ebene aufgerufen`pkt_buf`, die standardmäßig auf 4.096 gesetzt ist. Wenn der Workload Abfragepakete mit mehr als 4.096 Byte durchsendet, empfehlen wir PgBouncer, die Einstellung auf 8.192 zu erhöhen. `pkt_buf` Wenn die neue Einstellung die Anzahl der `Client:ClientRead`-Ereignisse nicht verringert, empfehlen wir, die `pkt_buf`-Einstellung auf höhere Werte zu erhöhen, z. B. 16.384 oder 32.768. Wenn der Abfragetext groß ist, kann die größere Einstellung besonders hilfreich sein.

## Aktionen
<a name="apg-waits.clientread.actions"></a>

Abhängig von den Ursachen Ihres Warteereignisses empfehlen wir verschiedene Aktionen.

**Topics**
+ [Platzieren Sie die Clients im selben Availability Zone- und VPC-Subnetz wie der Cluster](#apg-waits.clientread.actions.az-vpc-subnet)
+ [Skalieren Sie Ihren -C](#apg-waits.clientread.actions.scale-client)
+ [Instances der aktuellen Generation verwenden](#apg-waits.clientread.actions.db-instance-class)
+ [Erhöhung der Netzwerkbandbreite](#apg-waits.clientread.actions.increase-network-bandwidth)
+ [Überwachen Sie Maximen für die Netzwerkleistung](#apg-waits.clientread.actions.monitor-network-performance)
+ [Überwachen Sie auf Transaktionen im Status „Leerlauf in Transaktion“](#apg-waits.clientread.actions.check-idle-in-transaction)

### Platzieren Sie die Clients im selben Availability Zone- und VPC-Subnetz wie der Cluster
<a name="apg-waits.clientread.actions.az-vpc-subnet"></a>

Um die Netzwerklatenz zu reduzieren und den Netzwerkdurchsatz zu erhöhen, platzieren Sie Clients in dieselbe Availability Zone und Virtual Private Cloud (VPC) -Subnetz wie der Aurora PostgreSQL DB-Cluster. Stellen Sie sicher, dass sich die Clients so geografisch wie möglich am DB-Cluster befinden.

### Skalieren Sie Ihren -C
<a name="apg-waits.clientread.actions.scale-client"></a>

Ermitteln Sie anhand von Amazon CloudWatch oder anderen Host-Metriken, ob Ihr Client derzeit durch CPU- oder Netzwerkbandbreite oder beides eingeschränkt ist. Wenn der Kunde eingeschränkt ist, skalieren Sie Ihren Kunden entsprechend.

### Instances der aktuellen Generation verwenden
<a name="apg-waits.clientread.actions.db-instance-class"></a>

In einigen Fällen verwenden Sie möglicherweise keine DB-Instance-Klasse, die Jumbo-Frames unterstützt. Wenn Sie Ihre Anwendung auf Amazon EC2 ausführen, sollten Sie eine Instance der aktuellen Generation für den Client verwenden. Konfigurieren Sie außerdem die maximale Übertragungseinheit (MTU) im Kundenvorgangssystem Diese Technik könnte die Anzahl der Netzläufe reduzieren und den Netzwerkdurchsatz erhöhen. Weitere Informationen finden Sie unter [Jumbo-Frames (9.001 MTU)](https://docs.aws.amazon.com/AWSEC2/latest/UserGuide/network_mtu.html#jumbo_frame_instances) im *Amazon-EC2-Benutzerhandbuch*.

Weitere Informationen zu DB-Instance-Klassen finden Sie unter [Amazon Aurora Aurora-DB-Instance-Klassen](Concepts.DBInstanceClass.md). Um die DB-Instance-Klasse zu bestimmen, die einem Amazon EC2-Instance-Typ entspricht, platzieren Sie `db.` vor dem Namen des Amazon EC2-Instance-Typs. Beispielsweise entspricht die `r5.8xlarge`-Amazon EC2-Instance der `db.r5.8xlarge`-DB-Instance-Klasse.

### Erhöhung der Netzwerkbandbreite
<a name="apg-waits.clientread.actions.increase-network-bandwidth"></a>

Verwenden Sie `NetworkReceiveThroughput` und `NetworkTransmitThroughput` CloudWatch Amazon-Metriken, um den eingehenden und ausgehenden Netzwerkverkehr auf dem DB-Cluster zu überwachen. Diese Metriken können Ihnen helfen festzustellen, ob die Netzwerkbandbreite für Ihre Workload ausreicht. 

Wenn Ihre Netzwerkbandbreite nicht ausreicht, erhöhen Sie sie. Wenn der AWS Client oder Ihre DB-Instance die Grenzwerte für die Netzwerkbandbreite erreicht, besteht die einzige Möglichkeit, die Bandbreite zu erhöhen, darin, Ihre DB-Instance-Größe zu erhöhen.

Weitere Informationen zu CloudWatch Metriken finden Sie unter[CloudWatch Amazon-Metriken für Amazon Aurora](Aurora.AuroraMonitoring.Metrics.md).

### Überwachen Sie Maximen für die Netzwerkleistung
<a name="apg-waits.clientread.actions.monitor-network-performance"></a>

Wenn Sie Amazon EC2-Clients verwenden, bietet Amazon EC2 Maximum für Netzwerkleistungsmetriken, einschließlich der aggregierten eingehenden und ausgehenden Netzwerkbandbreite. Es bietet auch Verbindungsverfolgung, um sicherzustellen, dass Pakete wie erwartet zurückgegeben werden, und Zugriff auf Link-lokale Dienste für Dienste wie das Domain Name System (DNS). Um diese Maximen zu überwachen, verwenden Sie einen aktuell erweiterten Netzwerktreiber und überwachen Sie die Netzwerkleistung für Ihren Client. 

Weitere Informationen finden Sie unter [Überwachen der Netzwerkleistung für Ihre Amazon-EC2-Instance](https://docs.aws.amazon.com/AWSEC2/latest/UserGuide/monitoring-network-performance-ena.html) im *Amazon-EC2-Benutzerhandbuch* und unter [Überwachen der Netzwerkleistung für Ihre Amazon-EC2-Instance](https://docs.aws.amazon.com/AWSEC2/latest/WindowsGuide/monitoring-network-performance-ena.html) im *Amazon-EC2-Benutzerhandbuch*.

### Überwachen Sie auf Transaktionen im Status „Leerlauf in Transaktion“
<a name="apg-waits.clientread.actions.check-idle-in-transaction"></a>

Überprüfen Sie, ob Sie eine steigende Anzahl von `idle in transaction`-Verbindungen haben. Beobachten Sie dazu die `state`-Spalte in der `pg_stat_activity`-Tabelle. Möglicherweise können Sie die Verbindungsquelle identifizieren, indem Sie eine Abfrage ähnlich der folgenden ausführen.

```
select client_addr, state, count(1) from pg_stat_activity 
where state like 'idle in transaction%' 
group by 1,2 
order by 3 desc
```

# Kunde: ClientWrite
<a name="apg-waits.clientwrite"></a>

Das `Client:ClientWrite`-Ereignis tritt auf, wenn Aurora PostgreSQL darauf wartet, Daten an den Client zu schreiben.

**Topics**
+ [Unterstützte Engine-Versionen](#apg-waits.clientwrite.context.supported)
+ [Kontext](#apg-waits.clientwrite.context)
+ [Wahrscheinliche Ursachen für erhöhte Wartezeiten](#apg-waits.clientwrite.causes)
+ [Aktionen](#apg-waits.clientwrite.actions)

## Unterstützte Engine-Versionen
<a name="apg-waits.clientwrite.context.supported"></a>

Diese Warteereignisinformationen werden für Aurora PostgreSQL Version 10 und höher unterstützt.

## Kontext
<a name="apg-waits.clientwrite.context"></a>

Ein Clientprozess muss alle Daten lesen, die von einem Aurora PostgreSQL DB-Cluster empfangen wurden, bevor der Cluster weitere Daten senden kann. Die Zeit, die der Cluster wartet, bevor weitere Daten an den Client gesendet werden, ist ein `Client:ClientWrite`-Ereignis.

Ein reduzierter Netzwerkdurchsatz zwischen dem Aurora PostgreSQL DB-Cluster und dem Client kann dieses Ereignis verursachen. CPU-Druck und Netzwerksättigung auf dem Client können dieses Ereignis ebenfalls verursachen. *CPU-Druck* liegt vor, wenn die CPU voll ausgelastet ist und Aufgaben auf CPU-Zeit warten. *Eine Netzwerksättigung* liegt vor, wenn das Netzwerk zwischen Datenbank und Client mehr Daten überträgt, als es verarbeiten kann. 

## Wahrscheinliche Ursachen für erhöhte Wartezeiten
<a name="apg-waits.clientwrite.causes"></a>

Häufige Gründe dafür, dass das `Client:ClientWrite`-Ereignis in den Top-Wartezeiten angezeigt wird, sind die folgenden: 

**Erhöhte Netzwerklatenz**  
Es kann zu einer erhöhten Netzwerklatenz zwischen dem Aurora PostgreSQL-DB-Cluster und dem Client kommen. Eine höhere Netzwerklatenz erhöht die Zeit, die der Client benötigt, um die Daten zu empfangen.

**Erhöhte Belastung des Clients**  
Auf dem Client kann es zu CPU-Druck oder Netzwerksättigung kommen. Eine Erhöhung der Belastung des Clients verzögert den Empfang von Daten aus dem Aurora PostgreSQL DB-Cluster.

**Große Datenmenge, die an den Kunden gesendet werden**  
Der Aurora PostgreSQL DB-Cluster sendet möglicherweise eine große Datenmenge an den Client. Ein Client kann die Daten möglicherweise nicht so schnell empfangen, wie der Cluster sie sendet. Aktivitäten wie das Kopieren einer großen Tabelle können zu einer Zunahme von `Client:ClientWrite`-Ereignissen führen.

## Aktionen
<a name="apg-waits.clientwrite.actions"></a>

Abhängig von den Ursachen Ihres Warteereignisses empfehlen wir verschiedene Aktionen.

**Topics**
+ [Platzieren Sie die Clients im selben Availability Zone- und VPC-Subnetz wie der Cluster](#apg-waits.clientwrite.actions.az-vpc-subnet)
+ [Instances der aktuellen Generation verwenden](#apg-waits.clientwrite.actions.db-instance-class)
+ [Reduzieren Sie die an den Kunden gesendeten Daten](#apg-waits.clientwrite.actions.reduce-data)
+ [Skalieren Sie Ihren -C](#apg-waits.clientwrite.actions.scale-client)

### Platzieren Sie die Clients im selben Availability Zone- und VPC-Subnetz wie der Cluster
<a name="apg-waits.clientwrite.actions.az-vpc-subnet"></a>

Um die Netzwerklatenz zu reduzieren und den Netzwerkdurchsatz zu erhöhen, platzieren Sie Clients in dieselbe Availability Zone und Virtual Private Cloud (VPC) -Subnetz wie der Aurora PostgreSQL DB-Cluster.

### Instances der aktuellen Generation verwenden
<a name="apg-waits.clientwrite.actions.db-instance-class"></a>

In einigen Fällen verwenden Sie möglicherweise keine DB-Instance-Klasse, die Jumbo-Frames unterstützt. Wenn Sie Ihre Anwendung auf Amazon EC2 ausführen, sollten Sie eine Instance der aktuellen Generation für den Client verwenden. Konfigurieren Sie außerdem die maximale Übertragungseinheit (MTU) im Kundenvorgangssystem Diese Technik könnte die Anzahl der Netzläufe reduzieren und den Netzwerkdurchsatz erhöhen. Weitere Informationen finden Sie unter [Jumbo-Frames (9.001 MTU)](https://docs.aws.amazon.com/AWSEC2/latest/UserGuide/network_mtu.html#jumbo_frame_instances) im *Amazon-EC2-Benutzerhandbuch*.

Weitere Informationen zu DB-Instance-Klassen finden Sie unter [Amazon Aurora Aurora-DB-Instance-Klassen](Concepts.DBInstanceClass.md). Um die DB-Instance-Klasse zu bestimmen, die einem Amazon EC2-Instance-Typ entspricht, platzieren Sie `db.` vor dem Namen des Amazon EC2-Instance-Typs. Beispielsweise entspricht die `r5.8xlarge`-Amazon EC2-Instance der `db.r5.8xlarge`-DB-Instance-Klasse.

### Reduzieren Sie die an den Kunden gesendeten Daten
<a name="apg-waits.clientwrite.actions.reduce-data"></a>

Passen Sie Ihre Anwendung nach Möglichkeit an, um die Datenmenge zu reduzieren, die der Aurora PostgreSQL DB-Cluster an den Client sendet. Solche Anpassungen entlasten die CPU- und Netzwerkkonflikte auf dem Client.

### Skalieren Sie Ihren -C
<a name="apg-waits.clientwrite.actions.scale-client"></a>

Ermitteln Sie anhand von Amazon CloudWatch oder anderen Host-Metriken, ob Ihr Client derzeit durch CPU- oder Netzwerkbandbreite oder beides eingeschränkt ist. Wenn der Client eingeschränkt ist, skalieren Sie Ihren Client entsprechend.

# CPU
<a name="apg-waits.cpu"></a>

Dieses Ereignis tritt auf, wenn ein Thread in der CPU aktiv ist oder auf die CPU wartet.

**Topics**
+ [Unterstützte Engine-Versionen](#apg-waits.cpu.context.supported)
+ [Kontext](#apg-waits.cpu.context)
+ [Wahrscheinliche Ursachen für erhöhte Wartezeiten](#apg-waits.cpu.causes)
+ [Aktionen](#apg-waits.cpu.actions)

## Unterstützte Engine-Versionen
<a name="apg-waits.cpu.context.supported"></a>

Diese Warteereignisinformationen sind für Aurora PostgreSQL Version 9.6 und höher relevant. 

## Kontext
<a name="apg-waits.cpu.context"></a>

Die *Zentrale Verarbeitungseinheit (CPU)* ist die Komponente eines Computers, die Anweisungen ausführt. Beispielsweise führen CPU-Anweisungen arithmetische Vorgänge aus und tauschen Daten im Speicher aus. Wenn eine Abfrage die Anzahl der Anweisungen erhöht, die sie über das Datenbank-Engine ausführt, erhöht sich der Zeitaufwand für die Ausführung der Abfrage. *CPU-Scheduling* gibt einem Prozess CPU-Zeit. Die Planung wird vom Kernel des Betriebssystems orchestriert.

**Topics**
+ [Wie kann man sagen, wann diese Wartezeit stattfindet](#apg-waits.cpu.when-it-occurs)
+ [DBLoadCPU-Metrik](#apg-waits.cpu.context.dbloadcpu)
+ [Metriken für Os.cPuUtilization](#apg-waits.cpu.context.osmetrics)
+ [Wahrscheinliche Ursache für CPU-Planung](#apg-waits.cpu.context.scheduling)

### Wie kann man sagen, wann diese Wartezeit stattfindet
<a name="apg-waits.cpu.when-it-occurs"></a>

Dieses `CPU`-Warteereignis zeigt an, dass ein Backend-Prozess in der CPU aktiv ist oder auf die CPU wartet. Sie wissen, dass es passiert, wenn eine Abfrage die folgenden Informationen anzeigt:
+ Die Spalte `pg_stat_activity.state` hat den Wert `active`.
+ Die Spalten `wait_event_type` und `wait_event` in `pg_stat_activity` sind beide `null`.

Führen Sie die folgende Abfrage aus, um die Backend-Prozesse anzuzeigen, die auf der CPU verwenden oder auf dieser warten.

```
SELECT * 
FROM   pg_stat_activity
WHERE  state = 'active'
AND    wait_event_type IS NULL
AND    wait_event IS NULL;
```

### DBLoadCPU-Metrik
<a name="apg-waits.cpu.context.dbloadcpu"></a>

Die Performance Insights-Metrik für CPU ist `DBLoadCPU`. Der Wert für `DBLoadCPU` kann vom Wert für die CloudWatch Amazon-Metrik abweichen`CPUUtilization`. Die letztere Metrik wird aus der HyperVisor für eine Datenbank-Instance erfasst.

### Metriken für Os.cPuUtilization
<a name="apg-waits.cpu.context.osmetrics"></a>

Performance Insights Betriebssystem-Metriken liefern detaillierte Informationen zur CPU-Auslastung. Sie können beispielsweise die folgenden Metriken anzeigen:
+ `os.cpuUtilization.nice.avg`
+ `os.cpuUtilization.total.avg`
+ `os.cpuUtilization.wait.avg`
+ `os.cpuUtilization.idle.avg`

Performance Insights meldet die CPU-Auslastung durch die Datenbank-Engine als `os.cpuUtilization.nice.avg`.

### Wahrscheinliche Ursache für CPU-Planung
<a name="apg-waits.cpu.context.scheduling"></a>

Aus Sicht des Betriebssystems ist die CPU aktiv, wenn der Leerlauf-Thread nicht ausgeführt wird. Die CPU ist aktiv, während sie eine Berechnung durchführt, aber sie ist auch aktiv, wenn sie wartet, bis der Arbeitsspeicher eine typische I/O. This type of I/O Datenbank-Arbeitslast dominiert.

Wenn die folgenden Bedingungen erfüllt sind, werden Prozesse wahrscheinlich warten, bis die folgenden Bedingungen erfüllt sind:
+ Die CloudWatch `CPUUtilization` Metrik liegt bei fast 100 Prozent.
+ Die durchschnittliche Last ist größer als die Zahl von vCPUs, was auf eine hohe Last hindeutet. Sie finden die `loadAverageMinute`-Metrik im Abschnitt Betriebssystemmetriken in Performance Insights.

## Wahrscheinliche Ursachen für erhöhte Wartezeiten
<a name="apg-waits.cpu.causes"></a>

Wenn das CPU-Warteereignis mehr als normal auftritt und möglicherweise auf ein Leistungsproblem hinweist, sind typische Ursachen die folgenden.

**Topics**
+ [Wahrscheinliche Ursachen für plötzliche Stacheln](#apg-waits.cpu.causes.spikes)
+ [Wahrscheinliche Ursachen für langfristige Hochfrequenz](#apg-waits.cpu.causes.long-term)
+ [Corner Cases](#apg-waits.cpu.causes.corner-cases)

### Wahrscheinliche Ursachen für plötzliche Stacheln
<a name="apg-waits.cpu.causes.spikes"></a>

Die wahrscheinlichsten Ursachen für plötzliche Stacheln sind wie folgt:
+ Ihre Anwendung hat zu viele gleichzeitige Verbindungen zur Datenbank geöffnet. Dieses Szenario wird als „Verbindungssturm“ bezeichnet.
+ Ihre Anwendungs-Workload hat sich auf eine der folgenden Weisen geändert:
  + Neue Anfragen
  + Eine Zunahme der Größe Ihres Datensatzes
  + Indexpflege oder -erstellung
  + Neue Funktionen
  + Neue Betreiber
  + Eine Zunahme der parallelen Abfrageausführung
+ Ihre Abfrageausführungspläne haben sich geändert. In einigen Fällen kann eine Änderung zu einem Anstieg der Puffer führen. Beispielsweise verwendet die Abfrage jetzt einen sequentiellen Scan, als sie zuvor einen Index verwendet hat. In diesem Fall benötigen die Abfragen mehr CPU, um dasselbe Ziel zu erreichen.

### Wahrscheinliche Ursachen für langfristige Hochfrequenz
<a name="apg-waits.cpu.causes.long-term"></a>

Die wahrscheinlichsten Ursachen für Ereignisse, die über einen langen Zeitraum auftreten:
+ Zu viele Backend-Prozesse laufen gleichzeitig auf der CPU. Diese Prozesse können parallele Arbeiter sein.
+ Abfragen funktionieren suboptimal, da sie eine große Anzahl von Puffern benötigen.

### Corner Cases
<a name="apg-waits.cpu.causes.corner-cases"></a>

Wenn sich herausstellt, dass keine der wahrscheinlichen Ursachen tatsächliche Ursachen ist, können folgende Situationen auftreten:
+ Die CPU tauscht Prozesse ein- und aus.
+ Der CPU-Kontextwechsel hat zugenommen.
+ Aurora PostgreSQL-Code fehlen Warteereignisse.

## Aktionen
<a name="apg-waits.cpu.actions"></a>

Wenn das `CPU`-Wait-Ereignis die Datenbankaktivität dominiert, weist dies nicht unbedingt auf ein Leistungsproblem hin. Reagieren Sie auf dieses Ereignis nur, wenn sich die Leistung verschlechtert.

**Topics**
+ [Untersuchen Sie, ob die Datenbank den CPU-Anstieg verursacht](#apg-waits.cpu.actions.db-CPU)
+ [Bestimmen Sie, ob die Anzahl der Verbindungen gestiegen ist](#apg-waits.cpu.actions.connections)
+ [Reagieren auf Workload-Änderungen](#apg-waits.cpu.actions.workload)

### Untersuchen Sie, ob die Datenbank den CPU-Anstieg verursacht
<a name="apg-waits.cpu.actions.db-CPU"></a>

Untersuchen Sie die `os.cpuUtilization.nice.avg`-Metrik in Performance Insights. Wenn dieser Wert weit unter der CPU-Auslastung liegt, tragen Nicht-Datenbankprozesse den Hauptbeitrag zur CPU bei.

### Bestimmen Sie, ob die Anzahl der Verbindungen gestiegen ist
<a name="apg-waits.cpu.actions.connections"></a>

Untersuchen Sie die `DatabaseConnections` Metrik in Amazon CloudWatch. Ihre Aktion hängt davon ab, ob die Zahl während des Zeitraums erhöhter CPU-Warteereignisse erhöht oder gesunken ist.

#### Die Verbindungen nahmen zu
<a name="apg-waits.cpu.actions.connections.increased"></a>

Wenn die Anzahl der Verbindungen gestiegen ist, vergleichen Sie die Anzahl der Backend-Prozesse, die CPU verbrauchen, mit der Anzahl von v. CPUs Die folgenden Szenarien sind möglich:
+ Die Anzahl der Backend-Prozesse, die CPU verbrauchen, ist geringer als die Anzahl von v. CPUs

  In diesem Fall ist die Anzahl der Verbindungen kein Problem. Möglicherweise versuchen Sie jedoch weiterhin, die CPU-Auslastung zu reduzieren.
+ Die Anzahl der Backend-Prozesse, die CPU verbrauchen, ist größer als die Anzahl von v. CPUs

  Ziehen Sie in diesem Fall die folgenden Optionen in Betracht:
  + Verringern Sie die Anzahl der Backend-Prozesse, die mit Ihrer Datenbank verbunden sind. Implementieren Sie beispielsweise eine Verbindungs-Pooling-Lösung wie RDS Proxy. Weitere Informationen hierzu finden Sie unter [Amazon RDS-Proxy für Aurora](rds-proxy.md).
  + Aktualisieren Sie Ihre Instanzgröße, um eine höhere Anzahl von v CPUs zu erhalten.
  + Leiten Sie ggf. einige schreibgeschützte Workloads auf Reader-Knoten um.

#### Die Verbindungen haben nicht zugenommen
<a name="apg-waits.cpu.actions.connections.decreased"></a>

Untersuchen Sie die `blks_hit`-Metriken in Performance Insights. Suchen Sie nach einer Korrelation zwischen einem Anstieg von `blks_hit` und der CPU-Auslastung. Die folgenden Szenarien sind möglich:
+ CPU-Auslastung und `blks_hit` sind korreliert.

  Suchen Sie in diesem Fall die wichtigsten SQL-Anweisungen, die mit der CPU-Auslastung verknüpft sind, und suchen Sie nach Planänderungen. Sie können eine der folgenden Techniken verwenden:
  + Erklären Sie die Pläne manuell und vergleichen Sie sie mit dem erwarteten Ausführungsplan.
  + Achten Sie auf eine Zunahme der Blocktreffer pro Sekunde und lokalen Blocktreffern pro Sekunde. Wählen Sie im Abschnitt **Top-SQL** des Performance Insights-Dashboards **Einstellungen** aus.
+ CPU-Auslastung und `blks_hit` sind nicht korreliert.

  Stellen Sie in diesem Fall fest, ob einer der folgenden Fälle auftritt:
  + Die Anwendung stellt schnell eine Verbindung zur Datenbank her und trennt sie von dieser. 

    Diagnostizieren Sie dieses Verhalten, indem Sie `log_connections` und `log_disconnections` aktivieren und dann die PostgreSQL-Protokolle analysieren. Ziehen Sie in Erwägung, den `pgbadger`-Protokoll-Analyzer zu verwenden. Weitere Informationen finden Sie unter [https://github.com/darold/pgbadger](https://github.com/darold/pgbadger).
  + Das Betriebssystem ist überlastet.

    In diesem Fall zeigt Performance Insights, dass Backend-Prozesse länger CPU verbrauchen als gewöhnlich. Suchen Sie in den Performance Insights `os.cpuUtilization` Insights-Metriken oder der CloudWatch `CPUUtilization` Metrik nach Belegen. Wenn das Betriebssystem überlastet ist, sehen Sie sich Enhanced Monitoring-Metriken an, um eine weitere Diagnose zu erhalten. Schauen Sie sich insbesondere die Prozessliste und den Prozentsatz der CPU an, die von jedem Prozess verbraucht wird.
  + Top SQL-Anweisungen verbrauchen zu viel CPU.

    Untersuchen Sie Anweisungen, die mit der CPU-Auslastung verknüpft sind, um festzustellen, ob sie weniger CPU verbrauchen können. Führen Sie einen `EXPLAIN`-Befehl aus und konzentrieren Sie sich auf die Planknoten, die die größte Auswirkung haben. Erwägen Sie, einen Visualizer für PostgreSQL-Ausführungspläne zu verwenden. Um dieses Tool auszuprobieren, siehe [http://explain.dalibo.com/](http://explain.dalibo.com/).

### Reagieren auf Workload-Änderungen
<a name="apg-waits.cpu.actions.workload"></a>

Wenn sich Ihre Workload geändert hat, suchen Sie nach folgenden Arten von Änderungen:

Neue Anfragen  
Überprüfen Sie, ob die neuen Abfragen erwartet werden. Stellen Sie in diesem Fall sicher, dass ihre Ausführungspläne und die Anzahl der Ausführungen pro Sekunde erwartet werden.

Eine Zunahme der Größe des Datensatzes  
Bestimmen Sie, ob die Partitionierung, falls sie noch nicht implementiert ist, helfen könnte. Diese Strategie könnte die Anzahl der Seiten verringern, die eine Abfrage abrufen muss.

Indexpflege oder -erstellung  
Überprüfen Sie, ob der Zeitplan für die Wartung erwartet wird. Eine bewährte Methode besteht darin, Wartungsarbeiten außerhalb der Hauptverkehrszeiten zu planen.

Neue Funktionen  
Überprüfen Sie, ob diese Funktionen während des Tests erwartungsgemäß funktionieren. Überprüfen Sie insbesondere, ob die Anzahl der Ausführungen pro Sekunde erwartet wird.

Neue Betreiber  
Überprüfen Sie, ob sie während des Tests erwartungsgemäß funktionieren.

Eine Zunahme der laufenden parallelen Abfragen  
Stellen Sie fest, ob eine der folgenden Situationen aufgetreten ist:  
+ Die beteiligten Relationen oder Indizes sind plötzlich so groß geworden, dass sie sich deutlich von `min_parallel_table_scan_size` oder `min_parallel_index_scan_size` unterscheiden.
+ Die letzten Änderungen wurden an `parallel_setup_cost` oder `parallel_tuple_cost` vorgenommen.
+ Die letzten Änderungen wurden an `max_parallel_workers` oder `max_parallel_workers_per_gather` vorgenommen.

# IO: BufFileRead und IO: BufFileWrite
<a name="apg-waits.iobuffile"></a>

Die Ereignisse `IO:BufFileRead` und `IO:BufFileWrite` treten auf, wenn Aurora PostgreSQL temporäre Dateien erstellt. Wenn Vorgänge mehr Arbeitsspeicher benötigen, als die derzeit definierten Arbeitsspeicherparameter definieren, schreiben sie temporäre Daten in persistenten Speicher. Dieser Vorgang wird manchmal als Übertragung *auf die Festplatte* bezeichnet. Weitere Informationen zu den temporären Dateien und ihrer Verwendung finden Sie unter [Verwalten temporärer Dateien mit PostgreSQL](PostgreSQL.ManagingTempFiles.md).

**Topics**
+ [Unterstützte Engine-Versionen](#apg-waits.iobuffile.context.supported)
+ [Kontext](#apg-waits.iobuffile.context)
+ [Wahrscheinliche Ursachen für erhöhte Wartezeiten](#apg-waits.iobuffile.causes)
+ [Aktionen](#apg-waits.iobuffile.actions)

## Unterstützte Engine-Versionen
<a name="apg-waits.iobuffile.context.supported"></a>

Diese Warteereignisinformationen werden für alle Versionen von Aurora PostgreSQL unterstützt.

## Kontext
<a name="apg-waits.iobuffile.context"></a>

`IO:BufFileRead` und `IO:BufFileWrite` beziehen sich auf den Arbeitsspeicherbereich und den Wartungsarbeitsspeicherbereich. Weitere Informationen zu diesen lokalen Speicherbereichen finden Sie unter [Arbeitsspeicherbereich](AuroraPostgreSQL.Tuning.concepts.md#AuroraPostgreSQL.Tuning.concepts.local.work_mem) und [Wartungs-Arbeitsspeicherbereich](AuroraPostgreSQL.Tuning.concepts.md#AuroraPostgreSQL.Tuning.concepts.local.maintenance_work_mem).

Der Standardwert für `work_mem` ist 4 MB. Wenn eine Sitzung parallel Vorgänge ausführt, verwendet jeder Worker, der die Parallelität bearbeitet, 4 MB Speicher. Stellen Sie `work_mem` daher sorgfältig ein. Wenn Sie den Wert zu stark erhöhen, verbraucht eine Datenbank mit vielen Sitzungen möglicherweise zu viel Speicher. Wenn Sie den Wert zu niedrig festlegen, erstellt Aurora PostgreSQL temporäre Dateien im lokalen Speicher. Die Festplatte I/O für diese temporären Dateien kann die Leistung beeinträchtigen.

Wenn Sie die folgende Ereignisfolge beobachten, generiert Ihre Datenbank möglicherweise temporäre Dateien:

1. Plötzlicher und starker Rückgang der Verfügbarkeit

1. Schnelle Erholung für den freien Speicherplatz

Möglicherweise sehen Sie auch ein „Kettensäge“ -Muster. Dieses Muster kann darauf hinweisen, dass Ihre Datenbank ständig kleine Dateien erstellt.

## Wahrscheinliche Ursachen für erhöhte Wartezeiten
<a name="apg-waits.iobuffile.causes"></a>

Im Allgemeinen werden diese Warteereignisse durch Vorgänge verursacht, die mehr Speicher verbrauchen, als die Parameter `work_mem` oder `maintenance_work_mem` zuweisen. Um dies zu kompensieren, schreiben die Vorgänge in temporäre Dateien. Häufige Ursachen für die `IO:BufFileRead`- und `IO:BufFileWrite`-Ereignisse sind die folgenden:

**Abfragen, die mehr Speicher benötigen als im Arbeitsspeicherbereich vorhanden**  
Abfragen mit den folgenden Merkmalen verwenden den Arbeitsspeicherbereich:  
+ Hash-Verknüpfungen
+ `ORDER BY`-Klausel
+ `GROUP BY`-Klausel
+ `DISTINCT`
+ Fensterfunktionen
+ `CREATE TABLE AS SELECT`
+ Aktualisierung der materialisierten Ansicht

**Anweisungen, die mehr Speicher benötigen als im Arbeitsspeicherbereich für Wartungsarbeiten vorhanden**  
Die folgenden Anweisungen verwenden den Arbeitsspeicherbereich für Wartungsarbeiten:  
+ `CREATE INDEX`
+ `CLUSTER`

## Aktionen
<a name="apg-waits.iobuffile.actions"></a>

Abhängig von den Ursachen Ihres Warteereignisses empfehlen wir verschiedene Aktionen.

**Topics**
+ [Identifizieren Sie das Problem](#apg-waits.iobuffile.actions.problem)
+ [Untersuchen Sie Ihre Join-Anfragen](#apg-waits.iobuffile.actions.joins)
+ [Überprüfen Sie Ihre ORDER BY- und GROUP BY Anfragen](#apg-waits.iobuffile.actions.order-by)
+ [Verwenden Sie den DISTINCT-Vorgang nicht](#apg-waits.iobuffile.actions.distinct)
+ [Erwägen Sie, Fensterfunktionen anstelle von GROUP-BY-Funktionen zu verwenden](#apg-waits.iobuffile.actions.window)
+ [Untersuchen Sie materialisierte Ansichten und CTAS-Aussagen](#apg-waits.iobuffile.actions.mv-refresh)
+ [Verwenden Sie pg\$1repack, wenn Sie Indizes erstellen](#apg-waits.iobuffile.actions.pg_repack)
+ [Erhöhen Sie maintenance work\$1mem, wenn Sie Tabellen clustern](#apg-waits.iobuffile.actions.cluster)
+ [Passen Sie den Speicher an, um IO: BufFileRead und IO: zu verhindern BufFileWrite](#apg-waits.iobuffile.actions.tuning-memory)

### Identifizieren Sie das Problem
<a name="apg-waits.iobuffile.actions.problem"></a>

Sie können die Nutzung temporärer Dateien direkt in Performance Insights anzeigen. Weitere Informationen finden Sie unter [Anzeigen der Nutzung temporärer Dateien mit Performance Insights](PostgreSQL.ManagingTempFiles.Example.md). Wenn Performance Insights deaktiviert ist, stellen Sie möglicherweise eine Zunahme der `IO:BufFileRead` `IO:BufFileWrite` Betriebsabläufe fest. Gehen Sie wie folgt vor, um Fehler zu beheben:

1. Untersuchen Sie die `FreeLocalStorage` Metrik in Amazon CloudWatch.

1. Suchen Sie nach einem Kettensägenmuster, bei dem es sich um eine Reihe von gezackten Stacheln handelt.

Ein Kettensägenmuster weist auf einen schnellen Verbrauch und die Freigabe von Speicher hin, die häufig mit temporären Dateien verbunden sind. Wenn Sie dieses Muster bemerken, aktivieren Sie Performance Insights. Wenn Sie Performance Insights verwenden, können Sie feststellen, wann die Wait-Ereignisse auftreten und welche Abfragen mit ihnen verknüpft sind. Ihre Lösung hängt von der spezifischen Abfrage ab, die die Ereignisse verursacht.

Oder stellen Sie den Parameter `log_temp_files` ein. Dieser Parameter protokolliert alle Abfragen, die mehr als Schwellenwert für temporäre Dateien erzeugen. Wenn der Wert `0` ist, protokolliert Aurora PostgreSQL alle temporären Dateien. Wenn der Wert `1024` ist, protokolliert Aurora PostgreSQL alle Abfragen, die temporäre Dateien erzeugen, die größer als 1 MB sind. Weitere Informationen zu `log_temp_files` finden Sie unter [Fehlerberichte und -protokollierung](https://www.postgresql.org/docs/10/runtime-config-logging.html) in der PostgreSQL-Dokumentation.

### Untersuchen Sie Ihre Join-Anfragen
<a name="apg-waits.iobuffile.actions.joins"></a>

Ihre Anwendung verwendet wahrscheinlich Joins. Die folgende Abfrage verbindet beispielsweise vier Tabellen.

```
SELECT * 
       FROM order 
 INNER JOIN order_item 
       ON (order.id = order_item.order_id)
 INNER JOIN customer 
       ON (customer.id = order.customer_id)
 INNER JOIN customer_address 
       ON (customer_address.customer_id = customer.id AND 
           order.customer_address_id = customer_address.id)
 WHERE customer.id = 1234567890;
```

Eine mögliche Ursache für Spitzen bei der Verwendung temporärer Dateien ist ein Problem in der Abfrage selbst. Beispielsweise filtert eine defekte Klausel die Joins möglicherweise nicht richtig. Betrachten Sie den zweiten inneren Join im folgenden Beispiel.

```
SELECT * 
       FROM order
 INNER JOIN order_item 
       ON (order.id = order_item.order_id)
 INNER JOIN customer 
       ON (customer.id = customer.id)
 INNER JOIN customer_address 
       ON (customer_address.customer_id = customer.id AND 
           order.customer_address_id = customer_address.id)
 WHERE customer.id = 1234567890;
```

Die obige Abfrage verknüpft fälschlicherweise `customer.id` mit `customer.id`, wodurch zwischen jedem Kunden und jeder Bestellung ein kartesisches Produkt generiert wird. Diese Art des versehentlichen Joins generiert große temporäre Dateien. Abhängig von der Größe der Tabellen kann eine kartesische Abfrage sogar Speicher füllen. Wenn die folgenden Bedingungen erfüllt sind, hat Ihre Anwendung möglicherweise kartesische Joins:
+ Sie sehen einen großen, starken Rückgang der Speicherverfügbarkeit, gefolgt von einer schnellen Wiederherstellung.
+ Es werden keine Indizes erstellt.
+ Es werden keine `CREATE TABLE FROM SELECT`-Anweisungen ausgegeben.
+ Es werden keine materialisierten Ansichten aktualisiert.

Um festzustellen, ob die Tabellen mit den richtigen Schlüsseln verbunden werden, überprüfen Sie Ihre Abfrage- und objektrelationalen Mapping-Anweisungen. Denken Sie daran, dass bestimmte Abfragen Ihrer Anwendung nicht ständig aufgerufen werden und einige Abfragen dynamisch generiert werden.

### Überprüfen Sie Ihre ORDER BY- und GROUP BY Anfragen
<a name="apg-waits.iobuffile.actions.order-by"></a>

In einigen Fällen kann eine `ORDER BY`-Klausel zu übermäßig vielen temporären Dateien führen. Berücksichtigen Sie die folgenden Hinweise:
+ Schließen Sie Spalten nur dann in eine `ORDER BY`-Klausel ein, wenn sie sortiert werden müssen. Diese Richtlinie ist besonders wichtig für Abfragen, die Tausende von Zeilen zurückgeben und viele Spalten in der `ORDER BY`-Klausel angeben.
+ Ziehen Sie in Betracht, Indizes zu erstellen, um `ORDER BY`-Klauseln zu beschleunigen, wenn sie mit Spalten übereinstimmen, die dieselbe aufsteigende oder absteigende Reihenfolge aufweisen. Partielle Indizes sind vorzuziehen, da sie kleiner sind. Kleinere Indizes werden schneller gelesen und durchquert.
+ Wenn Sie Indizes für Spalten erstellen, die Nullwerte akzeptieren können, überlegen Sie, ob die Nullwerte am Ende oder am Anfang der Indizes gespeichert werden sollen.

  Reduzieren Sie nach Möglichkeit die Anzahl der Zeilen, die sortiert werden müssen, indem Sie die Ergebnismenge filtern. Wenn Sie `WITH`-Klausel-Anweisungen oder Unterabfragen verwenden, denken Sie daran, dass eine innere Abfrage eine Ergebnismenge generiert und an die äußere Abfrage übergibt. Je mehr Zeilen eine Abfrage herausfiltern kann, desto weniger muss die Abfrage erledigen.
+ Wenn Sie nicht die vollständige Ergebnismenge abrufen müssen, verwenden Sie die `LIMIT`-Klausel. Wenn Sie beispielsweise nur die obersten fünf Zeilen benötigen, generiert eine Abfrage mit der `LIMIT`-Klausel keine Ergebnisse. Auf diese Weise benötigt die Abfrage weniger Speicher und temporäre Dateien.

Eine Abfrage, die eine `GROUP BY`-Klausel verwendet, kann auch temporäre Dateien erfordern. `GROUP BY`-Abfragen fassen Werte mithilfe von Funktionen wie den folgenden zusammen:
+ `COUNT`
+ `AVG`
+ `MIN`
+ `MAX`
+ `SUM`
+ `STDDEV`

Befolgen Sie zum Optimieren von `GROUP BY`-Abfragen die Empfehlungen für `ORDER BY`-Abfragen.

### Verwenden Sie den DISTINCT-Vorgang nicht
<a name="apg-waits.iobuffile.actions.distinct"></a>

Vermeiden Sie nach Möglichkeit die Verwendung des `DISTINCT`-Vorgangs, um doppelte Zeilen zu entfernen. Je mehr unnötige und doppelte Zeilen Ihre Abfrage zurückgibt, desto teurer wird der `DISTINCT`-Vorgang. Fügen Sie nach Möglichkeit Filter in der `WHERE`-Klausel hinzu, auch wenn Sie dieselben Filter für verschiedene Tabellen verwenden. Das Filtern der Abfrage und der korrekte Beitritt verbessern Ihre Leistung und reduziert den Ressourcennutzung. Es verhindert auch falsche Berichte und Ergebnisse.

Wenn Sie `DISTINCT` für mehrere Zeilen derselben Tabelle verwenden müssen, sollten Sie einen zusammengesetzten Index erstellen. Das Gruppieren mehrerer Spalten in einem Index kann die Zeit zum Auswerten verschiedener Zeilen verbessern. Wenn Sie Amazon-Aurora-PostgreSQL-Version 10 oder höher verwenden, können Sie außerdem mithilfe des `CREATE STATISTICS`-Befehls Statistiken zwischen mehreren Spalten korrelieren.

### Erwägen Sie, Fensterfunktionen anstelle von GROUP-BY-Funktionen zu verwenden
<a name="apg-waits.iobuffile.actions.window"></a>

Mit `GROUP BY` ändern Sie die Ergebnismenge und rufen dann das aggregierte Ergebnis ab. Mithilfe von Fensterfunktionen aggregieren Sie Daten, ohne die Ergebnismenge zu ändern. Eine Fensterfunktion verwendet die `OVER`-Klausel, um Berechnungen über die von der Abfrage definierten Mengen durchzuführen und eine Zeile mit einer anderen zu korrelieren. Sie können alle `GROUP BY`-Funktionen in Fensterfunktionen verwenden, aber auch Funktionen wie die folgenden verwenden:
+ `RANK`
+ `ARRAY_AGG`
+ `ROW_NUMBER`
+ `LAG`
+ `LEAD`

Um die Anzahl der temporären Dateien zu minimieren, die von einer Fensterfunktion generiert werden, entfernen Sie Duplikationen für dieselbe Ergebnismenge, wenn Sie zwei verschiedene Aggregationen benötigen. Betrachten Sie folgende Abfrage.

```
SELECT sum(salary) OVER (PARTITION BY dept ORDER BY salary DESC) as sum_salary
     , avg(salary) OVER (PARTITION BY dept ORDER BY salary ASC) as avg_salary
  FROM empsalary;
```

Sie können die Abfrage mit der `WINDOW`-Klausel wie folgt umschreiben.

```
SELECT sum(salary) OVER w as sum_salary
         , avg(salary) OVER w as_avg_salary
    FROM empsalary
  WINDOW w AS (PARTITION BY dept ORDER BY salary DESC);
```

Standardmäßig konsolidiert der Ausführungsplaner von Aurora PostgreSQL ähnliche Knoten, sodass keine Vorgänge dupliziert werden. Durch die Verwendung einer expliziten Deklaration für den Fensterblock können Sie die Abfrage jedoch einfacher pflegen. Sie können die Leistung auch verbessern, indem Sie Doppelarbeit verhindern.

### Untersuchen Sie materialisierte Ansichten und CTAS-Aussagen
<a name="apg-waits.iobuffile.actions.mv-refresh"></a>

Wenn eine materialisierte Ansicht aktualisiert wird, wird eine Abfrage ausgeführt. Diese Abfrage kann einen Vorgang wie `GROUP BY`, `ORDER BY` oder `DISTINCT` enthalten. Während einer Aktualisierung können Sie eine große Anzahl temporärer Dateien und die Warteereignisse `IO:BufFileWrite` und `IO:BufFileRead` beobachten. Wenn Sie eine Tabelle basierend auf einer `SELECT`-Anweisung erstellen, führt die `CREATE TABLE`-Anweisung eine Abfrage aus. Um die benötigten temporären Dateien zu reduzieren, optimieren Sie die Abfrage.

### Verwenden Sie pg\$1repack, wenn Sie Indizes erstellen
<a name="apg-waits.iobuffile.actions.pg_repack"></a>

Wenn Sie einen Index erstellen, ordnet die Engine die Ergebnismenge an. Wenn Tabellen größer werden und die Werte in der indizierten Spalte vielfältiger werden, benötigen die temporären Dateien mehr Speicherplatz. In den meisten Fällen können Sie die Erstellung temporärer Dateien für große Tabellen nicht verhindern, ohne den Speicherbereich für Wartungsarbeiten zu ändern. Weitere Informationen finden Sie unter [Wartungs-Arbeitsspeicherbereich](AuroraPostgreSQL.Tuning.concepts.md#AuroraPostgreSQL.Tuning.concepts.local.maintenance_work_mem). 

Eine mögliche Problemumgehung beim Neuerstellen eines großen Index besteht darin, das pg\$1repack-Tool zu verwenden. Weitere Informationen finden Sie unter [Reorganisieren von Tabellen in PostgreSQL-Datenbanken mit minimalen Sperren](https://reorg.github.io/pg_repack/) in der pg\$1repack-Dokumentation.

### Erhöhen Sie maintenance work\$1mem, wenn Sie Tabellen clustern
<a name="apg-waits.iobuffile.actions.cluster"></a>

Der Befehl `CLUSTER` gruppiert die durch *table\$1name* angegebene Tabelle basierend auf einem vorhandenen Index, der durch *index\$1name* angegeben wird. Aurora PostgreSQL erstellt die Tabelle physisch so neu, dass sie der Reihenfolge eines bestimmten Indexes entspricht.

Als magnetische Speicherung vorherrschend war, war Clustering üblich, da der Speicherdurchsatz begrenzt war. Jetzt, da SSD-basierter Speicher üblich ist, ist Clustering weniger beliebt. Wenn Sie jedoch Tabellen clustern, können Sie die Leistung je nach Tabellengröße, Index, Abfrage usw. immer noch geringfügig steigern. 

Wenn Sie den Befehl `CLUSTER` ausführen und die Warteereignisse `IO:BufFileWrite` und `IO:BufFileRead` beobachten, stimmen Sie `maintenance_work_mem` ab. Erhöhen Sie die Speichergröße auf einen ziemlich großen Betrag. Ein hoher Wert bedeutet, dass die Engine mehr Speicher für den Clustering-Vorgang verwenden kann.

### Passen Sie den Speicher an, um IO: BufFileRead und IO: zu verhindern BufFileWrite
<a name="apg-waits.iobuffile.actions.tuning-memory"></a>

In irgendeiner Situation müssen Sie den Speicher abstimmen. Ihr Ziel ist es, die folgenden Anforderungen auszugleichen:
+ Der `work_mem`-Wert (siehe [Arbeitsspeicherbereich](AuroraPostgreSQL.Tuning.concepts.md#AuroraPostgreSQL.Tuning.concepts.local.work_mem))
+ Der Speicher, der nach dem Diskontieren des`shared_buffers`Wert (siehe[Puffer Pool](AuroraMySQL.Managing.Tuning.concepts.md#AuroraMySQL.Managing.Tuning.concepts.memory.buffer-pool))
+ Die maximale Anzahl geöffneter und verwendeter Verbindungen, die durch `max_connections` begrenzt ist

#### Erhöhen Sie die Größe des Arbeitsspeicherbereichs
<a name="apg-waits.iobuffile.actions.tuning-memory.work-mem"></a>

In einigen Situationen besteht Ihre einzige Möglichkeit darin, den von Ihrer Sitzung verwendeten Speicher zu erhöhen. Wenn Ihre Abfragen richtig geschrieben sind und die richtigen Schlüssel für Joins verwenden, sollten Sie den `work_mem`-Wert erhöhen. Weitere Informationen finden Sie unter [Arbeitsspeicherbereich](AuroraPostgreSQL.Tuning.concepts.md#AuroraPostgreSQL.Tuning.concepts.local.work_mem).

Um herauszufinden, wie viele temporäre Dateien eine Abfrage generiert, setzen Sie `log_temp_files` auf `0`. Wenn Sie den `work_mem`-Wert auf den in den Protokollen angegebenen Höchstwert erhöhen, verhindern Sie, dass die Abfrage temporäre Dateien generiert. `work_mem` legt jedoch das Maximum pro Planknoten für jede Verbindung oder jeden parallelen Worker fest. Wenn die Datenbank über 5.000 Verbindungen verfügt und jede 256 MiB-Speicher verwendet, benötigt die Engine 1,2 TiB RAM. Daher kann es sein, dass Ihrer Instance der Speicher knapp wird.

#### Reservieren Sie ausreichend Speicher für den freigegebenen Pufferpool
<a name="apg-waits.iobuffile.actions.tuning-memory.shared-pool"></a>

Ihre Datenbank verwendet Speicherbereiche wie den freigegebenen Pufferpool, nicht nur den Arbeitsspeicherbereich. Berücksichtigen Sie die Anforderungen dieser zusätzlichen Speicherbereiche, bevor Sie `work_mem` erhöhen. Weitere Informationen zum Pufferpool finden Sie unter [Puffer Pool](AuroraMySQL.Managing.Tuning.concepts.md#AuroraMySQL.Managing.Tuning.concepts.memory.buffer-pool).

Angenommen, Ihre Aurora PostgreSQL-Instance-Klasse ist db.r5.2xlarge. Diese Klasse hat 64 GiB Speicher. Standardmäßig sind 75 Prozent des Arbeitsspeichers für den freigegebenen Pufferpool reserviert. Nachdem Sie den dem Shared Memory-Bereich zugewiesenen Betrag abgezogen haben, bleiben 16.384 MB übrig. Weisen Sie den verbleibenden Speicher nicht ausschließlich dem Arbeitsspeicherbereich zu, da das Betriebssystem und die Engine ebenfalls Speicher benötigen.

Der Speicher, den Sie `work_mem` zuordnen können, hängt von der Instance-Klasse ab. Wenn Sie eine größere Instance-Klasse verwenden, ist mehr Speicher verfügbar. Im vorhergehenden Beispiel können Sie jedoch nicht mehr als 16 GiB verwenden. Andernfalls ist Ihre Instance nicht verfügbar, wenn ihr der Speicher ausgeht. Um die Instance aus dem nicht verfügbaren Status wiederherzustellen, werden die Aurora PostgreSQL-Automatisierungsdienste automatisch neu gestartet.

#### Verwalten der Anzahl der Verbindungen
<a name="apg-waits.iobuffile.actions.tuning-memory.connections"></a>

Angenommen, Ihre Datenbank-Instance hat 5.000 gleichzeitige Verbindungen. Jede Verbindung verwendet mindestens 4 MB `work_mem`. Der hohe Speicherverbrauch der Verbindungen dürfte die Leistung beeinträchtigen. Als Reaktion darauf haben Sie die folgenden Optionen:
+ Aktualisieren Sie auf eine größere Instance-Klasse.
+ Verringern Sie die Anzahl gleichzeitiger Datenbankverbindungen mit einem Verbindungsproxy oder Pooler.

Berücksichtigen Sie bei Proxys Amazon RDS Proxy, PGBouncer oder einen auf Ihrer Anwendung basierenden Verbindungspooler. Diese Lösung lindert die CPU-Last. Es reduziert auch das Risiko, wenn alle Verbindungen den Arbeitsspeicherbereich benötigen. Wenn weniger Datenbankverbindungen vorhanden sind, können Sie den Wert von `work_mem` erhöhen. Auf diese Weise reduzieren Sie das Auftreten der `IO:BufFileRead`- und `IO:BufFileWrite`-Warteereignisse. Auch die Abfragen, die auf den Arbeitsspeicherbereich warten, beschleunigen sich erheblich.

# IO: DataFileRead
<a name="apg-waits.iodatafileread"></a>

Das `IO:DataFileRead`-Ereignis tritt auf, wenn eine Verbindung darauf wartet, dass ein Backend-Prozess eine erforderliche Seite aus dem Speicher liest, da die Seite nicht im gemeinsam genutzten Speicher verfügbar ist.

**Topics**
+ [Unterstützte Engine-Versionen](#apg-waits.iodatafileread.context.supported)
+ [Kontext](#apg-waits.iodatafileread.context)
+ [Wahrscheinliche Ursachen für erhöhte Wartezeiten](#apg-waits.iodatafileread.causes)
+ [Aktionen](#apg-waits.iodatafileread.actions)

## Unterstützte Engine-Versionen
<a name="apg-waits.iodatafileread.context.supported"></a>

Diese Warteereignisinformationen werden für alle Versionen von Aurora PostgreSQL unterstützt.

## Kontext
<a name="apg-waits.iodatafileread.context"></a>

Alle Abfragen und Datenmanipulationsvorgänge (DML) greifen auf Seiten im Pufferpool zu. Zu den Anweisungen, die Lesevorgänge auslösen können, gehören `SELECT`, `UPDATE` und `DELETE`. Ein `UPDATE` kann beispielsweise Seiten aus Tabellen oder Indizes lesen. Wenn sich die angeforderte oder aktualisierte Seite nicht im gemeinsam genutzten Pufferpool befindet, kann dieser Lesevorgang zum `IO:DataFileRead`-Ereignis führen.

Da der gemeinsame Pufferpool endlich ist, kann er sich füllen. In diesem Fall zwingen Anfragen nach Seiten, die sich nicht im Speicher befinden, die Datenbank dazu, Blöcke von der Festplatte zu lesen. Wenn das `IO:DataFileRead`-Ereignis häufig auftritt, ist Ihr gemeinsam genutzter Pufferpool möglicherweise zu klein für Ihre Workload. Dieses Problem ist bei `SELECT`-Abfragen akut, die eine große Anzahl von Zeilen lesen, die nicht in den Pufferpool passen. Weitere Informationen zum Pufferpool finden Sie unter [Puffer Pool](AuroraMySQL.Managing.Tuning.concepts.md#AuroraMySQL.Managing.Tuning.concepts.memory.buffer-pool).

## Wahrscheinliche Ursachen für erhöhte Wartezeiten
<a name="apg-waits.iodatafileread.causes"></a>

Häufige Ursachen für das Ereignis `IO:DataFileRead` sind die folgenden:

**Verbindungsspitzen**  
Möglicherweise stellen Sie fest, dass mehrere Verbindungen dieselbe Anzahl von IO: DataFileRead Wait-Ereignissen generieren. In diesem Fall kann eine Spitze (plötzlicher und starker Anstieg) bei `IO:DataFileRead`-Ereignissen auftreten. 

**SELECT- und DML-Anweisungen, die sequentielle Scans durchführen**  
Ihre Anwendung führt möglicherweise einen neuen Vorgang aus. Oder ein vorhandener Vorgang könnte sich aufgrund eines neuen Ausführungsplans ändern. Suchen Sie in solchen Fällen nach Tabellen (insbesondere großen Tabellen), die einen größeren `seq_scan`-Wert haben. Finden Sie sie, indem Sie `pg_stat_user_tables` abfragen. Verwenden Sie die Erweiterung `pg_stat_statements`, um Abfragen zu verfolgen, die mehr Lesevorgänge generieren.

**CTAS und CREATE INDEX für große Datensätze**  
Ein *CTAS* ist eine `CREATE TABLE AS SELECT`-Anweisung. Wenn Sie ein CTAS mit einem großen Datensatz als Quelle ausführen oder einen Index für eine große Tabelle erstellen, kann das `IO:DataFileRead`-Ereignis auftreten. Wenn Sie einen Index erstellen, muss die Datenbank möglicherweise das gesamte Objekt mithilfe eines sequentiellen Scans lesen. Ein CTAS generiert `IO:DataFile`-Reads, wenn Seiten nicht im Speicher sind.

**Mehrere Vakuumarbeiter laufen gleichzeitig**  
Vakuumarbeiter können manuell oder automatisch ausgelöst werden. Wir empfehlen, eine aggressive Vakuumstrategie zu verabschieden. Wenn eine Tabelle jedoch viele aktualisierte oder gelöschte Zeilen enthält, erhöhen sich die `IO:DataFileRead`-Wartezeiten. Nachdem der Raum zurückgewonnen wurde, nimmt die für `IO:DataFileRead` aufgewendete Vakuumzeit ab.

**Aufnahme großer Datenmengen**  
Wenn Ihre Anwendung große Datenmengen aufnimmt, können `ANALYZE`-Vorgänge häufiger auftreten. Der `ANALYZE`-Prozess kann durch einen Autovacuum Launcher ausgelöst oder manuell aufgerufen werden.  
Der `ANALYZE`-Vorgang liest eine Teilmenge der Tabelle. Die Anzahl der zu scannenden Seiten wird berechnet, indem 30 mit dem `default_statistics_target`-Wert multipliziert wird. Weitere Informationen finden Sie in der [PostgreSQL-Dokumentation](https://www.postgresql.org/docs/current/runtime-config-query.html#GUC-DEFAULT-STATISTICS-TARGET). Der Parameter `default_statistics_target` akzeptiert Werte zwischen 1 und 10.000, wobei der Standardwert 100 ist.

**Hungertod**  
Wenn Netzwerkbandbreite oder CPU der Instance verbraucht werden, kann das `IO:DataFileRead`-Ereignis häufiger auftreten.

## Aktionen
<a name="apg-waits.iodatafileread.actions"></a>

Abhängig von den Ursachen Ihres Warteereignisses empfehlen wir verschiedene Aktionen.

**Topics**
+ [Überprüfen Sie Prädikatfilter auf Abfragen, die Wartezeiten generieren](#apg-waits.iodatafileread.actions.filters)
+ [Minimieren Sie die Auswirkungen von Wartungsvorgängen](#apg-waits.iodatafileread.actions.maintenance)
+ [Reagieren Sie auf eine hohe Anzahl von Verbindungen](#apg-waits.iodatafileread.actions.connections)

### Überprüfen Sie Prädikatfilter auf Abfragen, die Wartezeiten generieren
<a name="apg-waits.iodatafileread.actions.filters"></a>

Angenommen, Sie identifizieren bestimmte Abfragen, die `IO:DataFileRead`-Warteereignisse generieren. Sie können sie mit den folgenden Techniken identifizieren:
+ Performance Insights
+ Katalogansichten wie die der Erweiterung `pg_stat_statements`
+ Die Katalogansicht `pg_stat_all_tables`, wenn sie periodisch eine erhöhte Anzahl von physischen Lesevorgängen anzeigt
+ Die `pg_statio_all_tables`-Ansicht, wenn sie zeigt, dass `_read`-Zähler steigen

Wir empfehlen Ihnen, zu bestimmen, welche Filter im Prädikat (`WHERE`-Klausel) dieser Abfragen verwendet werden. Befolgen Sie diese Richtlinien:
+ Führen Sie den Befehl `EXPLAIN` aus. Geben Sie in der Ausgabe an, welche Arten von Scans verwendet werden. Ein sequentieller Scan weist nicht zwangsläufig ein Problem an. Abfragen, die sequenzielle Scans verwenden, erzeugen im Vergleich zu Abfragen, die Filter verwenden, natürlich mehr `IO:DataFileRead`-Ereignisse.

  Finden Sie heraus, ob die in der `WHERE`-Klausel aufgeführte Spalte indiziert ist. Wenn nicht, erwägen Sie, einen Index für diese Spalte zu erstellen. Dieser Ansatz vermeidet die sequentiellen Scans und reduziert die `IO:DataFileRead`-Ereignisse. Wenn eine Abfrage restriktive Filter enthält und immer noch sequenzielle Scans erzeugt, bewerten Sie, ob die richtigen Indizes verwendet werden.
+ Finden Sie heraus, ob die Abfrage auf eine sehr große Tabelle zugreift. In einigen Fällen kann das Partitionieren einer Tabelle die Leistung verbessern, sodass die Abfrage nur notwendige Partitionen lesen kann.
+ Untersuchen Sie die Kardinalität (Gesamtzahl der Zeilen) Ihrer Join-Vorgänge. Beachten Sie, wie restriktiv die Werte sind, die Sie den Filtern für Ihre `WHERE`-Klausel übergeben. Wenn möglich, stimmen Sie Ihre Abfrage ein, um die Anzahl der Zeilen zu reduzieren, die in jedem Schritt des Plans übergeben werden.

### Minimieren Sie die Auswirkungen von Wartungsvorgängen
<a name="apg-waits.iodatafileread.actions.maintenance"></a>

Wartungsvorgänge wie `VACUUM` und `ANALYZE` sind wichtig. Wir empfehlen, sie nicht zu deaktivieren, da Sie `IO:DataFileRead`-Warteereignisse im Zusammenhang mit diesen Wartungsvorgängen finden. Die folgenden Ansätze können die Auswirkungen dieser Vorgänge minimieren:
+ Führen Sie Wartungsvorgänge während außerhalb der Hauptverkehrszeiten manuell aus. Diese Technik verhindert, dass die Datenbank den Schwellenwert für automatische Vorgänge erreicht.
+ Erwägen Sie bei sehr großen Tabellen, die Tabelle zu partitionieren. Diese Technik reduziert den Overhead von Wartungsvorgängen. Die Datenbank greift nur auf die Partitionen zu, die gewartet werden müssen.
+ Wenn Sie große Datenmengen aufnehmen, sollten Sie die Funktion zur automatischen Analyse deaktivieren.

Die Auto-Vakuum-Funktion wird automatisch für eine Tabelle ausgelöst, wenn die folgende Formel zutrifft.

```
pg_stat_user_tables.n_dead_tup > (pg_class.reltuples x autovacuum_vacuum_scale_factor) + autovacuum_vacuum_threshold
```

Die Ansicht `pg_stat_user_tables` und der Katalog `pg_class` haben mehrere Zeilen. Eine Zeile kann einer Zeile in Ihrer Tabelle entsprechen. Diese Formel geht davon aus, dass die `reltuples` für eine bestimmte Tabelle stehen. Die Parameter `autovacuum_vacuum_scale_factor` (standardmäßig 0.20) und `autovacuum_vacuum_threshold` (standardmäßig 50 Tupel) werden normalerweise global für die gesamte Instance gesetzt. Sie können jedoch verschiedene Werte für eine bestimmte Tabelle festlegen.

**Topics**
+ [Suchen Sie nach Tabellen, die unnötigerweise Speicherplatz belegen.](#apg-waits.iodatafileread.actions.maintenance.tables)
+ [Finden Sie Indizes mit unnötigem Speicherplatz](#apg-waits.iodatafileread.actions.maintenance.indexes)
+ [Finden Sie Tabellen, die für die automatische Vakuumierung berechtigt sind](#apg-waits.iodatafileread.actions.maintenance.autovacuumed)

#### Suchen Sie nach Tabellen, die unnötigerweise Speicherplatz belegen.
<a name="apg-waits.iodatafileread.actions.maintenance.tables"></a>

Um Tabellen zu finden, die mehr Speicherplatz belegen als nötig, führen Sie die folgende Abfrage aus. Wenn diese Abfrage von einer Datenbankbenutzerrolle ausgeführt wird, die nicht über die `rds_superuser`-Rolle verfügt, gibt sie nur Informationen zu den Tabellen zurück, für die die Benutzerrolle Leserechte besitzt. Diese Abfrage wird von PostgreSQL Version 12 und späteren Versionen unterstützt. 

```
WITH report AS (
   SELECT   schemaname
           ,tblname
           ,n_dead_tup
           ,n_live_tup
           ,block_size*tblpages AS real_size
           ,(tblpages-est_tblpages)*block_size AS extra_size
           ,CASE WHEN tblpages - est_tblpages > 0
              THEN 100 * (tblpages - est_tblpages)/tblpages::float
              ELSE 0
            END AS extra_ratio, fillfactor, (tblpages-est_tblpages_ff)*block_size AS bloat_size
           ,CASE WHEN tblpages - est_tblpages_ff > 0
              THEN 100 * (tblpages - est_tblpages_ff)/tblpages::float
              ELSE 0
            END AS bloat_ratio
           ,is_na
    FROM (
           SELECT  ceil( reltuples / ( (block_size-page_hdr)/tpl_size ) ) + ceil( toasttuples / 4 ) AS est_tblpages
                  ,ceil( reltuples / ( (block_size-page_hdr)*fillfactor/(tpl_size*100) ) ) + ceil( toasttuples / 4 ) AS est_tblpages_ff
                  ,tblpages
                  ,fillfactor
                  ,block_size
                  ,tblid
                  ,schemaname
                  ,tblname
                  ,n_dead_tup
                  ,n_live_tup
                  ,heappages
                  ,toastpages
                  ,is_na
             FROM (
                    SELECT ( 4 + tpl_hdr_size + tpl_data_size + (2*ma)
                               - CASE WHEN tpl_hdr_size%ma = 0 THEN ma ELSE tpl_hdr_size%ma END
                               - CASE WHEN ceil(tpl_data_size)::int%ma = 0 THEN ma ELSE ceil(tpl_data_size)::int%ma END
                           ) AS tpl_size
                           ,block_size - page_hdr AS size_per_block
                           ,(heappages + toastpages) AS tblpages
                           ,heappages
                           ,toastpages
                           ,reltuples
                           ,toasttuples
                           ,block_size
                           ,page_hdr
                           ,tblid
                           ,schemaname
                           ,tblname
                           ,fillfactor
                           ,is_na
                           ,n_dead_tup
                           ,n_live_tup
                          FROM (
                                SELECT  tbl.oid                       AS tblid
                                       ,ns.nspname                    AS schemaname
                                       ,tbl.relname                   AS tblname
                                       ,tbl.reltuples                 AS reltuples
                                       ,tbl.relpages                  AS heappages
                                       ,coalesce(toast.relpages, 0)   AS toastpages
                                       ,coalesce(toast.reltuples, 0)  AS toasttuples
                                       ,psat.n_dead_tup               AS n_dead_tup
                                       ,psat.n_live_tup               AS n_live_tup
                                       ,24                            AS page_hdr
                                       ,current_setting('block_size')::numeric AS block_size
                                       ,coalesce(substring( array_to_string(tbl.reloptions, ' ') FROM 'fillfactor=([0-9]+)')::smallint, 100) AS fillfactor
                                       ,CASE WHEN version()~'mingw32' OR version()~'64-bit|x86_64|ppc64|ia64|amd64' THEN 8 ELSE 4 END        AS ma
                                       ,23 + CASE WHEN MAX(coalesce(null_frac,0)) > 0 THEN ( 7 + count(*) ) / 8 ELSE 0::int END              AS tpl_hdr_size
                                       ,sum( (1-coalesce(s.null_frac, 0)) * coalesce(s.avg_width, 1024) )                                    AS tpl_data_size
                                       ,bool_or(att.atttypid = 'pg_catalog.name'::regtype) OR count(att.attname) <> count(s.attname)         AS is_na
                                  FROM  pg_attribute       AS att
                                  JOIN  pg_class           AS tbl    ON (att.attrelid = tbl.oid)
                                  JOIN  pg_stat_all_tables AS psat   ON (tbl.oid = psat.relid)
                                  JOIN  pg_namespace       AS ns     ON (ns.oid = tbl.relnamespace)
                             LEFT JOIN  pg_stats           AS s      ON (s.schemaname=ns.nspname AND s.tablename = tbl.relname AND s.inherited=false AND s.attname=att.attname)
                             LEFT JOIN  pg_class           AS toast  ON (tbl.reltoastrelid = toast.oid)
                                 WHERE  att.attnum > 0
                                   AND  NOT att.attisdropped
                                   AND  tbl.relkind = 'r'
                              GROUP BY  tbl.oid, ns.nspname, tbl.relname, tbl.reltuples, tbl.relpages, toastpages, toasttuples, fillfactor, block_size, ma, n_dead_tup, n_live_tup
                              ORDER BY  schemaname, tblname
                           ) AS s
                 ) AS s2
       ) AS s3
 ORDER BY bloat_size DESC
)
  SELECT * 
    FROM report 
   WHERE bloat_ratio != 0
 -- AND schemaname = 'public'
 -- AND tblname = 'pgbench_accounts'
;

-- WHERE NOT is_na
--   AND tblpages*((pst).free_percent + (pst).dead_tuple_percent)::float4/100 >= 1
```

Sie können in Ihrer Anwendung nach einer Überlastung von Tabellen und Indizes suchen. Weitere Informationen finden Sie unter [Diagnostizieren einer Überlastung von Tabellen und Indizes](AuroraPostgreSQL.diag-table-ind-bloat.md).

#### Finden Sie Indizes mit unnötigem Speicherplatz
<a name="apg-waits.iodatafileread.actions.maintenance.indexes"></a>

Um Indizes zu finden, die unnötigen Speicherplatz benötigen, führen Sie die folgende Abfrage aus.

```
-- WARNING: run with a nonsuperuser role, the query inspects
-- only indexes on tables you have permissions to read.
-- WARNING: rows with is_na = 't' are known to have bad statistics ("name" type is not supported).
-- This query is compatible with PostgreSQL 8.2 and later.

SELECT current_database(), nspname AS schemaname, tblname, idxname, bs*(relpages)::bigint AS real_size,
  bs*(relpages-est_pages)::bigint AS extra_size,
  100 * (relpages-est_pages)::float / relpages AS extra_ratio,
  fillfactor, bs*(relpages-est_pages_ff) AS bloat_size,
  100 * (relpages-est_pages_ff)::float / relpages AS bloat_ratio,
  is_na
  -- , 100-(sub.pst).avg_leaf_density, est_pages, index_tuple_hdr_bm, 
  -- maxalign, pagehdr, nulldatawidth, nulldatahdrwidth, sub.reltuples, sub.relpages 
  -- (DEBUG INFO)
FROM (
  SELECT coalesce(1 +
       ceil(reltuples/floor((bs-pageopqdata-pagehdr)/(4+nulldatahdrwidth)::float)), 0 
       -- ItemIdData size + computed avg size of a tuple (nulldatahdrwidth)
    ) AS est_pages,
    coalesce(1 +
       ceil(reltuples/floor((bs-pageopqdata-pagehdr)*fillfactor/(100*(4+nulldatahdrwidth)::float))), 0
    ) AS est_pages_ff,
    bs, nspname, table_oid, tblname, idxname, relpages, fillfactor, is_na
    -- , stattuple.pgstatindex(quote_ident(nspname)||'.'||quote_ident(idxname)) AS pst, 
    -- index_tuple_hdr_bm, maxalign, pagehdr, nulldatawidth, nulldatahdrwidth, reltuples 
    -- (DEBUG INFO)
  FROM (
    SELECT maxalign, bs, nspname, tblname, idxname, reltuples, relpages, relam, table_oid, fillfactor,
      ( index_tuple_hdr_bm +
          maxalign - CASE -- Add padding to the index tuple header to align on MAXALIGN
            WHEN index_tuple_hdr_bm%maxalign = 0 THEN maxalign
            ELSE index_tuple_hdr_bm%maxalign
          END
        + nulldatawidth + maxalign - CASE -- Add padding to the data to align on MAXALIGN
            WHEN nulldatawidth = 0 THEN 0
            WHEN nulldatawidth::integer%maxalign = 0 THEN maxalign
            ELSE nulldatawidth::integer%maxalign
          END
      )::numeric AS nulldatahdrwidth, pagehdr, pageopqdata, is_na
      -- , index_tuple_hdr_bm, nulldatawidth -- (DEBUG INFO)
    FROM (
      SELECT
        i.nspname, i.tblname, i.idxname, i.reltuples, i.relpages, i.relam, a.attrelid AS table_oid,
        current_setting('block_size')::numeric AS bs, fillfactor,
        CASE -- MAXALIGN: 4 on 32bits, 8 on 64bits (and mingw32 ?)
          WHEN version() ~ 'mingw32' OR version() ~ '64-bit|x86_64|ppc64|ia64|amd64' THEN 8
          ELSE 4
        END AS maxalign,
        /* per page header, fixed size: 20 for 7.X, 24 for others */
        24 AS pagehdr,
        /* per page btree opaque data */
        16 AS pageopqdata,
        /* per tuple header: add IndexAttributeBitMapData if some cols are null-able */
        CASE WHEN max(coalesce(s.null_frac,0)) = 0
          THEN 2 -- IndexTupleData size
          ELSE 2 + (( 32 + 8 - 1 ) / 8) 
          -- IndexTupleData size + IndexAttributeBitMapData size ( max num filed per index + 8 - 1 /8)
        END AS index_tuple_hdr_bm,
        /* data len: we remove null values save space using it fractionnal part from stats */
        sum( (1-coalesce(s.null_frac, 0)) * coalesce(s.avg_width, 1024)) AS nulldatawidth,
        max( CASE WHEN a.atttypid = 'pg_catalog.name'::regtype THEN 1 ELSE 0 END ) > 0 AS is_na
      FROM pg_attribute AS a
        JOIN (
          SELECT nspname, tbl.relname AS tblname, idx.relname AS idxname, 
            idx.reltuples, idx.relpages, idx.relam,
            indrelid, indexrelid, indkey::smallint[] AS attnum,
            coalesce(substring(
              array_to_string(idx.reloptions, ' ')
               from 'fillfactor=([0-9]+)')::smallint, 90) AS fillfactor
          FROM pg_index
            JOIN pg_class idx ON idx.oid=pg_index.indexrelid
            JOIN pg_class tbl ON tbl.oid=pg_index.indrelid
            JOIN pg_namespace ON pg_namespace.oid = idx.relnamespace
          WHERE pg_index.indisvalid AND tbl.relkind = 'r' AND idx.relpages > 0
        ) AS i ON a.attrelid = i.indexrelid
        JOIN pg_stats AS s ON s.schemaname = i.nspname
          AND ((s.tablename = i.tblname AND s.attname = pg_catalog.pg_get_indexdef(a.attrelid, a.attnum, TRUE)) 
          -- stats from tbl
          OR  (s.tablename = i.idxname AND s.attname = a.attname))
          -- stats from functionnal cols
        JOIN pg_type AS t ON a.atttypid = t.oid
      WHERE a.attnum > 0
      GROUP BY 1, 2, 3, 4, 5, 6, 7, 8, 9
    ) AS s1
  ) AS s2
    JOIN pg_am am ON s2.relam = am.oid WHERE am.amname = 'btree'
) AS sub
-- WHERE NOT is_na
ORDER BY 2,3,4;
```

#### Finden Sie Tabellen, die für die automatische Vakuumierung berechtigt sind
<a name="apg-waits.iodatafileread.actions.maintenance.autovacuumed"></a>

Führen Sie die folgende Abfrage aus, um Tabellen zu finden, die für die automatische Vakuumierung berechtigt sind.

```
--This query shows tables that need vacuuming and are eligible candidates.
--The following query lists all tables that are due to be processed by autovacuum. 
-- During normal operation, this query should return very little.
WITH  vbt AS (SELECT setting AS autovacuum_vacuum_threshold 
              FROM pg_settings WHERE name = 'autovacuum_vacuum_threshold')
    , vsf AS (SELECT setting AS autovacuum_vacuum_scale_factor 
              FROM pg_settings WHERE name = 'autovacuum_vacuum_scale_factor')
    , fma AS (SELECT setting AS autovacuum_freeze_max_age 
              FROM pg_settings WHERE name = 'autovacuum_freeze_max_age')
    , sto AS (SELECT opt_oid, split_part(setting, '=', 1) as param, 
                split_part(setting, '=', 2) as value 
              FROM (SELECT oid opt_oid, unnest(reloptions) setting FROM pg_class) opt)
SELECT
    '"'||ns.nspname||'"."'||c.relname||'"' as relation
    , pg_size_pretty(pg_table_size(c.oid)) as table_size
    , age(relfrozenxid) as xid_age
    , coalesce(cfma.value::float, autovacuum_freeze_max_age::float) autovacuum_freeze_max_age
    , (coalesce(cvbt.value::float, autovacuum_vacuum_threshold::float) + 
         coalesce(cvsf.value::float,autovacuum_vacuum_scale_factor::float) * c.reltuples) 
         as autovacuum_vacuum_tuples
    , n_dead_tup as dead_tuples
FROM pg_class c 
JOIN pg_namespace ns ON ns.oid = c.relnamespace
JOIN pg_stat_all_tables stat ON stat.relid = c.oid
JOIN vbt on (1=1) 
JOIN vsf ON (1=1) 
JOIN fma on (1=1)
LEFT JOIN sto cvbt ON cvbt.param = 'autovacuum_vacuum_threshold' AND c.oid = cvbt.opt_oid
LEFT JOIN sto cvsf ON cvsf.param = 'autovacuum_vacuum_scale_factor' AND c.oid = cvsf.opt_oid
LEFT JOIN sto cfma ON cfma.param = 'autovacuum_freeze_max_age' AND c.oid = cfma.opt_oid
WHERE c.relkind = 'r' 
AND nspname <> 'pg_catalog'
AND (
    age(relfrozenxid) >= coalesce(cfma.value::float, autovacuum_freeze_max_age::float)
    or
    coalesce(cvbt.value::float, autovacuum_vacuum_threshold::float) + 
      coalesce(cvsf.value::float,autovacuum_vacuum_scale_factor::float) * c.reltuples <= n_dead_tup
    -- or 1 = 1
)
ORDER BY age(relfrozenxid) DESC;
```

### Reagieren Sie auf eine hohe Anzahl von Verbindungen
<a name="apg-waits.iodatafileread.actions.connections"></a>

Wenn Sie Amazon überwachen CloudWatch, stellen Sie möglicherweise fest, dass die `DatabaseConnections` Metrik ansteigt. Dieser Anstieg deutet auf eine erhöhte Anzahl von Verbindungen zu Ihrer Datenbank hin. Wir empfehlen folgende Vorgehensweise:
+ Beschränken Sie die Anzahl der Verbindungen, die die Anwendung mit jeder Instance öffnen kann. Wenn Ihre Anwendung über eine eingebettete Verbindungspool-Funktion verfügt, legen Sie eine angemessene Anzahl von Verbindungen fest. Basieren Sie die Zahl darauf, was das v CPUs in Ihrer Instance effektiv parallelisieren kann.

  Wenn Ihre Anwendung keine Verbindungspool-Funktion verwendet, sollten Sie den Amazon RDS Proxy oder eine Alternative in Betracht ziehen. Mit diesem Ansatz können Ihre Anwendung mehrere Verbindungen mit dem Load Balancer öffnen. Der Balancer kann dann eine begrenzte Anzahl von Verbindungen mit der Datenbank öffnen. Da weniger Verbindungen parallel laufen, führt Ihre DB-Instance weniger Kontextwechsel im Kernel durch. Abfragen sollten schneller voranschreiten und zu weniger Warteereignissen führen. Weitere Informationen finden Sie unter [Amazon RDS-Proxy für Aurora](rds-proxy.md).
+ Nutzen Sie nach Möglichkeit die Reader-Knoten für Aurora PostgreSQL und lesen Sie Replikate für RDS für PostgreSQL. Wenn Ihre Anwendung einen schreibgeschützten Vorgang ausführt, senden Sie diese Anfragen an den reader-Endpunkt. Durch diese Technik werden Anwendungsanfragen auf alle Leseknoten verteilt, wodurch der I/O Druck auf den Writer-Knoten verringert wird.
+ Ziehen Sie, Ihre DB-Instance zu skalieren. Eine Instance-Klasse mit höherer Kapazität bietet mehr Speicher, was Aurora PostgreSQL einen größeren freigegebenen Pufferpool zum Speichern von Seiten gibt. Die größere Größe gibt der DB-Instance auch mehr V CPUs für die Verarbeitung von Verbindungen. Mehr v CPUs sind besonders hilfreich, wenn es sich bei den Vorgängen, die `IO:DataFileRead` Warte-Ereignisse erzeugen, um Schreibvorgänge handelt.

# IO:XactSync
<a name="apg-waits.xactsync"></a>

Das `IO:XactSync` Ereignis tritt ein, wenn die Datenbank darauf wartet, dass das Aurora-Storage-Subsystem den Commit einer regulären Transaktion bzw. den Commit oder Rollback einer vorbereiteten Transaktion ausführt. Eine vorbereitete Transaktion ist Teil des Supports von PostgreSQL für einen zweiphasigen Commit. Dieses Ereignis kann auch auftreten, wenn eine Abfrage darauf wartet, dass eine andere Transaktion übergeben wird, insbesondere in Fällen, in denen Auto-Commit deaktiviert ist. In solchen Szenarien kann es vorkommen, dass Updates scheinbar auf XactSync warten, obwohl sie noch nicht übergeben wurden.

**Topics**
+ [Unterstützte Engine-Versionen](#apg-waits.xactsync.context.supported)
+ [Kontext](#apg-waits.xactsync.context)
+ [Wahrscheinliche Ursachen für erhöhte Wartezeiten](#apg-waits.xactsync.causes)
+ [Aktionen](#apg-waits.xactsync.actions)

## Unterstützte Engine-Versionen
<a name="apg-waits.xactsync.context.supported"></a>

Diese Warteereignisinformationen werden für alle Versionen von Aurora PostgreSQL unterstützt.

## Kontext
<a name="apg-waits.xactsync.context"></a>

Das Ereignis `IO:XactSync` zeigt an, dass die Instance-Zeit damit verbringt, darauf zu warten, dass das Aurora-Speichersubsystem bestätigt, dass Transaktionsdaten verarbeitet wurden.

## Wahrscheinliche Ursachen für erhöhte Wartezeiten
<a name="apg-waits.xactsync.causes"></a>

Wenn das `IO:XactSync`-Ereignis mehr als normal auftritt, was möglicherweise auf ein Leistungsproblem hinweist, sind die folgenden typischen Ursachen:

**Netzwerksättigung**  
Der Datenverkehr zwischen Clients und der DB-Instance oder der Datenverkehr zum Speicher-Subsystem ist möglicherweise zu hoch für die Netzwerkbandbreite.

**CPU-Druck**  
Eine hohe Workload könnte verhindern, dass der Aurora-Speicher-Daemon genügend CPU-Zeit erhält.

## Aktionen
<a name="apg-waits.xactsync.actions"></a>

Abhängig von den Ursachen Ihres Warteereignisses empfehlen wir verschiedene Aktionen.

**Topics**
+ [Überwachen Sie Ihre Ressourcen](#apg-waits.xactsync.actions.monitor)
+ [Hochskalieren Sie die CPU](#apg-waits.xactsync.actions.scalecpu)
+ [Erhöhung der Netzwerkbandbreite](#apg-waits.xactsync.actions.scalenetwork)
+ [Reduzieren Sie die Anzahl der Commits](#apg-waits.xactsync.actions.commits)

### Überwachen Sie Ihre Ressourcen
<a name="apg-waits.xactsync.actions.monitor"></a>

Um die Ursache der erhöhten `IO:XactSync`-Ereignisse zu ermitteln, überprüfen Sie die folgenden Metriken:
+ `WriteThroughput` und `CommitThroughput` – Änderungen des Schreibdurchsatzes oder des Commit-Durchsatzes können eine Zunahme der Workload anzeigen.
+ `WriteLatency` und `CommitLatency` – Änderungen der Schreib- oder Commit-Latenz können darauf hinweisen, dass das Speichersubsystem zu mehr Arbeit aufgefordert wird.
+ `CPUUtilization` – Wenn die CPU-Auslastung der Instance über 90 Prozent liegt, erhält der Aurora-Speicher-Daemon möglicherweise nicht genügend Zeit auf der CPU. In diesem Fall verschlechtert sich die I/O-Leistung.

Informationen zu diesen Metriken finden Sie unter [Metriken auf Instance-Ebene für Amazon Aurora](Aurora.AuroraMonitoring.Metrics.md#Aurora.AuroraMySQL.Monitoring.Metrics.instances).

### Hochskalieren Sie die CPU
<a name="apg-waits.xactsync.actions.scalecpu"></a>

Um Probleme mit CPU-Hunger zu beheben, sollten Sie in Betracht ziehen, zu einem Instance-Typ mit mehr CPU-Kapazität zu wechseln. Informationen zur CPU-Kapazität für eine DB-Instance-Klasse finden Sie unter [Hardwarespezifikationen für DB-Instance-Klassen für Aurora](Concepts.DBInstanceClass.Summary.md).

### Erhöhung der Netzwerkbandbreite
<a name="apg-waits.xactsync.actions.scalenetwork"></a>

Um festzustellen, ob die Instance ihre Netzwerkbandbreitenlimits erreicht, suchen Sie nach den folgenden anderen Warteereignissen: 
+ `IO:DataFileRead`, `IO:BufferRead`, `IO:BufferWrite` und `IO:XactWrite` – Abfragen, die große Mengen an I/O verwenden, können mehr dieser Warteereignisse generieren.
+ `Client:ClientRead` und`Client:ClientWrite` – Abfragen mit großen Mengen an Client-Kommunikation können mehr dieser Warteereignisse generieren.

Wenn die Netzwerkbandbreite ein Problem darstellt, sollten Sie erwägen, zu einem Instance-Typ mit mehr Netzwerkbandbreite zu wechseln. Informationen zur Netzwerkleistung für eine DB-Instance-Klasse finden Sie unter [Hardwarespezifikationen für DB-Instance-Klassen für Aurora](Concepts.DBInstanceClass.Summary.md).

### Reduzieren Sie die Anzahl der Commits
<a name="apg-waits.xactsync.actions.commits"></a>

Um die Anzahl der Commits zu reduzieren, kombinieren Sie Anweisungen in Transaktionsblöcken.

# IPC:DamRecordTxAck
<a name="apg-waits.ipcdamrecordtxac"></a>

Das `IPC:DamRecordTxAck`-Ereignis tritt auf, wenn Aurora PostgreSQL in einer Sitzung, die Datenbank-Aktivitätsstreams verwendet, ein Aktivitätsstream-Ereignis generiert und dann wartet, bis dieses Ereignis dauerhaft wird. 

**Topics**
+ [Relevante Engine-Versionen](#apg-waits.ipcdamrecordtxac.context.supported)
+ [Kontext](#apg-waits.ipcdamrecordtxac.context)
+ [Ursachen](#apg-waits.ipcdamrecordtxac.causes)
+ [Aktionen](#apg-waits.ipcdamrecordtxac.actions)

## Relevante Engine-Versionen
<a name="apg-waits.ipcdamrecordtxac.context.supported"></a>

Diese Warteereignisinformationen sind für alle Aurora PostgreSQL 10.7 und höher 10 Versionen, 11.4 und höher 11 Versionen sowie alle 12 und 13 Versionen relevant.

## Kontext
<a name="apg-waits.ipcdamrecordtxac.context"></a>

Im synchronen Modus wird die Dauerhaftigkeit von Aktivitätsstream-Ereignissen gegenüber der Datenbankleistung bevorzugt. Während auf ein dauerhaftes Schreiben des Ereignisses gewartet wird, blockiert die Sitzung andere Datenbankaktivitäten, was das `IPC:DamRecordTxAck`-Warteereignis verursacht.

## Ursachen
<a name="apg-waits.ipcdamrecordtxac.causes"></a>

Die häufigste Ursache für das Auftreten des `IPC:DamRecordTxAck`-Ereignisses in Top-Waits ist, dass die Funktion Database Activity Streams (DAS) ein ganzheitliches Audit ist. Eine höhere SQL-Aktivität generiert Aktivitätsstream-Ereignisse, die aufgezeichnet werden müssen.

## Aktionen
<a name="apg-waits.ipcdamrecordtxac.actions"></a>

Abhängig von den Ursachen Ihres Wait-Ereignisses empfehlen wir verschiedene Aktionen:
+ Reduzieren Sie die Anzahl der SQL-Anweisungen oder deaktivieren Sie Datenbank-Aktivitätsströme. Dadurch wird die Anzahl der Ereignisse reduziert, die dauerhafte Schreibvorgänge erfordern.
+ Wechseln Sie in den asynchronen Modus. Dadurch können Konflikte beim `IPC:DamRecordTxAck`-Warteereignis reduziert werden.

  Die DAS-Funktion kann jedoch nicht die Haltbarkeit jedes Ereignisses im asynchronen Modus garantieren.

# IPC:parallel-Warteereignisse
<a name="apg-ipc-parallel"></a>

Die folgenden `IPC:parallel wait events` weisen darauf hin, dass eine Sitzung auf die Interprozesskommunikation in Bezug auf parallele Abfrageausführungen wartet.
+ `IPC:BgWorkerStartup` - Ein Prozess wartet darauf, dass ein paralleler Worker-Prozess seine Startsequenz abgeschlossen hat. Dies geschieht, wenn Worker für eine parallele Abfrageausführung initialisiert werden.
+ `IPC:BgWorkerShutdown` - Ein Prozess wartet darauf, dass ein paralleler Worker-Prozess seine Shutdown-Sequenz abgeschlossen hat. Dies geschieht während der Bereinigungsphase der parallelen Abfrageausführung.
+ `IPC:ExecuteGather` - Ein Prozess wartet darauf, während der Abfrageausführung Daten von parallelen Worker-Prozessen zu empfangen. Dies ist der Fall, wenn der Leader-Prozess Ergebnisse von seinen Workern erfassen muss.
+ `IPC:ParallelFinish` - Ein Prozess wartet darauf, dass parallele Worker ihre Ausführung beenden und ihre Endergebnisse melden. Dies geschieht während der Abschlussphase der parallelen Abfrageausführung.

**Topics**
+ [Unterstützte Engine-Versionen](#apg-ipc-parallel-context-supported)
+ [Kontext](#apg-ipc-parallel-context)
+ [Wahrscheinliche Ursachen für erhöhte Wartezeiten](#apg-ipc-parallel-causes)
+ [Aktionen](#apg-ipc-parallel-actions)

## Unterstützte Engine-Versionen
<a name="apg-ipc-parallel-context-supported"></a>

Diese Warteereignisinformationen werden für alle Versionen von Aurora PostgreSQL unterstützt.

## Kontext
<a name="apg-ipc-parallel-context"></a>

Bei der parallelen Abfrageausführung in PostgreSQL arbeiten mehrere Prozesse zusammen, um eine einzelne Abfrage zu verarbeiten. Wenn festgestellt wird, dass eine Abfrage für die Parallelisierung geeignet ist, koordiniert ein Leader-Prozess die Arbeit mit einem oder mehreren parallelen Worker-Prozessen je nach `max_parallel_workers_per_gather`-Parametereinstellung. Der Leader-Prozess teilt die Arbeit auf die einzelnen Worker auf und jeder Worker verarbeitet unabhängig seinen Teil der Daten. Die Ergebnisse werden dann an den Leader-Prozess zurückgemeldet.

**Anmerkung**  
Jeder parallele Worker fungiert als separater Prozess mit Ressourcenanforderungen, die einer vollständigen Benutzersitzung ähneln. Das bedeutet, dass eine parallel Abfrage mit 4 Workern bis zu fünfmal so viele Ressourcen (CPU, Arbeitsspeicher, I/O Bandbreite) verbrauchen kann wie eine nicht parallele Abfrage, da sowohl der Leader-Prozess als auch jeder Worker-Prozess ihre eigenen Ressourcenzuweisungen beibehalten. So werden beispielsweise Einstellungen wie `work_mem` individuell auf jeden Worker angewendet, wodurch sich die gesamte Speicherbelegung aller Prozesse vervielfachen kann.

Die Architektur einer parallelen Abfrage besteht aus drei Hauptkomponenten:
+ Leader-Prozess: Dies ist der Hauptprozess, der den Parallelbetrieb einleitet, den Workload aufteilt und die Abstimmung mit den Worker-Prozessen vornimmt.
+ Worker-Prozesse: Dies sind Hintergrundprozesse, die Teile der Abfrage parallel ausführen.
+ Gather/Gather merge: Dies sind Operationen, die Ergebnisse mehrerer Worker-Prozesse kombinieren und zurück an den Leader melden.

Während der parallelen Ausführung müssen Prozesse über Mechanismen der Interprozesskommunikation (IPC) miteinander kommunizieren. Diese IPC-Warteereignisse treten in verschiedenen Phasen auf:
+ Worker-Start: wenn parallele Worker initialisiert werden
+ Datenaustausch: wenn Worker Daten verarbeiten und Ergebnisse an den Leader senden
+ Worker-Shutdown: wenn die parallele Ausführung abgeschlossen ist und Worker beendet werden
+ Synchronisierungspunkte: wenn Prozesse koordiniert werden oder darauf warten müssen, dass andere Prozesse ihre Aufgaben abschließen

Das Kennen dieser Warteereignisse ist entscheidend für die Diagnose von Leistungsproblemen im Zusammenhang mit der parallelen Abfrageausführung, insbesondere in Umgebungen mit hoher Nichtsequentialität, in denen mehrere parallele Abfragen gleichzeitig ausgeführt werden.

## Wahrscheinliche Ursachen für erhöhte Wartezeiten
<a name="apg-ipc-parallel-causes"></a>

Verschiedene Faktoren können zu einer Zunahme parallel-bezogener IPC-Warteereignisse beitragen:

**Hohe Nichtsequentialität paralleler Abfragen**  
Wenn viele parallele Abfragen gleichzeitig ausgeführt werden, kann dies zu Ressourcenkonflikten und längeren Wartezeiten für IPC-Operationen führen. Dies ist besonders häufig bei Systemen mit hohem Transaktionsvolumen oder analytischen Workloads der Fall.

**Suboptimale Pläne für parallele Abfragen**  
Wenn der Abfrageplaner ineffiziente Parallelisierungspläne auswählt, kann dies zu unnötiger Parallelisierung oder schlechter Arbeitsverteilung unter den Workern führen. Dies kann zu erhöhten IPC-Wartezeiten führen, insbesondere bei IPC: - und IPC: ExecuteGather -Ereignissen. ParallelFinish Diese Planungsprobleme sind häufig auf veraltete Statistiken und unübersichtliche Zahlen zurückzuführen. table/index 

**Häufiges Starten und Herunterfahren paralleler Worker**  
Kurzlebige Abfragen, die häufig parallele Worker initiieren und beenden, können zu einer Zunahme von `IPC:BgWorkerStartup`- und `IPC:BgWorkerShutdown`-Ereignissen führen. Dies kommt oftmals bei OLTP-Workloads mit vielen kleinen, parallelisierbaren Abfragen vor.

**Einschränkungen für Ressourcen**  
Eine begrenzte CPU, ein begrenzter Arbeitsspeicher oder eine begrenzte I/O Kapazität können zu Engpässen bei der parallel Ausführung führen, was zu längeren Wartezeiten bei allen IPC-Ereignissen führt. Wenn beispielsweise die CPU ausgelastet ist, kann es länger dauern, bis Worker-Prozesse starten oder ihren Teil der Arbeit erledigen.

**Komplexe Abfragestrukturen**  
Abfragen mit mehreren Parallelitätsebenen (z. B. parallele Joins, auf die parallele Aggregationen folgen) können zu komplexeren IPC-Mustern und potenziell längeren Wartezeiten führen, insbesondere bei `IPC:ExecuteGather`-Ereignissen.

**Große Ergebnismengen**  
Abfragen, die große Ergebnismengen liefern, können zu längeren `IPC:ExecuteGather`-Wartezeiten führen, da der Leader-Prozess mehr Zeit damit verbringt, Ergebnisse von Worker-Prozessen zu erfassen und zu verarbeiten.

Das Kennen dieser Faktoren kann bei der Diagnose und Behebung von Leistungsproblemen im Zusammenhang mit der parallelen Abfrageausführung in Aurora PostgreSQL hilfreich sein.

## Aktionen
<a name="apg-ipc-parallel-actions"></a>

Wenn Sie Wartezeiten im Zusammenhang mit parallelen Abfragen bemerken, bedeutet dies in der Regel, dass ein Backend-Prozess parallele Worker-Prozesse koordiniert oder auf diese wartet. Diese Wartezeiten treten häufig bei der Ausführung von Parallelisierungsplänen auf. Sie können die Auswirkungen dieser Wartezeiten untersuchen und abmildern, indem Sie die Verwendung paralleler Worker überwachen, die Parametereinstellungen überprüfen und die Abfrageausführung und Ressourcenzuweisung optimieren.

**Topics**
+ [Analysieren von Abfrageplänen in Bezug auf ineffiziente Parallelität](#apg-ipc-parallel-analyze-plans)
+ [Überwachen der Verwendung paralleler Abfragen](#apg-ipc-parallel-monitor)
+ [Überprüfen und Anpassen von Einstellungen für parallele Abfragen](#apg-ipc-parallel-adjust-settings)
+ [Optimieren der Ressourcenzuweisung](#apg-ipc-parallel-optimize-resources)
+ [Untersuchen der Verbindungsverwaltung](#apg-ipc-parallel-connection-management)
+ [Überprüfen und Optimieren von Wartungsvorgängen](#apg-ipc-parallel-maintenance)
+ [Verwenden der Abfrageplanverwaltung (QPM)](#apg-ipc-parallel-query-plan-management)

### Analysieren von Abfrageplänen in Bezug auf ineffiziente Parallelität
<a name="apg-ipc-parallel-analyze-plans"></a>

Die parallele Ausführung von Abfragen kann häufig zu Systeminstabilität, CPU-Spitzen und unvorhersehbaren Leistungsschwankungen bei Abfragen führen. Es ist wichtig, gründlich zu analysieren, ob eine Parallelität Ihrem spezifischen Workload tatsächlich zugutekommt. Verwenden Sie EXPLAIN ANALYZE, um Pläne für die parallele Ausführung von Abfragen zu überprüfen.

Deaktivieren Sie zur Ermittlung der Planeffizienz vorübergehend die Parallelität auf Sitzungsebene:

```
SET max_parallel_workers_per_gather = 0;
EXPLAIN ANALYZE <your_query>;
```

Aktivieren Sie zwecks Vergleich wieder die Parallelität:

```
RESET max_parallel_workers_per_gather;
EXPLAIN ANALYZE <your_query>;
```

Wenn die Deaktivierung der Parallelität zu besseren oder konsistenteren Ergebnissen führt, sollten Sie erwägen, sie für bestimmte Abfragen auf Sitzungsebene mithilfe von SET-Befehlen zu deaktivieren. Um eine umfassendere Wirkung zu erzielen, können Sie die Parallelität auf Instance-Ebene deaktivieren, indem Sie die entsprechenden Parameter in Ihrem Cluster oder Ihrer Instance-Parametergruppe anpassen. Weitere Informationen finden Sie unter [Amazon-Aurora-PostgreSQL-Parameter](AuroraPostgreSQL.Reference.ParameterGroups.md).

### Überwachen der Verwendung paralleler Abfragen
<a name="apg-ipc-parallel-monitor"></a>

Verwenden Sie die folgenden Abfragen, um einen Einblick in die Aktivität und Kapazität paralleler Abfragen zu gewinnen:

Überprüfen Sie die aktiven, parallelen Worker-Prozesse:

```
SELECT
    COUNT(*)
FROM
    pg_stat_activity
WHERE
    backend_type = 'parallel worker';
```

Diese Abfrage zeigt die Anzahl der aktiven, parallelen Worker-Prozesse. Ein hoher Wert kann darauf hinweisen, dass Ihr „max\$1parallel\$1workers“ mit einem hohen Wert konfiguriert ist. Erwägen Sie, diesen zu verringern.

Überprüfen Sie gleichzeitige parallele Abfragen:

```
SELECT
    COUNT(DISTINCT leader_pid)
FROM
    pg_stat_activity
WHERE
    leader_pid IS NOT NULL;
```

Diese Abfrage gibt die Anzahl der verschiedenen Leader-Prozesse zurück, durch die parallele Abfragen gestartet wurden. Eine hohe Zahl weist hier darauf hin, dass mehrere Sitzungen gleichzeitig parallele Abfragen ausführen, was die CPU- und Speicherauslastung erhöhen kann.

### Überprüfen und Anpassen von Einstellungen für parallele Abfragen
<a name="apg-ipc-parallel-adjust-settings"></a>

Überprüfen Sie die folgenden Parameter, um sicherzustellen, dass sie Ihrem Workload entsprechen:
+ `max_parallel_workers`: Gesamtzahl der parallelen Worker in allen Sitzungen
+ `max_parallel_workers_per_gather`: Max. Worker-Anzahl pro Abfrage

Bei OLAP-Workloads kann eine Erhöhung dieser Werte die Leistung verbessern. Für OLTP-Workloads werden im Allgemeinen niedrigere Werte bevorzugt.

```
SHOW max_parallel_workers;
SHOW max_parallel_workers_per_gather;
```

### Optimieren der Ressourcenzuweisung
<a name="apg-ipc-parallel-optimize-resources"></a>

Überwachen Sie die CPU-Auslastung und erwägen Sie, die Anzahl von v CPUs anzupassen, wenn sie konstant hoch ist und Ihre Anwendung von parallel Abfragen profitiert. Stellen Sie sicher, dass ausreichend Speicher für parallele Operationen verfügbar ist.
+ Ermitteln Sie anhand von Performance Insights, ob das System CPU-gebunden ist.
+ Jeder parallele Worker verwendet seinen eigenen `work_mem`. Stellen Sie sicher, dass die Gesamtspeichernutzung innerhalb der Instance-Grenzen liegt.

Parallele Abfragen können erheblich mehr Ressourcen verbrauchen als nicht parallele, da jeder Worker-Prozess ein vollständig separater Prozess ist, der ungefähr die gleichen Auswirkungen auf das System hat wie eine zusätzliche Benutzersitzung. Dies sollte bei der Auswahl eines Werts für diese Einstellung sowie bei der Konfiguration anderer Einstellungen zur Steuerung der Ressourcennutzung berücksichtigt werden, zum Beispiel `work_mem`. Weitere Informationen finden Sie in der [PostgreSQL-Dokumentation](https://www.postgresql.org/docs/current/runtime-config-resource.html#GUC-WORK-MEM). Ressourcenbegrenzungen, wie `work_mem` werden individuell auf jeden Worker angewendet, das bedeutet, dass die Gesamtauslastung über alle Prozesse hinweg viel höher sein kann, als dies normalerweise für einen einzelnen Prozess der Fall wäre.

Erwägen Sie, v zu erhöhen CPUs oder die Speicherparameter zu optimieren, wenn Ihre Arbeitslast stark parallelisiert ist.

### Untersuchen der Verbindungsverwaltung
<a name="apg-ipc-parallel-connection-management"></a>

Wenn die Verbindung überlastet ist, prüfen Sie Strategien für ein Verbindungspooling der Anwendung. Erwägen Sie die Implementierung von Verbindungspooling auf Anwendungsebene, sofern es nicht bereits verwendet wird.

### Überprüfen und Optimieren von Wartungsvorgängen
<a name="apg-ipc-parallel-maintenance"></a>

Koordinieren Sie die Indexerstellung und andere Wartungsaufgaben, um Ressourcenkonflikte zu vermeiden. Erwägen Sie, diese Vorgänge für Zeiten außerhalb der Spitzenzeiten einzuplanen. Vermeiden Sie es, umfangreiche Wartungsvorgänge (z. B. parallele Indexerstellungen) für Zeiten mit hoher Benutzerabfragelast einzuplanen. Diese Operationen können parallele Worker beanspruchen und die Leistung bei regulären Abfragen negativ beeinträchtigen.

### Verwenden der Abfrageplanverwaltung (QPM)
<a name="apg-ipc-parallel-query-plan-management"></a>

In Amazon Aurora PostgreSQL ist das Abfrageplanverwaltung (QPM)-Feature so ausgelegt, dass die Anpassungsfähigkeit und Stabilität des Plans unabhängig von Änderungen der Datenbankumgebung, die zu einer Regression des Abfrageplans führen könnten, sichergestellt ist. Weitere Informationen finden Sie unter [Übersicht über die Abfrageplanverwaltung in Aurora PostgreSQL](AuroraPostgreSQL.Optimize.overview.md). QPM bietet eine gewisse Kontrolle über den Optimierer. Überprüfen Sie die genehmigten Pläne in QPM, um sicherzustellen, dass sie den aktuellen Parallelitätseinstellungen entsprechen. Aktualisieren oder entfernen Sie veraltete Pläne, die möglicherweise eine suboptimale parallele Ausführung erzwingen.

Sie können die Pläne auch mit pg\$1hint\$1plan korrigieren. Weitere Informationen finden Sie unter [Reparieren von Plänen mit pg\$1hint\$1plan](AuroraPostgreSQL.Optimize.Maintenance.md#AuroraPostgreSQL.Optimize.Maintenance.pg_hint_plan). Sie können mit dem `Parallel`-Hinweis eine parallele Ausführung erzwingen. Weitere Informationen finden Sie in unter [Hints for parallel plans](https://github.com/ossc-db/pg_hint_plan/blob/master/docs/hint_table.md#hints-for-parallel-plans).

# IPC: ProcArrayGroupUpdate
<a name="apg-rpg-ipcprocarraygroup"></a>

Das `IPC:ProcArrayGroupUpdate` Ereignis tritt ein, wenn eine Sitzung darauf wartet, dass der Gruppenleiter den Transaktionsstatus am Ende des Vorgangs aktualisiert. Während PostgreSQL im Allgemeinen Warteereignisse vom Typ IPC mit parallel Abfrageoperationen verknüpft, ist dieses spezielle Wartungsereignis nicht spezifisch für parallel Abfragen.

**Topics**
+ [Unterstützte Engine-Versionen](#apg-rpg-ipcprocarraygroup.supported)
+ [Kontext](#apg-rpg-ipcprocarraygroup.context)
+ [Wahrscheinliche Ursachen für erhöhte Wartezeiten](#apg-rpg-ipcprocarraygroup.causes)
+ [Aktionen](#apg-rpg-ipcprocarraygroup.actions)

## Unterstützte Engine-Versionen
<a name="apg-rpg-ipcprocarraygroup.supported"></a>

Diese Warteereignisinformationen werden für alle Versionen von Aurora PostgreSQL unterstützt.

## Kontext
<a name="apg-rpg-ipcprocarraygroup.context"></a>

**Das Prozessarray verstehen** — Das Prozessarray (proc) ist eine gemeinsam genutzte Speicherstruktur in PostgreSQL. Es enthält Informationen über alle laufenden Prozesse, einschließlich Transaktionsdetails. Während des Abschlusses der Transaktion (`COMMIT`oder`ROLLBACK`) ProcArray muss die Datei aktualisiert werden, um die Änderung widerzuspiegeln und die TransactionID aus dem Array zu löschen. Die Sitzung, die versucht, ihre Transaktion abzuschließen, muss eine exklusive Sperre für erhalten. ProcArray Dadurch wird verhindert, dass andere Prozesse gemeinsame oder exklusive Sperren für die Datei erhalten.

**Mechanismus zur Gruppenaktualisierung** — Wenn ein Back-End-Prozess bei der Ausführung eines COMMIT- oder ROLLBACK-Vorgangs ProcArrayLock im exklusiven Modus keinen Wert abrufen kann, aktualisiert er ein spezielles Feld mit dem Namen. ProcArrayGroupMember Dadurch wird die Transaktion der Liste der Sitzungen hinzugefügt, die beendet werden sollen. Dieser Backend-Prozess schläft dann, und die Zeit, in der er sich befindet, wird als ProcArrayGroupUpdate Warteereignis instrumentiert. Der erste Prozess im ProcArray procArrayGroup With-Member, der als Leader-Prozess bezeichnet wird, erfolgt ProcArrayLock im exklusiven Modus. Anschließend wird die Liste der Prozesse gelöscht, die auf das Löschen der GruppentransactionID warten. Sobald dieser Vorgang abgeschlossen ist, gibt der Leader alle Prozesse in dieser Liste frei ProcArrayLock und aktiviert sie, sodass sie darüber informiert werden, dass ihre Transaktion abgeschlossen ist.

## Wahrscheinliche Ursachen für erhöhte Wartezeiten
<a name="apg-rpg-ipcprocarraygroup.causes"></a>

Je mehr Prozesse ausgeführt werden, desto länger hält ein Leader an einem procArrayLock im exklusiven Modus fest. Je mehr Schreibtransaktionen in einem Gruppenaktualisierungsszenario enden, was zu einer potenziellen Anhäufung von Prozessen führt, die auf das Warteereignis `ProcArrayGroupUpdate` warten. In der Top-SQL-Ansicht von Database Insights werden Sie sehen, dass COMMIT die Anweisung ist, bei der der Großteil dieses Warteereignisses auftritt. Dies ist zu erwarten, erfordert jedoch eine eingehendere Untersuchung der spezifischen Schreib-SQL, die gerade ausgeführt wird, um festzustellen, welche geeigneten Maßnahmen zu ergreifen sind.

## Aktionen
<a name="apg-rpg-ipcprocarraygroup.actions"></a>

Abhängig von den Ursachen Ihres Warteereignisses empfehlen wir verschiedene Aktionen. Identifizieren Sie `IPC:ProcArrayGroupUpdate` Ereignisse mithilfe von Amazon RDS Performance Insights oder durch Abfragen der PostgreSQL-Systemansicht. `pg_stat_activity`

**Topics**
+ [Überwachung von Transaktions-, Commit- und Rollback-Vorgängen](#apg-rpg-ipcprocarraygroup.actions.monitor)
+ [Reduzierung der Parallelität](#apg-rpg-ipcprocarraygroup.actions.concurrency)
+ [Implementierung von Verbindungspooling](#apg-rpg-ipcprocarraygroup.actions.pooling)

### Überwachung von Transaktions-, Commit- und Rollback-Vorgängen
<a name="apg-rpg-ipcprocarraygroup.actions.monitor"></a>

**Überwachen Sie Commits und Rollbacks** — Eine erhöhte Anzahl von Commits und Rollbacks kann zu einem erhöhten Druck auf die führen. ProcArray Wenn beispielsweise eine SQL-Anweisung aufgrund einer erhöhten Anzahl von Verletzungen doppelter Schlüssel zu scheitern beginnt, kann es zu einer Zunahme von Rollbacks kommen, was wiederum zu Konflikten und zu einer Überlastung der Tabellen führen kann. ProcArray

Amazon RDS Database Insights stellt die PostgreSQL-Metriken `xact_rollback` bereit `xact_commit` und berichtet über die Anzahl der Commits und Rollbacks pro Sekunde.

### Reduzierung der Parallelität
<a name="apg-rpg-ipcprocarraygroup.actions.concurrency"></a>

**Batch-Transaktionen** — Wenn möglich, sollten Operationen in Einzeltransaktionen gebündelt werden, um die Anzahl der Operationen zu reduzieren commit/rollback .

**Parallelität einschränken** — Reduzieren Sie die Anzahl der gleichzeitig aktiven Transaktionen, um Sperrkonflikte bei der zu vermeiden. ProcArray Es sind zwar einige Tests erforderlich, aber eine Reduzierung der Gesamtzahl gleichzeitiger Verbindungen kann Konflikte reduzieren und den Durchsatz aufrechterhalten.

### Implementierung von Verbindungspooling
<a name="apg-rpg-ipcprocarraygroup.actions.pooling"></a>

**Verbindungspooling-Lösungen** — Verwenden Sie Verbindungspooling, um Datenbankverbindungen effizient zu verwalten und so die Gesamtzahl der Backends und damit die Arbeitslast auf dem zu reduzieren. ProcArray Es sind zwar einige Tests erforderlich, aber die Reduzierung der Gesamtzahl gleichzeitiger Verbindungen kann Konflikte reduzieren und den Durchsatz aufrechterhalten.

Weitere Informationen finden Sie unter [Verbindungspooling für Aurora PostgreSQL](https://docs.aws.amazon.com/AmazonRDS/latest/AuroraUserGuide/AuroraPostgreSQL.BestPractices.connection_pooling.html).

**Reduzieren Sie Verbindungsstürme** — In ähnlicher Weise führt ein Muster, bei dem häufig Verbindungen hergestellt und beendet werden, zu zusätzlichem Druck auf die. ProcArray Durch die Reduzierung dieses Musters werden Konflikte insgesamt reduziert.

# Lock:advisory
<a name="apg-waits.lockadvisory"></a>

Das `Lock:advisory`-Ereignis tritt auf, wenn eine PostgreSQL-Anwendung eine Sperre verwendet, um Aktivitäten über mehrere Sitzungen hinweg zu koordinieren.

**Topics**
+ [Relevante Engine-Versionen](#apg-waits.lockadvisory.context.supported)
+ [Kontext](#apg-waits.lockadvisory.context)
+ [Ursachen](#apg-waits.lockadvisory.causes)
+ [Aktionen](#apg-waits.lockadvisory.actions)

## Relevante Engine-Versionen
<a name="apg-waits.lockadvisory.context.supported"></a>

Diese Warteereignisinformationen sind für Aurora PostgreSQL Versionen 9.6 und höher relevant.

## Kontext
<a name="apg-waits.lockadvisory.context"></a>

PostgreSQL-Beratungssperren sind Anwendungsebene, kooperative Sperren werden explizit durch den Anwendungscode des Benutzers gesperrt und freigeschaltet. Eine Anwendung kann PostgreSQL-Beratungssperren verwenden, um Aktivitäten über mehrere Sitzungen hinweg zu koordinieren. Im Gegensatz zu normalen Sperren auf Objekt- oder Zeilenebene hat die Anwendung die volle Kontrolle über die Lebensdauer des Schlosses. Weitere Informationen finden Sie unter [Empfohlene Sperren](https://www.postgresql.org/docs/12/explicit-locking.html#ADVISORY-LOCKS) in der PostgreSQL-Dokumentation.

Beratungssperren können vor dem Ende einer Transaktion freigegeben werden oder von einer Sitzung über Transaktionen hinweg gehalten werden. Dies gilt nicht für implizite, vom System erzwungene Sperren, wie z. B. eine zugriffsexklusive Sperre für eine Tabelle, die von einer `CREATE INDEX`-Anweisung abgerufen wird.

Eine Beschreibung der Funktionen zum Erlangen (Sperren) und Freigeben (Entsperren) von Advisory Locks finden Sie unter [Advisory Lock Functions](https://www.postgresql.org/docs/current/functions-admin.html#FUNCTIONS-ADVISORY-LOCKS) in der PostgreSQL-Dokumentation.

Advisory Locks werden zusätzlich zum regulären PostgreSQL-Locking-System implementiert und sind in der `pg_locks`-Systemansicht sichtbar.

## Ursachen
<a name="apg-waits.lockadvisory.causes"></a>

Dieser Schlosstyp wird ausschließlich von einer Anwendung gesteuert, die ihn explizit verwendet. Beratungssperren, die für jede Zeile als Teil einer Abfrage erworben werden, können zu einem Anstieg der Sperren oder zu einem langfristigen Aufbau führen.

Diese Effekte treten auf, wenn die Abfrage so ausgeführt wird, dass Sperren für mehr Zeilen erwirbt, als von der Abfrage zurückgegeben werden. Die Anwendung muss schließlich jede Sperre freigeben, aber wenn Sperren für Zeilen erworben werden, die nicht zurückgegeben werden, kann die Anwendung nicht alle Sperren finden.

Das folgende Beispiel stammt aus [Empfohlene Sperren](https://www.postgresql.org/docs/12/explicit-locking.html#ADVISORY-LOCKS) in der PostgreSQL-Dokumentation.

```
SELECT pg_advisory_lock(id) FROM foo WHERE id > 12345 LIMIT 100;
```

In diesem Beispiel kann die `LIMIT`-Klausel die Ausgabe der Abfrage nur stoppen, nachdem die Zeilen bereits intern ausgewählt und ihre ID-Werte gesperrt wurden. Dies kann plötzlich passieren, wenn ein wachsendes Datenvolumen dazu führt, dass der Planer einen anderen Ausführungsplan auswählt, der während der Entwicklung nicht getestet wurde. Der Aufbau erfolgt in diesem Fall, weil die Anwendung `pg_advisory_unlock` explizit für jeden gesperrten ID-Wert aufruft. In diesem Fall kann es jedoch nicht die Sperren finden, die für Zeilen erworben wurden, die nicht zurückgegeben wurden. Da die Sperren auf Sitzungsebene erworben werden, werden sie am Ende der Transaktion nicht automatisch freigegeben.

Eine weitere mögliche Ursache für Spikes bei blockierten Sperrversuchen sind unbeabsichtigte Konflikte. In diesen Konflikten teilen sich nicht verwandte Teile der Anwendung versehentlich denselben Sperren-ID-Raum.

## Aktionen
<a name="apg-waits.lockadvisory.actions"></a>

Überprüfen Sie die Anwendungsnutzung von Beratungssperren und Details, wo und wann im Anwendungsablauf jede Art von Beratungssperre erworben und freigegeben wird.

Stellen Sie fest, ob eine Sitzung zu viele Sperren erwirbt oder eine lang andauernde Sitzung keine Sperren früh genug freigibt, was zu einem langsamen Aufbau von Sperren führt. Sie können einen langsamen Aufbau von Sperren auf Sitzungsebene korrigieren, indem Sie die Sitzung mit `pg_terminate_backend(pid)` beenden. 

Ein Client, der auf eine Beratungssperre wartet, erscheint in `pg_stat_activity` mit `wait_event_type=Lock` und `wait_event=advisory`. Sie können bestimmte Sperrwerte erhalten, indem Sie die `pg_locks`-Systemansicht nach demselben `pid` abfragen und nach `locktype=advisory` und `granted=f` suchen.

Sie können dann die blockierende Sitzung identifizieren, indem Sie `pg_locks` nach derselben beratenden Sperre mit `granted=t` abfragen, wie im folgenden Beispiel gezeigt.

```
SELECT blocked_locks.pid AS blocked_pid,
         blocking_locks.pid AS blocking_pid,
         blocked_activity.usename AS blocked_user,
         blocking_activity.usename AS blocking_user,
         now() - blocked_activity.xact_start AS blocked_transaction_duration,
         now() - blocking_activity.xact_start AS blocking_transaction_duration,
         concat(blocked_activity.wait_event_type,':',blocked_activity.wait_event) AS blocked_wait_event,
         concat(blocking_activity.wait_event_type,':',blocking_activity.wait_event) AS blocking_wait_event,
         blocked_activity.state AS blocked_state,
         blocking_activity.state AS blocking_state,
         blocked_locks.locktype AS blocked_locktype,
         blocking_locks.locktype AS blocking_locktype,
         blocked_activity.query AS blocked_statement,
         blocking_activity.query AS blocking_statement
    FROM pg_catalog.pg_locks blocked_locks
    JOIN pg_catalog.pg_stat_activity blocked_activity ON blocked_activity.pid = blocked_locks.pid
    JOIN pg_catalog.pg_locks blocking_locks
        ON blocking_locks.locktype = blocked_locks.locktype
        AND blocking_locks.DATABASE IS NOT DISTINCT FROM blocked_locks.DATABASE
        AND blocking_locks.relation IS NOT DISTINCT FROM blocked_locks.relation
        AND blocking_locks.page IS NOT DISTINCT FROM blocked_locks.page
        AND blocking_locks.tuple IS NOT DISTINCT FROM blocked_locks.tuple
        AND blocking_locks.virtualxid IS NOT DISTINCT FROM blocked_locks.virtualxid
        AND blocking_locks.transactionid IS NOT DISTINCT FROM blocked_locks.transactionid
        AND blocking_locks.classid IS NOT DISTINCT FROM blocked_locks.classid
        AND blocking_locks.objid IS NOT DISTINCT FROM blocked_locks.objid
        AND blocking_locks.objsubid IS NOT DISTINCT FROM blocked_locks.objsubid
        AND blocking_locks.pid != blocked_locks.pid
    JOIN pg_catalog.pg_stat_activity blocking_activity ON blocking_activity.pid = blocking_locks.pid
    WHERE NOT blocked_locks.GRANTED;
```

Alle API-Funktionen für beratende Sperren haben zwei Sätze von Argumenten, entweder ein `bigint`-Argument oder zwei `integer`-Argumente:
+ Bei den API-Funktionen mit einem `bigint`-Argument befinden sich die oberen 32 Bit in `pg_locks.classid` und die unteren 32 Bit in `pg_locks.objid`.
+ Bei den API-Funktionen mit zwei `integer`-Argumenten ist das erste Argument `pg_locks.classid` und das zweite Argument ist `pg_locks.objid`.

Der `pg_locks.objsubid`-Wert gibt an, welches API-Formular verwendet wurde: `1` bedeutet ein `bigint`-Argument; `2` bedeutet zwei `integer`-Argumente.

# Lock:extend
<a name="apg-waits.lockextend"></a>

Das `Lock:extend`-Ereignis tritt ein, wenn ein Backend-Prozess darauf wartet, eine Beziehung zu sperren, um sie zu erweitern, während ein anderer Prozess diese Beziehung für denselben Zweck gesperrt hat.

**Topics**
+ [Unterstützte Engine-Versionen](#apg-waits.lockextend.context.supported)
+ [Kontext](#apg-waits.lockextend.context)
+ [Wahrscheinliche Ursachen für erhöhte Wartezeiten](#apg-waits.lockextend.causes)
+ [Aktionen](#apg-waits.lockextend.actions)

## Unterstützte Engine-Versionen
<a name="apg-waits.lockextend.context.supported"></a>

Diese Warteereignisinformationen werden für alle Versionen von Aurora PostgreSQL unterstützt.

## Kontext
<a name="apg-waits.lockextend.context"></a>

Das Ereignis `Lock:extend` zeigt an, dass ein Backend-Prozess darauf wartet, eine Beziehung zu erweitern, für die ein anderer Backend-Prozess eine Sperre hält, während er diese Beziehung erweitert. Da jeweils nur ein Prozess eine Beziehung erweitern kann, generiert das System ein `Lock:extend`-Warteereignis. `INSERT`-, `COPY`- und `UPDATE`-Vorgänge können dieses Ereignis erzeugen.

## Wahrscheinliche Ursachen für erhöhte Wartezeiten
<a name="apg-waits.lockextend.causes"></a>

Wenn das `Lock:extend`-Ereignis mehr als normal auftritt, was möglicherweise auf ein Leistungsproblem hinweist, sind die folgenden typischen Ursachen:

**Anstieg der gleichzeitigen Einfügungen oder Aktualisierungen derselben Tabelle **  
Es kann zu einer Zunahme der Anzahl gleichzeitiger Sitzungen mit Abfragen kommen, die in dieselbe Tabelle einfügen oder aktualisieren.

**Unzureichende Netzwerkbandbreite**  
Die Netzwerkbandbreite auf der DB-Instance reicht möglicherweise nicht aus, um die Speicherkommunikationsanforderungen der aktuellen Workload zu gewährleisten. Dies kann zu einer Speicherlatenz führen, die zu einem Anstieg der `Lock:extend`-Ereignisse führt.

## Aktionen
<a name="apg-waits.lockextend.actions"></a>

Abhängig von den Ursachen Ihres Warteereignisses empfehlen wir verschiedene Aktionen.

**Topics**
+ [Reduzieren Sie gleichzeitige Einfügungen und Aktualisierungen auf dieselbe Beziehung](#apg-waits.lockextend.actions.action1)
+ [Erhöhung der Netzwerkbandbreite](#apg-waits.lockextend.actions.increase-network-bandwidth)

### Reduzieren Sie gleichzeitige Einfügungen und Aktualisierungen auf dieselbe Beziehung
<a name="apg-waits.lockextend.actions.action1"></a>

Stellen Sie zunächst fest, ob die `tup_inserted`- und `tup_updated`-Metriken und damit auch dieses Warteereignis gestiegen ist. Überprüfen Sie in diesem Fall, welche Beziehungen für Einfüge- und Aktualisierungsvorgänge in hohem Streit stehen. Um dies zu ermitteln, fragen Sie die `pg_stat_all_tables`-Ansicht nach den Werten in den `n_tup_ins`- und `n_tup_upd`-Feldern ab. Informationen zur Ansicht `pg_stat_all_tables` finden Sie unter [pg\$1stat\$1all\$1tables](https://www.postgresql.org/docs/13/monitoring-stats.html#MONITORING-PG-STAT-ALL-TABLES-VIEW) in der PostgreSQL-Dokumentation. 

Um weitere Informationen über das Blockieren und blockierte Abfragen zu erhalten, fragen Sie `pg_stat_activity` wie im folgenden Beispiel ab:

```
SELECT
    blocked.pid,
    blocked.usename,
    blocked.query,
    blocking.pid AS blocking_id,
    blocking.query AS blocking_query,
    blocking.wait_event AS blocking_wait_event,
    blocking.wait_event_type AS blocking_wait_event_type
FROM pg_stat_activity AS blocked
JOIN pg_stat_activity AS blocking ON blocking.pid = ANY(pg_blocking_pids(blocked.pid))
where
blocked.wait_event = 'extend'
and blocked.wait_event_type = 'Lock';
 
   pid  | usename  |            query             | blocking_id |                         blocking_query                           | blocking_wait_event | blocking_wait_event_type
  ------+----------+------------------------------+-------------+------------------------------------------------------------------+---------------------+--------------------------
   7143 |  myuser  | insert into tab1 values (1); |        4600 | INSERT INTO tab1 (a) SELECT s FROM generate_series(1,1000000) s; | DataFileExtend      | IO
```

Nachdem Sie Beziehungen identifiziert haben, die zur Erhöhung von `Lock:extend`-Ereignissen beitragen, verwenden Sie die folgenden Techniken, um die Konflikte zu reduzieren:
+ Finden Sie heraus, ob Sie Partitionierung verwenden können, um die Konflikte für dieselbe Tabelle zu reduzieren. Das Trennen eingefügter oder aktualisierter Tupel in verschiedene Partitionen kann die Konflikte verringern. Weitere Informationen zur Partitionierung finden Sie unter [Verwalten von PostgreSQL-Partitionen mit der Erweiterung pg\$1partman](PostgreSQL_Partitions.md).
+ Wenn das Warteereignis hauptsächlich auf Aktualisierungsaktivitäten zurückzuführen ist, sollten Sie erwägen, den Füllfaktor-Wert der Beziehung zu reduzieren. Dies kann Anfragen nach neuen Blöcken während des Updates reduzieren. Der Füllfaktor ist ein Speicherparameter für eine Tabelle, der den maximalen Speicherplatz zum Packen einer Tabellenseite bestimmt. Es wird als Prozentsatz des gesamten Speicherplatzes für eine Seite ausgedrückt. Weitere Informationen zum Parameter fillfactor finden Sie unter [CREATE TABLE](https://www.postgresql.org/docs/13/sql-createtable.html) in der PostgreSQL-Dokumentation. 
**Wichtig**  
Wir empfehlen dringend, Ihr System zu testen, wenn Sie den Füllfaktor ändern, da sich die Änderung dieses Wertes je nach Workload negativ auf die Leistung auswirken kann.

### Erhöhung der Netzwerkbandbreite
<a name="apg-waits.lockextend.actions.increase-network-bandwidth"></a>

Um zu sehen, ob die Schreiblatenz zunimmt, überprüfen Sie die `WriteLatency`-Metrik in CloudWatch. Wenn ja, verwenden Sie die Amazon CloudWatch-Metriken von `WriteThroughput` und `ReadThroughput`, um den speicherbezogenen Datenverkehr auf dem DB-Cluster zu überwachen. Diese Metriken können Ihnen helfen festzustellen, ob die Netzwerkbandbreite für die Speicheraktivität Ihrer Workload ausreicht.

Wenn Ihre Netzwerkbandbreite nicht ausreicht, erhöhen Sie sie. Wenn Ihre DB-Instance die Grenzen der Netzwerkbandbreite erreicht, besteht die einzige Möglichkeit, die Bandbreite zu erhöhen, darin, die Größe Ihrer DB-Instance zu erhöhen.

Weitere Informationen zu CloudWatch-Metriken finden Sie unter [CloudWatch Amazon-Metriken für Amazon Aurora](Aurora.AuroraMonitoring.Metrics.md). Informationen zur Netzwerkleistung für jede DB-Instance-Klasse finden Sie unter [Hardwarespezifikationen für DB-Instance-Klassen für Aurora](Concepts.DBInstanceClass.Summary.md).

# Lock:Relation
<a name="apg-waits.lockrelation"></a>

Das `Lock:Relation`-Ereignis tritt ein, wenn eine Abfrage darauf wartet, eine Sperre für eine Tabelle oder Sicht (Relation) zu erhalten, die derzeit von einer anderen Transaktion gesperrt ist.

**Topics**
+ [Unterstützte Engine-Versionen](#apg-waits.lockrelation.context.supported)
+ [Kontext](#apg-waits.lockrelation.context)
+ [Wahrscheinliche Ursachen für erhöhte Wartezeiten](#apg-waits.lockrelation.causes)
+ [Aktionen](#apg-waits.lockrelation.actions)

## Unterstützte Engine-Versionen
<a name="apg-waits.lockrelation.context.supported"></a>

Diese Warteereignisinformationen werden für alle Versionen von Aurora PostgreSQL unterstützt.

## Kontext
<a name="apg-waits.lockrelation.context"></a>

Die meisten PostgreSQL-Befehle verwenden implizit Sperren, um den gleichzeitigen Zugriff auf Daten in Tabellen zu steuern. Sie können diese Sperren auch explizit mit dem `LOCK`-Befehl in Ihrem Anwendungscode verwenden. Viele Sperrmodi sind nicht miteinander kompatibel und können Transaktionen blockieren, wenn sie versuchen, auf dasselbe Objekt zuzugreifen. In diesem Fall generiert Aurora PostgreSQL ein `Lock:Relation`-Ereignis. Einige gängige Beispiele sind die folgenden:
+ Exklusive Sperren wie `ACCESS EXCLUSIVE` können alle gleichzeitigen Zugriffe blockieren. Vorgänge in der Datendefinitionssprache (DDL) wie `DROP TABLE`, `TRUNCATE`, `VACUUM FULL` und `CLUSTER` erwerben implizit `ACCESS EXCLUSIVE`-Sperren. `ACCESS EXCLUSIVE` ist auch der Standardsperrmodus für `LOCK TABLE`-Anweisungen, die keinen Modus explizit angeben.
+ Die Verwendung von `CREATE INDEX (without CONCURRENT)` für eine Tabelle steht in Konflikt mit den DML-Anweisungen `UPDATE`, `DELETE` und `INSERT`, die `ROW EXCLUSIVE`-Sperren anfordern.

Weitere Informationen zu Sperren auf Tabellenebene und widersprüchlichen Sperrmodi finden Sie unter [Explizite Sperren](https://www.postgresql.org/docs/13/explicit-locking.html) in der PostgreSQL-Dokumentation.

Blockieren von Abfragen und Transaktionen entsperren in der Regel auf eine der folgenden Arten:
+ Blockierende Abfrage — Die Anwendung kann die Abfrage abbrechen oder der Benutzer kann den Prozess beenden. Die Engine kann die Abfrage auch aufgrund des Statement-Timeouts einer Sitzung oder eines Deadlock-Erkennungsmechanismus zum Ende zwingen.
+ Blockieren einer Transaktion – Eine Transaktion stoppt die Blockierung, wenn sie eine `ROLLBACK`- oder `COMMIT`-Anweisung ausführt. Rollbacks erfolgen auch automatisch, wenn Sitzungen von einem Client oder durch Netzwerkprobleme getrennt oder beendet werden. Sitzungen können beendet werden, wenn das Datenbank-Engine heruntergefahren wird, wenn das System keinen Arbeitsspeicher mehr hat usw.

## Wahrscheinliche Ursachen für erhöhte Wartezeiten
<a name="apg-waits.lockrelation.causes"></a>

Wenn das `Lock:Relation`-Ereignis häufiger als normal auftritt, kann dies auf ein Leistungsproblem hinweisen. Zu den typischen Ursachen zählen auch die Folgenden:

**Gleichzeitige Sitzungen mit widersprüchlichen Tabellensperren erhöht**  
Es kann zu einer Zunahme der Anzahl gleichzeitiger Sitzungen mit Abfragen kommen, die dieselbe Tabelle mit widersprüchlichen Sperrmodi sperren.

**Wartungsvorgänge**  
Zustandswartungsvorgänge wie `VACUUM` und `ANALYZE` können die Anzahl widersprüchlicher Sperren erheblich erhöhen. `VACUUM FULL` erhält eine `ACCESS EXCLUSIVE`-Sperre und `ANALYZE` erhält eine `SHARE UPDATE EXCLUSIVE`-Sperre. Beide Arten von Sperren können ein `Lock:Relation`-Wait-Ereignis verursachen. Wartungsvorgänge für Anwendungsdaten wie das Aktualisieren einer materialisierten Ansicht können auch blockierte Abfragen und Transaktionen erhöhen.

**Sperrt bei Reader-In**  
Es könnte ein Konflikt zwischen den Beziehungssperren bestehen, die vom Writer und den Readern gehalten werden. Derzeit werden nur `ACCESS EXCLUSIVE`-Beziehungssperren auf Reader-Instances repliziert. Allerdings gerät die `ACCESS EXCLUSIVE`-Beziehungssperre in Konflikt mit jeder `ACCESS SHARE`-Beziehungssperre, die vom Reader gehalten wird. Dies kann zu einer Erhöhung der Warteereignisse für die Sperrbeziehung des Readers führen. 

## Aktionen
<a name="apg-waits.lockrelation.actions"></a>

Abhängig von den Ursachen Ihres Warteereignisses empfehlen wir verschiedene Aktionen.

**Topics**
+ [Reduzieren Sie die Auswirkungen der Blockierung von SQL-Anweisungen](#apg-waits.lockrelation.actions.reduce-blocks)
+ [Minimieren Sie die Auswirkungen von Wartungsvorgängen](#apg-waits.lockrelation.actions.maintenance)
+ [Auf Lesersperren überprüfen](#apg-waits.lockrelation.actions.readerlocks)

### Reduzieren Sie die Auswirkungen der Blockierung von SQL-Anweisungen
<a name="apg-waits.lockrelation.actions.reduce-blocks"></a>

Um die Auswirkungen des Blockierens von SQL-Anweisungen zu reduzieren, ändern Sie Ihren Anwendungscode nach Möglichkeit. Es folgen zwei gängige Techniken zum Reduzieren von Blöcken:
+ Verwenden Sie die Option `NOWAIT` – Einige SQL-Befehle, wie z. B. `SELECT`- und `LOCK`-Anweisungen, unterstützen diese Option. Die `NOWAIT`-Direktive bricht die Sperre anfordernde Abfrage ab, wenn die Sperre nicht sofort erworben werden kann. Diese Technik kann dazu beitragen, zu verhindern, dass eine Blockiersitzung eine Anhäufung blockierter Sitzungen dahinter verursacht.

  Beispiel: Angenommen, Transaktion A wartet auf eine Sperre, die von Transaktion B gehalten wird. Wenn B nun eine Sperre für eine Tabelle anfordert, die durch Transaktion C gesperrt ist, könnte Transaktion A blockiert werden, bis die Transaktion C abgeschlossen ist. Wenn Transaktion B jedoch ein `NOWAIT` verwendet, wenn sie die Sperre für C anfordert, kann sie schnell fehlschlagen und sicherstellen, dass Transaktion A nicht unbegrenzt warten muss.
+ Verwenden Sie `SET lock_timeout` – Legen Sie einen `lock_timeout`-Wert fest, um die Zeit zu begrenzen, die eine SQL-Anweisung wartet, um eine Sperre für eine Beziehung zu erhalten. Wenn die Sperre nicht innerhalb des angegebenen Timeouts erworben wird, wird die Transaktion, die die Sperre anfordert, abgebrochen. Stellen Sie diesen Wert auf Sitzungsebene ein.

### Minimieren Sie die Auswirkungen von Wartungsvorgängen
<a name="apg-waits.lockrelation.actions.maintenance"></a>

Wartungsvorgänge wie `VACUUM` und `ANALYZE` sind wichtig. Wir empfehlen, sie nicht zu deaktivieren, da Sie `Lock:Relation`-Warteereignisse im Zusammenhang mit diesen Wartungsvorgängen finden. Die folgenden Ansätze können die Auswirkungen dieser Vorgänge minimieren:
+ Führen Sie Wartungsvorgänge während außerhalb der Hauptverkehrszeiten manuell aus.
+ Um `Lock:Relation`-Wartezeiten zu reduzieren, die durch Autovacuum-Aufgaben verursacht werden, führen Sie alle erforderlichen Autovacuum-Optimierungen durch. Informationen zum Optimieren von Autovacuum finden Sie unter [Arbeiten mit PostgreSQL Autovacuum auf Amazon RDS](https://docs.aws.amazon.com/AmazonRDS/latest/UserGuide/Appendix.PostgreSQL.CommonDBATasks.Autovacuum.html) im *Amazon-RDS-Benutzerhandbuch*.

### Auf Lesersperren überprüfen
<a name="apg-waits.lockrelation.actions.readerlocks"></a>

Sie können sehen, wie gleichzeitige Sitzungen bei einem Autor und Lesern Sperren halten, die sich gegenseitig blockieren. Eine Möglichkeit dazu besteht darin, Abfragen auszuführen, die den Sperrtyp und die Beziehung zurückgeben. Die Tabelle enthält eine Abfolge von Abfragen für zwei dieser gleichzeitigen Sitzungen, eine Writer-Sitzung und eine Reader-Sitzung.

Der Wiedergabeprozess wartet die Dauer von `max_standby_streaming_delay` ab, bevor die Reader-Abfrage abgebrochen wird. Wie im Beispiel gezeigt, liegt das Sperr-Timeout von 100 ms deutlich unter dem standardmäßigen `max_standby_streaming_delay`-Wert von 30 Sekunden. Für die Sperre tritt ein Timeout auf, bevor ein Problem entsteht. 


| Sequenzereignis | Sitzung | Befehl oder Ausgabe | 
| --- | --- | --- | 
|  Dieses legt eine Umgebungsvariable namens READER mit dem angegebenen Wert fest und versucht, mit diesem Endpunkt eine Verbindung zur DB-Instance herzustellen.  |  Lesersitzung  |  CLI-Befehl: <pre>export READER=aurorapg2.12345678910.us-west-1.rds.amazonaws.com<br /><br />psql -h $READER</pre> Ausgabe: 

```
psql (15devel, server 10.14)
Type "help" for help.
```  | 
|  Dieses legt eine Umgebungsvariable namens WRITER fest und versucht, mit diesem Endpunkt eine Verbindung zur DB-Instance herzustellen.  |  Writer session  |  CLI-Befehl: <pre>export WRITER=aurorapg1.12345678910.us-west-1.rds.amazonaws.com<br />psql -h $WRITER</pre> Ausgabe: 

```
psql (15devel, server 10.14) 
Type "help" for help.
```  | 
|  Die Schreibsitzung erstellt die Tabelle t1 auf der Writer-Instance.  |  Writer session  |  PostgreSQL-Abfrage: <pre>postgres=> CREATE TABLE t1(b integer);<br />CREATE TABLE</pre>  | 
|  Wenn es keine widersprüchlichen Abfragen für den Writer gibt, wird sofort die ACCESS EXCLUSIVE-Sperre für den Writer erworben.  |  Writer session  |  `ACCESS EXCLUSIVE`-Sperre aktiviert  | 
|  Die Lesesitzung legt ein Sperr-Timeout-Intervall von 100 Millisekunden fest.  |  Lesersitzung  |  PostgreSQL-Abfrage: <pre>postgres=> SET lock_timeout=100;<br />SET</pre>  | 
|  Die Lesesitzung versucht, Daten aus der Tabelle t1 auf der Reader-Instance zu lesen.  |  Lesersitzung  |  PostgreSQL-Abfrage: <pre>postgres=> SELECT * FROM t1;</pre> Beispielausgabe: 

```
b
---
(0 rows)
```  | 
|  Die Schreibsitzung verwirft t1.  |  Writer session  |  PostgreSQL-Abfrage: <pre>postgres=> BEGIN;<br />BEGIN<br />postgres=> DROP TABLE t1;<br />DROP TABLE<br />postgres=></pre>  | 
|  Die Abfrage ist abgelaufen und wird im Reader abgebrochen.  |  Lesersitzung  |  PostgreSQL-Abfrage: <pre>postgres=> SELECT * FROM t1;</pre> Beispielausgabe: 

```
ERROR:  canceling statement due to lock timeout
LINE 1: SELECT * FROM t1;
                      ^
```  | 
|  Die Lesesitzung fragt `pg_locks` und `pg_stat_activity` ab, um die Fehlerursache zu ermitteln.  |  Lesersitzung  |  PostgreSQL-Abfrage: <pre>postgres=> SELECT locktype, relation, mode, backend_type<br />postgres=> FROM pg_locks l, pg_stat_activity t1<br />postgres=> WHERE l.pid=t1.pid AND relation = 't1'::regclass::oid;</pre>  | 
|  Das Ergebnis zeigt an, dass der `aurora wal replay`-Prozess eine `ACCESS EXCLUSIVE`-Sperre für Tabelle t1 hält.  |  Lesersitzung  |  Abfrageergebnis: <pre> locktype | relation |        mode         |   backend_type<br />----------+----------+---------------------+-------------------<br /> relation | 68628525 | AccessExclusiveLock | aurora wal replay<br />(1 row)</pre>  | 

# Lock:transactionid
<a name="apg-waits.locktransactionid"></a>

Das `Lock:transactionid`-Ereignis tritt ein, wenn eine Transaktion auf eine Sperre auf Zeilenebene wartet.

**Topics**
+ [Unterstützte Engine-Versionen](#apg-waits.locktransactionid.context.supported)
+ [Kontext](#apg-waits.locktransactionid.context)
+ [Wahrscheinliche Ursachen für erhöhte Wartezeiten](#apg-waits.locktransactionid.causes)
+ [Aktionen](#apg-waits.locktransactionid.actions)

## Unterstützte Engine-Versionen
<a name="apg-waits.locktransactionid.context.supported"></a>

Diese Warteereignisinformationen werden für alle Versionen von Aurora PostgreSQL unterstützt.

## Kontext
<a name="apg-waits.locktransactionid.context"></a>

Das Ereignis `Lock:transactionid` tritt ein, wenn eine Transaktion versucht, eine Sperre auf Zeilenebene zu erlangen, die bereits einer gleichzeitig laufenden Transaktion gewährt wurde. Die Sitzung, die das `Lock:transactionid`-Wait-Ereignis anzeigt, ist aufgrund dieser Sperre blockiert. Nachdem die blockierende Transaktion entweder in einer `COMMIT`- oder `ROLLBACK`-Anweisung endet, kann die blockierte Transaktion fortgesetzt werden.

Die Semantik der Multiversions-Parallelität von Aurora PostgreSQL garantiert, dass Leser keine Autoren blockieren und Autoren Leser nicht blockieren. Damit Konflikte auf Zeilenebene auftreten können, müssen blockierende und blockierte Transaktionen widersprüchliche Anweisungen der folgenden Typen ausgeben:
+ `UPDATE`
+ `SELECT … FOR UPDATE`
+ `SELECT … FOR KEY SHARE`

Die Anweisung `SELECT … FOR KEY SHARE` ist ein Sonderfall. Die Datenbank verwendet die Klausel `FOR KEY SHARE`, um die Leistung der referenziellen Integrität zu optimieren. Eine Sperre auf Zeilenebene für eine Zeile kann `INSERT`-, `UPDATE`- und `DELETE`-Befehle für andere Tabellen blockieren, die auf die Zeile verweisen.

## Wahrscheinliche Ursachen für erhöhte Wartezeiten
<a name="apg-waits.locktransactionid.causes"></a>

Wenn dieses Ereignis mehr als normal auftritt, sind die Ursache normalerweise `UPDATE`-, `SELECT … FOR UPDATE`-, `SELECT … FOR KEY SHARE`-Anweisungen in Kombination mit den folgenden Bedingungen.

**Topics**
+ [Hohe Gleichzeitigkeit](#apg-waits.locktransactionid.concurrency)
+ [Leerlauf in Transaktion](#apg-waits.locktransactionid.idle)
+ [Lang laufende Transaktionen](#apg-waits.locktransactionid.long-running)

### Hohe Gleichzeitigkeit
<a name="apg-waits.locktransactionid.concurrency"></a>

Aurora PostgreSQL kann eine körnige Sperrsemantik auf Zeilenebene verwenden. Die Wahrscheinlichkeit von Konflikten auf Zeilenebene steigt, wenn die folgenden Bedingungen erfüllt sind:
+ Eine sehr gleichzeitige Workload beansprucht dieselben Zeilen.
+ Parallelbetrieb steigt.

### Leerlauf in Transaktion
<a name="apg-waits.locktransactionid.idle"></a>

Manchmal zeigt die Spalte `pg_stat_activity.state` den Wert `idle in transaction` an. Dieser Wert wird für Sitzungen angezeigt, die eine Transaktion gestartet, aber noch kein `COMMIT` oder `ROLLBACK` ausgegeben haben. Wenn der `pg_stat_activity.state`-Wert nicht `active` ist, ist die in `pg_stat_activity` angezeigte Abfrage die letzte, die ausgeführt wurde. Die blockierende Sitzung verarbeitet eine Abfrage nicht aktiv, da eine offene Transaktion eine Sperre hält.

Wenn eine Leerlauf-Transaktion eine Sperre auf Zeilenebene erworben hat, kann dies verhindern, dass andere Sitzungen sie erwerben. Diese Bedingung führt zu einem häufigen Auftreten des Warteereignisses `Lock:transactionid`. Um das Problem zu diagnostizieren, überprüfen Sie die Ausgabe von `pg_stat_activity` und `pg_locks`.

### Lang laufende Transaktionen
<a name="apg-waits.locktransactionid.long-running"></a>

Transaktionen, die lange laufen, erhalten lange Zeit Sperren. Diese langjährigen Sperren können die Ausführung anderer Transaktionen verhindern.

## Aktionen
<a name="apg-waits.locktransactionid.actions"></a>

Zeilensperre ist ein Konflikt zwischen `UPDATE`-, `SELECT … FOR UPDATE`- oder `SELECT … FOR KEY SHARE`-Anweisungen. Bevor Sie eine Lösung versuchen, sollten Sie herausfinden, wann diese Anweisungen in derselben Zeile ausgeführt werden. Wählen Sie mit diesen Informationen eine in den folgenden Abschnitten beschriebene Strategie aus.

**Topics**
+ [Reagieren auf hohe Parallelbetrieb](#apg-waits.locktransactionid.actions.problem)
+ [Reagieren Sie auf ungenutzte Transaktionen](#apg-waits.locktransactionid.actions.find-blocker)
+ [Reagieren Sie auf lang andauernde Transaktionen](#apg-waits.locktransactionid.actions.concurrency)

### Reagieren auf hohe Parallelbetrieb
<a name="apg-waits.locktransactionid.actions.problem"></a>

Wenn Parallelität das Problem darstellt, versuchen Sie eine der folgenden Techniken:
+ Senken Sie die Parallelität in der Anwendung. Verringern Sie beispielsweise die Anzahl der aktiven Sitzungen.
+ Implementieren Sie einen Verbindungspool. Informationen zum Poolen von Verbindungen mit RDS-Proxy finden Sie unter [Amazon RDS-Proxy für Aurora](rds-proxy.md).
+ Entwerfen Sie die Anwendung oder das Datenmodell, um konkurrierende `UPDATE`- und `SELECT … FOR UPDATE`-Anweisungen zu vermeiden. Sie können auch die Anzahl der Fremdschlüssel verringern, auf die von `SELECT … FOR KEY SHARE`-Anweisungen zugegriffen wird.

### Reagieren Sie auf ungenutzte Transaktionen
<a name="apg-waits.locktransactionid.actions.find-blocker"></a>

Wenn `pg_stat_activity.state` `idle in transaction` anzeigt, verwenden Sie die folgenden Strategien:
+ Schalten Sie nach Möglichkeit Autocommit ein. Dieser Ansatz verhindert, dass Transaktionen andere Transaktionen blockieren, während sie auf ein `COMMIT` oder `ROLLBACK` warten.
+ Suchen Sie nach Codepfaden, denen `COMMIT`, `ROLLBACK` oder `END` fehlt.
+ Stellen Sie sicher, dass die Ausnahmebehandlungslogik in Ihrer Anwendung immer einen Pfad zu einem gültigen `end of transaction` hat.
+ Stellen Sie sicher, dass Ihre Anwendung Abfrageergebnisse verarbeitet, nachdem die Transaktion mit `COMMIT` oder `ROLLBACK` beendet wurde.

### Reagieren Sie auf lang andauernde Transaktionen
<a name="apg-waits.locktransactionid.actions.concurrency"></a>

Wenn Transaktionen mit langer Laufzeit das häufige Auftreten von `Lock:transactionid` verursachen, versuchen Sie die folgenden Strategien:
+ Halten Sie Zeilensperren von lang andauernden Transaktionen fern.
+ Beschränken Sie die Länge von Abfragen, indem Sie nach Möglichkeit Autocommit implementieren.

# Lock:tuple
<a name="apg-waits.locktuple"></a>

Das `Lock:tuple`-Ereignis tritt ein, wenn ein Backend-Prozess darauf wartet, eine Sperre für ein Tupel zu erlangen.

**Topics**
+ [Unterstützte Engine-Versionen](#apg-waits.locktuple.context.supported)
+ [Kontext](#apg-waits.locktuple.context)
+ [Wahrscheinliche Ursachen für erhöhte Wartezeiten](#apg-waits.locktuple.causes)
+ [Aktionen](#apg-waits.locktuple.actions)

## Unterstützte Engine-Versionen
<a name="apg-waits.locktuple.context.supported"></a>

Diese Warteereignisinformationen werden für alle Versionen von Aurora PostgreSQL unterstützt.

## Kontext
<a name="apg-waits.locktuple.context"></a>

Das Ereignis `Lock:tuple` zeigt an, dass ein Back-End darauf wartet, eine Sperre für ein Tupel zu erlangen, während ein anderes Back-End eine widersprüchliche Sperre für dasselbe Tupel hält. Die folgende Tabelle veranschaulicht ein Szenario, in dem Sitzungen das `Lock:tuple`-Ereignis generieren.


|  Zeit  |  1. Sitzung  |  2. Sitzung  |  3. Sitzung  | 
| --- | --- | --- | --- | 
|  t1  |  Startet eine Transaktion.  |    |    | 
|  t2  |  Aktualisiert Zeile 1.  |    |    | 
|  t3  |    |  Aktualisiert Zeile 1. Die Sitzung erwirbt eine exklusive Sperre für das Tupel und wartet dann darauf, dass Sitzung 1 die Sperre durch Commit oder Rollback freigibt.  |    | 
|  t4  |    |    |  Aktualisiert Zeile 1. Die Sitzung wartet darauf, dass Sitzung 2 die exklusive Sperre für das Tupel freigibt.  | 

Oder Sie können dieses Warteereignis simulieren, indem Sie das Benchmarking-Tool `pgbench` verwenden. Konfigurieren Sie eine hohe Anzahl gleichzeitiger Sitzungen, um dieselbe Zeile in einer Tabelle mit einer benutzerdefinierten SQL-Datei zu aktualisieren.

Weitere Informationen zu widersprüchlichen Sperrmodi finden Sie unter [Explizite Sperren](https://www.postgresql.org/docs/current/explicit-locking.html) in der PostgreSQL-Dokumentation. Weitere Informationen zu `pgbench` finden Sie unter [pgbench](https://www.postgresql.org/docs/current/pgbench.html) in der PostgreSQL-Dokumentation.

## Wahrscheinliche Ursachen für erhöhte Wartezeiten
<a name="apg-waits.locktuple.causes"></a>

Wenn dieses Ereignis mehr als normal auftritt und möglicherweise auf ein Leistungsproblem hinweist, sind typische Ursachen:
+ Eine große Anzahl gleichzeitiger Sitzungen versucht, eine widersprüchliche Sperre für dasselbe Tupel zu erlangen, indem sie `UPDATE`- oder `DELETE`-Anweisungen ausführen.
+ In hochgradig gleichzeitigen Sitzungen wird eine `SELECT`-Anweisung ausgeführt, die den `FOR UPDATE`- oder `FOR NO KEY UPDATE`-Sperrmodus verwendet.
+ Verschiedene Faktoren veranlassen Anwendungs- oder Verbindungspools dazu, weitere Sitzungen zu öffnen, um dieselben Vorgänge auszuführen. Wenn neue Sitzungen versuchen, dieselben Zeilen zu ändern, kann die DB-Last stark ansteigen und `Lock:tuple` kann erscheinen.

Weitere Informationen finden Sie unter [Sperren auf Zeilenebene](https://www.postgresql.org/docs/current/explicit-locking.html#LOCKING-ROWS) in der PostgreSQL-Dokumentation.

## Aktionen
<a name="apg-waits.locktuple.actions"></a>

Abhängig von den Ursachen Ihres Warteereignisses empfehlen wir verschiedene Aktionen.

**Topics**
+ [Untersuchen Sie Ihre Anwendungslogik](#apg-waits.locktuple.actions.problem)
+ [Finde die Blocker-Sitzung](#apg-waits.locktuple.actions.find-blocker)
+ [Reduzieren Sie Parallelität, wenn es hoch ist](#apg-waits.locktuple.actions.concurrency)
+ [Beheben von Engpässen](#apg-waits.locktuple.actions.bottlenecks)

### Untersuchen Sie Ihre Anwendungslogik
<a name="apg-waits.locktuple.actions.problem"></a>

Finden Sie heraus, ob sich eine Blocker-Sitzung schon lange im `idle in transaction`-Zustand befindet. Wenn ja, erwägen Sie, die Blocker-Sitzung als kurzfristige Lösung zu beenden. Sie können die Funktion `pg_terminate_backend` verwenden. Weitere Informationen zu dieser Funktion finden Sie unter [Server-Signalisierungsfunktionen](https://www.postgresql.org/docs/13/functions-admin.html#FUNCTIONS-ADMIN-SIGNAL) in der PostgreSQL-Dokumentation.

Gehen Sie für eine langfristige Lösung wie folgt vor:
+ Passen Sie die Anwendungslogik an.
+ Verwenden Sie den Parameter `idle_in_transaction_session_timeout`. Dieser Parameter beendet jede Sitzung mit einer offenen Transaktion, die länger als die angegebene Zeitspanne im Leerlauf ist. Weitere Informationen finden Sie unter [Standardeinstellungen für Clientverbindungen](https://www.postgresql.org/docs/current/runtime-config-client.html#GUC-IDLE-IN-TRANSACTION-SESSION-TIMEOUT) in der PostgreSQL-Dokumentation.
+ Verwenden Sie Autocommit so weit wie möglich. Weitere Informationen finden Sie unter [SET AUTOCOMMIT](https://www.postgresql.org/docs/current/ecpg-sql-set-autocommit.html) in der PostgreSQL-Dokumentation.

### Finde die Blocker-Sitzung
<a name="apg-waits.locktuple.actions.find-blocker"></a>

Identifizieren Sie während des `Lock:tuple`-Wait-Ereignisses den Blocker und die blockierte Sitzung, indem Sie herausfinden, welche Sperren voneinander abhängen. Weitere Informationen finden Sie unter [Informationen zur Sperrabhängigkeit](https://wiki.postgresql.org/wiki/Lock_dependency_information) im PostgreSQL-Wiki. Um vergangene `Lock:tuple`-Ereignisse zu analysieren, verwenden Sie die Aurora-Funktion `aurora_stat_backend_waits`. 

Im folgenden Beispiel werden alle Sitzungen abgefragt, nach `tuple` gefiltert und nach `wait_time` sortiert.

```
--AURORA_STAT_BACKEND_WAITS
      SELECT a.pid, 
             a.usename, 
             a.app_name, 
             a.current_query,
             a.current_wait_type, 
             a.current_wait_event, 
             a.current_state, 
             wt.type_name AS wait_type, 
             we.event_name AS wait_event, 
             a.waits, 
             a.wait_time
        FROM (SELECT pid, 
                     usename, 
                     left(application_name,16) AS app_name,
                     coalesce(wait_event_type,'CPU') AS current_wait_type,
                     coalesce(wait_event,'CPU') AS current_wait_event, 
                     state AS current_state,
                     left(query,80) as current_query,
                     (aurora_stat_backend_waits(pid)).* 
                FROM pg_stat_activity 
               WHERE pid <> pg_backend_pid()
                 AND usename<>'rdsadmin') a
NATURAL JOIN aurora_stat_wait_type() wt 
NATURAL JOIN aurora_stat_wait_event() we
WHERE we.event_name = 'tuple'
    ORDER BY a.wait_time;

  pid  | usename | app_name |                 current_query                  | current_wait_type | current_wait_event | current_state | wait_type | wait_event | waits | wait_time
-------+---------+----------+------------------------------------------------+-------------------+--------------------+---------------+-----------+------------+-------+-----------
 32136 | sys     | psql     | /*session3*/ update tab set col=1 where col=1; | Lock              | tuple              | active        | Lock      | tuple      |     1 |   1000018
 11999 | sys     | psql     | /*session4*/ update tab set col=1 where col=1; | Lock              | tuple              | active        | Lock      | tuple      |     1 |   1000024
```

### Reduzieren Sie Parallelität, wenn es hoch ist
<a name="apg-waits.locktuple.actions.concurrency"></a>

Das `Lock:tuple`-Ereignis kann ständig auftreten, insbesondere in einer arbeitsreichen Zeit. Erwägen Sie in dieser Situation, die hohe Parallelität für sehr belegte Reihen zu reduzieren. Oft steuern nur wenige Zeilen eine Warteschlange oder die boolesche Logik, was diese Zeilen sehr ausgelastet macht.

Sie können die Parallelität reduzieren, indem Sie verschiedene Ansätze verwenden, die auf der Geschäftsanforderung, der Anwendungslogik und dem Workload-Typ basieren. Sie können z. B. Folgendes tun:
+ Gestalten Sie Ihre Tabellen- und Datenlogik neu, um hohe Parallelität zu reduzieren.
+ Ändern Sie die Anwendungslogik, um die hohe Parallelität auf Zeilenebene zu reduzieren.
+ Nutzen und gestalten Sie Abfragen mit Sperren auf Zeilenebene.
+ Verwenden Sie die `NOWAIT`-Klausel mit Wiederholungsvorgänge.
+ Erwägen Sie, optimistische und hybridsperrende Logik-Parallelitätssteuerung zu nutzen.
+ Überlegen Sie, die Isolationsstufe der Datenbank zu ändern.

### Beheben von Engpässen
<a name="apg-waits.locktuple.actions.bottlenecks"></a>

Das `Lock:tuple` kann bei Engpässen wie CPU-Aushungerungen oder maximaler Nutzung der Amazon EBS-Bandbreite auftreten. Um Engpässe zu verringern, sollten Sie die folgenden Ansätze berücksichtigen:
+ Skalieren Sie Ihren Instance-Klassentyp hoch.
+ Optimieren Sie ressourcenintensive Abfragen.
+ Ändern Sie die Anwendungslogik.
+ Archivieren Sie Daten, die selten zugegriffen wird.

# LWLock:buffer\$1content () BufferContent
<a name="apg-waits.lockbuffercontent"></a>

Das Ereignis `LWLock:buffer_content` tritt ein, wenn eine Sitzung darauf wartet, eine Datenseite im Speicher zu lesen oder zu schreiben, während eine andere Sitzung diese Seite zum Schreiben gesperrt hat. In Aurora PostgreSQL 13 und höher heißt dieses Warteereignis `BufferContent`.

**Topics**
+ [Unterstützte Engine-Versionen](#apg-waits.lockbuffercontent.context.supported)
+ [Kontext](#apg-waits.lockbuffercontent.context)
+ [Wahrscheinliche Ursachen für erhöhte Wartezeiten](#apg-waits.lockbuffercontent.causes)
+ [Aktionen](#apg-waits.lockbuffercontent.actions)

## Unterstützte Engine-Versionen
<a name="apg-waits.lockbuffercontent.context.supported"></a>

Diese Warteereignisinformationen werden für alle Versionen von Aurora PostgreSQL unterstützt.

## Kontext
<a name="apg-waits.lockbuffercontent.context"></a>

Um Daten zu lesen oder zu manipulieren, greift PostgreSQL über Shared Memory Puffer darauf zu. Um aus dem Puffer zu lesen, erhält ein Prozess im Shared-Modus eine einfache Sperre (LWLock) für den Pufferinhalt. Um in den Puffer zu schreiben, wird diese Sperre im exklusiven Modus angezeigt. Gemeinsame Sperren ermöglichen es anderen Prozessen, gleichzeitig gemeinsame Sperren für diesen Inhalt zu erwerben. Exklusive Sperren verhindern, dass andere Prozesse irgendeine Art von Sperre erhalten.

Das Ereignis `LWLock:buffer_content` (`BufferContent`) weist darauf hin, dass mehrere Prozesse versuchen, einfache Sperren (LWLocks) für den Inhalt eines bestimmten Puffers zu aktivieren.

## Wahrscheinliche Ursachen für erhöhte Wartezeiten
<a name="apg-waits.lockbuffercontent.causes"></a>

Wenn das `LWLock:buffer_content`(`BufferContent`)-Ereignis mehr als normal auftritt, was möglicherweise auf ein Leistungsproblem hinweist, sind die folgenden typischen Ursachen:

**Die gleichzeitigen Aktualisierungen der gleichen Daten wurden erhöht**  
Es kann zu einer Zunahme der Anzahl gleichzeitiger Sitzungen mit Abfragen kommen, die denselben Pufferinhalt aktualisieren. Diese Behauptung kann bei Tabellen mit vielen Indizes ausgeprägter sein.

**Workload-Daten befinden sich nicht im Speicher**  
Wenn sich Daten, die die aktive Workload verarbeitet, nicht im Speicher befinden, können diese Warteereignisse zunehmen. Dieser Effekt ist darauf zurückzuführen, dass Prozesse, die Sperren enthalten, diese länger behalten können, während sie I/O Festplattenoperationen ausführen.

**Übermäßiger Einsatz von Fremdschlüsselbeschränkungen**  
Fremdschlüsseleinschränkungen können die Zeit erhöhen, die ein Prozess an einer Pufferinhaltssperre hält. Dieser Effekt liegt daran, dass Lesevorgänge eine gemeinsame Pufferinhaltssperre für den referenzierten Schlüssel erfordern, während dieser Schlüssel aktualisiert wird.

## Aktionen
<a name="apg-waits.lockbuffercontent.actions"></a>

Abhängig von den Ursachen Ihres Warteereignisses empfehlen wir verschiedene Aktionen. Sie können `LWLock:buffer_content`(`BufferContent`)-Ereignisse identifizieren, indem Sie Amazon RDS Performance Insights verwenden oder die Ansicht `pg_stat_activity` abfragen.

**Topics**
+ [Verbessern Sie die Effizienz im Speicher](#apg-waits.lockbuffercontent.actions.in-memory)
+ [Reduzieren Sie die Verwendung von Fremdschlüsselbeschränkungen](#apg-waits.lockbuffercontent.actions.foreignkey)
+ [Entferne nicht verwendete Indizes](#apg-waits.lockbuffercontent.actions.indexes)
+ [Entfernen von doppelten Indizes](#apg-waits.lockbuffercontent.actions.duplicate-indexes)
+ [Löschen oder NEU INDIZIEREN von ungültigen Indizes](#apg-waits.lockbuffercontent.actions.invalid-indexes)
+ [Verwenden von partiellen Indizes](#apg-waits.lockbuffercontent.actions.partial-indexes)
+ [Entfernen von überflüssigen Daten aus Tabellen und Indizes (Bloat)](#apg-waits.lockbuffercontent.actions.bloat)

### Verbessern Sie die Effizienz im Speicher
<a name="apg-waits.lockbuffercontent.actions.in-memory"></a>

Um die Wahrscheinlichkeit zu erhöhen, dass sich aktive Workload-Daten im Speicher befinden, partitionieren Sie Tabellen oder skalieren Sie Ihre Instance-Klasse hoch. Weitere Informationen zu DB-Instance-Klassen finden Sie unter [Amazon Aurora Aurora-DB-Instance-Klassen](Concepts.DBInstanceClass.md).

Überwachen Sie die `BufferCacheHitRatio`-Metrik. Diese misst den Prozentsatz der Anfragen, die vom Puffer-Cache einer DB-Instance in Ihrem DB-Cluster verarbeitet werden. Diese Metrik gibt Aufschluss über die Datenmenge, die vom Speicher bereitgestellt wird. Eine hohe Trefferrate bedeutet, dass Ihre DB-Instance über ausreichend Speicherplatz für Ihren Arbeitsdatensatz verfügt, während eine niedrige Trefferrate darauf hindeutet, dass Ihre Abfragen häufig auf Daten aus dem Speicher zugreifen.

Die Cache-Lesetreffer pro Tabelle und die Cache-Lesetreffer pro Index im Abschnitt zu den Speichereinstellungen des [PG-Collector](https://github.com/awslabs/pg-collector)-Berichts können Aufschluss über die Cache-Trefferrate von Tabellen und Indizes geben.

### Reduzieren Sie die Verwendung von Fremdschlüsselbeschränkungen
<a name="apg-waits.lockbuffercontent.actions.foreignkey"></a>

Untersuchen Sie Workloads, bei denen eine hohe Anzahl von `LWLock:buffer_content`(`BufferContent`)-Wait-Ereignissen auf die Verwendung von Fremdschlüsseleinschränkungen auftritt. Entfernen Sie unnötige Fremdschlüsselbeschränkungen.

### Entferne nicht verwendete Indizes
<a name="apg-waits.lockbuffercontent.actions.indexes"></a>

Identifizieren Sie bei Workloads mit einer hohen Anzahl von `LWLock:buffer_content`(`BufferContent`)-Wait-Ereignissen nicht verwendete Indizes und entfernen Sie sie.

Der Abschnitt zu nicht genutzten Indizes im [PG-Collector](https://github.com/awslabs/pg-collector)-Bericht kann Aufschluss über die nicht genutzten Indizes in der Datenbank geben.

### Entfernen von doppelten Indizes
<a name="apg-waits.lockbuffercontent.actions.duplicate-indexes"></a>

Identifizieren Sie doppelte Indizes und entfernen Sie sie.

Der Abschnitt zu doppelten Indizes im [PG-Collector](https://github.com/awslabs/pg-collector)-Bericht kann Aufschluss über die doppelten Indizes in der Datenbank geben.

### Löschen oder NEU INDIZIEREN von ungültigen Indizes
<a name="apg-waits.lockbuffercontent.actions.invalid-indexes"></a>

Ungültige Indizes kommen in der Regel vor, wenn `CREATE INDEX CONCURRENTLY` oder `REINDEX CONCURRENTLY` verwendet wird und der Befehl fehlschlägt oder abgebrochen wird.

Ungültige Indizes können nicht für Abfragen verwendet werden, werden aber trotzdem aktualisiert und beanspruchen Speicherplatz.

Der Abschnitt zu ungültigen Indizes im [PG-Collector](https://github.com/awslabs/pg-collector)-Bericht kann Aufschluss über ungültige Indizes in der Datenbank geben.

### Verwenden von partiellen Indizes
<a name="apg-waits.lockbuffercontent.actions.partial-indexes"></a>

Partielle Indizes können verwendet werden, um die Abfrageleistung zu verbessern und die Indexgröße zu reduzieren. Ein partieller Index ist ein Index, der auf einer Teilmenge einer Tabelle basiert, wobei die Teilmenge durch einen bedingten Ausdruck definiert ist. Wie in der [partial index](https://www.postgresql.org/docs/current/indexes-partial.html)-Dokumentation beschrieben, können partielle Indizes den Aufwand für die Verwaltung von Indizes reduzieren, da PostgreSQL den Index nicht in jedem Fall aktualisieren muss.

### Entfernen von überflüssigen Daten aus Tabellen und Indizes (Bloat)
<a name="apg-waits.lockbuffercontent.actions.bloat"></a>

Ein übermäßiger Tabellen- und Index-Bloat kann sich negativ auf die Datenbankleistung auswirken. Tabellen und Indizes, die viel überflüssige Daten enthalten, erhöhen die Größe des aktiven Arbeitssatzes, wodurch die Effizienz im Arbeitsspeicher beeinträchtigt wird. Darüber hinaus erhöhen überflüssige Daten die Speicherkosten und verlangsamen die Ausführung von Abfragen. Informationen zur Bloat-Diagnose finden Sie unter [Diagnostizieren einer Überlastung von Tabellen und Indizes](AuroraPostgreSQL.diag-table-ind-bloat.md). Darüber hinaus gibt der Abschnitt zur Fragmentierung (Bloat) im [PG-Collector](https://github.com/awslabs/pg-collector)-Bericht Aufschluss über Tabellen und Indizes mit überflüssigen Daten.

Zur Behebung des Problems der überflüssigen Daten in Tabellen und Indizes gibt es einige Optionen:

**VACUUM FULL**  
`VACUUM FULL` erstellt eine neue Kopie der Tabelle, wobei nur die aktiven Tupel kopiert werden, und ersetzt dann die alte Tabelle durch die neue, wobei eine `ACCESS EXCLUSIVE`-Sperre beibehalten wird. Dadurch wird jegliches Lesen oder Schreiben in die Tabelle verhindert, was zu einem Ausfall führen kann. Außerdem dauert `VACUUM FULL` länger, wenn die Tabelle groß ist.

**pg\$1repack**  
`pg_repack` ist hilfreich in Situationen, in denen `VACUUM FULL` möglicherweise nicht geeignet ist. Es erstellt eine neue Tabelle, die die Daten der Tabelle mit den überflüssigen Daten enthält, verfolgt die Änderungen gegenüber der Originaltabelle nach und ersetzt diese Tabelle dann durch die neue. Es sperrt die Originaltabelle nicht für Lese- oder Schreibvorgänge, während die neue Tabelle erstellt wird. Weitere Informationen zur Verwendung von `pg_repack` finden Sie unter [Reduzieren von überflüssigen Daten mit pg\$1repack](https://docs.aws.amazon.com/prescriptive-guidance/latest/postgresql-maintenance-rds-aurora/pg-repack.html) und unter [pg\$1repack](https://reorg.github.io/pg_repack/).

**REINDEX**  
Der `REINDEX`-Befehl kann genutzt werden, um das Problem eines Index-Bloat zu beheben. `REINDEX` schreibt eine neue Version des Index ohne die „toten“ oder leeren bzw. fast leeren Seiten, was den Platzverbrauch des Index reduziert. Detaillierte Informationen zum [https://www.postgresql.org/docs/current/sql-reindex.html](https://www.postgresql.org/docs/current/sql-reindex.html)-Befehl finden Sie in der REINDEX-Dokumentation.

Nach dem Entfernen der überflüssigen Daten aus Tabellen und Indizes kann es notwendig sein, die Selbstbereinigungsfrequenzen für diese Tabellen zu erhöhen. Die Implementierung von Einstellungen für eine aggressive Selbstbereinigung auf Tabellenebene kann dazu beitragen, überflüssige Daten zu vermeiden. Weitere Informationen finden Sie in der Dokumentation über [https://docs.aws.amazon.com/prescriptive-guidance/latest/postgresql-maintenance-rds-aurora/autovacuum.html](https://docs.aws.amazon.com/prescriptive-guidance/latest/postgresql-maintenance-rds-aurora/autovacuum.html).

# LWLock:buffer\$1mapping
<a name="apg-waits.lwl-buffer-mapping"></a>

Dieses Ereignis tritt ein, wenn eine Sitzung darauf wartet, einen Datenblock einem Puffer im gemeinsam genutzten Pufferpool zuzuordnen.

**Anmerkung**  
Dieses Ereignis wird in Aurora PostgreSQL Version 12 und niedriger als `LWLock:buffer_mapping` und in Version 13 und höher als `LWLock:BufferMapping` angezeigt.

**Topics**
+ [Unterstützte Engine-Versionen](#apg-waits.lwl-buffer-mapping.context.supported)
+ [Kontext](#apg-waits.lwl-buffer-mapping.context)
+ [Ursachen](#apg-waits.lwl-buffer-mapping.causes)
+ [Aktionen](#apg-waits.lwl-buffer-mapping.actions)

## Unterstützte Engine-Versionen
<a name="apg-waits.lwl-buffer-mapping.context.supported"></a>

Diese Warteereignisinformationen sind für Aurora PostgreSQL Version 9.6 und höher relevant.

## Kontext
<a name="apg-waits.lwl-buffer-mapping.context"></a>

Der *freigegebene Pufferpool* ist ein Aurora PostgreSQL-Speicherbereich, der alle Seiten enthält, die von Prozessen verwendet werden oder wurden. Wenn ein Prozess eine Seite benötigt, liest er die Seite in den freigegebenen Pufferpool. Der Parameter `shared_buffers` legt die Größe des gemeinsam genutzten Puffers fest und reserviert einen Speicherbereich zum Speichern der Tabellen- und Indexseiten. Wenn Sie diesen Parameter ändern, stellen Sie sicher, dass Sie die Datenbank neu starten. Weitere Informationen finden Sie unter [Freigegebene Puffer](AuroraPostgreSQL.Tuning.concepts.md#AuroraPostgreSQL.Tuning.concepts.buffer-pool).

Das `LWLock:buffer_mapping`-Wait-Ereignis tritt in den folgenden Szenarien auf:
+ Ein Prozess durchsucht die Puffertabelle nach einer Seite und erwirbt eine freigegebene Puffer-Mapping-Sperre.
+ Ein Prozess lädt eine Seite in den Pufferpool und erwirbt eine exklusive Puffer-Mapping-Sperre.
+ Ein Prozess entfernt eine Seite aus dem Pool und erwirbt eine exklusive Puffer-Mapping-Sperre.

## Ursachen
<a name="apg-waits.lwl-buffer-mapping.causes"></a>

Wenn dieses Ereignis mehr als normal auftritt, was möglicherweise auf ein Leistungsproblem hinweist, greift die Datenbank in und aus dem freigegebenen Pufferpool aus. Zu den typischen Ursachen zählen auch die Folgenden:
+ Große Abfragen
+ Aufgeblähte Indizes und Tabellen
+ Vollständige Tabellenscans
+ Eine gemeinsame Poolgröße, die kleiner als der Arbeitssatz ist

## Aktionen
<a name="apg-waits.lwl-buffer-mapping.actions"></a>

Abhängig von den Ursachen Ihres Warteereignisses empfehlen wir verschiedene Aktionen.

**Topics**
+ [Überwachen Sie pufferbezogene Metriken](#apg-waits.lwl-buffer-mapping.actions.monitor-metrics)
+ [Bewerten Sie Ihre Indexierungsstrategie](#apg-waits.lwl-buffer-mapping.actions.indexes)
+ [Reduzieren Sie die Anzahl der Puffer, die schnell zugewiesen werden müssen](#apg-waits.lwl-buffer-mapping.actions.buffers)

### Überwachen Sie pufferbezogene Metriken
<a name="apg-waits.lwl-buffer-mapping.actions.monitor-metrics"></a>

Wenn `LWLock:buffer_mapping` auf Spitze wartet, untersuchen Sie die Puffertrefferquote. Sie können diese Metriken verwenden, um ein besseres Verständnis dafür zu erhalten, was im Puffer-Cache passiert. Untersuchen Sie die folgenden Metriken:

`BufferCacheHitRatio`  
Diese CloudWatch Amazon-Metrik misst den Prozentsatz der Anfragen, die vom Puffer-Cache einer DB-Instance in Ihrem DB-Cluster bedient werden. Möglicherweise sehen Sie diese Metrikabnahme im Vorfeld des `LWLock:buffer_mapping`-Wait-Ereignisses.

`blks_hit`  
Diese Zählermetrik für Performance Insights gibt die Anzahl der Blöcke an, die aus dem freigegebenen Pufferpool abgerufen wurden. Nachdem das Wait-Ereignis `LWLock:buffer_mapping` aufgetreten ist, können Sie eine Spitze in `blks_hit` beobachten.

`blks_read`  
Diese Performance Insights Insights-Zählermetrik gibt die Anzahl der Blöcke I/O an, die in den gemeinsam genutzten Pufferpool eingelesen werden mussten. Sie können im Vorfeld des `LWLock:buffer_mapping`-Warteereignisses eine Spitze in `blks_read` beobachten.

### Bewerten Sie Ihre Indexierungsstrategie
<a name="apg-waits.lwl-buffer-mapping.actions.indexes"></a>

Überprüfen Sie Folgendes, um zu bestätigen, dass Ihre Indexierungsstrategie die Leistung nicht beeinträchtigt:

Indexblähung  
Stellen Sie sicher, dass Index und Tabellenaufblähungen nicht dazu führen, dass unnötige Seiten in den freigegebenen Puffer gelesen werden. Wenn Ihre Tabellen nicht verwendete Zeilen enthalten, sollten Sie die Daten archivieren und die Zeilen aus den Tabellen entfernen. Sie können dann die Indizes für die skalierten Tabellen neu erstellen.

Indizes für häufig verwendete Abfragen  
Um festzustellen, ob Sie über die optimalen Indizes verfügen, überwachen Sie die Metriken der DB-Engine in Performance Insights. Die `tup_returned`-Metrik zeigt die Anzahl der gelesenen Zeilen an. Die `tup_fetched`-Metrik zeigt die Anzahl der an den Client zurückgegebenen Zeilen. Wenn `tup_returned` deutlich größer als `tup_fetched` ist, werden die Daten möglicherweise nicht richtig indiziert. Außerdem sind Ihre Tabellenstatistiken möglicherweise nicht aktuell.

### Reduzieren Sie die Anzahl der Puffer, die schnell zugewiesen werden müssen
<a name="apg-waits.lwl-buffer-mapping.actions.buffers"></a>

Um die `LWLock:buffer_mapping`-Warteereignisse zu reduzieren, versuchen Sie, die Anzahl der Puffer zu reduzieren, die schnell zugewiesen werden müssen. Eine Strategie besteht darin, kleinere Batch-Vorgänge durchzuführen. Möglicherweise können Sie kleinere Batches erreichen, indem Sie Ihre Tabellen partitionieren.

# LWLock:BufferIO (IPC:BufferIO)
<a name="apg-waits.lwlockbufferio"></a>

Das `LWLock:BufferIO`-Ereignis tritt ein, wenn Aurora PostgreSQL oder RDS for PostgreSQL darauf wartet, dass andere Prozesse ihre Eingabe-/Ausgabe-(I/O)-Vorgänge beenden, wenn sie gleichzeitig versuchen, auf eine Seite zuzugreifen. Sein Zweck besteht darin, dass dieselbe Seite in den freigegebenen Puffer eingelesen wird.

**Topics**
+ [Relevante Engine-Versionen](#apg-waits.lwlockbufferio.context.supported)
+ [Kontext](#apg-waits.lwlockbufferio.context)
+ [Ursachen](#apg-waits.lwlockbufferio.causes)
+ [Aktionen](#apg-waits.lwlockbufferio.actions)

## Relevante Engine-Versionen
<a name="apg-waits.lwlockbufferio.context.supported"></a>

Diese Warteereignisinformationen sind für alle Versionen von Aurora PostgreSQL. Für Aurora PostgreSQL 12 und frühere Versionen wird dieses Warteereignis als lwlock:buffer\$1io bezeichnet, während es in der Version Aurora PostgreSQL 13 den Namen lwlock:bufferio trägt. Aus der Version Aurora PostgreSQL 14 wurde das BufferIO-Warteereignis von `LWLock` zum Warteereignistyp `IPC` (ipc:bufferio) verschoben. 

## Kontext
<a name="apg-waits.lwlockbufferio.context"></a>

Jeder gemeinsam genutzte Puffer hat eine I/O-Sperre, die mit dem `LWLock:BufferIO`-Warteereignis verbunden ist, jedes Mal, wenn ein Block (oder eine Seite) außerhalb des gemeinsam genutzten Pufferpools abgerufen werden muss.

Diese Sperre wird verwendet, um mehrere Sitzungen zu behandeln, die alle Zugriff auf denselben Block benötigen. Dieser Block muss von außerhalb des gemeinsam genutzten Pufferpools gelesen werden, der durch den `shared_buffers`-Parameter definiert wird.

Sobald die Seite innerhalb des Shared Buffer Pool gelesen wird, wird die `LWLock:BufferIO`-Sperre freigegeben.

**Anmerkung**  
Das `LWLock:BufferIO`-Wait-Ereignis geht dem [IO: DataFileRead](apg-waits.iodatafileread.md)-Warteereignis voraus. Das `IO:DataFileRead`-Wait-Ereignis tritt auf, während Daten aus dem Speicher gelesen werden.

Weitere Informationen zu leichten Sperren finden Sie unter [Übersicht über Sperren](https://github.com/postgres/postgres/blob/65dc30ced64cd17f3800ff1b73ab1d358e92efd8/src/backend/storage/lmgr/README#L20).

## Ursachen
<a name="apg-waits.lwlockbufferio.causes"></a>

Häufige Gründe dafür, dass das `LWLock:BufferIO`-Ereignis in den Top-Wartezeiten angezeigt wird, sind die folgenden:
+ Mehrere Backends oder Verbindungen, die versuchen, auf dieselbe Seite zuzugreifen, für die auch ein I/O-Vorgang aussteht
+ Das Verhältnis zwischen der Größe des gemeinsam genutzten Pufferpools (definiert durch den `shared_buffers`-Parameter) und der Anzahl der Puffer, die von der aktuellen Workload benötigt werden
+ Die Größe des freigegebenen Pufferpools ist nicht gut mit der Anzahl der Seiten, die durch andere Vorgänge geräumt werden
+ Große oder aufgeblähte Indizes, bei denen die Engine mehr Seiten als nötig in den freigegebenen Pufferpool lesen muss
+ Mangel an Indizes, die die DB-Engine dazu zwingen, mehr Seiten aus den Tabellen als nötig zu lesen
+ Plötzliche Spitzen für Datenbankverbindungen, die versuchen, Vorgänge auf derselben Seite auszuführen

## Aktionen
<a name="apg-waits.lwlockbufferio.actions"></a>

Abhängig von den Ursachen Ihres Wait-Ereignisses empfehlen wir verschiedene Aktionen:
+ Beobachten Sie die Amazon CloudWatch-Metriken auf Korrelation zwischen starken Abnahmen der `BufferCacheHitRatio`- und `LWLock:BufferIO`-Warteereignisse. Dieser Effekt kann bedeuten, dass Sie eine kleine Einstellung für gemeinsame Puffer haben. Möglicherweise müssen Sie es erhöhen oder Ihre DB-Instance-Klasse hochskalieren. Sie können Ihre Workload in mehr Reader-Knoten aufteilen.
+ Überprüfen Sie, ob Sie nicht verwendete Indizes haben, und entfernen Sie sie dann.
+ Verwenden Sie partitionierte Tabellen (die auch partitionierte Indizes haben). Dies hilft, die Neuordnung des Index niedrig zu halten und ihre Auswirkungen zu reduzieren.
+ Vermeiden Sie, Spalten unnötig zu indizieren.
+ Verhindern Sie plötzliche Spitzen der Datenbankverbindung, indem Sie einen Verbindungspool verwenden.
+ Beschränken Sie die maximale Anzahl von Verbindungen zur Datenbank als bewährte Methode

# LWLock:lock\$1manager
<a name="apg-waits.lw-lock-manager"></a>

Dieses Ereignis tritt ein, wenn die Aurora PostgreSQL-Engine den Speicherbereich der gemeinsam genutzten Sperre verwaltet, um eine Sperre zuzuweisen, zu überprüfen und aufzuheben, wenn eine Fast-Path-Sperre nicht möglich ist.

**Topics**
+ [Unterstützte Engine-Versionen](#apg-waits.lw-lock-manager.context.supported)
+ [Kontext](#apg-waits.lw-lock-manager.context)
+ [Wahrscheinliche Ursachen für erhöhte Wartezeiten](#apg-waits.lw-lock-manager.causes)
+ [Aktionen](#apg-waits.lw-lock-manager.actions)

## Unterstützte Engine-Versionen
<a name="apg-waits.lw-lock-manager.context.supported"></a>

Diese Warteereignisinformationen sind für Aurora PostgreSQL Version 9.6 und höher relevant. 

## Kontext
<a name="apg-waits.lw-lock-manager.context"></a>

Wenn Sie eine SQL-Anweisung ausgeben, zeichnet Aurora PostgreSQL Sperren auf, um die Struktur, Daten und Integrität Ihrer Datenbank während gleichzeitiger Vorgänge zu schützen. Der Motor kann dieses Ziel mit einer schnellen Pfadsperre oder einer nicht schnellen Pfadsperre erreichen. Eine Pfadsperre, die nicht schnell ist, ist teurer und erzeugt mehr Overhead als eine schnelle Pfadsperre.

### Schnelle Pfadsperre
<a name="apg-waits.lw-lock-manager.context.fast-path"></a>

Um den Overhead von Sperren zu reduzieren, die häufig genommen und freigegeben werden, aber selten in Konflikt geraten, können Backend-Prozesse eine schnelle Pfadsperrung verwenden. Die Datenbank verwendet diesen Mechanismus für Sperren, die die folgenden Kriterien erfüllen:
+ Sie verwenden die STANDARD–Sperrmethode.
+ Sie stellen eine Sperre für eine Datenbankbeziehung statt einer gemeinsamen Beziehung dar.
+ Sie sind schwache Sperren, die wahrscheinlich nicht in Konflikt stehen.
+ Die Engine kann schnell überprüfen, dass keine widersprüchlichen Sperren existieren können.

Die Engine kann keine schnelle Pfadsperre verwenden, wenn eine der folgenden Bedingungen erfüllt ist:
+ Die Sperre erfüllt nicht die vorhergehenden Kriterien.
+ Für den Backend-Prozess sind keine Slots mehr verfügbar.

Weitere Informationen zum Sperren von Fast Path finden Sie unter [Fast Path](https://github.com/postgres/postgres/blob/master/src/backend/storage/lmgr/README#L70-L76) in der README-Datei des PostgreSQL-Sperrmanagers und unter [pg-locks](https://www.postgresql.org/docs/15/view-pg-locks.html) in der PostgreSQL-Dokumentation. 

### Beispiel für ein Skalierungsproblem für den Sperrmanager
<a name="apg-waits.lw-lock-manager.context.lock-manager"></a>

In diesem Beispiel speichert eine Tabelle mit dem Namen `purchases` Daten aus fünf Jahren, aufgeteilt nach Tagen. Jede Partition hat zwei Indizes. Die folgende Abfolge von Ereignissen tritt auf:

1. Sie fragen Daten für viele Tage ab, wodurch die Datenbank viele Partitionen lesen muss.

1. Die Datenbank erstellt einen Sperreintrag für jede Partition. Wenn Partitionsindizes Teil des Optimizer-Zugriffspfads sind, erstellt die Datenbank auch für sie einen Sperreintrag.

1. Wenn die Anzahl der angeforderten Sperreneinträge für denselben Backend-Prozess höher als 16 ist, was dem Wert von `FP_LOCK_SLOTS_PER_BACKEND` entspricht, verwendet der Sperrenmanager die Sperrmethode ohne Fast Path.

Moderne Anwendungen haben möglicherweise Hunderte von Sitzungen. Wenn gleichzeitige Sitzungen das übergeordnete Element ohne ordnungsgemäßen Schnitt von Partitionen abfragen, erstellt die Datenbank möglicherweise Hunderte oder sogar Tausende von nicht schnellen Pfadsperren. Wenn diese Parallelität höher als die Anzahl von v istCPUs, tritt normalerweise das Wait-Ereignis auf`LWLock:lock_manager`.

**Anmerkung**  
Das Wait-Ereignis `LWLock:lock_manager` hat nichts mit der Anzahl der Partitionen oder Indizes in einem Datenbankschema zu tun. Stattdessen hängt es mit der Anzahl der nicht schnellen Pfadsperren zusammen, die die Datenbank steuern muss.

## Wahrscheinliche Ursachen für erhöhte Wartezeiten
<a name="apg-waits.lw-lock-manager.causes"></a>

Wenn das `LWLock:lock_manager` häufiger als normal auftritt, was möglicherweise auf ein Leistungsproblem hinweist, sind die wahrscheinlichsten Ursachen für plötzliche Spitzen wie folgt:
+ Gleichzeitige aktive Sitzungen führen Abfragen aus, die keine schnellen Pfadsperren verwenden. Diese Sitzungen überschreiten auch die maximale vCPU.
+ Eine große Anzahl gleichzeitiger aktiver Sitzungen greift auf eine stark partitionierte Tabelle zu. Jede Partition hat mehrere Indizes.
+ Die Datenbank erlebt einen Verbindungssturm. Standardmäßig erzeugen einige Anwendungen und Connection Pool-Software mehr Verbindungen, wenn die Datenbank langsam ist. Diese Praxis verschlimmert das Problem. Optimieren Sie Ihre Connection Pool-Software so, dass keine Verbindungsstürme auftreten.
+ Eine große Anzahl von Sitzungen fragt eine übergeordnete Tabelle ab, ohne Partitionen zu beschneiden.
+ Eine Datendefinitionssprache (DDL), Datenmanipulationssprache (DML) oder ein Wartungsbefehl sperrt ausschließlich eine Beleg-Beziehung oder Tupel, auf die häufig zugegriffen oder geändert werden.

## Aktionen
<a name="apg-waits.lw-lock-manager.actions"></a>

Abhängig von den Ursachen Ihres Warteereignisses empfehlen wir verschiedene Aktionen.

**Topics**
+ [Verwenden Sie das Beschneiden von Partitionen](#apg-waits.lw-lock-manager.actions.pruning)
+ [Entfernen unnötiger Indizes](#apg-waits.lw-lock-manager.actions.indexes)
+ [Optimieren Sie Ihre Abfragen für schnelles Pfadsperren](#apg-waits.lw-lock-manager.actions.tuning)
+ [Tune auf andere Warteereignisse](#apg-waits.lw-lock-manager.actions.other-waits)
+ [Reduzieren von Hardware-Engpässen](#apg-waits.lw-lock-manager.actions.hw-bottlenecks)
+ [Verwenden eines Verbindungs-Poolers](#apg-waits.lw-lock-manager.actions.pooler)
+ [Aktualisieren Sie Ihre Aurora PostgreSQL Version](#apg-waits.lw-lock-manager.actions.pg-version)

### Verwenden Sie das Beschneiden von Partitionen
<a name="apg-waits.lw-lock-manager.actions.pruning"></a>

Die *Partitionsbereinigung* ist eine Strategie zur Abfrageoptimierung, die nicht benötigte Partitionen von Tabellenscans ausschließt und dadurch die Leistung verbessert. Das Beschneiden der Partition ist standardmäßig aktiviert. Wenn es ausgeschaltet ist, schalten Sie es wie folgt ein.

```
SET enable_partition_pruning = on;
```

Abfragen können die Partitionsbereinigung nutzen, wenn ihre `WHERE`-Klausel die für die Partitionierung verwendete Spalte enthält. Weitere Informationen finden Sie unter [Partitionsbereinigung](https://www.postgresql.org/docs/current/ddl-partitioning.html#DDL-PARTITION-PRUNING) in der PostgreSQL-Dokumentation.

### Entfernen unnötiger Indizes
<a name="apg-waits.lw-lock-manager.actions.indexes"></a>

Ihre Datenbank enthält möglicherweise nicht verwendete oder selten verwendete Indizes. Wenn ja, erwägen Sie, sie zu löschen. Führen Sie eine der folgenden Aufgaben aus:
+ Erfahren Sie, wie Sie unnötige Indizes finden, indem Sie [Ungenutzte Indizes](https://wiki.postgresql.org/wiki/Index_Maintenance#Unused_Indexes) im PostgreSQL-Wiki lesen.
+ Führen Sie PG Collector aus. Dieses SQL-Skript sammelt Datenbankinformationen und präsentiert sie in einem konsolidierten HTML-Bericht. Überprüfen Sie den Abschnitt „Unbenutzte Indizes“. Weitere Informationen finden Sie unter [pg-collector im Labs-Repository](https://github.com/awslabs/pg-collector). AWS GitHub 

### Optimieren Sie Ihre Abfragen für schnelles Pfadsperren
<a name="apg-waits.lw-lock-manager.actions.tuning"></a>

Um herauszufinden, ob Ihre Abfragen Fast Path Locking verwenden, fragen Sie die `fastpath`-Spalte in der `pg_locks`-Tabelle ab. Wenn Ihre Abfragen keine schnelle Pfadsperre verwenden, versuchen Sie, die Anzahl der Beziehungen pro Abfrage auf weniger als 16 zu reduzieren.

### Tune auf andere Warteereignisse
<a name="apg-waits.lw-lock-manager.actions.other-waits"></a>

Wenn `LWLock:lock_manager` in der Liste der Top-Waits an erster oder zweiter Stelle steht, überprüfen Sie, ob die folgenden Wait-Ereignisse auch in der Liste erscheinen:
+ `Lock:Relation`
+ `Lock:transactionid`
+ `Lock:tuple`

Wenn die vorhergehenden Ereignisse in der Liste hoch erscheinen, sollten Sie zuerst diese Warteereignisse optimieren. Diese Ereignisse können ein Treiber für `LWLock:lock_manager`.

### Reduzieren von Hardware-Engpässen
<a name="apg-waits.lw-lock-manager.actions.hw-bottlenecks"></a>

Möglicherweise haben Sie einen Hardware-Engpass wie CPU-Hunger oder maximale Auslastung Ihrer Amazon EBS-Bandbreite. Ziehen Sie in diesen Fällen die Verringerung der Hardware-Engpässe in Betracht. Berücksichtigen Sie die folgenden Aktionen:
+ Skalieren Sie Ihre Instance-Klasse hoch.
+ Optimieren Sie Abfragen, die große Mengen an CPU und Speicher verbrauchen.
+ Ändern Sie Ihre Anwendungslogik.
+ Archiviere deine Daten.

Weitere Informationen zu CPU, Arbeitsspeicher und EBS-Netzwerkbandbreite finden Sie unter [Amazon-RDS-Instance-Typen](https://aws.amazon.com/rds/instance-types/).

### Verwenden eines Verbindungs-Poolers
<a name="apg-waits.lw-lock-manager.actions.pooler"></a>

Wenn Ihre Gesamtzahl aktiver Verbindungen die maximale vCPU überschreitet, benötigen mehr Betriebssystemprozesse CPU, als Ihr Instance-Typ unterstützen kann. Ziehen Sie in diesem Fall die Verwendung oder Abstimmung eines Verbindungspool in Betracht. Weitere Informationen über das v CPUs für Ihren Instance-Typ finden Sie unter [Amazon RDS-Instance-Typen](https://aws.amazon.com/rds/instance-types/).

Weitere Informationen zum Verbindungspooling finden Sie in den folgenden Ressourcen:
+ [Amazon RDS-Proxy für Aurora](rds-proxy.md)
+ [pgbouncer](http://www.pgbouncer.org/usage.html)
+ [Verbindungspools und Datenquellen](https://www.postgresql.org/docs/7.4/jdbc-datasource.html) in der *PostgreSQL-Dokumentation*

### Aktualisieren Sie Ihre Aurora PostgreSQL Version
<a name="apg-waits.lw-lock-manager.actions.pg-version"></a>

Wenn Ihre aktuelle Version von Aurora PostgreSQL niedriger als 12 ist, aktualisieren Sie auf Version 12 oder höher. PostgreSQL Versionen 12 und 13 haben einen verbesserten Partitionsmechanismus. Weitere Informationen zu Version 12 finden Sie in den [Versionshinweisen zu PostgreSQL 12.0]( https://www.postgresql.org/docs/release/12.0/). Weitere Informationen zum Aktualisieren von Aurora PostgreSQL finden Sie unter [Aktualisierungen der Datenbank-Engine für Amazon Aurora PostgreSQL](AuroraPostgreSQL.Updates.md).

# LWLock:MultiXact
<a name="apg-waits.lwlockmultixact"></a>

Die Warteereignisse `LWLock:MultiXactMemberBuffer`, `LWLock:MultiXactOffsetBuffer`, `LWLock:MultiXactMemberSLRU` und `LWLock:MultiXactOffsetSLRU` geben an, dass eine Sitzung darauf wartet, eine Liste von Transaktionen abzurufen, die dieselbe Zeile in einer bestimmten Tabelle ändern. 
+ `LWLock:MultiXactMemberBuffer` – Ein Prozess wartet auf I/O in einem einfachen, am wenigsten zuletzt verwendeten (SLRU) Puffer für ein Multixact-Mitglied.
+ `LWLock:MultiXactMemberSLRU` – Ein Prozess wartet darauf, auf den einfachen, am wenigsten zuletzt verwendeten (SLRU) Cache für ein Multixact-Mitglied zuzugreifen.
+ `LWLock:MultiXactOffsetBuffer` – Ein Prozess wartet auf I/O in einem einfachen, am wenigsten zuletzt verwendeten (SLRU) Puffer für ein Multixact-Offset.
+ `LWLock:MultiXactOffsetSLRU` – Ein Prozess wartet darauf, auf den einfachen, am wenigsten zuletzt verwendeten (SLRU) Cache für ein Multixact-Offset zuzugreifen.

**Topics**
+ [Unterstützte Engine-Versionen](#apg-waits.xactsync.context.supported)
+ [Kontext](#apg-waits.lwlockmultixact.context)
+ [Wahrscheinliche Ursachen für erhöhte Wartezeiten](#apg-waits.lwlockmultixact.causes)
+ [Aktionen](#apg-waits.lwlockmultixact.actions)

## Unterstützte Engine-Versionen
<a name="apg-waits.xactsync.context.supported"></a>

Diese Warteereignisinformationen werden für alle Versionen von Aurora PostgreSQL unterstützt.

## Kontext
<a name="apg-waits.lwlockmultixact.context"></a>

*Multixact* ist eine Datenstruktur, die eine Liste von Transaktions-IDs (XIDs) speichert, welche dieselbe Tabellenzeile ändern. Wenn eine einzelne Transaktion auf eine Zeile in einer Tabelle verweist, wird die Transaktions-ID in der Kopfzeile der Tabelle gespeichert. Verweisen mehrere Transaktionen auf dieselbe Zeile in einer Tabelle, wird die Liste der Transaktions-IDs in der Multixact-Datenstruktur gespeichert. Die Multixact-Warteereignisse geben an, dass eine Sitzung die Liste der Transaktionen, die sich auf eine bestimmte Zeile in einer Tabelle beziehen, aus der Datenstruktur abruft.

## Wahrscheinliche Ursachen für erhöhte Wartezeiten
<a name="apg-waits.lwlockmultixact.causes"></a>

3 häufige Ursachen für die Verwendung von Multixact sind die folgenden:
+ **Untertransaktionen expliziter Savepoints** – Wenn Sie explizit einen Savepoint in Ihren Transaktionen erstellen, werden neue Transaktionen für dieselbe Zeile generiert. Verwenden Sie beispielsweise `SELECT FOR UPDATE`, `SAVEPOINT` und dann `UPDATE`. 

  Einige Treiber, objektrelationale Mappers (ORMs) und Abstraktionsschichten verfügen über Konfigurationsoptionen, um alle Operationen automatisch mit Savepoints zu umschließen. Dies kann bei einigen Workloads zu vielen Multixact-Warteereignissen führen. Die `autosave`-Option des PostgreSQL-JDBC-Treibers ist ein Beispiel dafür. Weitere Informationen finden Sie unter [pgJDBC](https://jdbc.postgresql.org/) in der PostgreSQL-JDBC-Dokumentation. Ein anderes Beispiel ist der PostgreSQL-ODBC-Treiber und seine `protocol`-Option. Weitere Informationen finden Sie unter [psqlODBC-Konfigurationsoptionen](https://odbc.postgresql.org/docs/config.html) in der Dokumentation zu PostgreSQL-ODBC-Treibern. 
+ **Untertransaktionen von PL/pgSQL-EXCEPTION-Klauseln** – Jede `EXCEPTION`-Klausel, die Sie in Ihren PL/pgSQL-Funktionen oder -Prozeduren schreiben, erstellt intern einen `SAVEPOINT`.
+ **Fremdschlüssel** – Mehrere Transaktionen erwerben eine Freigabesperre für den übergeordneten Datensatz.

Wenn eine bestimmte Zeile in einer Operation mit mehreren Transaktionen enthalten ist, müssen für die Verarbeitung der Zeile die Transaktions-IDs aus den `multixact`-Auflistungen abgerufen werden. Wenn durch Lookups der Multixact nicht aus dem Speichercache abgerufen werden kann, muss die Datenstruktur aus der Aurora-Speicherschicht gelesen werden. Dieser I/O-Vorgang aus dem Speicher bedeutet, dass SQL-Abfragen länger dauern können. Speicher-Cache-Fehler können bei starker Auslastung aufgrund einer großen Anzahl von mehreren Transaktionen auftreten. All diese Faktoren tragen zu einer Zunahme dieses Warteereignisses bei.

## Aktionen
<a name="apg-waits.lwlockmultixact.actions"></a>

Abhängig von den Ursachen Ihres Warteereignisses empfehlen wir verschiedene Aktionen. Einige dieser Aktionen können dazu beitragen, die Warteereignisse sofort zu reduzieren. Andere erfordern jedoch möglicherweise eine Untersuchung und Korrektur, um Ihren Workload zu skalieren.

**Topics**
+ [Durchführen einer Bereinigungseinfrierung auf Tabellen mit diesem Warteereignis](#apg-waits.lwlockmultixact.actions.vacuumfreeze)
+ [Erhöhen der Häufigkeit der Selbstbereinigung in Tabellen mit diesem Warteereignis](#apg-waits.lwlockmultixact.actions.autovacuum)
+ [Erhöhen der Speicherparameter](#apg-waits.lwlockmultixact.actions.memoryparam)
+ [Reduzieren von Transaktionen mit langer Laufzeit](#apg-waits.lwlockmultixact.actions.longtransactions)
+ [Langfristige Aktionen](#apg-waits.lwlockmultixact.actions.longactions)

### Durchführen einer Bereinigungseinfrierung auf Tabellen mit diesem Warteereignis
<a name="apg-waits.lwlockmultixact.actions.vacuumfreeze"></a>

Wenn die Anzahl dieses Warteereignisses plötzlich stark ansteigt und sich auf Ihre Produktionsumgebung auswirkt, können Sie eine der folgenden temporären Methoden verwenden, um die Anzahl zu reduzieren.
+ Verwenden Sie *VACUUM FREEZE* für die betroffene Tabelle oder Tabellenpartition, um das Problem sofort zu beheben. Weitere Informationen finden Sie unter [VACUUM](https://www.postgresql.org/docs/current/sql-vacuum.html).
+ Verwenden Sie die Klausel VACUUM (FREEZE, INDEX\$1CLEANUP FALSE), um eine schnelle Bereinigung durch Überspringen von Indizes durchzuführen. Weitere Informationen finden Sie unter [Möglichst schnelles Bereinigen einer Tabelle](https://docs.aws.amazon.com/AmazonRDS/latest/UserGuide/Appendix.PostgreSQL.CommonDBATasks.Autovacuum.LargeIndexes.html#Appendix.PostgreSQL.CommonDBATasks.Autovacuum.LargeIndexes.Executing).

### Erhöhen der Häufigkeit der Selbstbereinigung in Tabellen mit diesem Warteereignis
<a name="apg-waits.lwlockmultixact.actions.autovacuum"></a>

Nach dem Scannen aller Tabellen in allen Datenbanken entfernt die VACUUM-Operation schließlich Multixacts, wobei die ältesten Multixact-Werte weiterverwendet werden. Weitere Informationen finden Sie unter [Multixacts und Wraparound](https://www.postgresql.org/docs/current/routine-vacuuming.html#VACUUM-FOR-MULTIXACT-WRAPAROUND). Um die LWLock:MultiXact-Warteereignisse auf ein Minimum zu beschränken, müssen Sie den VACUUM-Prozess so oft wie nötig ausführen. Stellen Sie dazu sicher, dass der VACUUM-Prozess in Ihrem Aurora PostgreSQL-DB-Cluster optimal konfiguriert ist.

Wenn die Verwendung von VACUUM FREEZE für die betroffene Tabelle oder Tabellenpartition das Problem mit dem Warteereignis behebt, empfehlen wir, einen Scheduler wie `pg_cron` für die VACUUM-Durchführung zu verwenden, anstatt den Selbstbereinigung auf Instance-Ebene anzupassen. 

Damit die Selbstbereinigung häufiger stattfindet, können Sie den Wert des `autovacuum_multixact_freeze_max_age`-Speicherparameters in der betroffenen Tabelle reduzieren. Weitere Informationen finden Sie unter [autovacuum\$1multixact\$1freeze\$1max\$1age](https://www.postgresql.org/docs/current/runtime-config-autovacuum.html#GUC-AUTOVACUUM-MULTIXACT-FREEZE-MAX-AGE).

### Erhöhen der Speicherparameter
<a name="apg-waits.lwlockmultixact.actions.memoryparam"></a>

Sie können die Speichernutzung für Multixact-Caches optimieren, indem Sie die folgenden Parameter anpassen. Diese Einstellungen steuern, wie viel Speicher für diese Caches reserviert wird. Dies kann dazu beitragen, Multixact-Warteereignisse in Ihrem Workload zu reduzieren. Wir empfehlen, mit den folgenden Werten zu beginnen:

Für Aurora PostgreSQL 17 und höher:  
+ `multixact_offset_buffers` = 128
+ `multixact_member_buffers` = 256

Für Aurora PostgreSQL 16 und niedriger:  
+ `multixact_offsets_cache_size` = 128
+ `multixact_members_cache_size` = 256

**Anmerkung**  
In Aurora PostgreSQL 17 wurden Parameternamen von `multixact_offsets_cache_size` in `multixact_offset_buffers` und von `multixact_members_cache_size` in `multixact_member_buffers` geändert, um sie an die Community von PostgreSQL 17 anzupassen.

Sie können diese Parameter auf Cluster-Ebene festlegen, sodass alle Instances in Ihrem Cluster konsistent bleiben. Wir empfehlen Ihnen, die Werte zu testen und anzupassen, damit sie Ihren spezifischen Workload-Anforderungen und Ihrer Instance-Klasse optimal entsprechen. Sie müssen die Writer-Instance neu starten, damit die Parameteränderung wirksam wird.

Die Parameter werden in Form von Multixact-Cache-Einträgen ausgedrückt. Jeder Cache-Eintrag belegt Speicherplatz Höhe von `8 KB`. Um den gesamten reservierten Speicher zu berechnen, multiplizieren Sie jeden Parameterwert mit `8 KB`. Wenn Sie beispielsweise einen Parameter auf 128 setzen, beträgt der gesamte reservierte Speicher `128 * 8 KB = 1 MB`.

### Reduzieren von Transaktionen mit langer Laufzeit
<a name="apg-waits.lwlockmultixact.actions.longtransactions"></a>

Transaktionen mit langer Laufzeit führen dazu, dass der Bereinigungsprozess Informationen beibehält, bis die Transaktion bestätigt oder die schreibgeschützte Transaktion geschlossen wird. Wir empfehlen, langlebige Transaktionen proaktiv zu überwachen und zu verwalten. Weitere Informationen finden Sie unter [Die Datenbank läuft seit langem inaktiv in Transaktionsverbindung](PostgreSQL.Tuning_proactive_insights.md#proactive-insights.idle-txn). Ändern Sie Ihre Anwendung, wenn möglich, um die Verwendung von Transaktionen mit langer Laufzeit zu vermeiden oder zu minimieren.

### Langfristige Aktionen
<a name="apg-waits.lwlockmultixact.actions.longactions"></a>

Untersuchen Sie Ihren Workload, um die Ursache für den Multixact-Überlauf zu ermitteln. Sie müssen das Problem beheben, um Ihren Workload zu skalieren und Warteereignisse zu reduzieren.
+ Sie müssen die DDL (Datendefinitionssprache) analysieren, die zum Erstellen Ihrer Tabellen verwendet wurde. Stellen Sie sicher, dass die Tabellenstrukturen und Indizes optimal gestaltet sind.
+ Wenn die betroffenen Tabellen Fremdschlüssel enthalten, ermitteln Sie, ob sie benötigt werden oder ob es eine andere Möglichkeit gibt, die referenzielle Integrität durchzusetzen.
+ Wenn eine Tabelle große, ungenutzte Indizes enthält, kann das dazu führen, dass der Selbstbereinigungsvorgang nicht zu Ihrem Workload passt und die Ausführung möglicherweise blockiert. Um dies zu vermeiden, suchen Sie nach ungenutzten Indizes und entfernen Sie diese vollständig. Weitere Informationen finden Sie unter [Verwalten der automatischen Bereinigung mit großen Indizes](https://docs.aws.amazon.com/AmazonRDS/latest/UserGuide/Appendix.PostgreSQL.CommonDBATasks.Autovacuum.LargeIndexes.html).
+ Reduzieren Sie die Verwendung von Savepoints in Ihren Transaktionen.

# LWLock:pg\$1stat\$1statements
<a name="apg-rpg-lwlockpgstat"></a>

Das LWLock Warteereignis:PG\$1STAT\$1STATEMENTS tritt ein, wenn die Erweiterung die Hashtabelle, die SQL-Anweisungen verfolgt, exklusiv sperrt. `pg_stat_statements` Dies passiert in folgenden Szenarien:
+ Wenn die Anzahl der nachverfolgten Anweisungen den konfigurierten `pg_stat_statements.max`-Parameterwert erreicht und Platz für weitere Einträge geschaffen werden muss, sortiert die Erweiterung die Anzahl der Aufrufe, entfernt die 5 % der am wenigsten ausgeführten Anweisungen und füllt den Hash mit den verbleibenden Einträgen neu auf.
+ Wenn `pg_stat_statements` eine `garbage collection`-Operation für die `pgss_query_texts.stat`-Datei auf der Festplatte durchführt und die Datei neu schreibt

**Topics**
+ [Unterstützte Engine-Versionen](#apg-rpg-lwlockpgstat.supported)
+ [Kontext](#apg-rpg-lwlockpgstat.context)
+ [Wahrscheinliche Ursachen für erhöhte Wartezeiten](#apg-rpg-lwlockpgstat.causes)
+ [Aktionen](#apg-rpg-lwlockpgstat.actions)

## Unterstützte Engine-Versionen
<a name="apg-rpg-lwlockpgstat.supported"></a>

 Diese Warteereignisinformationen werden für alle Versionen von Aurora PostgreSQL unterstützt. 

## Kontext
<a name="apg-rpg-lwlockpgstat.context"></a>

**Grundlagen der pg\$1stat\$1statements-Erweiterung** – Die pg\$1stat\$1statements-Erweiterung verfolgt Statistiken zur Ausführung von SQL-Anweisungen in einer Hash-Tabelle nach. Die Erweiterung verfolgt SQL-Anweisungen bis zu dem durch den `pg_stat_statements.max`-Parameter definierten Grenzwert nach. Dieser Parameter bestimmt die maximale Anzahl von Anweisungen, die nachverfolgt werden können, was der maximalen Anzahl von Zeilen in der pg\$1stat\$1statements-Ansicht entspricht.

**Persistenz von Anweisungsstatistiken** – Die Erweiterung behält die Anweisungsstatistiken über Instance-Neustarts hinweg bei, indem sie Folgendes durchführt:
+ Schreiben von Daten in eine Datei mit dem Namen pg\$1stat\$1statements.stat
+ Steuern des Persistenzverhaltens mit dem pg\$1stat\$1statements.save-Parameter

Wenn pg\$1stat\$1statements.save auf Folgendes gesetzt ist:
+ on (Standard): Statistiken werden beim Herunterfahren gespeichert und beim Serverstart neu geladen
+ off: Statistiken werden weder beim Herunterfahren gespeichert noch beim Serverstart neu geladen

**Abfragetextspeicher** – Die Erweiterung speichert den Text nachverfolgter Abfragen in einer Datei mit dem Namen `pgss_query_texts.stat`. Diese Datei kann auf das Doppelte der durchschnittlichen Größe aller nachverfolgten SQL-Anweisungen anwachsen, ehe eine Garbage Collection erfolgt. Die Erweiterung erfordert eine exklusive Hash-Tabellen-Sperre während der Bereinigungsvorgänge und beim Neuschreiben der `pgss_query_texts.stat`-Datei.

**Prozess der Freigabe von Anweisungen** – Wenn die Anzahl der nachverfolgten Anweisungen den `pg_stat_statements.max`-Grenzwert erreicht und neue Anweisungen nachverfolgt werden müssen, führt die Erweiterung Folgendes durch:
+ Erhält eine exklusive Sperre (LWLock:pg\$1stat\$1statements) für die Hashtabelle.
+ Sie lädt vorhandene Daten in den lokalen Speicher.
+ Sie führt eine Schnellsortierung auf der Grundlage der Anzahl der Aufrufe durch.
+ Sie entfernt die am wenigsten aufgerufenen Anweisungen (unterste 5 %).
+ Sie füllt die Hash-Tabelle mit den verbleibenden Einträgen neu auf.

**Überwachung der Anweisungsfreigabe** – In PostgreSQL 14 und höher können Sie die Freigabe von Anweisungen mit der pg\$1stat\$1statements\$1info-Ansicht überwachen. Diese Ansicht enthält eine Freigabe-Spalte, in der angezeigt wird, wie oft Anweisungen freigegeben wurden, um Platz für neue Anweisungen zu schaffen.

Wenn die Freigabe von Anweisungen häufig erfolgt, führt dies zu einer häufigeren Garbage Collection bei der `pgss_query_texts.stat`-Datei auf der Festplatte.

## Wahrscheinliche Ursachen für erhöhte Wartezeiten
<a name="apg-rpg-lwlockpgstat.causes"></a>

Zu den typischen Ursachen für eine Zunahme bei den `LWLock:pg_stat_statements`-Wartezeiten gehören:
+ eine Zunahme bei der Anzahl eindeutiger Abfragen, die von der Anwendung verwendet werden
+ ein `pg_stat_statements.max`-Parameterwert, der im Vergleich zur Anzahl der verwendeten eindeutigen Abfragen klein ist

## Aktionen
<a name="apg-rpg-lwlockpgstat.actions"></a>

Abhängig von den Ursachen Ihres Warteereignisses empfehlen wir verschiedene Aktionen. Sie können `LWLock:pg_stat_statements`-Ereignisse identifizieren, indem Sie Erkenntnisse zur Amazon-RDS-Leistung verwenden oder die `pg_stat_activity`-Ansicht abfragen.

Passen Sie die folgenden `pg_stat_statements` Parameter an, um das Tracking-Verhalten zu steuern und die Warteereignisse von pg\$1stat\$1-Anweisungen zu reduzieren. LWLock

**Topics**
+ [Deaktivieren des pg\$1stat\$1statements.track-Parameters](#apg-rpg-lwlockpgstat.actions.disabletrack)
+ [Erhöhen des pg\$1stat\$1statements.max-Parameters](#apg-rpg-lwlockpgstat.actions.increasemax)
+ [Deaktivieren des pg\$1stat\$1statements.track\$1utility-Parameters](#apg-rpg-lwlockpgstat.actions.disableutility)

### Deaktivieren des pg\$1stat\$1statements.track-Parameters
<a name="apg-rpg-lwlockpgstat.actions.disabletrack"></a>

Wenn sich das LWLock Warteereignis:pg\$1stat\$1statements negativ auf die Datenbankleistung auswirkt und eine schnelle Lösung erforderlich ist, bevor die Ansicht weiter analysiert wird, um die Ursache `pg_stat_statements` zu ermitteln, kann der Parameter deaktiviert werden, indem er auf gesetzt wird. `pg_stat_statements.track` `none` Dadurch wird die Erfassung von Anweisungsstatistiken deaktiviert.

### Erhöhen des pg\$1stat\$1statements.max-Parameters
<a name="apg-rpg-lwlockpgstat.actions.increasemax"></a>

Erhöhen Sie den Wert des `pg_stat_statements.max`-Parameters, um die Freigabe zu reduzieren und die Garbage Collection für die `pgss_query_texts.stat`-Datei auf der Festplatte zu minimeren. Der Standardwert ist `5,000`.

**Anmerkung**  
Der `pg_stat_statements.max`-Parameter ist statisch. Sie müssen Ihre DB-Instance neu starten, um Änderungen an diesem Parameter zu übernehmen. 

### Deaktivieren des pg\$1stat\$1statements.track\$1utility-Parameters
<a name="apg-rpg-lwlockpgstat.actions.disableutility"></a>

Sie können die pg\$1stat\$1statements-Ansicht analysieren, um festzustellen, welche Dienstprogrammbefehle die meisten Ressourcen verbrauchen, die von `pg_stat_statements` nachverfolgt werden.

Der `pg_stat_statements.track_utility`-Parameter steuert, ob das Modul Dienstprogrammbefehle nachverfolgt, zu denen alle Befehle außer SELECT, INSERT, UPDATE, DELETE und MERGE gehören. Dieser Parameter ist standardmäßig auf `on` festgelegt.

Wenn Ihre Anwendung beispielsweise viele Savepoint-Abfragen verwendet, die von Natur aus eindeutig sind, kann dies die Freigabe von Anweisungen erhöhen. Als Abhilfemaßnahme können Sie den `pg_stat_statements.track_utility`-Parameter deaktivieren, sodass Savepoint-Abfragen nicht mehr von `pg_stat_statements` nachverfolgt werden.

**Anmerkung**  
Der `pg_stat_statements.track_utility`-Parameter ist ein dynamischer Parameter. Sie können dessen Wert ändern, ohne Ihre Datenbank-Instance neu starten zu müssen.

**Example Beispiel für eindeutige Savepoint-Abfragen in pg\$1stat\$1statements**  <a name="savepoint-queries"></a>

```
                     query                       |       queryid       
-------------------------------------------------+---------------------
 SAVEPOINT JDBC_SAVEPOINT_495701                 | -7249565344517699703
 SAVEPOINT JDBC_SAVEPOINT_1320                   | -1572997038849006629
 SAVEPOINT JDBC_SAVEPOINT_26739                  |  54791337410474486
 SAVEPOINT JDBC_SAVEPOINT_1294466                |  8170064357463507593
 ROLLBACK TO SAVEPOINT JDBC_SAVEPOINT_65016      | -33608214779996400
 SAVEPOINT JDBC_SAVEPOINT_14185                  | -2175035613806809562
 SAVEPOINT JDBC_SAVEPOINT_45837                  | -6201592986750645383
 SAVEPOINT JDBC_SAVEPOINT_1324                   |  6388797791882029332
```

PostgreSQL 17 führt mehrere Verbesserungen für die Nachverfolgung von Dienstprogrammbefehlen ein:
+ Savepoint-Namen werden jetzt als Konstanten angezeigt.
+ Die globale Transaktion IDs (GIDs) von zweiphasigen Commit-Befehlen wird jetzt als Konstanten angezeigt.
+ Die Namen von DEALLOCATE-Anweisungen werden als Konstanten angezeigt.
+ CALL-Parameter werden jetzt als Konstanten angezeigt.

# Timeout:PgSleep
<a name="apg-waits.timeoutpgsleep"></a>

Das `Timeout:PgSleep`-Ereignis tritt ein, wenn ein Serverprozess die `pg_sleep`-Funktion aufgerufen hat und auf das Ablaufen des Sleep-Timeouts wartet.

**Topics**
+ [Unterstützte Engine-Versionen](#apg-waits.timeoutpgsleep.context.supported)
+ [Wahrscheinliche Ursachen für erhöhte Wartezeiten](#apg-waits.timeoutpgsleep.causes)
+ [Aktionen](#apg-waits.timeoutpgsleep.actions)

## Unterstützte Engine-Versionen
<a name="apg-waits.timeoutpgsleep.context.supported"></a>

Diese Warteereignisinformationen werden für alle Versionen von Aurora PostgreSQL unterstützt.

## Wahrscheinliche Ursachen für erhöhte Wartezeiten
<a name="apg-waits.timeoutpgsleep.causes"></a>

Dieses Wait-Ereignis tritt auf, wenn eine Anwendung, eine gespeicherte Funktion oder ein Benutzer eine SQL-Anweisung ausgibt, die eine der folgenden Funktionen aufruft:
+ `pg_sleep`
+ `pg_sleep_for`
+ `pg_sleep_until`

Die vorhergehenden Funktionen verzögern die Ausführung, bis die angegebene Anzahl von Sekunden verstrichen ist. Beispielsweise pausiert `SELECT pg_sleep(1)` für 1 Sekunde. Weitere Informationen finden Sie unter [Ausführung verzögern](https://www.postgresql.org/docs/current/functions-datetime.html#FUNCTIONS-DATETIME-DELAY) in der PostgreSQL-Dokumentation.

## Aktionen
<a name="apg-waits.timeoutpgsleep.actions"></a>

Identifizieren Sie die Anweisung, die die `pg_sleep`-Funktion ausgeführt hat. Überprüfen Sie, ob die Verwendung der Funktion angemessen ist.