Serverless Framework v1.38 - Introducing Websockets Support

Feb 21, 2019

As many of you likely remember, AWS finally added support for WebSockets in API Gateway & Lambda at last year's re:Invent. While we were all waiting for CloudFormation support, we created an official Serverless Framework plugin to support WebSockets in the Framework right away.

This was only a temporary measure until CloudFormation support was added. And now, it has been! So we are incredibly excited to announce that the Serverless Framework v1.38 now has support for WebSockets integrated into Framework core. No plugin required.

Note: This means that the serverless-websockets-plugin is officially deprecated. We will no longer maintain it.

Get Started with WebSockets on the Serverless Framework

To start using WebSockets in your serverless projects, subscribe your functions to the new websocket event by specifying the desired routes that would invoke your function:

functions:
  default:
    handler: handler.default
    events:
      - websocket: $default

This will create a $default route that will forward all WebSocket events (including $connect and $disconnect) to your default function.

You can also specify your event as an object and add more routes:

functions:
  connect:
    handler: handler.connect
    events:
        - websocket:
            route: $connect
  disconnect:
    handler: handler.disconnect
    events:
      - websocket:
          route: $disconnect
  default:
    handler: handler.default
    events:
      - websocket:
          route: $default
  echo:
    handler: handler.echo
    events:
      - websocket:
          route: $echo

The object notation will be useful when you want to add more configuration to your WebSocket events. For example, when we add support for authorizers in an upcoming release.

Once you deploy this service, you'll see the endpoint of your WebSocket backend in your terminal. Using this endpoint, you can connect to your WebSocket backend using any WebSocket client.

You could also have another function with http event, so your service would expose two endpoints: one for websockets, the other for http.

Specifying Route Selection Expression

By default, the route selection expression is set to $request.body.action. This property tells API Gateway how to parse the data coming into your WebSocket endpoint.

So with this default behavior and using the service above, you can invoke the echo function by using the following JSON object as your websocket event body:

{
  "action": "echo",
  "data":  "hello"
}

You can overwrite the route expression by specifying the websocketsApiRouteSelectionExpression key in the provider object:

provider:
  name: aws
  runtime: nodejs8.10
  websocketsApiRouteSelectionExpression: "$request.body.route"

In that case, your WebSocket body should be:

{
  "route": "echo",
  "data":  "hello"
}

Remember that any other body/data coming to your WebSocket backend would invoke the default function.

Communicating with clients

The Framework also takes care of setting the permissions required for your Lambda function to communicate to the connected clients. This means you'll be able to send data to any client right away by using the new ApiGatewayManagementApi Service, without having to worry about IAM policies:

  const client = new AWS.ApiGatewayManagementApi({
    apiVersion: '2018-11-29',
    endpoint: `https://${event.requestContext.domainName}/${event.requestContext.stage}`
  });

  await client
    .postToConnection({
      ConnectionId: event.requestContext.connectionId,
      Data: `echo route received: ${event.body}`
    })
    .promise();

Note: At the time of writing, the Lambda runtime does not include the latest version of the AWS SDK that contains this new ApiGatewayManagementApi service. So you'll have to deploy your own by adding it to your package.json.

And that's pretty much all you need to do to get started with WebSockets events! For more information, please check out our docs.

Changelog

Other than WebSockets support, we added a lot of enhancements and bug fixes in this release. Here's our changelog, with some links to the corresponding PRs.

Roadmap and focus

Over the next few releases, we'll be enhancing WebSockets support with more features, like authorizers and request responses. We're also focusing on improving the local development experience. Keep an eye on the upcoming milestones to stay up to date with what's coming:

Contributor thanks

We had more than 20 contributors have their work go into this release and we can't thank each of them enough. You all make the community special.

Want to have your github avatar and name in the next release post? Check out these issues we are looking for help on!

Subscribe to our newsletter to get the latest product updates, tips, and best practices!

Thank you! Your submission has been received!
Oops! Something went wrong while submitting the form.