pcuzner / ansible-runner-service

Python project that wraps the ansible_runner 'engine' inside a RESTful API
Other
16 stars 9 forks source link

ansible-runner-service Build statuscodecov

This project wraps the ansible_runner interface inside a REST API enabling ansible playbooks to be executed and queried from other platforms.

The incentive for this is two-fold;

Features

The core of this project is ansible_runner, so first of all, a quick call out to those folks for such an awesome tool!

Security

Monitoring

Playbook Execution

Playbook State

Inventory management

Developer Friendly

Deployment

Prerequisites

So far, testing has been mainly against Fedora (28) and the CentOS7 for the docker image. Other distros may work fine (Travis build uses Ubuntu Trusty for example!).

Package Dependencies

(see requirements.txt for a more complete list of the python dependencies)

if in doubt, look in the misc/docker folder and build the container!

Installation

Try before you buy...assuming you have an environment that meets the python3 dependencies, simply unzip the archive and run :)

python3 ansible_runner_service.py

When you run from any directory outside of /usr, the script regards this as 'dev' mode. In this mode, all files and paths are relative to the path that you've unzipped the project into.

For 'prod' mode, a setup.py is provided. Once the package is installed and called from /usr/*/bin, the script will expect config and output files to be found in all the normal 'production' locations (see proposed file layout below)

sudo python3 setup.py install --record installed_files --single-version-externally-managed

Once this is installed, you may start the service with

ansible_runner_service

API Endpoints

Once the service is running, you can point your browser at https://localhost:5001/api to show which endpoints are available. Each endpoint is described along with a curl example showing invocation and output.

API endpoints

You may click on any row to expand the description of the API route and show the curl example. The app uses a self-signed certificate, so all examples use the -k parameter (insecure mode).

Note: It is not the intent of this API to validate the parameters passed to it. It is assumed that parameter selection and validation happen prior to the API call.

Here's a quick 'cheat sheet' of the API endpoints.

API Route Description
/api Show available API endpoints (this page)
/api/v1/groups List all the defined groups in the inventory
/api/v1/groups/ Manage groups within the inventory
/api/v1/hosts Return a list of hosts from the inventory
/api/v1/hosts/ Show group membership for a given host
/api/v1/hosts//groups/ Manage ansible control of a given host
/api/v1/jobs//events Return a list of events within a given playbook run (job)
/api/v1/jobs//events/ Return the output of a specific task within a playbook
/api/v1/login Authenticate user and provide token
/api/v1/playbooks Return the names of all available playbooks
/api/v1/playbooks/ Query the state or cancel a playbook run (by uuid)
/api/v1/playbooks/ Start a playbook by name, returning the play's uuid
/api/v1/playbooks//tags/ Start a playbook using tags to control which tasks run
/metrics Provide prometheus compatible statistics which describe playbook activity

Testing

Testing to date has all been lab based, so please bear this in mind if considering using this tool for production use cases (bug reports welcome!). Playbook integration with Ceph and Gluster has been the primary focus together with the probe-disks.yml playbook. Did you spot the theme?..It's all about the storage™ :)

For example, with ceph the osd-configure.yml playbook has been tested successfully.

Manual Testing

The archive, downloaded from github, contains a simple playbook that just uses the bash sleep command - enabling you to quickly experiment with the API.

Use the steps below (dev mode), to quickly exercise the API

  1. Authenticate user and provide token
    curl -k -i --user admin:admin https://localhost:5001/api/v1/login -X get
  2. Get the list of available playbooks (should just be test.yml)
    curl -k -i -H "Authorization: eyJ0eXAiOiJKV1QiLCJhbGciOiJIUzI1NiJ9.eyJleHAiOjE1MzczODA3MTR9.CbTXvBum5mCq9s56wJNiMn8JLJ0UzzRdwdeOFctJtbI" https://localhost:5001/api/v1/playbooks -X GET
  3. Run the test.yml playbook, passing the time_delay parameter (30 secs should be enough).
    curl -k -i -H "Authorization: eyJ0eXAiOiJKV1QiLCJhbGciOiJIUzI1NiJ9.eyJleHAiOjE1MzczODA3MTR9.CbTXvBum5mCq9s56wJNiMn8JLJ0UzzRdwdeOFctJtbI" -H "Content-Type: application/json" --data '{"time_delay": 30}' https://localhost:5001/api/v1/playbooks/test.yml -X POST
  4. The previous command will return the playbooks UUID. Use this identifier to query the state or progress of the run.
    curl -k -i -H "Authorization: eyJ0eXAiOiJKV1QiLCJhbGciOiJIUzI1NiJ9.eyJleHAiOjE1MzczODA3MTR9.CbTXvBum5mCq9s56wJNiMn8JLJ0UzzRdwdeOFctJtbI" https://localhost:5001/api/v1/playbooks/f39069aa-9f3d-11e8-852f-c85b7671906d -X GET
  5. Get a list of all the events in a playbook. The return list consists of all the job event ID's
    curl -k -i -H "Authorization: eyJ0eXAiOiJKV1QiLCJhbGciOiJIUzI1NiJ9.eyJleHAiOjE1MzczODA3MTR9.CbTXvBum5mCq9s56wJNiMn8JLJ0UzzRdwdeOFctJtbI" https://localhost:5001/api/v1/jobs/f39069aa-9f3d-11e8-852f-c85b7671906d/events -X GET
  6. To get specific output from a job event, you can query the job event
    curl -k -i -H "Authorization: eyJ0eXAiOiJKV1QiLCJhbGciOiJIUzI1NiJ9.eyJleHAiOjE1MzczODA3MTR9.CbTXvBum5mCq9s56wJNiMn8JLJ0UzzRdwdeOFctJtbI" https://localhost:5001/api/v1/jobs/f39069aa-9f3d-11e8-852f-c85b7671906d/events/13-c85b7671-906d-e52d-d421-000000000008 -X GET

Obviously you'll need to change the token, play and job uuids for your run :)

Tips & Tricks

  1. Tweaking the environment:The script uses a configuration module which is accessible across the different modules within the project. There are two ways that settings in the configuration module can be overridden;

    • by using a config.yaml file
    • by providing a setting value when starting the ansible_runner_service program
  2. Overriding configuration at run time, lets you do quick tests like this;

    • start the service, but don't perform any passwordless ssh tests
      $ ssh_checks=false python3 ansible_runner_service
    • change the target user when validating ssh connection is in place
      $ target_user=root python3 ansible_runner_service

Automated Build & Testing

The project uses Travis CI integration to check the following;

For more info, look at the .travis.yml file.

File Layout (Proposed)

/etc/ansible-runner-service

/usr/share/ansible-runner-service

/var/log/ansible-runner-service.log

/usr/share/doc/ansible-runner-service

/etc/systemd/system

/usr/bin/ or /usr/local/bin