miso_soup3 Blog

主に ASP.NET 関連について書いています。

Lambda(SAM) に Datadog を導入したときのメモ

f:id:miso_soup3:20201126120602p:plain
Trace Serverless Functions より

全ては Datadog の公式ドキュメントに記載されている通りですが、引っかかったところをメモします。

導入

サーバーレスモニタリングのインストール の通りに行いました。

1. AWS インテグレーションをインストール
  • 「自動:CloudFormation」 にて、CloudFormation で作成するときは、
    • 作成先のリージョンが意図したリージョンであるか確認します(任意)。
    • 作成ページの最後のチェックボックス「The following resource(s) require capabilities: [AWS::CloudFormation::Stack]」にチェックするのを忘れないようにします。

Update the Datadog AWS インテグレーション タイルを、CloudFormation のスタック作成に使用した IAM ロール名とアカウント ID で更新します。

このとき、ロール名などの入力が正しいかどうかに注意します。また、Datadog の UI の関係により、キーの入力途中のタイミングで検証が行われる可能性があります。上手くいかない時はコピーアンドペーストを利用して、良いタイミングで検証してもらえるよう頑張ります。失敗したときは、作成した CloudFormation から丸ごと削除します。AWS External ID が一致しないときは編集もしてみたのですが、なんだかんだで 4,5回やり直しました😅

2. Datadog Forwarder のインストール

Note: Skip this step if you already have the Forwarder function installed as part of the AWS integration CloudFormation Stack. https://docs.datadoghq.com/serverless/installation/

と書いてあるように、1 の手順の CloudFormation でインストールされているのでここはスキップします。

1 の手順の CloudFormation を確認すると、ネストされた子の CloudFormation があり、Role を作るものと Datadog Forwarder を作るものが確認できました。その作成されたリソースを見ると「Forwarder」という名前の AWS::Lambda::Function が確認できます。これが Datadog Forwarder であり、CloudWatch Logs などのログを Datadog に送信しているものと思われます。

3. アプリケーションのインスツルメンテーション

Lambda に Datadog を設定するステップです。

Lambda は SAM で作っているので、「AWS SAM」の方法でトライしました。そしてエラーが解決できなかったので結局は「Custom」にある Lambda Layer を使う方法で導入しました。お手軽だったので今後も Lambda Layer の方法にすると思います。

AWS SAM」でつまづいた部分は以下の通り↓

Error message: ‘logGroupNamePrefix’ failed to satisfy constraint… Datadog Serverless Macro

とあるように「logGroupNamePrefix」というエラーが発生しました。ドキュメントには対応策が記載されていますが、それでも解決できませんでした。

Lambda Layer の方法で気をつけるのは以下の通りです。

The minor version of the datadog-lambda package always matches the layer version. E.g., datadog-lambda v0.5.0 matches the content of layer version 5.

The available RUNTIME options are Python27, Python36, Python37, and Python38. For VERSION, see the latest release. For example: Instrumenting Python Applications

とあるように、pip install する datadog-lambda のバージョン0.5.05と、arn:aws:lambda:<AWS_REGION>:464622532012:layer:Datadog-<RUNTIME>:<VERSION> の VERSION の数字は同じにします。

また、

Optionally add a service and env tag with appropriate values to your function.

とある部分は、環境変数ではなく Lambda のタグを指しています。

Lambda をデプロイするユーザーに lambda:GetLayerVersion の権限を追加します。でないと以下のようにエラーが発生します。

hogehoge is not authorized to perform:lambda:GetLayerVersion on resource:arn:aws:lambda:ap-northeast-1:464622532012:layer:Datadog-Python**:** (Service: AWSLambdaInternal;Status Code: 403; Error Code: AccessDeniedException;Request ID: xxx; Proxy: null) 

ログとトレースの接続

Connecting Python Logs and Traces この方法に沿って、ログとトレースの接続を行いました。

このとき、出力された CloudWatch Logs のメッセージを確認すると、dd.env dd.version の部分が出力されていませんでした。Lambda の環境変数DD_SERVICE DD_VERSION DD_ENV を追加することで、出力されるようになり、結果 Datadog 上でログとトレースの接続が行えるようになりました。Lambda のタグと内容が重複しますが、どちらかのみの定義で済むかどうかは分かっていません。

最終的な template.yaml は以下の通りとなりました。

  MyLambda:
    Type: AWS::Serverless::Function
    Properties:
      FunctionName: 省略
      Handler: datadog_lambda.handler.handler
      ...省略
      Environment:
        Variables:
          DD_LAMBDA_HANDLER: hogehoge.lambda_handler
          DD_TRACE_ENABLED: true
          DD_FLUSH_TO_LOG: true
          DD_SERVICE: Datadog APM のためのサービス名
          DD_VERSION: 1
          DD_ENV: dev
      Layers:
        - arn:aws:lambda:<AWS_REGION>:464622532012:layer:Datadog-<RUNTIME>:<VERSION> ←書き換える
      Tags:
        env: dev
        service: Datadog APM のためのサービス名

カスタムメトリクスの送信

カスタムメトリクス

の通りに行いました。

Datadog Lambda ライブラリ を使用して送信する場合、カスタムメトリクスにタグを付ける必要があります。 カスタムメトリクス

↑これは、下↓の操作の部分のことを示しています。(タグという名前だけだとどのタグのことか紛らわしい…)

Datadog のページにアクセスし、Distributions の通りにメトリクス収集の定義を行いました。p99の値と環境ごとでみたいので、p99 env のタグを設定しました。このタグの数は、後述する課金に影響します。(なので無駄なタグは設定しない方がいいかな)

お値段を把握する

以上のように、Lambda に Datadog APM の導入と カスタムメトリクスの送信に成功しました。ところで、お値段はどれくらいになるんでしょう? 結論としては、月額$5で、あとは使用量次第で増えていきます。

最初、以下の表記をみて「えっ $31/月 もかかるの?」と勘違いしました。

STARTING AT $ 31 Per host, per month* 料金プラン | Datadog

Lambda 1つは1つのホストとみられてしまうから$31/月かかる…?と思いましたがそうではありませんでした。

Pro および Enterprise プランには、請求対象の関数ごとに 150,000 件の Indexed Span と 5 個のカスタムメトリクスが含まれます。サーバーレス APM の請求は、Datadog APM サービスに送信された Indexed Span のうち、バンドルされた数量を超過した総数に基づき、月末に課金されます。サーバーレス使用時は、請求可能な APM ホストはありません。 Datadog

というように、「サーバーレス使用時は、請求可能な APM ホストはありません。」との記載があるので、「STARTING AT $ 31 Per host, per month*」は適用されません。

また、以下のようにサーバーレスの場合の料金が記載されています。

ケース 6: Lambda 関数と Indexed Span Lambda 関数を 1 か月間毎時間継続して呼び出し、2,000 万件の Indexed Span を送信。 f:id:miso_soup3:20201126120346p:plain APM 料金

この「月額5ドル」というのは、以下の Serverless の料金ページの部分から。

STARTING AT $ 5 Per function, per month* 料金プラン | Datadog

つまり、1つの Lambda で Datadog APM を使う場合は以下のような費用となると認識しました。

分散型トレーシング

複数の Lambda を運用していますが、それらを一貫してトレースで見られるようにしたいと思いました。ここで使えるのが、分散型トレーシング です。

最初自分は何も考えずに Datadog APM だけを選択していましたが、しかしそれでは不十分なようで、AWS のリソースを挟む場合は、AWS X-Ray と Datadog APM の両方が必要なようです。料金も増える模様💸(まあそうですよね。Datadog APM だけで何か頑張っているのかと勘違いしてました)

Datadog のサポデから以下の回答をもらいました。3つのドキュメントが参考になりそうです。

S3, SQS and Dynamo would need to be traced with AWS X-Ray, and the Lambdas with Datadog's APM. These can then be combined to produce the full trace.

Here are some more details on that: https://docs.datadoghq.com/tracing/setup_overview/serverless_functions/?tab=nodejs#augment-aws-x-ray-tracing-with-datadog-apm

Specifically this portion may be of interest: https://docs.datadoghq.com/tracing/setup_overview/serverless_functions/?tab=nodejs#tracing-in-a-serverless-first-environment

For more details on X-Ray tracing with Datadog: https://docs.datadoghq.com/tracing/guide/serverless_enable_aws_xray/?tab=nodejs