Auf dieser Seite finden Sie Best Practices zur Leistungsoptimierung bei der Verwendung eines Cloud Run-Dienstes mit einer GPU für KI-Inferenzen, wobei der Schwerpunkt auf Large Language Models (LLMs) liegt.
Sie müssen einen Cloud Run-Dienst erstellen und bereitstellen, der in Echtzeit auf Skalierungsereignisse reagieren kann. Das bedeutet, dass Sie Folgendes tun müssen:
- Verwenden Sie Modelle, die schnell geladen werden und nur eine minimale Transformation in GPU-fähige Strukturen erfordern, und optimieren Sie das Laden.
- Verwenden Sie Konfigurationen, die eine maximale, effiziente, gleichzeitige Ausführung ermöglichen, um die Anzahl der GPUs zu reduzieren, die zum Ausführen einer Zielanfrage pro Sekunde erforderlich sind, und gleichzeitig die Kosten niedrig zu halten.
Empfohlene Methoden zum Laden großer ML-Modelle in Cloud Run
Google empfiehlt, ML-Modelle entweder in Container-Images zu speichern oder das Laden aus Cloud Storage zu optimieren.
Vor- und Nachteile beim Speichern und Laden von ML-Modellen
Hier ist ein Vergleich der Optionen:
Modellstandort | Bereitstellungszeit | Entwicklungserfahrung | Containerstartzeit | Speicherkosten |
Container-Image | Langsam. Der Import eines Images mit einem großen Modell in Cloud Run dauert länger. | Änderungen am Container-Image erfordern eine erneute Bereitstellung, was bei großen Images langsam sein kann. | Abhängig von der Größe des Modells. Bei sehr großen Modellen sollten Sie Cloud Storage verwenden, um eine vorhersehbarere, aber langsamere Leistung zu erzielen. | Potenziell mehrere Kopien in Artifact Registry. |
Cloud Storage über das Cloud Storage FUSE-Volume bereitgestellt | Schnell. Modell, das beim Starten des Containers heruntergeladen wurde. | Einfach einzurichten, erfordert keine Änderungen am Docker-Image. | Schnell bei Netzwerkoptimierungen. Der Download wird nicht parallelisiert. | Eine Kopie in Cloud Storage. |
Cloud Storage, gleichzeitig mit dem Google Cloud CLI-Befehl gcloud storage cp oder der Cloud Storage API heruntergeladen, wie im Codebeispiel für den gleichzeitigen Download über den Übertragungsmanager gezeigt.
|
Schnell. Modell, das beim Starten des Containers heruntergeladen wurde. | Die Einrichtung ist etwas schwieriger, da Sie entweder die Google Cloud CLI auf dem Image installieren oder Ihren Code so aktualisieren müssen, dass die Cloud Storage API verwendet wird. | Schnell bei Netzwerkoptimierungen. Die Google Cloud CLI lädt die Modelldatei parallel herunter, was schneller ist als die FUSE-Bereitstellung. | Eine Kopie in Cloud Storage. |
Internet | Schnell. Modell, das beim Starten des Containers heruntergeladen wurde. | In der Regel einfacher (viele Frameworks laden Modelle aus zentralen Repositories herunter). | In der Regel schlecht und unvorhersehbar:
|
Abhängig vom Anbieter des Modell-Hostings. |
Modelle in Container-Images speichern
Wenn Sie ML-Modelle in Container-Images speichern, die in Cloud Run bereitgestellt werden, profitieren Sie von den integrierten Optimierungen für das Streaming von Container-Images in Cloud Run. So wird die Dateiladezeit ohne zusätzliche Netzwerkoptimierungen maximiert.
Das Erstellen von Containern mit ML-Modellen kann einige Zeit in Anspruch nehmen. Wenn Sie Cloud Build verwenden, können Sie Cloud Build so konfigurieren, dass größere Maschinen für schnellere Builds verwendet werden. Erstellen Sie dazu ein Image mit einer Build-Konfigurationsdatei mit den folgenden Schritten:
steps: - name: 'gcr.io/cloud-builders/docker' args: ['build', '-t', 'IMAGE', '.'] - name: 'gcr.io/cloud-builders/docker' args: ['push', 'IMAGE'] images: - IMAGE options: machineType: 'E2_HIGHCPU_32' diskSizeGb: '500'
Es kann eine Modellkopie pro Bild erstellt werden, wenn sich die Ebene mit dem Modell zwischen den Bildern unterscheidet (unterschiedlicher Hash). Es können zusätzliche Kosten für die Artefaktdatenbank anfallen, da es eine Kopie des Modells pro Bild geben kann, wenn Ihre Modellebene für jedes Bild eindeutig ist.
Modelle in Cloud Storage speichern
Wenn Sie das Laden von ML-Modellen aus Cloud Storage optimieren möchten, entweder über Cloud Storage-Volumen-Bereitstellungen oder direkt über die Cloud Storage API oder die Befehlszeile, müssen Sie Direct VPC mit der Einstellung für ausgehenden Traffic auf all-traffic
und Private Service Connect verwenden.
Modelle aus dem Internet laden
Um das Laden von ML-Modellen aus dem Internet zu optimieren, leiten Sie den gesamten Traffic über das VPC-Netzwerk, wobei die Egress-Einstellung auf all-traffic
festgelegt ist. Richten Sie dann Cloud NAT ein, um das öffentliche Internet mit hoher Bandbreite zu erreichen.
Erwägungen zu Build, Bereitstellung, Laufzeit und Systemdesign
In den folgenden Abschnitten werden Überlegungen zum Build-, Bereitstellungs-, Laufzeit- und Systemdesign beschrieben.
Während des Builds
In der folgenden Liste finden Sie einige Punkte, die Sie bei der Planung Ihres Builds berücksichtigen sollten:
- Wählen Sie ein gutes Basis-Image aus. Sie sollten mit einem Image aus den Deep Learning Containers oder der NVIDIA Container Registry für das von Ihnen verwendete ML-Framework beginnen. Auf diesen Images sind die neuesten leistungsbezogenen Pakete installiert. Wir raten davon ab, ein benutzerdefiniertes Image zu erstellen.
- Wählen Sie Modelle mit 4‑Bit-Quantisierung aus, um die Parallelität zu maximieren, es sei denn, Sie können nachweisen, dass sie sich auf die Ergebnisqualität auswirken. Durch die Quantisierung werden kleinere und schnellere Modelle erstellt, wodurch der für die Bereitstellung des Modells erforderliche GPU-Arbeitsspeicher reduziert wird. Außerdem kann die Parallelität bei der Laufzeit erhöht werden. Idealerweise sollten die Modelle mit der Zielbittiefe trainiert werden, anstatt auf diese herunterquantisiert zu werden.
- Wählen Sie ein Modellformat mit kurzen Ladezeiten aus, um die Containerstartzeit zu minimieren, z. B. GGUF. Diese Formate spiegeln den Zielquantisierungstyp genauer wider und erfordern beim Laden auf die GPU weniger Transformationen. Verwenden Sie aus Sicherheitsgründen keine Checkpoints im Pickle-Format.
- LLM-Caches beim Build erstellen und vorwärmen Starten Sie LLM auf dem Build-Computer, während Sie das Docker-Image erstellen. Aktivieren Sie das Prompt-Caching und geben Sie häufig verwendete oder Beispiel-Prompts ein, um den Cache für die praktische Nutzung vorzuwärmen. Speichern Sie die generierten Ausgaben, um sie zur Laufzeit zu laden.
- Speichern Sie Ihr eigenes Inferenzmodell, das Sie während der Erstellung generieren. Das spart viel Zeit im Vergleich zum Laden weniger effizient gespeicherter Modelle und zum Anwenden von Transformationen wie Quantisierung beim Starten des Containers.
Bei der Bereitstellung
- Achten Sie darauf, dass Sie die Gleichzeitigkeit des Dienstes in Cloud Run korrekt festlegen.
- Passen Sie Ihre Startprüfungen an Ihre Konfiguration an.
Startprüfungen ermitteln, ob der Container gestartet wurde und bereit ist, Traffic entgegenzunehmen. Beachten Sie beim Konfigurieren von Startprüfungen die folgenden wichtigen Punkte:
- Ausreichende Startzeit: Sie sollten genügend Zeit für die vollständige Initialisierung und das Laden Ihres Containers, einschließlich der Modelle, einplanen.
- Überprüfung der Modellbereitschaft: Konfigurieren Sie die Prüfung so, dass sie nur dann besteht, wenn Ihre Anwendung bereit ist, Anfragen zu bearbeiten. Die meisten Bereitstellungs-Engines erreichen dies automatisch, wenn das Modell in den GPU-Speicher geladen wird, wodurch vorzeitige Anfragen verhindert werden.
Hinweis: Ollama kann einen TCP-Port öffnen, bevor ein Modell geladen wird. Um dies zu beheben können Sie
- Modelle vorab laden: Eine Anleitung zum Vorladen von Modellen beim Starten finden Sie in der Ollama-Dokumentation.
Während der Laufzeit
- Sie können die unterstützte Kontextlänge aktiv verwalten. Je kleiner das Kontextfenster ist, desto mehr Abfragen können parallel ausgeführt werden. Die Details hängen vom Framework ab.
- Verwenden Sie die LLM-Caches, die Sie zum Zeitpunkt des Builds generiert haben. Geben Sie dieselben Flags an, die Sie während der Buildzeit beim Generieren des Prompt- und Präfix-Caches verwendet haben.
- Laden Sie es aus dem gerade erstellten gespeicherten Modell. Im Hilfeartikel Vor- und Nachteile von Modellspeicherung und ‑ladevorgang finden Sie einen Vergleich der verschiedenen Lademethoden.
- Verwenden Sie einen quantisierten Schlüssel/Wert-Cache, falls Ihr Framework dies unterstützt. Dadurch kann der Speicherbedarf pro Abfrage gesenkt und eine höhere Parallelität konfiguriert werden. Dies kann sich jedoch auch auf die Qualität auswirken.
- Passen Sie die Menge des GPU-Speichers an, die für Modellgewichte, Aktivierungen und Schlüssel/Wert-Caches reserviert werden soll. Legen Sie den Wert so hoch fest, dass kein Fehler aufgrund von fehlendem Arbeitsspeicher auftritt.
- Konfigurieren Sie die Gleichzeitigkeit im Dienstcode richtig. Achten Sie darauf, dass der Dienstcode für die Einstellungen zur Gleichzeitigkeit Ihres Cloud Run-Dienstes konfiguriert ist.
- Prüfen Sie, ob Ihr Framework Optionen zur Verbesserung der Containerstartleistung bietet, z. B. die Parallelisierung des Modellladens.
Auf Systemdesignebene
- Fügen Sie gegebenenfalls semantische Caches hinzu. In einigen Fällen kann das Caching ganzer Abfragen und Antworten eine gute Möglichkeit sein, die Kosten für häufige Abfragen zu begrenzen.
- Abweichungen in den Präambeln steuern Prompt-Caches sind nur dann nützlich, wenn sie die Prompts in der richtigen Reihenfolge enthalten. Caches werden effektiv mit Präfixen im Cache gespeichert. Einfügen oder Bearbeiten von Elementen in der Sequenz bedeutet, dass sie entweder nicht im Cache gespeichert sind oder nur teilweise vorhanden sind.
Autoscaling und GPUs
In Cloud Run wird die Anzahl der Instanzen jeder Version automatisch skaliert, basierend auf Faktoren wie CPU-Auslastung und Anfrageparallelität. Bei Cloud Run wird die Anzahl der Instanzen jedoch nicht automatisch basierend auf der GPU-Auslastung skaliert.
Wenn eine Version mit einer GPU keine erhebliche CPU-Auslastung aufweist, wird Cloud Run für die Anfrageparallelität hochskaliert. Um eine optimale Skalierung für die Anfrageparallelität zu erreichen, müssen Sie eine optimale maximale Anzahl gleichzeitiger Anfragen pro Instanz festlegen, wie im nächsten Abschnitt beschrieben.
Maximale Anzahl gleichzeitiger Anfragen pro Instanz
Mit der Einstellung Maximale Anzahl gleichzeitiger Anfragen pro Instanz wird die maximale Anzahl von Anfragen festgelegt, die Cloud Run gleichzeitig an eine einzelne Instanz sendet. Sie müssen die Nebenläufigkeit anpassen, damit sie der maximalen Parallelität entspricht, die der Code in jeder Instanz mit guter Leistung verarbeiten kann.
Maximale Nebenläufigkeit und KI-Arbeitslasten
Wenn Sie eine KI-Inferenzarbeitslast auf einer GPU in jeder Instanz ausführen, hängt die maximale Nebenläufigkeit, die der Code mit guter Leistung verarbeiten kann, von den spezifischen Details des Frameworks und der Implementierung ab. Folgende Faktoren wirken sich darauf aus, wie Sie die optimale Einstellung für die maximale Anzahl gleichzeitiger Anfragen festlegen:
- Anzahl der Modellinstanzen, die auf die GPU geladen werden
- Anzahl der parallelen Abfragen pro Modell
- Batch-Verarbeitung
- Spezifische Parameter für die Batchkonfiguration
- Menge der Arbeit ohne GPU
Wenn die maximale Anzahl gleichzeitiger Anfragen zu hoch ist, müssen Anfragen möglicherweise innerhalb der Instanz auf den Zugriff auf die GPU warten, was zu einer höheren Latenz führt. Wenn die maximale Anzahl gleichzeitiger Anfragen zu niedrig ist, wird die GPU möglicherweise nicht optimal genutzt, was dazu führt, dass Cloud Run mehr Instanzen als nötig skaliert.
Als Faustregel für die Konfiguration der maximalen Anzahl gleichzeitiger Anfragen für KI-Arbeitslasten gilt:
(Number of model instances * parallel queries per model) + (number of model instances * ideal batch size)
Angenommen, eine Instanz lädt 3
Modellinstanzen auf die GPU und jede Modellinstanz kann 4
parallele Abfragen verarbeiten. Die ideale Batchgröße ist ebenfalls 4
, da dies die Anzahl der parallelen Abfragen ist, die jede Modellinstanz verarbeiten kann. Gemäß dieser Faustregel würden Sie die maximale Anzahl gleichzeitiger Anfragen auf 24
festlegen: (3
* 4
) + (3
* 4
).
Diese Formel ist nur eine Faustregel. Die ideale Einstellung für die maximale Anzahl gleichzeitiger Anfragen hängt von den spezifischen Details Ihrer Implementierung ab. Um die tatsächlich optimale Leistung zu erzielen, empfehlen wir Ihnen, Ihren Dienst mit verschiedenen Einstellungen für die maximale Anzahl gleichzeitiger Anfragen einen Lasttest durchzuführen, um zu ermitteln, welche Option die beste Leistung erzielt.
Kompromisse zwischen Durchsatz, Latenz und Kosten
Unter Kompromisse zwischen Durchsatz, Latenz und Kosten finden Sie Informationen dazu, wie sich die maximale Anzahl gleichzeitiger Anfragen auf Durchsatz, Latenz und Kosten auswirkt. Beachten Sie, dass allen Cloud Run-Diensten, die GPUs verwenden, immer CPU zugewiesen wird.