ちょっと話題の記事

コマンド一発でLambdaをチューニングする

2020.07.31

AWS Lambda Power Tuningというものがあります

Lambdaのメモリ割り当てを自動で最適化するためのツールです。

Lambda関数に割り当てられるコンピューティングリソースとして設定できるのはメモリだけです。が、設定したメモリ量に比例してCPUやネットワーク帯域の性能も向上します。また、スペックを上げたことで処理時間が短縮化され、結果としてコストダウンに繋がる場合もあります。というわけでLambda関数においてメモリ量の設定は重要なのですが、実際のところ最適な設定を見つけ出すのは面倒な作業です。設定変更→実行→結果確認→設定変更→実行→結果確認...なんてやりたくないですよね。

Lambda Power Tuningを使うと、Step Functionsステートマシンが作成されます。このステートマシンが同一の関数を複数の異なるメモリ設定で実行し、その結果をレポートしてくれます。便利!

より詳細な情報は以下の弊社岩田のエントリをどうぞ。

このLambda Power TuningはSAR(Serverless Application Repository)にて公開されています。ですのでSARからあなたのAWSアカウントにデプロイ(つまりSAMテンプレートの実行)し、できあがったStep Functionsステートマシンを実行して使うことになります。ですがそれすらやりたくない!もしくは、このLambda Power Tuningは結構頻繁にアップデートされているのですが、その追従が面倒というかたに、今回は1コマンドでLambda関数をチューニングする方法をご紹介します。

lumigo-cliで楽しよう

その方法がlumigo-cliです。lumigo-cliはLambdaを中心としたサーバレス周りの便利なコマンド集、みたいなもので、そのサブコマンドの一つに今回ご紹介するpowertune-lambdaがあります。これは先程のLambda Power Tuningをラップしたコマンドです。このコマンドを実行すれば裏でいい感じにLambda Power Tuningをデプロイ、アップデート、ステートマシン実行、レポーティングをしてくれます。便利!

やってみた

インストール

npmから行ないます。グローバルインストールしても良いですが今回はローカルインストールにしました。

$ npm init -y
$ npm install -D lumigo-cli

チューニング対象のLambda関数のデプロイ

先程紹介した岩田のエントリで使われていたのと同じのを使うことにします。外部APIを叩くだけの処理なので求められるコンピューティングリソーススペックは高くないはずで、最低のメモリ設定である128MBがおすすめされるのではと予想します。

import urllib.request


def handler(event, context):

    req = urllib.request.Request('https://petstore.swagger.io/v2/pet/findByStatus?status=pending')
    
    urllib.request.urlopen(req)
    urllib.request.urlopen(req)
    urllib.request.urlopen(req)

Serverless Frameworkでデプロイしました。テンプレートは以下です。メモリサイズの設定をしていませんが、その場合はデフォルト値の1024MBが設定されます。

serverless.yml

service: petstore

provider:
  name: aws
  runtime: python3.8
  region: ap-northeast-1


functions:
  hello:
    handler: handler.handler

コマンド実行

コマンドパラメーターはこちらで確認できます。もしくは$ npx lumigo-cli powertune-lambda --helpコマンドでも可です。

$ npx lumigo-cli powertune-lambda -n petstore-dev-hello -r ap-northeast-1 -s balanced
checking the aws-lambda-power-tuning SAR in [ap-northeast-1]
the latest version of aws-lambda-power-tuning SAR is 3.3.3
looking for deployed CloudFormation stack [serverlessrepo-lumigo-cli-powertuning-lambda] in [ap-northeast-1]
stack is deployed but is running an outdated version [3.3.2]
CloudFormation template has been generated
waiting for SAR deployment to finish...
.......
SAR deployment completed
the State Machine is arn:aws:states:ap-northeast-1:012345678901:stateMachine:powerTuningStateMachine-QMMBseb0OmEk
State Machine execution started
execution ARN is arn:aws:states:ap-northeast-1:012345678901:execution:powerTuningStateMachine-QMMBseb0OmEk:504b46a3-21ee-4c87-8298-8ee752010343
.......................
{
  "power": 256,
  "cost": 0.0000091652,
  "duration": 2154.462,
  "stateMachine": {
    "executionCost": 0.0003,
    "lambdaCost": 0.022298098400000008,
    "visualization": "https://lambda-power-tuning.show/#xxxxxxxxxxxxxxxx;xxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxx;xxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxx"
  },
  "functionName": "petstore-dev-hello"
}
? Do you want to open the visualization to see more results? yes

途中でaws-lambda-power-tuningのアップデート処理が走ってますね。一ヶ月ほど前に一度触っていてそれから放置していたためです。

最後のJSONが結果です。power値がおすすめメモリ設定です。今回s(strategy)オプションでbalanced、つまりコストとスピードのちょうど良い塩梅のところをおすすめするように指定したので256MBがおすすめされました。試しにcostを指定して再実行したところ、以下のように128MBになりました。

{
  "power": 128,
  "cost": 0.0000049992,
  "duration": 2311.6058333333335,
  "stateMachine": {
    "executionCost": 0.0003,
    "lambdaCost": 0.02224081590000001,
    "visualization": "https://lambda-power-tuning.show/#yyyyyyyyyyyyyyyy;yyyyyyyyyyyyyyyyyyyyyyyyyyyyyyyy;yyyyyyyyyyyyyyyyyyyyyyyyyyyyyyyy"
  },
  "functionName": "petstore-dev-hello"
}

ブラウザで結果確認

コマンドの最後の? Do you want to open the visualization to see more results?でyesと答えるとブラウザで結果ページが表示されます。

おすすめだけじゃなくて設定変更もできちゃう

上記は最適な設定をおすすめするだけですが、おすすめ結果を実際にLambdaの設定に反映することもできます。autoOptimizeオプションを使います。

$ npx lumigo-cli powertune-lambda -n petstore-dev-hello -r ap-northeast-1 -s balanced --autoOptimize

また、autoOptimizeオプションに加えて--autoOptimizeAlias=(エイリアス名)も追加すれば、そのLambda関数エイリアスに設定を反映することも可能です。

まとめ

lumigo-cliで簡単にLambda関数をチューニングする方法をご紹介しました。これを活用してより賢くLambdaをご利用いただければと思います。

参考情報