Developers are moving their apps to serverless architectures and one of the most common questions is how to store user sessions. You need to keep your state and session data in an external data store because serverless environments are stateless by design. Unfortunately most of the databases are not serverless friendly. They do not support per-request pricing or they require heavy and persistent connections. These also explain the motivations why we built Upstash. Upstash is a serverless Redis database with per-request pricing, durable storage.
In this article I will write a basic web application which will run on Google Cloud Run and keep the user sessions in Upstash Redis. Google Cloud Run provides Serverless Container service which is also stateless. Cloud Run is more powerful than serverless functions (AWS Lambda, Cloud Functions) as you can run your own container. But you can not guarantee that the same container instance will process the requests of the same user. So you need to keep the user session in an external storage. Redis is the most popular choice to keep the session data thanks to its speed and simplicity. Upstash gives you the serverless Redis database which fits perfectly to your serverless stack.
Here is the live demo.
Here is the source code
Serverless processing: Google Cloud Run
Serverless data: Upstash
Web framework: Express
Create a directory for your project:
Create a node project and install dependencies:
Create a Redis DB from Upstash. In the database details page, click the Connect button, copy the connection code (Node.js node-redis).
If you do not have it already, install Google Cloud SDK as described here. Set the project and enable Google Run and Build services:
Create index.js and update as below:
Run the app:
Check http://localhost:3000/foo in different browsers to validate it keeps the session.
Add the start script to your
Create a Docker file (Dockerfile) in the project folder as below:
Build your container image:
List your container images:
gcloud container images list
Run the container locally:
In case you have an issue on docker run, check here.
This command should give you the URL of your application as below:
I have developed two small prototypes with both. Here my impression:
- Simplicity: Cloud functions are simpler to deploy as it does not require any container building step.
- Portability: Cloud Run leverages your container, so anytime you can move your application to any containerized system. This is a plus for Cloud Run.
- Cloud Run looks more powerful as it runs your own container with more configuration options. It also allows running longer tasks (can be extended to 60 minutes)
- Cloud Run looks more testable as you can run the container locally. Cloud Functions require a simulated environment.
Personally, I see Cloud Functions as a pure serverless solution where Cloud Run is a hybrid solution. I would choose Cloud functions for simple, self contained tasks or event driven solutions. If my use case is more complex with portability/testability requirements, then I would choose Cloud Run.