1.2.0 • Published 5 months ago

runl v1.2.0

Weekly downloads
-
License
MIT
Repository
github
Last release
5 months ago

RunL

Run AWS Lambda functions locally in node.

The main focus of this project is to enable you to use your functions locally, either in a dev-server or for testing, without any adjustments needed.

With a variety of alternatives available, why choose this library?

It's lightweight and comes with zero runtime dependencies. Moreover, it runs your lambda functions as isolated as possible, executing each lambda in a separate child process.

How does it work?

Instead of loading the lambda handler directly into the current node process, RunL forks a child process in which the handler is executed. To execute the handler the child process requires the handler code, executes it and passes the result back to the parent process.

Why so complicated?
Other libraries, which repeatedly re-import lambda code in the same node process, encounter an issue where residual memory from each import is not fully cleared by the garbage collector. This results in memory leaks. Consequently, when running numerous tests locally or doing a lot of requests, these memory leaks can cause the development server to eventually cease functioning.

Unfortunately, this scenario is not merely theoretical; in fact, it was the primary motivation behind the creation of this library.

Modes

RunL comes with two execution modes, Ephemeral and Persistent. Ephemeral always forks a new child process, executes the handler within this process and passes the result to the parent process.

This has the advantage that every request runs totally isolated from every other request. The disadvantage is, that the lambda handler code must always be newly required inside the child process. This can take a few seconds if the handler is several megabytes in size.

How to use Ephemeral mode

const { Lambda } = require('runl');

const lambda = new Lambda({
  mode: 'Ephemeral',
  lambdaPath: __dirname + '/handler/example-handler.js',
  environment: {
    BASE_URL: '/'
  }
});

lambda.execute({ path: '/index.html' });

The Persistent mode in contrast creates a long running fork that is reused for every invocation. The advantage is that the handler code must not be newly required for every request, which can drastically reduce the request times in your dev server.

How to use Persistent mode

import { APIGatewayProxyResult } from 'aws-lambda';
import { Lambda, LambdaMode } from 'runl';

const lambda = new Lambda({
  mode: LambdaMode.Persistent,
  lambdaPath: __dirname + '/handler/example-handler.js'
});

const result = lambda.execute<APIGatewayProxyResult>();

// you can manually stop the child process
// otherwise the child process lives
// until the parent process is terminated
lambda.stop();

Options

The Lambda constructor accepts the following options:

required:

  • lambdaPath: absolute path to the lambda handler.

optional:

  • environment: environment variables accessible in the lambda handler.

  • lambdaHandler: the name of lambda handler, defaults to handler.

  • lambdaTimeout: maximum execution time for the lambda, defaults to 30.000ms.

  • autoReload: if true, the lambda handler is automatically updated every time the file associated with lambdaPath is changed. Defaults to false.

  • debugPort: when node is started with the debug flag (--inspect or NODE_OPTIONS="--inspect") and a debugPort is specified, the forked process will listen on this port for debug messages.

The execute method:

CLI

You can also use the CLI to run a lambda function from a file.

CLI Options
-t, --timeoutMaximal execution time in ms
-e, --envEnvironment variables, either a JSON object or file path
-o, --eventThe event object passed to the lambda function, either a JSON object or file path
-h, --handlerThe name of lambda handler, defaults to: handler

Examples:

# passing environment variables 
runl -e '{"LOG_LEVEL": "DEBUG"}' ./index.cjs

# specify event data and milliseconds until lambda timeout
runl -o '{"action": "delete"}' -t 1000 ./index.cjs
1.2.0

5 months ago

1.1.0

5 months ago

0.8.2

5 months ago

0.8.1

1 year ago

0.8.0

1 year ago

0.7.0

1 year ago

0.6.0

2 years ago

0.3.5

2 years ago

0.5.0

2 years ago

0.3.2

2 years ago

0.4.0

2 years ago

0.5.2

2 years ago

0.3.4

2 years ago

0.5.1

2 years ago

0.3.3

2 years ago

0.3.1

2 years ago

0.3.0

2 years ago

0.2.2

2 years ago

0.2.1

2 years ago

0.2.0

2 years ago

0.0.1

2 years ago