It's possible to deploy an application hosted on the Vercel platform (formerly Zeit Now) to multiple environments with a little extra configuration. This post will explain the following:
- How to deploy an application to two different environments (e.g. staging & production) that are accessible at 2 different subdomains (e.g. staging.app.com and app.com).
- Deploy to multiple environments from a local machine that is already authenticated with Vercel using
now login
- Deploy to multiple environments from a CI machine that is not authenticated with Vercel
Vercel project setup
In order to deploy an app to 2 different environments, it's required to have Vercel projects for each environment. In your project directory, you can execute the now
command to deploy a new project. Once you've deployed the project for one environment (e.g. staging), take note of the projectId
and orgId
values found in the generated .now/project.json
file as those values will be needed later.
Once the projectId
and orgId
values have been recorded somewhere for the first environment, delete the .now
directory and re-execute the now
command to setup a project for the other environment (e.g. prod). Again, record the projectId
and orgId
values found in the generated .now/project.json
file and then delete the .now
directory.
If you've already created a project in Vercel, you can still run the now
command above since the now
command will prompt you to create a new project OR link to an existing project.
Each environment will likely have a different set of environment variable values, so make sure to setup 2 different now.json
configuration files for each environment. For example you can create a now.staging.json
and a now.prod.json
file to map your environment variables to the appropriate Now secret.
Make sure to configure the domain names for each environment in the Vercel dashboard in order to have the deployed apps accessible at custom domain names.
Deploy from local machine that is already authenticated with Vercel
With the projectId
and orgId
values known for each environment and the Vercel configuration files set for each environment, it's possible to deploy to both environments using the Vercel CLI.
1# Deploy to staging environment2export NOW_PROJECT_ID=xxx && export NOW_ORG_ID=xxx && now --prod --local-config ./now.staging.json3# Deploy to prod environment4export NOW_PROJECT_ID=xxx && export NOW_ORG_ID=xxx && now --prod --local-config ./now.prod.json
Replace the xxx
for NOW_PROJECT_ID
and NOW_ORG_ID
with the values of projectId
and orgId
, respectively, that correspond with the Vercel project you wish to deploy. The above commands sets the NOW_PROJECT_ID
and NOW_ORG_ID
environment variables which are used by the Now CLI to determine to which project the app should be deployed.
Personally, I use the dotenv-cli library to set the NOW_PROJECT_ID
and NOW_ORG_ID
environment variables. It requires installing dotenv-cli and creating a file that will hold the values of the environment variables.
1# .now.env.staging2NOW_ORG_ID=xxx3NOW_PROJECT_ID=xxx
Then the command to deploy to Vercel is as follows:
1# Deploy to staging environment2dotenv -e now.env.staging -- now --prod --local-config ./now.staging.json3# Deploy to prod environment4dotenv -e now.env.prod -- now --prod --local-config ./now.prod.json
This allows me to store the values of the NOW_ORG_ID
and NOW_PROJECT_ID
environment variables in files that can be ignored by git so I don't need to commit secrets to source control.
Deploy from CI machine that is not authenticated with Vercel
On CI machines, make sure to load the environment variables using the environment variable system that comes with your CI provider. For example, with GitHub actions you would set GitHub secrets that contain the projectId
and orgId
for all your deployment environments and then map the values of those secrets to environment variables specified in a workflow file.
Also, in order to run Now CLI commands from a CI machine, it is required to provide a ZEIT Now token to the Now CLI command to be executed. You can generate a Vercel token here.
1now --prod --local-config ./now.staging.json --token xxx
References
Spectrum chat discussion on project linking and CI/CD pipelines
GitHub issue comment by Honza Javorek about the environment variables needed to be set