How to build a React chat app with AWS API Gateway WebSockets, Custom Lambda Authorizer
AWS announced the launch of a widely-requested feature: WebSockets for Amazon API Gateway few days ago. To test out this new feature, I spent a couple of hours building a realtime chat App using WebSockets with custom lambda authorizer.
Before You Start
Please read below articles to understand WebSocket APIs in Amazon API Gateway and Cognito User Pool
This post is courtesy of Diego Magalhaes, AWS Senior Solutions Architect - World Wide Public Sector-Canada & JT…aws.amazon.com
With a user pool, your users can sign in to your web or mobile app through Amazon Cognito.docs.aws.amazon.com
Now, Let’s Start
You can find all the code on GitHub
Realtime chat web app using React, AWS API Gateway Websockets, Dynamodb and custom Cognito authorizer. …github.com
Main Libraries in Backend
- API Gateway WebSockets
- Cognito User Pool
- Serverless 1.35.1
- Node.js 8.10
Main Libraries in Frontend
I always get 500 error when trying to connect to WebSockets with authoriztion if authorizer lambda function and WebSockets functions are in same project, so i split authorizer lambda function and WebSockets lambda functions to two Serverless projects.
There are three sub projects:
API Gateway WebSockets and lambda functions to manage WebSockets routes ($connect, $disconnect, sendMessage) and create DynamoDb to store WebSockets connectionIds.
Custom authorizer lambda function.
React online app with live chat functionality.
Building API, the Serverless Framework, and AWS Lambda
You’ll need to have
serverless-websockets-pluginplugin in your
serverless.yml plugins listing:
Your serverless.yml might look something like the following
- Effect: Allow
# required for WebSocket APIs
Deploy Backend and Auth Serverless Projects
Go to Backend and Auth directory, run
sls deploy --stage dev
API and lambda functions will be created automatically after deployment.
Configure REQUEST Authorizer function
Serverless Framework doesn’t support custom authorizer for WebSockets route yet, to configure a lambda function as a REQUEST authorizer for a WebSocket API, follow below steps:
- Go to AWS console, find api deployed in previous step, in this example the api name is websocket-chat-dev
- Go to Authorizers-> Create Authorizer,
- Set lambda function to serverless-chat-auth-dev-authorizerFunc which is deployed in previous step .
- Set Identity Sources to Query String, value is query string variable, i set to token in this example.
Next, Set Authorizer to $connect route
- Go to Routes->$connect->Route Request
- Set auth to Authorization and Save
3. Deploy API from AWS API gateway console.
React Frontend Implementation
AWS Amplify (1.1.17) pubsub module doesn’t support API Gateway WebSockets yet. I decide to use sockette as WebSockets client. It is a tiny library and truly simple to use.
Below are example of declaring all event listeners on initialization and sending messages:
import Sockette from "sockette";
//Init WebSockets with Cognito Access Token
ws = new Sockette(
onopen: e => console.log("connected:", e),
onmessage: e => console.log("Message Received:", e),
onreconnect: e => console.log("Reconnecting...", e),
onmaximum: e => console.log("Stop Attempting!", e),
onclose: e => console.log("Closed!", e),
onerror: e => console.log("Error:", e)
data: "Hello World"
In Frontend project, I have no Class components by integrating React Hook, Hooks make it possible to take a React function component and add state to it, or hook into lifecycle methods like componentDidMount and componentDidUpdate.
At the version of 16.7.0-alpha.2, Hooks are in alpha. Their API can change at any time. I recommend you experiment, have fun, and use Hooks in your side projects, but not in production code until they’re stable.
All set to go, Try it out!
Go to frontend directory, run
$ npm install
$ npm start
There is also WebSocket support in AWS AppSync, It is fantastic and I highly recommend it if you like to use GraphQL for your application.