* `rundeck_remove_missing` Whether to delete jobs present in rundeck and not in file. Defaults to true.
* `rundeck_jobs_group` the group of job to check for removal
* `rundeck_ignore_creation_errors` whether to ignore job creation error. Default to true to follow the 200 status given by rundeck API
+* `rundeck_jobs_keys` a list of keys to import in rundeck. Each key is a dict with a `path`, a `value` and a `type` as declared in [https://docs.rundeck.com/3.0.x/api/index.html#upload-keys]().
+* `rundeck_keys_scoped_by_project` scope each key by project (In a project/ProjectName subdirectory)
+* `rundeck_keys_scoped_by_group` scope each key by group. Defaults to true if the group is defined, false otherwise
+* `rundeck_remove_missing_keys` remove keys that are not declared in ansible (possibly restrained to the scope defined above)
A [dhall](https://dhall-lang.org/) Type representing the roles' variables is available in the `./dhall/Config.dhall` file to help you configure your projects with some type checking.
---
rundeck_api_version: 26
rundeck_remove_missing: true
+rundeck_remove_missing_keys: false
rundeck_ignore_creation_error: true
rundeck_keys_scoped_by_project: true
rundeck_jobs_keys: []
, rundeck_api_token : Text
, rundeck_api_version : Optional Natural
, rundeck_remove_missing : Optional Bool
+ , rundeck_remove_missing_keys : Optional Bool
, rundeck_ignore_creation_error : Optional Bool
, rundeck_jobs_group : Optional Text
, rundeck_jobs_keys : List Key
, default =
{ rundeck_api_version = Some 26
, rundeck_remove_missing = Some True
+ , rundeck_remove_missing_keys = Some False
, rundeck_ignore_creation_error = Some True
, rundeck_jobs_group = None Text
, rundeck_jobs_keys = [] : List Key
--- /dev/null
+#!/usr/bin/env bash
+
+set -euo pipefail
+
+BASE_URL="$1"
+TOKEN="$2"
+BASE_PATH="$3"
+
+list_path_rec() {
+ path="$1"
+ result=$(curl -ks "$BASE_URL/storage/$path?authtoken=$TOKEN")
+
+ case "$(echo "$result" | jq -r .type)" in
+ "file") echo "$result" | jq -r .path | sed -e "s@^$BASE_PATH/@@"
+ ;;
+ "directory")
+ echo "$result" | jq -r ".resources[]|.path" | while read p; do list_path_rec "$p"; done
+ ;;
+ esac
+}
+
+list_path_rec "$BASE_PATH"
--- /dev/null
+---
+- name: Build scoped path
+ set_fact:
+ rundeck_key_full_path: "{{ rundeck_keys_base_path }}/{{ item.path }}"
+
+- name: Check key existence
+ uri:
+ url: "{{ rundeck_api_url }}/{{ rundeck_api_version }}/storage/keys/{{ rundeck_key_full_path }}"
+ method: GET
+ headers:
+ Accept: application/json
+ X-Rundeck-Auth-Token: "{{ rundeck_api_token }}"
+ status_code: [200, 404]
+ register: rundeck_existing_key
+
+- name: Set method
+ set_fact:
+ rundeck_key_uri_method: "{{ (rundeck_existing_key.status == 404) | ternary('POST', 'PUT') }}"
+
+- name: Import key
+ uri:
+ url: "{{ rundeck_api_url }}/{{ rundeck_api_version }}/storage/keys/{{ rundeck_key_full_path }}"
+ method: "{{ rundeck_key_uri_method }}"
+ headers:
+ Accept: application/json
+ Content-Type: "{{ item.type }}"
+ X-Rundeck-Auth-Token: "{{ rundeck_api_token }}"
+ status_code: [200, 201]
+ body: "{{ item.value }}"
+ body_format: raw
---
-- name: Build scoped path
+- name: Set scope variables
set_fact:
- rundeck_key_full_path: "{{ rundeck_keys_scoped_by_project | default(true) | ternary('project/' + rundeck_project + '/' + key_group_path, key_group_path) }}"
+ rundeck_keys_base_path: "{{ rundeck_keys_scoped_by_project | default(true) | ternary('project/' + rundeck_project + '/' + rundeck_keys_group_path, rundeck_keys_group_path) }}"
vars:
group_name: "{{ rundeck_jobs_group | default('') }}"
- key_group_path: "{{ rundeck_keys_scoped_by_group | default((group_name|length) > 0) | ternary(group_name + '/' + item.path, item.path) }}"
+ rundeck_keys_group_path: "{{ rundeck_keys_scoped_by_group | default((group_name|length) > 0) | ternary(group_name, '') }}"
-- name: Check key existence
- uri:
- url: "{{ rundeck_api_url }}/{{ rundeck_api_version }}/storage/keys/{{ rundeck_key_full_path }}"
- method: GET
- headers:
- Accept: application/json
- X-Rundeck-Auth-Token: "{{ rundeck_api_token }}"
- status_code: [200, 404]
- register: rundeck_existing_key
+- name: Include rundeck key
+ include_tasks: key.yml
+ with_items: "{{ rundeck_jobs_keys }}"
+
+- name: Get all stored keys
+ script:
+ cmd: "{{ role_path }}/files/fetch_keys.sh {{ rundeck_api_url }}/{{ rundeck_api_version }} {{ rundeck_api_token }} keys/{{ rundeck_keys_base_path }}"
+ register: rundeck_existing_keys
+ when: rundeck_remove_missing_keys
-- name: Set method
+- name: "Prepare list of keys to remove"
set_fact:
- rundeck_key_uri_method: "{{ (rundeck_existing_key.status == 404) | ternary('POST', 'PUT') }}"
+ rundeck_existing_keys: "{{ rundeck_existing_keys.stdout_lines | list }}"
+ rundeck_known_keys: "{{ rundeck_jobs_keys | map(attribute='path') | list }}"
+ when: rundeck_remove_missing_keys
-- name: Import key
+- name: "Remove jobs not declared"
uri:
- url: "{{ rundeck_api_url }}/{{ rundeck_api_version }}/storage/keys/{{ rundeck_key_full_path }}"
- method: "{{ rundeck_key_uri_method }}"
+ url: "{{ rundeck_api_url }}/{{ rundeck_api_version }}/storage/keys/{{ rundeck_keys_base_path }}/{{ item }}"
+ method: DELETE
headers:
Accept: application/json
- Content-Type: "{{ item.type }}"
X-Rundeck-Auth-Token: "{{ rundeck_api_token }}"
- status_code: [200, 201]
- body: "{{ item.value }}"
- body_format: raw
+ status_code: [204, 404]
+ with_items: "{{ rundeck_existing_keys | difference(rundeck_known_keys) }}"
+ when: rundeck_remove_missing_keys
tags:
- rundeck-jobs
- name: Include rundeck keys
- include_tasks: keys.yml
tags:
- rundeck-keys
- with_items: "{{ rundeck_jobs_keys }}"
+ include_tasks: keys.yml