Nick
Nick

Reputation: 361

AWS CDK deployment for multiple tenants

As per the CDK "Best Practices" documentation, we should "model all production stages in code".

In the CDK, you can, and should, build that configuration right into your source code. Create a stack for your production environment, and a separate one for each of your other stages, and put the configuration values for each right there in the code.

I got recently reminded of that best practice and read some more on the non-deterministic results you get if you don't abide by it.

For an environment that includes dev, test and prod (for simplicity) this seems doable and combined with AWS Pipeline sounds like a great idea to run deployments (code driven CI/CD). A commit in the code will automatically result in a re-deploy and changes in the environment as necessary. Great.

However where things seem to be a little more complicated is when prod is really 100s of different tenant environments. So they all "look" the same in terms of the resources they have, but there are differences in, say the network subnets allocations they each use, the vanity name for the access point, etc...

If we want to stick to the deterministic approach referred to above, what is the recommended approach ?

Any other suggestions ? Am I missing the point. ?

Or should we somewhat ignore the anti-pattern and introduce more "lookup" and conditional behavior in the code ?

Upvotes: 4

Views: 1535

Answers (1)

moltar
moltar

Reputation: 1781

This is a very interesting question, and one that I also have explored.

NOTE: I am not a pro at this, take everything below with a grain of salt.

As far as I can see, there are two approaches.

StackSets (docs)

I believe StackSets were designed exactly for this purpose, and supposedly they work well.

The only problem is there is no good CDK support for it. There are several issues in the CDK repo discussing this.

There is an RFC for getting the support for StackSets. Sooner or later it will make it into CDK, just not there yet at the time of writing this.

Multiple Stage Definitions

Alternatively, just like with dev, test and prod stages you may just have multiple prod stages.

Each prod stage may it's own configuration that the stack class gets instantiated with. You can pass any config you want to the stack and use it inside the stack for configuring services, capacity and so on.

We use this approach right now with a small number of production deployments. Essentially, we just have an array of stack configs, that we iterate over in the CodePipeline and deploy stages in parallel.

This is infra-as-code, right? Let's use the full benefits of a real programming language!

You can also keep this config list externally (e.g. in a database), and then fetch the config, and instantiate the stack classes. E.g. you can fetch the config as the first step in the pipeline and dump it as JSON to disk, then in the stack app.ts read the JSON config and creates an array of stack instances.

Cons: I think there is an arbitrary limit of how many stages you can have per pipeline (or phase?), and it's not very large.

Upvotes: 2

Related Questions