@@ -9,7 +9,12 @@ import type {
99import type { Context , Handler } from 'aws-lambda' ;
1010import merge from 'lodash.merge' ;
1111import { EnvironmentVariablesService } from './config/EnvironmentVariablesService.js' ;
12- import { LogJsonIndent , LogLevelThreshold , ReservedKeys } from './constants.js' ;
12+ import {
13+ LogJsonIndent ,
14+ LogLevelThreshold ,
15+ ReservedKeys ,
16+ UncaughtErrorLogMessage ,
17+ } from './constants.js' ;
1318import type { LogFormatter } from './formatter/LogFormatter.js' ;
1419import type { LogItem } from './formatter/LogItem.js' ;
1520import { PowertoolsLogFormatter } from './formatter/PowertoolsLogFormatter.js' ;
@@ -39,6 +44,7 @@ import type {
3944 * * Capture key fields from AWS Lambda context, cold start, and structure log output as JSON
4045 * * Append additional keys to one or all log items
4146 * * Switch log level to `DEBUG` based on a sample rate value for a percentage of invocations
47+ * * Ability to buffer logs in memory and flush them when there's an error
4248 *
4349 * After initializing the Logger class, you can use the methods to log messages at different levels.
4450 *
@@ -54,7 +60,7 @@ import type {
5460 * };
5561 * ```
5662 *
57- * To enrich the log items with information from the Lambda context, you can use the {@link Logger.addContext | addContext()} method.
63+ * To enrich the log items with information from the Lambda context, you can use the {@link Logger.addContext | ` addContext()` } method.
5864 *
5965 * @example
6066 * ```typescript
@@ -69,7 +75,7 @@ import type {
6975 * };
7076 * ```
7177 *
72- * You can also add additional attributes to all log items using the {@link Logger.appendKeys | appendKeys()} method.
78+ * You can also add additional attributes to all log items using the {@link Logger.appendKeys | ` appendKeys()` } method.
7379 *
7480 * @example
7581 * ```typescript
@@ -82,10 +88,10 @@ import type {
8288 * };
8389 *```
8490 *
85- * If you write your functions as classes and use TypeScript, you can use the {@link Logger.injectLambdaContext} class method decorator
91+ * If you write your functions as classes and use TypeScript, you can use the {@link Logger.injectLambdaContext | `injectLambdaContext()` } class method decorator
8692 * to automatically add context to your logs and clear the state after the invocation.
8793 *
88- * If instead you use Middy.js middlewares, you use the {@link "middleware/middy".injectLambdaContext | injectLambdaContext()} middleware.
94+ * If instead you use Middy.js middlewares, you use the {@link "middleware/middy".injectLambdaContext | ` injectLambdaContext()` } middleware.
8995 *
9096 * @see https://docs.powertools.aws.dev/lambda/typescript/latest/core/logger/
9197 */
@@ -97,7 +103,7 @@ class Logger extends Utility implements LoggerInterface {
97103 * full control over the output of the logs. In testing environments, we use the
98104 * default console instance.
99105 *
100- * This property is initialized in the constructor in setOptions().
106+ * This property is initialized in the constructor in ` setOptions()` .
101107 */
102108 private console ! : Console ;
103109 /**
@@ -191,7 +197,7 @@ class Logger extends Utility implements LoggerInterface {
191197 #maxBufferBytesSize = 20480 ;
192198
193199 /**
194- * Contains buffered logs, grouped by _X_AMZN_TRACE_ID, each group with a max size of `maxBufferBytesSize`
200+ * Contains buffered logs, grouped by ` _X_AMZN_TRACE_ID` , each group with a max size of `maxBufferBytesSize`
195201 */
196202 #buffer?: CircularMap < string > ;
197203
@@ -379,8 +385,8 @@ class Logger extends Utility implements LoggerInterface {
379385 * Class method decorator that adds the current Lambda function context as extra
380386 * information in all log items.
381387 *
382- * This decorator is useful when you want to add the Lambda context to all log items
383- * and it works only when decorating a class method that is a Lambda function handler .
388+ * This decorator is useful when you want to enrich your logs with information
389+ * from the function context, such as the function name, version, and request ID, and more .
384390 *
385391 * @example
386392 * ```typescript
@@ -401,7 +407,18 @@ class Logger extends Utility implements LoggerInterface {
401407 * export const handler = handlerClass.handler.bind(handlerClass);
402408 * ```
403409 *
410+ * The decorator can also be used to log the Lambda invocation event; this can be configured both via
411+ * the `logEvent` parameter and the `POWERTOOLS_LOGGER_LOG_EVENT` environment variable. When both
412+ * are set, the `logEvent` parameter takes precedence.
413+ *
414+ * Additionally, the decorator can be used to reset the temporary keys added with the `appendKeys()` method
415+ * after the invocation, or to flush the buffer when an uncaught error is thrown in the handler.
416+ *
404417 * @see https://www.typescriptlang.org/docs/handbook/decorators.html#method-decorators
418+ *
419+ * @param options.logEvent - When `true` the logger will log the event.
420+ * @param options.resetKeys - When `true` the logger will clear temporary keys added with {@link Logger.appendKeys() `appendKeys()`} method.
421+ * @param options.flushBufferOnUncaughtError - When `true` the logger will flush the buffer when an uncaught error is thrown in the handler.
405422 */
406423 public injectLambdaContext (
407424 options ?: InjectLambdaContextOptions
@@ -420,16 +437,24 @@ class Logger extends Utility implements LoggerInterface {
420437 callback
421438 ) {
422439 loggerRef . refreshSampleRateCalculation ( ) ;
423- Logger . injectLambdaContextBefore ( loggerRef , event , context , options ) ;
440+ loggerRef . addContext ( context ) ;
441+ loggerRef . logEventIfEnabled ( event , options ?. logEvent ) ;
424442
425- let result : unknown ;
426443 try {
427- result = await originalMethod . apply ( this , [ event , context , callback ] ) ;
444+ return await originalMethod . apply ( this , [ event , context , callback ] ) ;
445+ } catch ( error ) {
446+ if ( options ?. flushBufferOnUncaughtError ) {
447+ loggerRef . flushBuffer ( ) ;
448+ loggerRef . error ( {
449+ message : UncaughtErrorLogMessage ,
450+ error,
451+ } ) ;
452+ }
453+ throw error ;
454+ /* v8 ignore next */
428455 } finally {
429456 if ( options ?. clearState || options ?. resetKeys ) loggerRef . resetKeys ( ) ;
430457 }
431-
432- return result ;
433458 } ;
434459 } ;
435460 }
@@ -450,7 +475,7 @@ class Logger extends Utility implements LoggerInterface {
450475 /**
451476 * @deprecated - This method is deprecated and will be removed in the next major version.
452477 */
453- public static injectLambdaContextBefore (
478+ /* v8 ignore start */ public static injectLambdaContextBefore (
454479 logger : Logger ,
455480 event : unknown ,
456481 context : Context ,
@@ -463,7 +488,7 @@ class Logger extends Utility implements LoggerInterface {
463488 shouldLogEvent = options . logEvent ;
464489 }
465490 logger . logEventIfEnabled ( event , shouldLogEvent ) ;
466- }
491+ } /* v8 ignore stop */
467492
468493 /**
469494 * Log the AWS Lambda event payload for the current invocation if the environment variable `POWERTOOLS_LOGGER_LOG_EVENT` is set to `true`.
@@ -1239,6 +1264,11 @@ class Logger extends Utility implements LoggerInterface {
12391264 persistentKeys && this . appendPersistentKeys ( persistentKeys ) ;
12401265 }
12411266
1267+ /**
1268+ * Configure the buffer settings for the Logger instance.
1269+ *
1270+ * @param options - Options to configure the Logger instance
1271+ */
12421272 #setLogBuffering(
12431273 options : NonNullable < ConstructorOptions [ 'logBufferOptions' ] >
12441274 ) {
@@ -1269,30 +1299,34 @@ class Logger extends Utility implements LoggerInterface {
12691299 }
12701300
12711301 /**
1272- * Add a log to the buffer
1273- * @param xrayTraceId - _X_AMZN_TRACE_ID of the request
1302+ * Add a log to the buffer.
1303+ *
1304+ * @param xrayTraceId - `_X_AMZN_TRACE_ID` of the request
12741305 * @param log - Log to be buffered
1275- * @param logLevel - level of log to be buffered
1306+ * @param logLevel - The level of log to be buffered
12761307 */
12771308 protected bufferLogItem (
12781309 xrayTraceId : string ,
12791310 log : LogItem ,
12801311 logLevel : number
12811312 ) : void {
12821313 log . prepareForPrint ( ) ;
1283-
1284- const stringified = JSON . stringify (
1285- log . getAttributes ( ) ,
1286- this . getJsonReplacer ( ) ,
1287- this . logIndentation
1314+ this . #buffer?. setItem (
1315+ xrayTraceId ,
1316+ JSON . stringify (
1317+ log . getAttributes ( ) ,
1318+ this . getJsonReplacer ( ) ,
1319+ this . logIndentation
1320+ ) ,
1321+ logLevel
12881322 ) ;
1289-
1290- this . #buffer?. setItem ( xrayTraceId , stringified , logLevel ) ;
12911323 }
12921324
12931325 /**
1294- * Flushes all items of the respective _X_AMZN_TRACE_ID within
1295- * the buffer.
1326+ * Flush all logs in the request buffer.
1327+ *
1328+ * This is called automatically when you use the {@link injectLambdaContext | `@logger.injectLambdaContext()`} decorator and
1329+ * your function throws an error.
12961330 */
12971331 public flushBuffer ( ) : void {
12981332 const traceId = this . envVarsService . getXrayTraceId ( ) ;
@@ -1328,9 +1362,10 @@ class Logger extends Utility implements LoggerInterface {
13281362 this . #buffer?. delete ( traceId ) ;
13291363 }
13301364 /**
1331- * Tests if the log meets the criteria to be buffered
1332- * @param traceId - _X_AMZN_TRACE_ID of the request
1333- * @param logLevel - The level of the log being considered
1365+ * Test if the log meets the criteria to be buffered.
1366+ *
1367+ * @param traceId - `_X_AMZN_TRACE_ID` of the request
1368+ * @param logLevel - The level of the log being considered
13341369 */
13351370 protected shouldBufferLog (
13361371 traceId : string | undefined ,
0 commit comments