State
Tracking the infrastructure created by your app.
When you deploy your app, SST creates a state file locally to keep track of the state of the infrastructure in your app.
So when you make a change, it’ll allow SST to do a diff with the state and only deploy what’s changed.
The state of your app includes:
- A state file for your resources. This is a JSON file.
- A passphrase that is used to encrypt the secrets in your state.
Aside from these, SST also creates some other resources when your app is first deployed. We’ll look at this below.
The state is generated locally but is backed up to your provider using:
- A bucket to store the state, typically named
sst-state-<hash>
. This is created in the region of yourhome
. More on this below. - An SSM parameter to store the passphrase used to encrypt your secrets, under
/sst/passphrase/<app>/<stage>
. Also created in the region of yourhome
.
The passphrase is used to encrypt any secrets and sensitive information. Without it SST won’t be able to read the state file and deploy your app.
Home
Your sst.config.ts
specifies which provider to use for storing your state. We call this the home
of your app.
You can specify which provider you’d like to use for this. Currently aws
and cloudflare
are supported.
When you specify your home provider, SST assumes you’d like to use that provider in your app as well and adds it to your providers internally. So the above is equivalent to doing this.
This also means that if you change the region of the aws
provider above, you are changing the region for your home
as well.
You can read more about the home
provider in Config.
Bootstrap
As SST starts deploying the resources in your app, it creates some additional bootstrap resources. If your app has a Lambda function or a Docker container, then SST will create the following in the same region as the given resource:
- An assets bucket to store the function packages, typically named
sst-asset-<hash>
. - An ECR repository to store container images, called
sst-asset
. - An SSM parameter to store the assets bucket name and the ECR repository, stored under
/sst/bootstrap
. - An AppSync Events API endpoint to power Live.
The SSM parameter is used to look up the location of these resources.
When you remove an SST app, it does not remove the state or bootstrap resources. This is because it does not know if there are other apps that might be using this. So if you want to completely remove any SST created resources, you’ll need to manually remove these in the regions you’ve deployed to.
Reset
If you accidentally remove the bootstrap resources the SST CLI will not be able to start up.
To fix this you’ll need to reset your bootstrap resources.
- Remove the resources that are listed in the parameter. For example, the
asset
orstate
bucket. Or the ECR repository. - Remove the SSM parameter.
Now when you run the SST CLI, it’ll bootstrap your account again.
How it works
The state file is a JSON representation of all the low level resources created by your app. It is a cached version of the state of resources in the cloud provider.
So when you do a deploy the following happens.
- The components in the
sst.config.ts
get converted into low level resource definitions. These get compared to the the state file. - The differences between the two are turned into API calls that are made to your cloud provider.
- If there’s a new resource, it gets created.
- If a resource has been removed, it gets removed.
- If there’s a change in config of the resource, it gets applied.
- The state file is updated to reflect the new state of these resources. Now the
sst.config.ts
, the state file, and the resources in the cloud provider are all in sync.
Out of sync
This process works fine until you manually go change these resources through the cloud provider’s console. This will cause the state and the resources to not be in sync anymore. This can cause an issue in some cases.
Let’s look at a couple of scenarios.
Say we’ve deployed a Function
with it set to { timeout: 10 seconds" }
. At this point, the config, state, and resource are in sync.
Change the resource
- We now go change the timeout to 20 seconds in the AWS Console.
- The config and state are out of sync with the resource since they are still set to 10 seconds.
- Now if we deploy our app, the config will be compared to the state.
- It’ll find no differences and so it won’t update the resource.
The config and state will stay out of sync with the resource.
Change the config
- If we change our config to
{ timeout: 30 seconds" }
and do a deploy. - The config and state will have some differences.
- SST will make a call to AWS to set the timeout of the resource to 30 seconds.
- Once updated, it’ll update the state file to match the current state of the resource.
The config, state, and resource are back being in sync.
Remove the resource
- Next we go to the AWS Console and remove the function.
- The config and state still have the function with the timeout set to 30 seconds.
- If we change our config to
{ timeout: 60 seconds }
and do a deploy. - The config and state will be different.
- SST will make a call to update the timeout of the resource to 60 seconds.
- But this call to AWS will fail because the function doesn’t exist.
Your deploys will fail moving forward because your state shows that a resource exists but it doesn’t anymore. To fix this, you’ll need to refresh your state file.
Refresh
To fix scenarios where the resources in the cloud are out of sync with the state of your app, you’ll need to run.
This command does a couple of simple things:
- It goes through every single resource in your state.
- Makes a call to the cloud provider to check the resource.
- If the configs are different, it’ll update the state to reflect the change.
- If the resource doesn’t exist anymore, it’ll remove it from the state.
Now the state and the resources are in sync. So if we take the scenario from above where we removed the function from the AWS Console but not from our config or state. To fix it, we’ll need to:
- Run
sst refresh
- This will remove the function from the state as well.
- Now if we change our config to
{ timeout: 60 seconds }
and do a deploy. - The config and state will be compared and it’ll find that a function with that config doesn’t exist.
- So SST will make a call to AWS to create a new function with the given config.
In general we do not recommend manually changing resources in a cloud provider since it puts your state out of sync. But if you find yourself in a situation where this happens, you can use the sst refresh
command to put them back in sync.