Utilizzo AWS Lambda delle funzioni in Amazon Neptune - Amazon Neptune

Le traduzioni sono generate tramite traduzione automatica. In caso di conflitto tra il contenuto di una traduzione e la versione originale in Inglese, quest'ultima prevarrà.

Utilizzo AWS Lambda delle funzioni in Amazon Neptune

AWS Lambda le funzioni hanno molti usi nelle applicazioni Amazon Neptune. Qui forniamo una guida generale per l'utilizzo delle funzioni Lambda con tutti i driver e le varianti di linguaggio Gremlin più diffusi ed esempi specifici di funzioni Lambda scritte in Java e Python. JavaScript

Nota

Il modo migliore per utilizzare le funzioni Lambda con Neptune è cambiato con i rilasci recenti del motore. Neptune lasciava aperte le connessioni inattive per periodi prolungati dopo il riciclo di un contesto di esecuzione Lambda, causando potenzialmente una perdita di risorse sul server. Per mitigare questo problema, era consigliabile aprire e chiudere una connessione con ogni invocazione Lambda. A partire dalla versione del motore 1.0.3.0, tuttavia, il timeout per le connessioni inattive è stato ridotto per evitare perdite delle connessioni dopo il riciclo di un contesto di esecuzione Lambda inattivo, quindi ora è consigliabile utilizzare una singola connessione per la durata del contesto di esecuzione. Ciò dovrebbe includere la gestione degli errori e un codice standard per gestire le connessioni che back-off-and-retry vengono chiuse in modo imprevisto.

Gestione delle connessioni Gremlin nelle funzioni WebSocket AWS Lambda

Se si utilizza una variante del linguaggio Gremlin per interrogare Neptune, il driver si connette al database tramite una connessione. WebSocket WebSockets sono progettati per supportare scenari di connessione client-server di lunga durata. AWS Lambda, d'altra parte, è progettato per supportare esecuzioni relativamente brevi e senza stato. Questa discrepanza nella filosofia di progettazione può causare alcuni problemi imprevisti durante l'utilizzo di Lambda per l'esecuzione di query su Neptune.

Una AWS Lambda funzione viene eseguita in un contesto di esecuzione che isola la funzione dalle altre funzioni. Il contesto di esecuzione viene creato la prima volta che la funzione viene richiamata e può essere riutilizzato per le successive invocazioni della stessa funzione.

Tuttavia, un contesto di esecuzione non viene mai utilizzato per gestire più invocazioni simultanee della funzione. Se la funzione viene richiamata simultaneamente da più client, Lambda crea un contesto di esecuzione aggiuntivo per ogni istanza della funzione. Tutti questi nuovi contesti di esecuzione possono a loro volta essere riutilizzati per le successive invocazioni della funzione.

A un certo punto, Lambda ricicla i contesti di esecuzione, in particolare se sono rimasti inattivi per qualche tempo. AWS Lambda espone il ciclo di vita del contesto di esecuzione, incluse le Shutdown fasi Invoke eInit, tramite estensioni Lambda. Usando queste estensioni, è possibile scrivere codice che esegue la pulizia delle risorse esterne, come le connessioni al database, quando il contesto di esecuzione viene riciclato.

Una best practice comune prevede l'apertura della connessione al database all'esterno della funzione del gestore Lambda affinché possa essere riutilizzata con ogni chiamata al gestore. Se a un certo punto la connessione al database si interrompe, puoi riconnetterti dall'interno del gestore. Tuttavia, questo approccio comporta il rischio di perdite di connessione. Se una connessione inattiva rimane aperta a lungo dopo la distruzione di un contesto di esecuzione, gli scenari di invocazione Lambda intermittenti possono causare la perdita graduale delle connessioni ed esaurire le risorse del database.

I limiti di connessione e i timeout di connessione di Neptune hanno subito modifiche con i nuovi rilasci del motore. In precedenza, ogni istanza supportava fino a 60.000 connessioni. WebSocket Ora, il numero massimo di WebSocket connessioni simultanee per istanza di Neptune varia a seconda del tipo di istanza.

Inoltre, a partire dal rilascio del motore 1.0.3.0, Neptune ha ridotto il timeout di inattività per le connessioni da un'ora a circa 20 minuti. Se un client non chiude una connessione, la connessione viene chiusa automaticamente dopo un timeout di inattività da 20 a 25 minuti. AWS Lambda non documenta la durata del contesto di esecuzione, ma gli esperimenti mostrano che il nuovo timeout di connessione Neptune si allinea bene con i timeout del contesto di esecuzione Lambda inattivi. Quando un contesto di esecuzione inattivo viene riciclato, esistono sono buone probabilità che la sua connessione sia già stata chiusa da Neptune o che venga chiusa subito dopo.

Consigli per l'utilizzo AWS Lambda con Amazon Neptune Gremlin

È consigliabile utilizzare un'unica connessione e origine di attraversamento del grafo per l'intera durata di un contesto di esecuzione Lambda, anziché una per ogni invocazione di funzione (ogni invocazione di funzione gestisce solo una richiesta client). Poiché le richieste client simultanee vengono gestite da diverse istanze di funzione in esecuzione in contesti di esecuzione separati, non è necessario mantenere un pool di connessioni per gestire le richieste simultanee all'interno di un'istanza di funzione. Se il driver Gremlin in uso ha un pool di connessioni, configuralo affinché utilizzi una sola connessione.

Per gestire gli errori di connessione, utilizza la logica di ripetizione dei tentativi per ogni query. Anche se l'obiettivo è mantenere una singola connessione per tutta la durata di un contesto di esecuzione, eventi di rete imprevisti possono causare l'interruzione improvvisa della connessione. Tali errori di connessione si manifestano come errori diversi a seconda del driver in uso. È necessario codificare la funzione Lambda per gestire questi problemi di connessione e tentare una riconnessione, se necessario.

Alcuni driver Gremlin gestiscono automaticamente le riconnessioni. Il driver Java, ad esempio, tenta automaticamente di ristabilire la connettività a Neptune per conto del codice client. Con questo driver, è sufficiente che il codice della funzione esegua il backoff e ripeta la query. I driver JavaScript e Python, al contrario, non implementano alcuna logica di riconnessione automatica, quindi con questi driver il codice funzione deve provare a riconnettersi dopo il backup e riprovare la query solo dopo aver ristabilito la connessione.

Gli esempi di codice qui riportati includono la logica di riconnessione anziché presupporre che questa venga gestita dal client.

Raccomandazioni per l'utilizzo delle richieste di scrittura Gremlin in Lambda

Se la tua funzione Lambda modifica i dati del grafico, prendi in considerazione l'adozione di una back-off-and-retry strategia per gestire le seguenti eccezioni:

  • ConcurrentModificationException: la semantica delle transazioni di Neptune prevede che le richieste di scrittura abbiano talvolta esito negativo con un'eccezione ConcurrentModificationException. In queste situazioni, prova un meccanismo di ripetizione esponenziale. back-off-based

  • ReadOnlyViolationException: poiché la topologia del cluster può cambiare in qualsiasi momento a seguito di eventi pianificati o non pianificati, le responsabilità di scrittura potrebbero essere trasferite da un'istanza del cluster a un'altra. Se il codice della funzione tenta di inviare una richiesta di scrittura a un'istanza che non è più l'istanza primaria (scrittura), la richiesta ha esito negativo e restituisce un'eccezione ReadOnlyViolationException. In questo caso, chiudi la connessione esistente, riconnettiti all'endpoint del cluster e ripeti la richiesta.

Inoltre, se utilizzi una back-off-and-retry strategia per gestire i problemi relativi alle richieste di scrittura, prendi in considerazione l'implementazione di query idempotenti per le richieste di creazione e aggiornamento (ad esempio, utilizzando fold () .coalesce () .unfold ().

Raccomandazioni per l'utilizzo delle richieste di lettura Gremlin in Lambda

Se nel cluster sono presenti una o più repliche di lettura, è consigliabile bilanciare le richieste di lettura tra queste repliche. Un'opzione prevede l'utilizzo dell'endpoint di lettura. L'endpoint di lettura bilancia le connessioni tra le repliche anche se la topologia del cluster cambia a seguito dell'aggiunta o della rimozione di repliche o della promozione di una replica affinché diventi la nuova istanza primaria.

L'utilizzo dell'endpoint di lettura può tuttavia comportare un utilizzo non uniforme delle risorse del cluster in alcune circostanze. L'endpoint del lettore funziona cambiando periodicamente l'host a cui punta l'ingresso. DNS Se un client apre molte connessioni prima che la DNS voce venga modificata, tutte le richieste di connessione vengono inviate a una singola istanza di Neptune. Potrebbe essere il caso con uno scenario Lambda a velocità di trasmissione effettiva elevata in cui un gran numero di richieste simultanee alla funzione Lambda causa la creazione di più contesti di esecuzione, ognuno con la propria connessione. Se queste connessioni vengono create quasi simultaneamente, è probabile che puntino tutte alla stessa replica nel cluster e che continuino a puntare a quella replica fino al riciclo dei contesti di esecuzione.

Un modo per distribuire le richieste tra le istanze consiste nel configurare la funzione Lambda per connettersi a un endpoint dell'istanza, scelto casualmente da un elenco di endpoint di istanze di replica, anziché all'endpoint di lettura. Lo svantaggio di questo approccio è che richiede che il codice Lambda gestisca le modifiche nella topologia del cluster tramite il monitoraggio del cluster e l'aggiornamento dell'elenco degli endpoint ogni volta che cambia l'appartenenza al cluster.

Se stai scrivendo una funzione Lambda Java che deve bilanciare le richieste di lettura tra le istanze del cluster, puoi utilizzare il client Gremlin per Amazon Neptune, un client Gremlin Java che riconosce la topologia del cluster e che distribuisce equamente connessioni e richieste su un set di istanze in un cluster Neptune. Questo post del blog include una funzione Lambda Java di esempio che utilizza il client Gremlin per Amazon Neptune.

Fattori che possono rallentare l'avvio a freddo delle funzioni Lambda Gremlin in Neptune

La prima volta che una AWS Lambda funzione viene richiamata viene definita avvio a freddo. Esistono diversi fattori che possono aumentare la latenza di un avvio a freddo:

  • Assicurati di assegnare memoria sufficiente alla funzione Lambda.   — La compilazione durante un avvio a freddo può essere notevolmente più lenta per una funzione Lambda rispetto a quanto lo sarebbe EC2 perché AWS Lambda alloca i CPU cicli in modo lineare in proporzione alla memoria assegnata alla funzione. Con 1.769 MB di memoria, una funzione riceve l'equivalente di una v completa CPU (un v secondo di crediti al secondo). CPU L'impatto della mancata assegnazione di memoria sufficiente per ricevere CPU cicli adeguati è particolarmente pronunciato per le funzioni Lambda di grandi dimensioni scritte in Java.

  • Tieni presente che l'attivazione dell'autenticazione del IAM database può rallentare un avvio a freddo: AWS Identity and Access Management (IAM) l'autenticazione del database può anche rallentare l'avvio a freddo, in particolare se la funzione Lambda deve generare una nuova chiave di firma. Questa latenza influisce solo sull'avvio a freddo e non sulle richieste successive, perché una volta che l'autenticazione del IAM database ha stabilito le credenziali di connessione, Neptune verifica solo periodicamente che siano ancora valide.