Actions
Commands
st2 action list --pack=tutorialsst2 action get tutorials.echost2 run tutorials.echo message="Hello world"st2 action get tutorials.check-bash-versionst2 run tutorials.check-bash-version major=true minor=truest2 run tutorials.check-bash-versionst2 action get tutorials.check-python-versionst2 run tutorials.check-python-versionst2 run tutorials.check-python-version major=true minor=truest2 run tutorials.check-python-version major=truest2 action get tutorials.check-node-versionst2 run tutorials.check-node-versionst2 run tutorials.check-node-version major=truest2 run tutorials.check-node-version major=true minor=truenano actions/check-bash-version.yaml actions/check-python-version.yaml actions/check-node-version.yaml
Notes/Errata
- We do not delve into action runners in this tutorial. That will be covered in a future tutorial. However, see the Advanced Actions tutorial for actions run with more advanced runners, especially Python scripts!
- Running Python scripts with the
local-shell-scriptrunner is regarded as an anti-pattern. Please use thepython-scriptrunner from the Advanced Actions tutorial to run Python scripts. - In the video, you may not be able to see the “Logout” button in the user menu of the Workflow Composer. This is because the menu has the same background color as the toolbar, so it blends in. You should be able to see it on your screen.
Files
echo.yaml
---
name: echo
description: Action that executes the Linux echo command on the localhost.
pack: tutorials
runner_type: local-shell-cmd
enabled: true
parameters:
message:
description: The message that the command will echo.
type: string
required: true
cmd:
description: Arbitrary Linux command to be executed on the local host.
required: true
type: string
default: echo ""
immutable: true
check-bash-version.yaml
---
name: check-bash-version
description: Check Bash version on host
pack: tutorials
runner_type: local-shell-script
entry_point: check-bash-version.sh
enabled: true
parameters:
major:
type: boolean
description: Include the major part of the version string
minor:
type: boolean
description: Include the minor part of the version string
check-bash-version.sh
#!/bin/bash
MAJOR=""
MINOR=""
MICRO=""
# Parse arguments
while [[ $# -gt 0 ]]; do
case "$1" in
--major)
MAJOR=$(bash --version \
| grep 'GNU bash, version' \
| awk '{ print $4 }' \
| sed 's/\([[:digit:]]\{1,\}\)\.\([[:digit:]]\{1,\}\)\.\([[:digit:]]\{1,\}\).*/\1/')
shift
;;
--minor)
MINOR=$(bash --version \
| grep 'GNU bash, version' \
| awk '{ print $4 }' \
| sed 's/\([[:digit:]]\{1,\}\)\.\([[:digit:]]\{1,\}\)\.\([[:digit:]]\{1,\}\).*/\2/')
shift
;;
--micro)
MICRO=$(bash --version \
| grep 'GNU bash, version' \
| awk '{ print $4 }' \
| sed 's/\([[:digit:]]\{1,\}\)\.\([[:digit:]]\{1,\}\)\.\([[:digit:]]\{1,\}\).*/\3/')
shift
;;
*)
echo "Unrecognized argument: $1"
echo "Usage: $0 [flag [flag]]"
echo ""
echo "Flags:"
echo " --major - include the major version substring"
echo " --minor - include the minor version substring"
echo " --micro - include the micro/bugfix version substring"
echo ""
echo "One or more flags can be passed in, and the same flag passed"
echo "in more than once has no further effect."
echo "If no flags are passed in, the entire original version string"
echo "is printed."
exit -1
;;
esac
done
if [[ -n "$MAJOR" || -n "$MINOR" || -n "$MICRO" ]]; then
# The *_VERSION variables are either the version substring or are empty,
# so we join them all together with spaces, then strip off beginning and
# ending spaces, and finally replace any remaining spaces with periods.
echo " $MAJOR $MINOR $MICRO " \
| sed 's/^ \{0,\}//' \
| sed 's/ \{0,\}$//' \
| sed 's/ \{1,\}/./g'
else
# If we weren't passed any flags, just print the entire version string
bash --version \
| grep 'GNU bash, version' \
| awk '{ print $4 }'
fi
check-python-version.yaml
---
name: check-python-version
description: Check Python version on host
pack: tutorials
runner_type: local-shell-script
entry_point: check-python-version.py
enabled: true
parameters:
major:
type: boolean
description: Include the major part of the version string
minor:
type: boolean
description: Include the minor part of the version string
check-python-version.py
#!/usr/bin/python
from __future__ import print_function
import argparse
import sys
HELP = """
Usage: $0 [flag [flag]]
Flags:
--major - include the major version substring
--minor - include the minor version substring
--micro - include the micro/bugfix version substring
One or more flags can be passed in, and the same flag passed in more than once
has no further effect.
If no flags are passed in, the entire original version string is printed.
"""
# Parse the arguments to the script
parser = argparse.ArgumentParser(description='Get the version of Python')
parser.add_argument('--major', dest='major', action='store_true', default=False)
parser.add_argument('--minor', dest='minor', action='store_true', default=False)
parser.add_argument('--micro', dest='micro', action='store_true', default=False)
args = parser.parse_args()
# Build the version tuple
version_tuple = tuple()
if args.major:
version_tuple += (sys.version_info[0],)
if args.minor:
version_tuple += (sys.version_info[1],)
if args.micro:
version_tuple += (sys.version_info[2],)
if not any([args.major, args.minor, args.micro]):
version_tuple = tuple(version_part for version_part in sys.version_info)
print('.'.join([str(el) for el in version_tuple]))
check-node-version.yaml
---
name: check-node-version
description: Check Node.js version on host
pack: tutorials
runner_type: local-shell-script
entry_point: check-node-version.js
enabled: true
parameters:
major:
type: boolean
description: Include the major part of the version string
minor:
type: boolean
description: Include the minor part of the version string
check-node-version.js
#!/usr/bin/node
// Offsets into the versions array
var major = 0,
minor = 1,
micro = 2;
// This is a bit array - if an element is true, it indicates that it should be
// included in the printed result
var versions = [false, false, false];
// Parse all arguments, filling in the appropriate elements of the versions
// array
process.argv.slice(2).forEach(function (val) {
if (val === "--major") {
versions[major] = true;
} else if (val === "--minor") {
versions[minor] = true;
} else if (val === "--micro") {
versions[micro] = true;
}
});
var any_versions = versions.some(function (el) { return el; })
var result = "";
// Get the version string, strip it, and split it
// Then iterate over each value, appending the version substring to the output
// string.
// If there weren't any version substrings specified, then append every
// version substring.
process.version.replace(/^v/, '').split('.').forEach(function (val, i) {
if (versions[i] || !any_versions) {
result+=(' ' + val);
}
});
// Finally, strip any beginning or ending whitespace, replace all spaces with
// periods, and print the resulting version string
console.log(result.replace(/^\s*/, '').replace(/\s+/g, '.'));
Questions, Comments, and Corrections
Open an issue or submit a pull request.
Transcript
Hi everybody and welcome to StackStorm tutorials!
Today’s tutorial is on Actions.
To start off, I’m going to list all of the actions in the tutorials pack.
I’m going to run the ST2 command to list all of the actions, and limit it to the tutorials pack.
Now the first action we’re going to look at today is the echo action.
To take a look at that I execute st2 action get tutorials.echo.
This tells me some interesting information about the echo action: it belongs to the tutorials pack, there’s a short description of it, it uses the local-shell-cmd runner, and it takes a message parameter.
The message parameter is the most important part of this; this required option indicates to me that I have to pass it into the action itself, and it has to be a string.
The description of it is simply the message that the echo command will actually echo.
The local-shell-cmd runner will simply run the echo command on the StackStorm server itself.
If you don’t know what an action runner is yet, don’t worry - we’ll cover that in a future tutorial. For now, just know that it tells StackStorm what type of action it is.
In order to run this, all I have to do is use the st2 command to run it.
Here, StackStorm ran the command on the StackStorm server itself, the parameters that I passed in were “Hello world”, and the result is that it succeeded, and the standard out of that command was “Hello world”.
The next action I want to talk about is the check-bash-version action, so we’ll take a look at that.
This action is slightly more complex than the last echo action. It uses a different runner - it uses the local-shell-script runner, that runner accepts an entry_point parameter and for this runner it’s just the name of the shell script that we want to run. The shell script takes two boolean flags: major and minor, we can pass those in and we’ll run it with the major and the minor flags.
As you can see, from the standard out, it printed “4.3”, that means the StackStorm server is running Bash 4.3. But we don’t necessarily have to pass in either parameter.
Let’s see what happens when we don’t.
In this case, when you don’t pass in any flags, the script prints out the entire version string.
There are two other similar actions that we can take a look at: the first one is the check-python-version action.
This action is very similar to the check-bash-version action, except with this one the entry_point is different - instead of being a Bash script, it calls a Python script. But notice the parameters are very similar: it takes a minor and a major parameter, and both are booleans.
To call this action, it would be very similar to the last one.
And again, when I don’t pass in the major or minor parameters, it gives me the full version string of the installed version of Python.
Similar to the check-bash-version action, I can pass in the major and minor flags to the action.
I can also just pass in one of the flags.
The other action we can take a look at is the check-node-version action.
This, again, is very similar, but instead it runs a Node script. And this Node script accepts the same parameters: major and minor.
That gives us the full Node version.
And with that we can also pass one or both of the major and minor flags.
Now at this point, you’re probably asking “how are actions defined”? Let’s take a look.
I’m currently in the tutorials pack and all of the actions we just ran are right here. Let’s dig into them.
This action, the check-bash-version action, is defined in this YAML file.
It specifies the runner, and it specifies the entry_point to use. It also specifies all of the parameters, and the check-python-version action is going to be very similar.
Here we see it’s using the same runner, but it’s entry_point is different - exactly like what we saw before - and the check-node-version action is going to be the exact same as well.
Another way to run actions is to use the web interface.
Once it’s loaded in your web browser, you can go to the “Actions” tab, and go to the tutorials pack.
There we see all of the actions available to us, and one of them is the check-python-version action.
This is a list of all of the options that can be passed to the action - you’ll notice the boolean major and minor flags that we saw in the action metadata file.
If we wanted to get the major and minor versions of Python installed on the StackStorm host, we would select both of those and click “Run”.
StackStorm schedules the actions to run, so once we go into “Execution History”, we can see here that the check-python task has run and it has output “2.7”.