geek pro tem

Spacelift - Concepts

Mar 5, 2023 - 3 minute read

Here’s I’ll be discussing some of the core concepts Spacelift uses. My use case is Terraform based, so I’ll be framing things with that in mind.

Modules

This is the easiest piece to translate - these are just Terraform modules kept in the Spacelift private repository.

Each module will be sourced from a git repo and root path. There will be a .spacelift directory to create in your module repository roots that will define the version and any tests you want to use.

The tests are pretty slick - you can provide some variables and conditions and when you make a commit Spacelift will ensure that the resources declared can be planned/applied/destroyed before it actually accepts the new version to be published.

Stacks

A stack is where the magic really happens in Spacelift. Roughly the same as a Terraform workspace with some additional sugar on it, a stack is where you will actually see resources be created and where most work is done. Each stack has an independent state managed by Spacelift.

Stacks are also the scope where tasks can be run to perform things like drift detection, manual Terraform commands, etc.

Each stack is bound to a git repo/root path, and when a change is pushed the stack will detect that and perform a terraform plan with the changes. If any changes are detected, it will then either apply those changes or it will wait for confirmation to do so depending on how you have it setup.

You can also have stack dependencies so that if you make a change to one stack that will affect others, it will rebuild those stacks, too.

Contexts

A context is simply a store for environment variables and config files to present to the stacks that reference them. A stack can have multiple contexts it uses, and they are read from in the order you define so that you can have more specific values overriding general ones.

And since Spacelift can Terraform against itself, you can use this as a way to propagate outputs/values from one stack that can then be made available to others. Sort of an alternative to shared states or using some key/value store.

Policies

This is a feature that I like the idea of, but for my personal projects it just doesn’t do much so I haven’t played with it a lot, yet. What these are, though, are ways to define the permissions, operations, and options for other resources in a very granular and codified way.

Spaces

A space is a logical construct that lets you isolate all of the above. Spaces work similar to a directory structure with optional inheritance. So you could have foo/bar and foo/baz where foo could contain modules or contexts that bar and baz use, but bar and baz won’t be able to directly reference each other.