Target Environment Descriptor Reference

The target environment descriptor (aka "ted" file) is used to configure the Skopos engine to interact with a specific runtime environment.

This document covers the detailed settings. If you want to understand what target environment descriptors are and how to use them, see the Using Target Enviroments Guide

You can also see some ready-made target environment files for some standard environments supported by Skopos.

Examples

A simple environment file may look like this:

core_plugin: docker-swarm
service_discovery_plugin: docker-swarm
service_discovery_auto: true

A more detailed environment file for a docker-based application that uses AWS application-level load balancers can look like this:

core_plugin: docker                 # use Docker for creating instances (containers)
service_discovery_plugin: docker    # may be omitted since docker is the core plugin
service_discovery_auto: true        # should be always true for the docker plugin
load_balancer_plugin: docker-elb    # use AWS application level ELB tied to docker instances
chatops_plugin: slack               # deploy notifications

vars:
    env: production
    region: us-west1
    db_user: hellodb
    vault_path: secret/hello
    nginx_ver: "1.11.10"            # or set to "latest" to track the latest release

plugin_config:
    docker:
        volumes:
            myvol: { from: "/hello/vol1", readonly: false }
    docker-elb:
        lb:
            ingress: "hello-lb"     # model lb name mapped to AWS name for the LB for this application instance
    slack:
        url: 'https://hooks.slack.com/services/F0LFL61HF/L45LUWFM1/NlR6Gi4DMiGaWn3efatnpfsD'

quality_gates:
    websrv:
        images:                     # components with matching images deploy using the
            - my_registry/websrv:*  # specified steps (e.g., to gate the success of deployment)
        steps:
            - probe:
                image: opsani/probe-http
                action: get_ok
                label: "Probe: https healthcheck"
                arguments: { schema: "https", path: "/healthz" }
    customer_db:
        images:
            - my_registry/customer_db:*
        steps:
            - probe:
                image: opsani/probe-mariadb
                action: check_access
                label: "Probe: check customer db access"
                arguments:
                    user: my_user
                    password: ${db_password}
                    database: my_database

The following sections cover the different settings available in the target environment files.

Service Infrastructure Configuration

This section identifies what plugins will be used for discovering application state and deploying the application. In most cases, this section has the same contents for all instances of the same application (and, frequently, will be the same for all applications used in an organization).

This section can also contain and cover some differences in the service infrastructure setup, e.g., between using on-laptop docker for dev deployments and using a docker cluster for staging and production deployments.

This section supports the following attributes:

core_plugin

The name of the plugin that is used for enumerating, creating and destroying components of the application. The Plugins reference has a list of supported plugins that support the core operations. The core plugin is also used by the engine to find what components are currently running.

This attribute should be specified.

In addition, the core_plugin is used to access service discovery and/or load balancer functionality if the corresponding plugins have not been defined in the target environment file (i.e., the core plugin is called to provide capabilities not defined explicitly to use a different plugin)

service_discovery_plugin

(optional) The name of the plugin to use to control service discovery. This is usually required for automatic plan generation and may be omitted only if per-instance control of 'discoverability' is not required (or not available at all in the target environment).

In environments that provide built-in service discovery (e.g., recent versions of Docker), the core plugin also handles service discovery (and the name of the service plugin can be omitted). This attribute must be explicitly specified if using an external service discovery mechanism (e.g., consul, etcd, etc.). See the Plugins reference for a list of plugins that support service discovery and their configuration details.

service_discovery_auto

(optional) A boolean that specifies whether new instances automatically become enabled for service discovery, as soon as they are created. This setting is a hint for the automatic plan generator. The default is false.

NOTE: for Docker and, in most cases, for consul, this attribute should be explicitly set to true.

load_balancer_plugin

The name of the plugin to use for load balancer operations. This is required for automatic plan generation, if the application uses one or more external load balancers. It may be the same value as core_plugin if the plugin supports both core and load-balancer operations (e.g., the ec2-asg plugin).

load_balancer_auto

A boolean that specifies whether new instances are automatically connected to a load balancer, as soon as they are created. This setting is a hint for the automatic plan generator. The default is false and most current plugins supporting load balancers work with this default setting.

chatops_plugin

The name of the plugin to use for sending chatops notifications. If specified, Skopos will send notifications for the following events:

  • deploy started, completed or failed
  • deploy was auto-paused due to error
  • a change was detected that requires a deploy

Note that the plugin may require additional configuration, check the docs or the chatops plugin you want to use.

Variables

This section defines values for any variables used in the model. Typically, these variables reflect the differences between instances of the application (e.g., dev vs. prod, geographic area, credentials, etc.)

vars

The vars section is optional. If present, it can contain any number of key/value pairs. Note the values must be strings (numbers, object or list values are not supported).

The definitions in the vars section can be used for value substitution when plugins or scripts are invoked in a deployment plan, as well as for environment variables are passed to container instances and most values in the model.

See the Variable Substitution section for details and useful examples on using variable substitution in the model.

See the multiple environment files section below for rules of precedence.

Also, the quality_gates and plugin_config sections of a TED file support variable substitution within their contents, just like the model descriptor. Variables are substituted from those defined in the same TED file as the quality gates or plugin config, or from the merged (effective) TED where multiple TED files are loaded.

Advanced topic: see the Variable Interpolation section for details on using variable values in manually created deploy plans (rarely used).

Plugin Configuration

plugin_config

The plugin_config map contains configuration for one or more plugins, with the plugin names as keys. The format of the configuration data for each plugin varies and not all plugins support configuration. The Plugins document defines in detail the configuration formats for each plugin that supports configuration.

It is not an error to add configuration for a plugin that needs none (it will be ignored).

Note that scripts do not use plugin configuration. Defining a section for a script in plugin_config has no effect. To customise the operation of a script, use definitions in the vars section and refer to them in the command-line parameters for the script in the plan steps.

Here is a quick reference to the config sections in plugins that support them:

Quality Gates

quality_gates

The quality_gates map contains the specification for one or more quality gates, with the quality gate names as keys. Quality gates attach user defined actions to components in order to gate the success of component deployment.

See User Defined Quality Gates for specification details and examples.

Multiple Environment Files

Starting in version 0.11, Skopos supports multiple target environment files, allowing you to split (factor) environment configuration in building blocks that can easily be assembled for multiple deployments.

Multiple ted files can be specified with the load/run Skopos commands:

skopos load --project foo --env file1.yaml --env file2.yaml model.yaml

The files are evaluated in the order provided on the command line and values present in an earlier file may be overridden by values in a later file.

Factoring Environment

Skopos does not dictate how environment files are split. It is possible to put everything in one file or split into any groups. A single file is suitable when there is only one copy of the application (and the file can be checked into your version control together with the code of the project) or the file is generated by some external system, e.g., Jenkins.

For multiple environments - whether multiple deployments of the same type and/or different deployment types - it is best to split the environment files in meaningful groups.

Example commands supporting 2 development, 1 daily test, 1 staging and 2 production environments:

skopos load --project alice     --env docker.yaml       --env alice.yaml     --env dev-vers.yaml     model.yaml
skopos load --project bob       --env docker.yaml       --env bob.yaml       --env dev-vers.yaml     model.yaml
skopos load --project daily     --env docker.yaml       --env daily.yaml     --env dev-vers.yaml     model.yaml
skopos load --project staging   --env docker-swarm.yaml --env staging.yaml   --env staging-vers.yaml model.yaml
skopos load --project prod-emea --env docker-swarm.yaml --env prod-emea.yaml --env prod-vers.yaml    model.yaml
skopos load --project prod-na   --env docker-swarm.yaml --env prod-na.yaml   --env prod-vers.yaml    model.yaml

The above examples split the target environment files in 3 groups:

  • service infrastructure configuration (the set of plugins to use, e.g., docker vs. docker-swarm)
  • application service configurations (typically, env vars given to each service container, such as tuning parameters, credentials, external resources, port numbers, etc.); separate file for each deployment (project)
  • version configuration (e.g., version tags for all relevant containers/images); separate file for each type of deployment (dev/staging/prod)

It is possible to mix and match version tags: for example, in dev versions, latest mutable (dynamic) tags can be used for convenience; while in staging and production, fixed (immutable) tags like 1.11.1 can be used for better control.

In addition, the chatops plugin configuration can be added either as a separate ted file (when shared between projects) or placed in each configuration (alice, bob, prod-emea, etc.) to use different webhooks for the different projects.

Another effective factoring of environment files is to specify all quality gates in a single ted file. This file may then be used when deploying any application to provide a common specification for gating the success of component deployments.

Precedence rules

When the same setting is found in more than one file, the one found later (in the order they're given on Skopos load or run command line) takes precedence. The replacement is done according to the following rules:

  • service infrastructure configuration (plugin names/options): top level values are replaced in their entirety, each separately (e.g., chatops_plugin)
  • variables: each variable is replaced separately (i.e., values in vars found in a latter file replace those in an earlier one)
  • plugin configuration: each plugin's configuration is merged recursively, to any level of nested map objects (scalars and arrays are replaced entirely, including arrays of map objects - note that 'array of maps' constructs do not actually occur in any plugin configuration formats). The value for a map key (at any level of map-in-map-in-map.. nesting) is the one found in the last file containing it. A latter file cannot cause a key found in a prior file to disappear, only replace its value.
  • quality gates: same as for the plugin configuration, each gate's configuration is merged recursively.

A few examples illustrating the recursive merge used for plugin and gate configurations:

== file 1 ==

plugin_config:
   docker:
      command: ['/bin/sh', '/my-startup' ]
      volumes:
         db:
           from: '/usr/var/mysql'
           comment: 'db storage space'
         tmp: { from: '/tmp/tmpvols/1' }

== file 2 ==

plugin_config:
   docker:
      command: ['/bin/bash', '/advanced-startup' ]
      volumes:
         db: { from: '/usr/lib/vols/mysql' }
         tmp: { }

== result ==

plugin_config:
   docker:
      command: ['/bin/bash', '/advanced-startup' ] # array is replaced (entire array from 2nd file)
      volumes:
         db:
           from: '/usr/var/mysql' # 'from' is taken from the 2nd file
           comment: 'db storage space' # kept as in the 1st file
         tmp: { from: '/tmp/tmpvols/1' } # 'from' is kept as in the 1st file