Common Architecture Patterns

Understand the authentication and authorization pattern for the WebSocket API.


WebSocket API integration at the API Gateway works just as any REST API, except that the response integration isn’t mandatory. We can set up the API to invoke a Lambda function, any other AWS service, or even an external API. For example, we can have our WebSocket API wrapping another stateless API.

Integration with Lambda functions is easy to conceptualize because it fits well with the traditional three-tier architecture of API-Compute-DB. However, we have several other options when dealing with serverless microservices.

We can put the data directly into the database, translate it into an event or a notification, or queue it for eventual processing. This choice impacts API latency and the overall time required for the processing. It affects the API's resilience and the resulting application's maintainability.

It’s the architect's responsibility to choose wisely among the different forms of integration so that the application gets the best tradeoff between performance, latency, and resilience.

  • API lambda integration

  • Event/ notification using integration with EventBridge/SNS

  • Storage integration by storing the input request into DB/S3/SQS

Authentication and authorization

When we develop applications in the cloud, authentication and authorization form an important part of the architecture. This is more true when we work with APIs that are open to the world. WebSocket APIs on the AWS API Gateway follow a few standard authentication and authorization patterns. This lesson describes a common pattern used for authentication and authorization for a WebSocket API.

When we look at APIs in general, we have a few common patterns for the authentication of APIs.

  • A shared-secret-based authentication using an API key or a username/password pair.

  • A token obtained by authenticating the first call with a shared secret or asymmetric key verification.

  • A session created on the server based on authenticating the first call with a shared secret

API authorization is based on an internal DB query based on the API key or session ID, or it could be based on the content of the JWT signed by the server.

A REST API is stateless. It processes each new request independently. That involves a fresh authentication/authorization for each request coming from the client. Normally, we don’t want to go through the entire authentication/authorization process on every API call. That would produce unnecessary overhead. To avoid this, we have to use one of the methods above to contain the session information in each subsequent request and avoid the overhead of repeating the authentication every time.

Authentication in WebSocket

WebSocket follows a different pattern. WebSockets are stateful. The connectionId provides a link between subsequent calls. That’s why we need to authenticate the client only at the connection time. Once the connection is established, the subsequent requests can assume that it’s authenticated and doesn’t need an additional framework to validate the client.

There are two ways to manage the authentication of the connection request.

  • The WebSocket connect request carries the username and password in a header. This is verified in the $connect route before creating the connection.

  • The WebSocket connection is created after a basic authentication with a REST API. The REST API returns a signed token carried by the WebSocket connect request. In that case, the $connect route simply validates the token and trusts its content.

Authorization in WebSocket

In either case, once the connection is established, the other messages flowing to the server don’t carry any authentication or authorization information. This can pose a challenge for authorization. The $connect route should save the session details in a cache or DynamoDB. This includes authorization details along with the authentication information. We can therefore validate the following messages based on the connectionId and its record in the cache or the database.

Get hands-on with 1200+ tech skills courses.