AWSJavaScriptNode.jsTypeScript

Record the AWS Lambda function log by lambda-log or @dazn/lambda-powertools-logger

AWS Lambda’s log will store in CloudWatch Logs. So we want to log the script data as a JSON format to se […]

広告ここから
広告ここまで

AWS Lambda’s log will store in CloudWatch Logs. So we want to log the script data as a JSON format to search in the CloudWatch Logs console or APIs.

In this post, I’ll try to use two logging tools.

lambda-log

Install

We can install the packages by npm.

$ yarn add lambda-log 

// [for typescript]
$ yarn add -D @types/lambda-log 

If you want to use it with TypeScript, we need to add @types one.

Add logger to the handler

Then, we can use the logger in our own Lambda handler.

import { Handler } from 'aws-lambda'
import * as log from 'lambda-log'

export const handler: Handler = async (event) => {
  log.options.meta.event = event
  log.options.tags.push(process.env.NODE_ENV)
  log.info('info')
  log.warn('warn', {
    meta: {
      item1: 'hello'
    }
  })
  try {
    throw new Error('demo err')
  } catch (err) {
    log.error(err)
    throw err
  }
}

Log results

When execute the function, we can get these logs.

{"_logLevel":"info","msg":"info","event":{{"username": "dummy"}},"_tags":["log","info","development"]}

 {"_logLevel":"warn","msg":"warn","meta":true,"event":{{"username": "dummy"}},"_tags":["log","warn","development"]}

 {"_logLevel":"error","msg":"test","event":{{"username": "dummy"}},"stack":"Error: test\n    at handler (webpack-internal:///./handlers/updateCustomer.ts:42:54)\n    ...

And the following JSON has prettified the log.error.

{
   _logLevel: 'error',
   msg: 'test',
   event: {
     "username": "dummy"
   },
   stack: 'Error: test\n' +
     '    at handler (webpack-internal:///./handlers/updateCustomer.ts:42:54)\n' +
     '    at /Users/develop/.anyenv/envs/nodenv/versions/12.14.1/lib/node_modules/serverless/lib/plugins/aws/invokeLocal/index.js:866:30\n' +
     '    at Promise._execute (/Users/develop/.anyenv/envs/nodenv/versions/12.14.1/lib/node_modules/serverless/node_modules/bluebird/js/release/debuggability.js:384:9)\n' +
     '    at Promise._resolveFromExecutor (/Users/develop/.anyenv/envs/nodenv/versions/12.14.1/lib/node_modules/serverless/node_modules/bluebird/js/release/promise.js:518:18)\n' +
     '    at new Promise (/Users/develop/.anyenv/envs/nodenv/versions/12.14.1/lib/node_modules/serverless/node_modules/bluebird/js/release/promise.js:103:10)\n' +
     '    at AwsInvokeLocal.invokeLocalNodeJs (/Users/develop/.anyenv/envs/nodenv/versions/12.14.1/lib/node_modules/serverless/lib/plugins/aws/invokeLocal/index.js:819:12)\n' +
     '    at AwsInvokeLocal.invokeLocal (/Users/develop/.anyenv/envs/nodenv/versions/12.14.1/lib/node_modules/serverless/lib/plugins/aws/invokeLocal/index.js:225:19)\n' +
     '    at AwsInvokeLocal.tryCatcher (/Users/develop/.anyenv/envs/nodenv/versions/12.14.1/lib/node_modules/serverless/node_modules/bluebird/js/release/util.js:16:23)\n' +
     '    at Promise._settlePromiseFromHandler (/Users/develop/.anyenv/envs/nodenv/versions/12.14.1/lib/node_modules/serverless/node_modules/bluebird/js/release/promise.js:547:31)\n' +
     '    at Promise._settlePromise (/Users/develop/.anyenv/envs/nodenv/versions/12.14.1/lib/node_modules/serverless/node_modules/bluebird/js/release/promise.js:604:18)\n' +
     '    at Promise._settlePromiseCtx (/Users/develop/.anyenv/envs/nodenv/versions/12.14.1/lib/node_modules/serverless/node_modules/bluebird/js/release/promise.js:641:10)\n' +
     '    at _drainQueueStep (/Users/develop/.anyenv/envs/nodenv/versions/12.14.1/lib/node_modules/serverless/node_modules/bluebird/js/release/async.js:97:12)\n' +
     '    at _drainQueue (/Users/develop/.anyenv/envs/nodenv/versions/12.14.1/lib/node_modules/serverless/node_modules/bluebird/js/release/async.js:86:9)\n' +
     '    at Async._drainQueues (/Users/develop/.anyenv/envs/nodenv/versions/12.14.1/lib/node_modules/serverless/node_modules/bluebird/js/release/async.js:102:5)\n' +
     '    at Immediate.Async.drainQueues as _onImmediate\n' +
     '    at processImmediate (internal/timers.js:439:21)\n' +
     '    at process.topLevelDomainCallback (domain.js:130:23)',
   _tags: [ 'log', 'error', 'development' ]
 }

@dazn/lambda-powertools-logger

Install

The package support TypeScript. So we just install the package.

$ yarn add @dazn/lambda-powertools-lambda-client

When we want to use it with TypeScript, we need to set allowSyntheticDefaultImports flag to be true.

{
  "compilerOptions": {
    "allowSyntheticDefaultImports": true,

Add logger to the handler

import { Handler } from 'aws-lambda'
import log from '@dazn/lambda-powertools-logger'

export const handler: Handler = async (event) => {
  log.info('info')
  log.warn('warn', {
    meta: {
      item1: 'hello'
    }
  })
  try {
    throw new Error('demo err')
  } catch (err) {
    log.error('error', err)
    throw err
  }
}

Log results

The package will add the function information automatically.

{"message":"info","awsRegion":"us-east-1","functionName":"demo-function","functionVersion":"$LATEST","functionMemorySize":"256","environment":"development","level":30,"sLevel":"INFO"}
 {"message":"warn","meta":{"item1":"hello"},"awsRegion":"us-east-1","functionName":"demo-function","functionVersion":"$LATEST","functionMemorySize":"256","environment":"development","level":40,"sLevel":"WARN"}
 {"message":"error","errorName":"Error","errorMessage":"demo err","stackTrace":"Error: demo err\n    at handler (webpack-internal:///./handlers/updateCustomer.ts:44:15)\n  …

And the following JSON has prettified the log.error.

message: 'error',
   errorName: 'Error',
   errorMessage: 'demo err',
   stackTrace: 'Error: demo err\n' +
     '    at handler (webpack-internal:///./handlers/updateCustomer.ts:44:15)\n' +
     '    at /Users/develop/.anyenv/envs/nodenv/versions/12.14.1/lib/node_modules/serverless/lib/plugins/aws/invokeLocal/index.js:866:30\n' +
     '    at Promise._execute (/Users/develop/.anyenv/envs/nodenv/versions/12.14.1/lib/node_modules/serverless/node_modules/bluebird/js/release/debuggability.js:384:9)\n' +
     '    at Promise._resolveFromExecutor (/Users/develop/.anyenv/envs/nodenv/versions/12.14.1/lib/node_modules/serverless/node_modules/bluebird/js/release/promise.js:518:18)\n' +
     '    at new Promise (/Users/develop/.anyenv/envs/nodenv/versions/12.14.1/lib/node_modules/serverless/node_modules/bluebird/js/release/promise.js:103:10)\n' +
     '    at AwsInvokeLocal.invokeLocalNodeJs (/Users/develop/.anyenv/envs/nodenv/versions/12.14.1/lib/node_modules/serverless/lib/plugins/aws/invokeLocal/index.js:819:12)\n' +
     '    at AwsInvokeLocal.invokeLocal (/Users/develop/.anyenv/envs/nodenv/versions/12.14.1/lib/node_modules/serverless/lib/plugins/aws/invokeLocal/index.js:225:19)\n' +
     '    at AwsInvokeLocal.tryCatcher (/Users/develop/.anyenv/envs/nodenv/versions/12.14.1/lib/node_modules/serverless/node_modules/bluebird/js/release/util.js:16:23)\n' +
     '    at Promise._settlePromiseFromHandler (/Users/develop/.anyenv/envs/nodenv/versions/12.14.1/lib/node_modules/serverless/node_modules/bluebird/js/release/promise.js:547:31)\n' +
     '    at Promise._settlePromise (/Users/develop/.anyenv/envs/nodenv/versions/12.14.1/lib/node_modules/serverless/node_modules/bluebird/js/release/promise.js:604:18)\n' +
     '    at Promise._settlePromiseCtx (/Users/develop/.anyenv/envs/nodenv/versions/12.14.1/lib/node_modules/serverless/node_modules/bluebird/js/release/promise.js:641:10)\n' +
     '    at _drainQueueStep (/Users/develop/.anyenv/envs/nodenv/versions/12.14.1/lib/node_modules/serverless/node_modules/bluebird/js/release/async.js:97:12)\n' +
     '    at _drainQueue (/Users/develop/.anyenv/envs/nodenv/versions/12.14.1/lib/node_modules/serverless/node_modules/bluebird/js/release/async.js:86:9)\n' +
     '    at Async._drainQueues (/Users/develop/.anyenv/envs/nodenv/versions/12.14.1/lib/node_modules/serverless/node_modules/bluebird/js/release/async.js:102:5)\n' +
     '    at Immediate.Async.drainQueues as _onImmediate\n' +
     '    at processImmediate (internal/timers.js:439:21)\n' +
     '    at process.topLevelDomainCallback (domain.js:130:23)',
   awsRegion: 'us-east-1',
   functionName: 'demo-app',
   functionVersion: '$LATEST',
   functionMemorySize: '256',
   environment: 'development',
   level: 50,
   sLevel: 'ERROR'
 }

What’s the difference?

lambda-log can contain the request data into log.options.meta.

And @dazn/lambda-powertools-logger contains the Lambda function environment automatically. And easy to integrate other powertools packages.

ブックマークや限定記事(予定)など

WP Kyotoサポーター募集中

WordPressやフロントエンドアプリのホスティング、Algolia・AWSなどのサービス利用料を支援する「WP Kyotoサポーター」を募集しています。
月額または年額の有料プランを契約すると、ブックマーク機能などのサポーター限定機能がご利用いただけます。

14日間のトライアルも用意しておりますので、「このサイトよく見るな」という方はぜひご検討ください。

広告ここから
広告ここまで

Related Category posts