Dissecting Serverless Stacks (III)
This content is more than 4 years old and the cloud moves fast so some information may be slightly out of date.
Dissecting Serverless Stacks (III)
The third post of this series showed how to make IAM statements an external file, so we can deploy that one but still work with the sls
command. It still involved commenting out things in the configuration, so this post will show how to solve that issue.
When we are thinking about writing a Serverless project which can be deployed “all-in-one” or in some two-step process, we are basically discussion an “if/then/else” scenario. If we use the sls deploy
command normally, it should work like any other SLS project. But if we add some option, it should react differently (like skipping the external IAM stack). On a first glance, SLS does not offer such a mechanic. But let’s see how we can make it work nonetheless
Command line options
You can define your own command line switches, which are called “options” in the Serverless Framework. These switches can then be referenced via a $(opt:name)
statement:
custom:
deployment_option: $(opt:deployment, 'standard')
If we include this block in our serverless.yml
file, we define a command line option and its standard value. So basically this could be sls deploy
or sls deploy --deployment standard
. Or we could supply a different value. During the previous blog post of this series, we also learned that we can use references like $(custom.deployment_option)
in our file to reference parts of the file.
So how can we implement different cases? The answer lies in something which can be considered a mapping and then a “double-reference”:
custom:
deployment_option: $(opt:deployment, 'standard')
imports:
standard: $(file:iam.yaml)
no_includes: ""
# ... other parts of the file ...
resources:
- ${self:custom.imports.${self:custom.deployment_option}}
- Description: ${self:functions.fancy.description}
This looks confusing at first, so let us have a closer look:
-
When we supply no
--deployment
option, the$(custom.deployment_option)
reference will bestandard
. In that case, our reference will equal${self.custom.imports.standard)
and the content of this is the content of$(file:iam.yaml)
- so our IAM stack. -
But if we pass
--deployment no_includes
instead, the reference will equal${self.custom.imports.no_includes}
, which is just an empty string. Whilesls deploy
will throw a warning about that, it will still result in the IAM stack not being included.
So in short: with sls deploy
we have the IAM stack included, with sls deploy --deployment no_includes
we will not have it included.