We can do better than simple copy/paste. Since StackStorm is written in Python there is great support for creating actions using Python code.
Some of the benefits of using Python actions in StackStorm:
- python module dependency management (via
requirements.txt
) - access to a built-in logger
- support for
**kwargs
indef run()
- support for native python types (
int
,bool
,dict
,list
) - automatic conversion of native python types to structured output (
int
,bool
,dict
,list
) - access to the pack config
- access to the key/value datastore
In this demo we're going to convert the action we just created into a StackStorm native python action that receives the benefits above.
First, we need to create an Action Metadata with runner_type: python-script
.
This will tell StackStorm we're using a native Python action. It also defines our input
parameters for the action (this will allow us to remove all of our argparse
code within
the script).
Delete all of the content in the file /opt/stackstorm/packs/tutorial/actions/nasa_apod.yaml
:
# hint: delete all of the content in the file
echo "" > /opt/stackstorm/packs/tutorial/actions/nasa_apod.yaml
Edit /opt/stackstorm/packs/tutorial/actions/nasa_apod.yaml
and add the following content:
---
name: nasa_apod
pack: tutorial
description: "Queries NASA's APOD (Astronomy Picture Of the Day) API to get the link to the picture of the day."
runner_type: "python-script"
enabled: true
entry_point: nasa_apod.py
parameters:
api_key:
type: string
description: "API key to use for api.nasa.gov."
default: "DEMO_KEY"
hd:
type: boolean
description: "Retrieve the high resolution image."
default: false
date:
type: string
description: "The date [YYYY-MM-DD] of the APOD image to retrieve."
You can see in this metadata file that our datatypes are defined along with
the same defaults and descriptions from the original python script. We're going
to show you how these definitions make the argparse
code in the python script
no longer necessary!
NOTE If you're struggling and just need the answer, simply copy the file from our answers directory:
cp /opt/stackstorm/packs/tutorial/etc/answers/actions/nasa_apod_native.yaml /opt/stackstorm/packs/tutorial/actions/nasa_apod.yaml
Next, we'll need to convert our Python code over to something compatible with StackStorm. For native Python actions the following rules need to be met:
- The python script must contain a one and only one
class
that inherits fromst2common.runners.base_action.Action
- The
Action
sub-class must define adef run(self)
function.
Example of the most basic action:
from st2common.runners.base_action import Action
class HelloWorld(Action):
def run(self):
return "hello world"
The final code in /opt/stackstorm/packs/tutorial/actions/nasa_apod.py
should look like:
#!/usr/bin/env python
#
# Description:
# Queries NASA's APOD (Astronomy Picture Of the Day) API to get the link to the picture
# of the day.
#
import json
import requests
from st2common.runners.base_action import Action
API_URL = "https://api.nasa.gov/planetary/apod"
class Apod(Action):
def run(self, api_key, date, hd):
params = {'api_key': api_key,
'hd': hd}
if date is not None:
params['date'] = date
response = requests.get(API_URL, params=params)
response.raise_for_status()
data = response.json()
if hd:
data['url'] = data['hdurl']
return data
NOTE If you're struggling and just need the answer, simply copy the file from our answers directory:
cp /opt/stackstorm/packs/tutorial/etc/answers/actions/nasa_apod_native.py /opt/stackstorm/packs/tutorial/actions/nasa_apod.py
Let's register with StackStorm
st2ctl reload --register-actions
And test!
st2 run tutorial.nasa_apod date=2018-07-04