最大化 Lambda SnapStart 效能 - AWS Lambda

本文為英文版的機器翻譯版本,如內容有任何歧義或不一致之處,概以英文版為準。

最大化 Lambda SnapStart 效能

效能調校

注意

SnapStart 與大規模函數調用搭配使用時效果最佳。不常調用的函數效能改進效果可能不會相同。

為了最大限度地提高 的優勢 SnapStart,我們建議您預先載入導致初始化程式碼中啟動延遲的類別,而不是函數處理常式中的類別。這會將與繁重類別載入相關聯的延遲移出調用路徑,以 最佳化啟動效能 SnapStart。

如果您無法在初始化期間預先載入類別,建議您使用虛擬調用預先載入類別。若要執行此操作,請更新函數處理常式程式碼,如下列範例所示,從 AWS Labs GitHub 儲存庫上的寵物存放區函數

private static SpringLambdaContainerHandler<AwsProxyRequest, AwsProxyResponse> handler; static { try { handler = SpringLambdaContainerHandler.getAwsProxyHandler(PetStoreSpringAppConfig.class); // Use the onStartup method of the handler to register the custom filter handler.onStartup(servletContext -> { FilterRegistration.Dynamic registration = servletContext.addFilter("CognitoIdentityFilter", CognitoIdentityFilter.class); registration.addMappingForUrlPatterns(EnumSet.of(DispatcherType.REQUEST), false, "/*"); }); // Send a fake Amazon API Gateway request to the handler to load classes ahead of time ApiGatewayRequestIdentity identity = new ApiGatewayRequestIdentity(); identity.setApiKey("foo"); identity.setAccountId("foo"); identity.setAccessKey("foo"); AwsProxyRequestContext reqCtx = new AwsProxyRequestContext(); reqCtx.setPath("/pets"); reqCtx.setStage("default"); reqCtx.setAuthorizer(null); reqCtx.setIdentity(identity); AwsProxyRequest req = new AwsProxyRequest(); req.setHttpMethod("GET"); req.setPath("/pets"); req.setBody(""); req.setRequestContext(reqCtx); Context ctx = new TestContext(); handler.proxy(req, ctx); } catch (ContainerInitializationException e) { // if we fail here. We re-throw the exception to force another cold start e.printStackTrace(); throw new RuntimeException("Could not initialize Spring framework", e); } }

網路最佳實務

Lambda 從快照恢復函數時,無法保證函數在初始化階段建立的連線狀態。在大多數情況下, AWS SDK建立的網路連線會自動恢復。針對其他連線,建議遵循最佳實務操作。

重新建立網路連線

函數從快照恢復時,請務必重新建立網路連線。建議您在函數處理常式中重新建立網路連線。或者,您可以使用 afterRestore 執行階段掛鉤

請勿使用主機名做為唯一的執行環境識別符

建議您不要使用 hostname 將執行環境識別為應用程式中唯一的節點或容器。使用 時 SnapStart,單一快照會用作多個執行環境的初始狀態,且所有執行環境都會傳回 的相同hostnameInetAddress.getLocalHost()。如果應用程式需要唯一的執行環境識別或 hostname 值,建議您在函數處理常式中產生唯一的 ID。或者,使用 afterRestore 執行階段掛鉤來產生唯一的 ID,然後使用這個唯一 ID 做為執行環境的識別符。

避免將連線繫結至固定來源連接埠

建議您避免將網路連線繫結至固定來源連接埠。函數從快照恢復時連線會重新建立,而繫結至固定來源連接埠的網路連線可能會失敗。

避免使用 Java DNS快取

Lambda 函數已經快取DNS回應。如果您將另一個DNS快取與 搭配使用 SnapStart,則當函數從快照恢復時,您可能會遇到連線逾時。

java.util.logging.Logger 類別可以間接啟用JVMDNS快取。若要覆寫預設設定,請在初始化 之前將 networkaddress.cache.ttl 設定為 0logger。範例:

public class MyHandler { // first set TTL property static{ java.security.Security.setProperty("networkaddress.cache.ttl" , "0"); } // then instantiate logger var logger = org.apache.logging.log4j.LogManager.getLogger(MyHandler.class); }

為了防止 Java 11 執行期UnknownHostException失敗,我們建議networkaddress.cache.negative.ttl將 設定為 0。在 Java 17 和更新版本的執行時間中,此步驟是必要的。您可以使用AWS_LAMBDA_JAVA_NETWORKADDRESS_CACHE_NEGATIVE_TTL=0環境變數為 Lambda 函數設定此屬性。

停用JVMDNS快取不會停用 Lambda DNS 的受管快取。