Module Reference

Ansible

Summary: Configure ansible for instance

This module provides ansible integration for augmenting cloud-init’s configuration of the local node.

This module installs ansible during boot and then uses ansible-pull to run the playbook repository at the remote URL.

Internal name: cc_ansible

Module frequency: once-per-instance

Supported distros: all

Activate only on keys: ansible

Config schema:

ansible: (object)

install-method: (distro/pip) The type of installation for ansible. It can be one of the following values:

  • distro

  • pip.

package-name: (string)

pull: (object)

accept-host-key: (boolean)

clean: (boolean)

full: (boolean)

diff: (boolean)

ssh-common-args: (string)

scp-extra-args: (string)

sftp-extra-args: (string)

private-key: (string)

checkout: (string)

module-path: (string)

timeout: (string)

url: (string)

connection: (string)

vault-id: (string)

vault-password-file: (string)

module-name: (string)

sleep: (string)

tags: (string)

skip-tags: (string)

playbook-name: (string)

Examples:

#cloud-config
ansible:
  install-method: distro
  pull:
    url: "https://github.com/holmanb/vmboot.git"
    playbook-name: ubuntu.yml

# --- Example2 ---
#cloud-config
ansible:
  package-name: ansible-core
  install-method: pip
  pull:
    url: "https://github.com/holmanb/vmboot.git"
    playbook-name: ubuntu.yml

APK Configure

Summary: Configure apk repositories file

This module handles configuration of the /etc/apk/repositories file.

Note

To ensure that apk configuration is valid yaml, any strings containing special characters, especially : should be quoted.

Internal name: cc_apk_configure

Module frequency: once-per-instance

Supported distros: alpine

Activate only on keys: apk_repos

Config schema:

apk_repos: (object)

preserve_repositories: (boolean) By default, cloud-init will generate a new repositories file /etc/apk/repositories based on any valid configuration settings specified within a apk_repos section of cloud config. To disable this behavior and preserve the repositories file from the pristine image, set preserve_repositories to true.

The preserve_repositories option overrides all other config keys that would alter /etc/apk/repositories.

alpine_repo: (null/object)

base_url: (string) The base URL of an Alpine repository, or mirror, to download official packages from. If not specified then it defaults to https://alpine.global.ssl.fastly.net/alpine.

community_enabled: (boolean) Whether to add the Community repo to the repositories file. By default the Community repo is not included.

testing_enabled: (boolean) Whether to add the Testing repo to the repositories file. By default the Testing repo is not included. It is only recommended to use the Testing repo on a machine running the Edge version of Alpine as packages installed from Testing may have dependencies that conflict with those in non-Edge Main or Community repos.

version: (string) The Alpine version to use (e.g. v3.12 or edge).

local_repo_base_url: (string) The base URL of an Alpine repository containing unofficial packages.

Examples:

# Keep the existing /etc/apk/repositories file unaltered.
apk_repos:
    preserve_repositories: true

# --- Example2 ---
# Create repositories file for Alpine v3.12 main and community
# using default mirror site.
apk_repos:
    alpine_repo:
        community_enabled: true
        version: 'v3.12'

# --- Example3 ---
# Create repositories file for Alpine Edge main, community, and
# testing using a specified mirror site and also a local repo.
apk_repos:
    alpine_repo:
        base_url: 'https://some-alpine-mirror/alpine'
        community_enabled: true
        testing_enabled: true
        version: 'edge'
    local_repo_base_url: 'https://my-local-server/local-alpine'

Apt Configure

Summary: Configure apt for the user

This module handles both configuration of apt options and adding source lists. There are configuration options such as apt_get_wrapper and apt_get_command that control how cloud-init invokes apt-get. These configuration options are handled on a per-distro basis, so consult documentation for cloud-init’s distro support for instructions on using these config options.

Note

To ensure that apt configuration is valid yaml, any strings containing special characters, especially : should be quoted.

Note

For more information about apt configuration, see the Additional apt configuration example.

Internal name: cc_apt_configure

Module frequency: once-per-instance

Supported distros: ubuntu, debian

Config schema:

apt: (object)

preserve_sources_list: (boolean) By default, cloud-init will generate a new sources list in /etc/apt/sources.list.d based on any changes specified in cloud config. To disable this behavior and preserve the sources list from the pristine image, set preserve_sources_list to true.

The preserve_sources_list option overrides all other config keys that would alter sources.list or sources.list.d, except for additional sources to be added to sources.list.d.

disable_suites: (array of string) Entries in the sources list can be disabled using disable_suites, which takes a list of suites to be disabled. If the string $RELEASE is present in a suite in the disable_suites list, it will be replaced with the release name. If a suite specified in disable_suites is not present in sources.list it will be ignored. For convenience, several aliases are provided for`` disable_suites``:

  • updates => $RELEASE-updates

  • backports => $RELEASE-backports

  • security => $RELEASE-security

  • proposed => $RELEASE-proposed

  • release => $RELEASE.

When a suite is disabled using disable_suites, its entry in sources.list is not deleted; it is just commented out.

primary: (array of object) The primary and security archive mirrors can be specified using the primary and security keys, respectively. Both the primary and security keys take a list of configs, allowing mirrors to be specified on a per-architecture basis. Each config is a dictionary which must have an entry for arches, specifying which architectures that config entry is for. The keyword default applies to any architecture not explicitly listed. The mirror url can be specified with the uri key, or a list of mirrors to check can be provided in order, with the first mirror that can be resolved being selected. This allows the same configuration to be used in different environment, with different hosts used for a local APT mirror. If no mirror is provided by uri or search, search_dns may be used to search for dns names in the format <distro>-mirror in each of the following:

  • fqdn of this host per cloud metadata,

  • localdomain,

  • domains listed in /etc/resolv.conf.

If there is a dns entry for <distro>-mirror, then it is assumed that there is a distro mirror at http://<distro>-mirror.<domain>/<distro>. If the primary key is defined, but not the security key, then then configuration for primary is also used for security. If search_dns is used for the security key, the search pattern will be <distro>-security-mirror.

Each mirror may also specify a key to import via any of the following optional keys:

  • keyid: a key to import via shortid or fingerprint.

  • key: a raw PGP key.

  • keyserver: alternate keyserver to pull keyid key from.

If no mirrors are specified, or all lookups fail, then default mirrors defined in the datasource are used. If none are present in the datasource either the following defaults are used:

  • primary => http://archive.ubuntu.com/ubuntu.

  • security => http://security.ubuntu.com/ubuntu.

Each object in primary list supports the following keys:

arches: (array of string)

uri: (string)

search: (array of string)

search_dns: (boolean)

keyid: (string)

key: (string)

keyserver: (string)

security: (array of object) Please refer to the primary config documentation.

Each object in security list supports the following keys:

arches: (array of string)

uri: (string)

search: (array of string)

search_dns: (boolean)

keyid: (string)

key: (string)

keyserver: (string)

add_apt_repo_match: (string) All source entries in apt-sources that match regex in add_apt_repo_match will be added to the system using add-apt-repository. If add_apt_repo_match is not specified, it defaults to ^[\w-]+:\w.

debconf_selections: (object) Debconf additional configurations can be specified as a dictionary under the debconf_selections config key, with each key in the dict representing a different set of configurations. The value of each key must be a string containing all the debconf configurations that must be applied. We will bundle all of the values and pass them to debconf-set-selections. Therefore, each value line must be a valid entry for debconf-set-selections, meaning that they must possess for distinct fields:

pkgname question type answer

Where:

  • pkgname is the name of the package.

  • question the name of the questions.

  • type is the type of question.

  • answer is the value used to answer the question.

For example: ippackage ippackage/ip string 127.0.01.

^.+$: (string)

sources_list: (string) Specifies a custom template for rendering sources.list . If no sources_list template is given, cloud-init will use sane default. Within this template, the following strings will be replaced with the appropriate values:

  • $MIRROR

  • $RELEASE

  • $PRIMARY

  • $SECURITY

  • $KEY_FILE.

conf: (string) Specify configuration for apt, such as proxy configuration. This configuration is specified as a string. For multiline APT configuration, make sure to follow yaml syntax.

https_proxy: (string) More convenient way to specify https APT proxy. https proxy url is specified in the format https://[[user][:pass]@]host[:port]/.

http_proxy: (string) More convenient way to specify http APT proxy. http proxy url is specified in the format http://[[user][:pass]@]host[:port]/.

proxy: (string) Alias for defining a http APT proxy.

ftp_proxy: (string) More convenient way to specify ftp APT proxy. ftp proxy url is specified in the format ftp://[[user][:pass]@]host[:port]/.

sources: (object) Source list entries can be specified as a dictionary under the sources config key, with each key in the dict representing a different source file. The key of each source entry will be used as an id that can be referenced in other config entries, as well as the filename for the source’s configuration under /etc/apt/sources.list.d. If the name does not end with .list, it will be appended. If there is no configuration for a key in sources, no file will be written, but the key may still be referred to as an id in other sources entries.

Each entry under sources is a dictionary which may contain any of the following optional keys:
  • source: a sources.list entry (some variable replacements apply).

  • keyid: a key to import via shortid or fingerprint.

  • key: a raw PGP key.

  • keyserver: alternate keyserver to pull keyid key from.

  • filename: specify the name of the list file

The source key supports variable replacements for the following strings:

  • $MIRROR

  • $PRIMARY

  • $SECURITY

  • $RELEASE

  • $KEY_FILE.

^.+$: (object)

source: (string)

keyid: (string)

key: (string)

keyserver: (string)

filename: (string)

Examples:

apt:
  preserve_sources_list: false
  disable_suites:
    - $RELEASE-updates
    - backports
    - $RELEASE
    - mysuite
  primary:
    - arches:
        - amd64
        - i386
        - default
      uri: 'http://us.archive.ubuntu.com/ubuntu'
      search:
        - 'http://cool.but-sometimes-unreachable.com/ubuntu'
        - 'http://us.archive.ubuntu.com/ubuntu'
      search_dns: false
    - arches:
        - s390x
        - arm64
      uri: 'http://archive-to-use-for-arm64.example.com/ubuntu'

  security:
    - arches:
        - default
      search_dns: true
  sources_list: |
      deb $MIRROR $RELEASE main restricted
      deb-src $MIRROR $RELEASE main restricted
      deb $PRIMARY $RELEASE universe restricted
      deb $SECURITY $RELEASE-security multiverse
  debconf_selections:
      set1: the-package the-package/some-flag boolean true
  conf: |
      APT {
          Get {
              Assume-Yes 'true';
              Fix-Broken 'true';
          }
      }
  proxy: 'http://[[user][:pass]@]host[:port]/'
  http_proxy: 'http://[[user][:pass]@]host[:port]/'
  ftp_proxy: 'ftp://[[user][:pass]@]host[:port]/'
  https_proxy: 'https://[[user][:pass]@]host[:port]/'
  sources:
      source1:
          keyid: 'keyid'
          keyserver: 'keyserverurl'
          source: 'deb [signed-by=$KEY_FILE] http://<url>/ bionic main'
      source2:
          source: 'ppa:<ppa-name>'
      source3:
          source: 'deb $MIRROR $RELEASE multiverse'
          key: |
              ------BEGIN PGP PUBLIC KEY BLOCK-------
              <key data>
              ------END PGP PUBLIC KEY BLOCK-------

Apt Pipelining

Summary: Configure apt pipelining

This module configures apt’s Acquite::http::Pipeline-Depth option, which controls how apt handles HTTP pipelining. It may be useful for pipelining to be disabled, because some web servers, such as S3 do not pipeline properly (LP: #948461).

Value configuration options for this module are:

  • false (Default): disable pipelining altogether

  • none, unchanged, or os: use distro default

  • <number>: Manually specify pipeline depth. This is not recommended.

Internal name: cc_apt_pipelining

Module frequency: once-per-instance

Supported distros: ubuntu, debian

Activate only on keys: apt_pipelining

Config schema:

apt_pipelining: (integer/boolean/none/unchanged/os)

Examples:

apt_pipelining: false
# --- Example2 ---
apt_pipelining: none
# --- Example3 ---
apt_pipelining: unchanged
# --- Example4 ---
apt_pipelining: os
# --- Example5 ---
apt_pipelining: 3

Bootcmd

Summary: Run arbitrary commands early in the boot process

This module runs arbitrary commands very early in the boot process, only slightly after a boothook would run. This is very similar to a boothook, but more user friendly. The environment variable INSTANCE_ID will be set to the current instance id for all run commands. Commands can be specified either as lists or strings. For invocation details, see runcmd.

Note

bootcmd should only be used for things that could not be done later in the boot process.

Note

when writing files, do not use /tmp dir as it races with systemd-tmpfiles-clean LP: #1707222. Use /run/somedir instead.

Internal name: cc_bootcmd

Module frequency: always

Supported distros: all

Activate only on keys: bootcmd

Config schema:

bootcmd: (array of (array of string/string))

Examples:

bootcmd:
    - echo 192.168.1.130 us.archive.ubuntu.com > /etc/hosts
    - [ cloud-init-per, once, mymkfs, mkfs, /dev/vdb ]

Byobu

Summary: Enable/disable byobu system wide and for default user

This module controls whether byobu is enabled or disabled system wide and for the default system user. If byobu is to be enabled, this module will ensure it is installed. Likewise, if it is to be disabled, it will be removed if installed.

Valid configuration options for this module are:

  • enable-system: enable byobu system wide

  • enable-user: enable byobu for the default user

  • disable-system: disable byobu system wide

  • disable-user: disable byobu for the default user

  • enable: enable byobu both system wide and for default user

  • disable: disable byobu for all users

  • user: alias for enable-user

  • system: alias for enable-system

Internal name: cc_byobu

Module frequency: once-per-instance

Supported distros: ubuntu, debian

Config schema:

byobu_by_default: (enable-system/enable-user/disable-system/disable-user/enable/disable/user/system)

Examples:

byobu_by_default: enable-user
# --- Example2 ---
byobu_by_default: disable-system

CA Certificates

Summary: Add ca certificates

This module adds CA certificates to /etc/ca-certificates.conf and updates the ssl cert cache using update-ca-certificates. The default certificates can be removed from the system with the configuration option remove_defaults.

Note

certificates must be specified using valid yaml. in order to specify a multiline certificate, the yaml multiline list syntax must be used

Note

For Alpine Linux the “remove_defaults” functionality works if the ca-certificates package is installed but not if the ca-certificates-bundle package is installed.

Internal name: cc_ca_certs

Module frequency: once-per-instance

Supported distros: alpine, debian, ubuntu, rhel

Activate only on keys: ca_certs, ca-certs

Config schema:

ca_certs: (object)

remove-defaults: (boolean) DEPRECATED: Dropped after April 2027. Use remove_defaults.

remove_defaults: (boolean) Remove default CA certificates if true. Default: false.

trusted: (array of string) List of trusted CA certificates to add.

ca-certs: (object) DEPRECATED: Dropped after April 2027. Use ca_certs.

remove-defaults: (boolean) DEPRECATED: Dropped after April 2027. Use remove_defaults.

remove_defaults: (boolean) Remove default CA certificates if true. Default: false.

trusted: (array of string) List of trusted CA certificates to add.

Examples:

ca_certs:
  remove_defaults: true
  trusted:
    - single_line_cert
    - |
      -----BEGIN CERTIFICATE-----
      YOUR-ORGS-TRUSTED-CA-CERT-HERE
      -----END CERTIFICATE-----

Chef

Summary: module that configures, starts and installs chef

This module enables chef to be installed (from packages, gems, or from omnibus). Before this occurs, chef configuration is written to disk (validation.pem, client.pem, firstboot.json, client.rb), and required directories are created (/etc/chef and /var/log/chef and so-on). If configured, chef will be installed and started in either daemon or non-daemon mode. If run in non-daemon mode, post run actions are executed to do finishing activities such as removing validation.pem.

Internal name: cc_chef

Module frequency: always

Supported distros: all

Activate only on keys: chef

Config schema:

chef: (object)

directories: (array of string) Create the necessary directories for chef to run. By default, it creates the following directories:

  • /etc/chef

  • /var/log/chef

  • /var/lib/chef

  • /var/cache/chef

  • /var/backups/chef

  • /var/run/chef.

validation_cert: (string) Optional string to be written to file validation_key. Special value system means set use existing file.

validation_key: (string) Optional path for validation_cert. default to /etc/chef/validation.pem.

firstboot_path: (string) Path to write run_list and initial_attributes keys that should also be present in this configuration, defaults to /etc/chef/firstboot.json.

exec: (boolean) Set true if we should run or not run chef (defaults to false, unless a gem installed is requested where this will then default to true).

client_key: (string) Optional path for client_cert. Default to /etc/chef/client.pem.

encrypted_data_bag_secret: (string) Specifies the location of the secret key used by chef to encrypt data items. By default, this path is set to null, meaning that chef will have to look at the path /etc/chef/encrypted_data_bag_secret for it.

environment: (string) Specifies which environment chef will use. By default, it will use the _default configuration.

file_backup_path: (string) Specifies the location in which backup files are stored. By default, it uses the /var/backups/chef location.

file_cache_path: (string) Specifies the location in which chef cache files will be saved. By default, it uses the /var/cache/chef location.

json_attribs: (string) Specifies the location in which some chef json data is stored. By default, it uses the /etc/chef/firstboot.json location.

log_level: (string) Defines the level of logging to be stored in the log file. By default this value is set to :info.

log_location: (string) Specifies the location of the chef lof file. By default, the location is specified at /var/log/chef/client.log.

node_name: (string) The name of the node to run. By default, we will use th instance id as the node name.

omnibus_url: (string) Omnibus URL if chef should be installed through Omnibus. By default, it uses the https://www.chef.io/chef/install.sh.

omnibus_url_retries: (integer) The number of retries that will be attempted to reach the Omnibus URL. Default is 5.

omnibus_version: (string) Optional version string to require for omnibus install.

pid_file: (string) The location in which a process identification number (pid) is saved. By default, it saves in the /var/run/chef/client.pid location.

server_url: (string) The URL for the chef server.

show_time: (boolean) Show time in chef logs.

ssl_verify_mode: (string) Set the verify mode for HTTPS requests. We can have two possible values for this parameter:

  • :verify_none: No validation of SSL certificates.

  • :verify_peer: Validate all SSL certificates.

By default, the parameter is set as :verify_none.

validation_name: (string) The name of the chef-validator key that Chef Infra Client uses to access the Chef Infra Server during the initial Chef Infra Client run.

force_install: (boolean) If set to true, forces chef installation, even if it is already installed.

initial_attributes: (object of string) Specify a list of initial attributes used by the cookbooks.

install_type: (packages/gems/omnibus) The type of installation for chef. It can be one of the following values:

  • packages

  • gems

  • omnibus.

run_list: (array of string) A run list for a first boot json.

chef_license: (string) string that indicates if user accepts or not license related to some of chef products.

Examples:

chef:
  directories:
    - /etc/chef
    - /var/log/chef
  validation_cert: system
  install_type: omnibus
  initial_attributes:
    apache:
      prefork:
        maxclients: 100
      keepalive: off
  run_list:
    - recipe[apache2]
    - role[db]
  encrypted_data_bag_secret: /etc/chef/encrypted_data_bag_secret
  environment: _default
  log_level: :auto
  omnibus_url_retries: 2
  server_url: https://chef.yourorg.com:4000
  ssl_verify_mode: :verify_peer
  validation_name: yourorg-validator

Disable EC2 Metadata

Summary: Disable AWS EC2 Metadata

This module can disable the ec2 datasource by rejecting the route to 169.254.169.254, the usual route to the datasource. This module is disabled by default.

Internal name: cc_disable_ec2_metadata

Module frequency: always

Supported distros: all

Activate only on keys: disable_ec2_metadata

Config schema:

disable_ec2_metadata: (boolean) Set true to disable IPv4 routes to EC2 metadata. Default: false.

Examples:

disable_ec2_metadata: true

Disk Setup

Summary: Configure partitions and filesystems

This module is able to configure simple partition tables and filesystems.

Note

for more detail about configuration options for disk setup, see the disk setup example

For convenience, aliases can be specified for disks using the device_aliases config key, which takes a dictionary of alias: path mappings. There are automatic aliases for swap and ephemeral<X>, where swap will always refer to the active swap partition and ephemeral<X> will refer to the block device of the ephemeral image.

Disk partitioning is done using the disk_setup directive. This config directive accepts a dictionary where each key is either a path to a block device or an alias specified in device_aliases, and each value is the configuration options for the device. File system configuration is done using the fs_setup directive. This config directive accepts a list of filesystem configs.

Internal name: cc_disk_setup

Module frequency: once-per-instance

Supported distros: all

Activate only on keys: disk_setup, fs_setup

Config schema:

device_aliases: (object)

<alias_name>: (string) Path to disk to be aliased by this name.

disk_setup: (object)

<alias name/path>: (object)

table_type: (mbr/gpt) Specifies the partition table type, either mbr or gpt. Default: mbr.

layout: (remove/boolean/array) If set to true, a single partition using all the space on the device will be created. If set to false, no partitions will be created. If set to remove, any existing partition table will be purged. Partitions can be specified by providing a list to layout, where each entry in the list is either a size or a list containing a size and the numerical value for a partition type. The size for partitions is specified in percentage of disk space, not in bytes (e.g. a size of 33 would take up 1/3 of the disk space). Default: false.

overwrite: (boolean) Controls whether this module tries to be safe about writing partition tables or not. If overwrite: false is set, the device will be checked for a partition table and for a file system and if either is found, the operation will be skipped. If overwrite: true is set, no checks will be performed. Using overwrite: true is dangerous and can lead to data loss, so double check that the correct device has been specified if using this option. Default: false.

fs_setup: (array of object)

Each object in fs_setup list supports the following keys:

label: (string) Label for the filesystem.

filesystem: (string) Filesystem type to create. E.g., ext4 or btrfs.

device: (string) Specified either as a path or as an alias in the format <alias name>.<y> where <y> denotes the partition number on the device. If specifying device using the <device name>.<partition number> format, the value of partition will be overwritten.

partition: (string/integer/auto/any/none) The partition can be specified by setting partition to the desired partition number. The partition option may also be set to auto, in which this module will search for the existence of a filesystem matching the label, type and device of the fs_setup entry and will skip creating the filesystem if one is found. The partition option may also be set to any, in which case any file system that matches type and device will cause this module to skip filesystem creation for the fs_setup entry, regardless of label matching or not. To write a filesystem directly to a device, use partition: none. partition: none will always write the filesystem, even when the label and filesystem are matched, and overwrite is false.

overwrite: (boolean) If true, overwrite any existing filesystem. Using overwrite: true for filesystems is dangerous and can lead to data loss, so double check the entry in fs_setup. Default: false.

replace_fs: (string) Ignored unless partition is auto or any. Default false.

extra_opts: (string/array of string) Optional options to pass to the filesystem creation command. Ignored if you using cmd directly.

cmd: (string/array of string) Optional command to run to create the filesystem. Can include string substitutions of the other fs_setup config keys. This is only necessary if you need to override the default command.

Examples:

device_aliases:
  my_alias: /dev/sdb
disk_setup:
  my_alias:
    table_type: gpt
    layout: [50, 50]
    overwrite: true
fs_setup:
- label: fs1
  filesystem: ext4
  device: my_alias.1
  cmd: mkfs -t %(filesystem)s -L %(label)s %(device)s
- label: fs2
  device: my_alias.2
  filesystem: ext4
mounts:
- ["my_alias.1", "/mnt1"]
- ["my_alias.2", "/mnt2"]

Fan

Summary: Configure ubuntu fan networking

This module installs, configures and starts the ubuntu fan network system. For more information about Ubuntu Fan, see: https://wiki.ubuntu.com/FanNetworking.

If cloud-init sees a fan entry in cloud-config it will:

  • write config_path with the contents of the config key

  • install the package ubuntu-fan if it is not installed

  • ensure the service is started (or restarted if was previously running)

Additionally, the ubuntu-fan package will be automatically installed if not present.

Internal name: cc_fan

Module frequency: once-per-instance

Supported distros: ubuntu

Activate only on keys: fan

Config schema:

fan: (object)

config: (string) The fan configuration to use as a single multi-line string.

config_path: (string) The path to write the fan configuration to. Default: /etc/network/fan.

Examples:

fan:
  config: |
    # fan 240
    10.0.0.0/8 eth0/16 dhcp
    10.0.0.0/8 eth1/16 dhcp off
    # fan 241
    241.0.0.0/8 eth0/16 dhcp
  config_path: /etc/network/fan

Final Message

Summary: Output final message when cloud-init has finished

This module configures the final message that cloud-init writes. The message is specified as a jinja template with the following variables set:

  • version: cloud-init version

  • timestamp: time at cloud-init finish

  • datasource: cloud-init data source

  • uptime: system uptime

Upon exit, this module writes /var/lib/cloud/instance/boot-finished.

Internal name: cc_final_message

Module frequency: always

Supported distros: all

Config schema:

final_message: (string) The message to display at the end of the run.

Examples:

final_message: |
  cloud-init has finished
  version: $version
  timestamp: $timestamp
  datasource: $datasource
  uptime: $uptime

Growpart

Summary: Grow partitions

Growpart resizes partitions to fill the available disk space. This is useful for cloud instances with a larger amount of disk space available than the pristine image uses, as it allows the instance to automatically make use of the extra space.

The devices on which to run growpart are specified as a list under the devices key.

There is some functionality overlap between this module and the growroot functionality of cloud-initramfs-tools. However, there are some situations where one tool is able to function and the other is not. The default configuration for both should work for most cloud instances. To explicitly prevent cloud-initramfs-tools from running growroot, the file /etc/growroot-disabled can be created. By default, both growroot and cc_growpart will check for the existence of this file and will not run if it is present. However, this file can be ignored for cc_growpart by setting ignore_growroot_disabled to true. For more information on cloud-initramfs-tools see: https://launchpad.net/cloud-initramfs-tools

Growpart is enabled by default on the root partition. The default config for growpart is:

growpart:
  mode: auto
  devices: ["/"]
  ignore_growroot_disabled: false

Internal name: cc_growpart

Module frequency: always

Supported distros: all

Config schema:

growpart: (object)

mode: (auto/growpart/gpart/off) The utility to use for resizing. Default: auto

Possible options:

  • auto - Use any available utility

  • growpart - Use growpart utility

  • gpart - Use BSD gpart utility

  • off - Take no action. DEPRECATED: Specifying a boolean false value for this key is deprecated. Use off instead.

devices: (array of string) The devices to resize. Each entry can either be the path to the device’s mountpoint in the filesystem or a path to the block device in ‘/dev’. Default: [/].

ignore_growroot_disabled: (boolean) If true, ignore the presence of /etc/growroot-disabled. If false and the file exists, then don’t resize. Default: false.

Examples:

growpart:
  mode: auto
  devices: ["/"]
  ignore_growroot_disabled: false

# --- Example2 ---
growpart:
  mode: growpart
  devices:
    - "/"
    - "/dev/vdb1"
  ignore_growroot_disabled: true

Grub Dpkg

Summary: Configure grub debconf installation device

Configure which device is used as the target for grub installation. This module should work correctly by default without any user configuration. It can be enabled/disabled using the enabled config key in the grub_dpkg config dict. The global config key grub-dpkg is an alias for grub_dpkg. If no installation device is specified this module will execute grub-probe to determine which disk the /boot directory is associated with.

The value which is placed into the debconf database is in the format which the grub postinstall script expects. Normally, this is a /dev/disk/by-id/ value, but we do fallback to the plain disk name if a by-id name is not present.

If this module is executed inside a container, then the debconf database is seeded with empty values, and install_devices_empty is set to true.

Internal name: cc_grub_dpkg

Module frequency: once-per-instance

Supported distros: ubuntu, debian

Config schema:

grub_dpkg: (object)

enabled: (boolean) Whether to configure which device is used as the target for grub installation. Default: true.

grub-pc/install_devices: (string) Device to use as target for grub installation. If unspecified, grub-probe of /boot will be used to find the device.

grub-pc/install_devices_empty: (boolean) Sets values for grub-pc/install_devices_empty. If unspecified, will be set to true if grub-pc/install_devices is empty, otherwise false. DEPRECATED: Use a boolean value instead.

grub-dpkg: (object) DEPRECATED: Use grub_dpkg instead.

Examples:

grub_dpkg:
  enabled: true
  grub-pc/install_devices: /dev/sda
  grub-pc/install_devices_empty: false

Install Hotplug

Summary: Install hotplug udev rules if supported and enabled

This module will install the udev rules to enable hotplug if supported by the datasource and enabled in the userdata. The udev rules will be installed as /etc/udev/rules.d/10-cloud-init-hook-hotplug.rules.

When hotplug is enabled, newly added network devices will be added to the system by cloud-init. After udev detects the event, cloud-init will referesh the instance metadata from the datasource, detect the device in the updated metadata, then apply the updated network configuration.

Currently supported datasources: Openstack, EC2

Internal name: cc_install_hotplug

Module frequency: once-per-instance

Supported distros: all

Config schema:

updates: (object)

network: (object)

when: (array of string)

Examples:

# Enable hotplug of network devices
updates:
  network:
    when: ["hotplug"]

# --- Example2 ---
# Enable network hotplug alongside boot event
updates:
  network:
    when: ["boot", "hotplug"]

Keyboard

Summary: Set keyboard layout

Handle keyboard configuration.

Internal name: cc_keyboard

Module frequency: once-per-instance

Supported distros: arch, debian, ubuntu, almalinux, amazon, centos, cloudlinux, eurolinux, fedora, miraclelinux, openEuler, openmandriva, photon, rhel, rocky, virtuozzo, opensuse, sles

Activate only on keys: keyboard

Config schema:

keyboard: (object)

layout: (string) Required. Keyboard layout. Corresponds to XKBLAYOUT.

model: (string) Optional. Keyboard model. Corresponds to XKBMODEL. Default: pc105.

variant: (string) Optional. Keyboard variant. Corresponds to XKBVARIANT.

options: (string) Optional. Keyboard options. Corresponds to XKBOPTIONS.

Examples:

# Set keyboard layout to "us"
keyboard:
  layout: us

# --- Example2 ---
# Set specific keyboard layout, model, variant, options
keyboard:
  layout: de
  model: pc105
  variant: nodeadkeys
  options: compose:rwin

Keys to Console

Summary: Control which SSH host keys may be written to console

For security reasons it may be desirable not to write SSH host keys and their fingerprints to the console. To avoid either being written to the console the emit_keys_to_console config key under the main ssh config key can be used. To avoid the fingerprint of types of SSH host keys being written to console the ssh_fp_console_blacklist config key can be used. By default, all types of keys will have their fingerprints written to console. To avoid host keys of a key type being written to console the``ssh_key_console_blacklist`` config key can be used. By default, ssh-dss host keys are not written to console.

Internal name: cc_keys_to_console

Module frequency: once-per-instance

Supported distros: all

Config schema:

ssh: (object)

emit_keys_to_console: (boolean) Set false to avoid printing SSH keys to system console. Default: true.

ssh_key_console_blacklist: (array of string) Avoid printing matching SSH key types to the system console.

ssh_fp_console_blacklist: (array of string) Avoid printing matching SSH fingerprints to the system console.

Examples:

# Do not print any SSH keys to system console
ssh:
  emit_keys_to_console: false

# --- Example2 ---
# Do not print certain ssh key types to console
ssh_key_console_blacklist: [dsa, ssh-dss]

# --- Example3 ---
# Do not print specific ssh key fingerprints to console
ssh_fp_console_blacklist:
- E25451E0221B5773DEBFF178ECDACB160995AA89
- FE76292D55E8B28EE6DB2B34B2D8A784F8C0AAB0

Landscape

Summary: Install and configure landscape client

This module installs and configures landscape-client. The landscape client will only be installed if the key landscape is present in config. Landscape client configuration is given under the client key under the main landscape config key. The config parameters are not interpreted by cloud-init, but rather are converted into a ConfigObj formatted file and written out to the [client] section in /etc/landscape/client.conf.

The following default client config is provided, but can be overridden:

landscape:
    client:
        log_level: "info"
        url: "https://landscape.canonical.com/message-system"
        ping_url: "http://landscape.canoncial.com/ping"
        data_path: "/var/lib/landscape/client"

Note

see landscape documentation for client config keys

Note

if tags is defined, its contents should be a string delimited with , rather than a list

Internal name: cc_landscape

Module frequency: once-per-instance

Supported distros: ubuntu

Activate only on keys: landscape

Config schema:

landscape: (object)

client: (object)

url: (string) The Landscape server URL to connect to. Default: https://landscape.canonical.com/message-system.

ping_url: (string) The URL to perform lightweight exchange initiation with. Default: https://landscape.canonical.com/ping.

data_path: (string) The directory to store data files in. Default: /var/lib/land‐scape/client/.

log_level: (debug/info/warning/error/critical) The log level for the client. Default: info.

computer_title: (string) The title of this computer.

account_name: (string) The account this computer belongs to.

registration_key: (string) The account-wide key used for registering clients.

tags: (string) Comma separated list of tag names to be sent to the server.

http_proxy: (string) The URL of the HTTP proxy, if one is needed.

https_proxy: (string) The URL of the HTTPS proxy, if one is needed.

Examples:

# To discover additional supported client keys, run
# man landscape-config.
landscape:
    client:
        url: "https://landscape.canonical.com/message-system"
        ping_url: "http://landscape.canonical.com/ping"
        data_path: "/var/lib/landscape/client"
        http_proxy: "http://my.proxy.com/foobar"
        https_proxy: "https://my.proxy.com/foobar"
        tags: "server,cloud"
        computer_title: "footitle"
        registration_key: "fookey"
        account_name: "fooaccount"

# --- Example2 ---
# Any keys below `client` are optional and the default values will
# be used.
landscape:
    client: {}

Locale

Summary: Set system locale

Configure the system locale and apply it system wide. By default use the locale specified by the datasource.

Internal name: cc_locale

Module frequency: once-per-instance

Supported distros: all

Config schema:

locale: (string) The locale to set as the system’s locale (e.g. ar_PS).

locale_configfile: (string) The file in which to write the locale configuration (defaults to the distro’s default location).

Examples:

# Set the locale to ar_AE
locale: ar_AE

# --- Example2 ---
# Set the locale to fr_CA in /etc/alternate_path/locale
locale: fr_CA
locale_configfile: /etc/alternate_path/locale

LXD

Summary: Configure LXD with lxd init and optionally lxd-bridge

This module configures lxd with user specified options using lxd init. If lxd is not present on the system but lxd configuration is provided, then lxd will be installed. If the selected storage backend userspace utility is not installed, it will be installed. If network bridge configuration is provided, then lxd-bridge will be configured accordingly.

Internal name: cc_lxd

Module frequency: once-per-instance

Supported distros: ubuntu

Activate only on keys: lxd

Config schema:

lxd: (object)

init: (object)

network_address: (string) IP address for LXD to listen on.

network_port: (integer) Network port to bind LXD to.

storage_backend: (zfs/dir/lvm/btrfs) Storage backend to use. Default: dir.

storage_create_device: (string) Setup device based storage using DEVICE.

storage_create_loop: (integer) Setup loop based storage with SIZE in GB.

storage_pool: (string) Name of storage pool to use or create.

trust_password: (string) The password required to add new clients.

bridge: (object)

mode: (none/existing/new) Whether to setup LXD bridge, use an existing bridge by name or create a new bridge. none will avoid bridge setup, existing will configure lxd to use the bring matching name and new will create a new bridge.

name: (string) Name of the LXD network bridge to attach or create. Default: lxdbr0.

mtu: (integer) Bridge MTU, defaults to LXD’s default value.

ipv4_address: (string) IPv4 address for the bridge. If set, ipv4_netmask key required.

ipv4_netmask: (integer) Prefix length for the ipv4_address key. Required when ipv4_address is set.

ipv4_dhcp_first: (string) First IPv4 address of the DHCP range for the network created. This value will combined with ipv4_dhcp_last key to set LXC ipv4.dhcp.ranges.

ipv4_dhcp_last: (string) Last IPv4 address of the DHCP range for the network created. This value will combined with ipv4_dhcp_first key to set LXC ipv4.dhcp.ranges.

ipv4_dhcp_leases: (integer) Number of DHCP leases to allocate within the range. Automatically calculated based on ipv4_dhcp_first and ipv4_dchp_last when unset.

ipv4_nat: (boolean) Set true to NAT the IPv4 traffic allowing for a routed IPv4 network. Default: false.

ipv6_address: (string) IPv6 address for the bridge (CIDR notation). When set, ipv6_netmask key is required. When absent, no IPv6 will be configured.

ipv6_netmask: (integer) Prefix length for ipv6_address provided. Required when ipv6_address is set.

ipv6_nat: (boolean) Whether to NAT. Default: false.

domain: (string) Domain to advertise to DHCP clients and use for DNS resolution.

Examples:

# Simplest working directory backed LXD configuration
lxd:
  init:
    storage_backend: dir

# --- Example2 ---
lxd:
  init:
    network_address: 0.0.0.0
    network_port: 8443
    storage_backend: zfs
    storage_pool: datapool
    storage_create_loop: 10
  bridge:
    mode: new
    mtu: 1500
    name: lxdbr0
    ipv4_address: 10.0.8.1
    ipv4_netmask: 24
    ipv4_dhcp_first: 10.0.8.2
    ipv4_dhcp_last: 10.0.8.3
    ipv4_dhcp_leases: 250
    ipv4_nat: true
    ipv6_address: fd98:9e0:3744::1
    ipv6_netmask: 64
    ipv6_nat: true
    domain: lxd

Mcollective

Summary: Install, configure and start mcollective

This module installs, configures and starts mcollective. If the mcollective key is present in config, then mcollective will be installed and started.

Configuration for mcollective can be specified in the conf key under mcollective. Each config value consists of a key value pair and will be written to /etc/mcollective/server.cfg. The public-cert and private-cert keys, if present in conf may be used to specify the public and private certificates for mcollective. Their values will be written to /etc/mcollective/ssl/server-public.pem and /etc/mcollective/ssl/server-private.pem.

Note

The ec2 metadata service is readable by non-root users. If security is a concern, use include-once and ssl urls.

Internal name: cc_mcollective

Module frequency: once-per-instance

Supported distros: all

Activate only on keys: mcollective

Config schema:

mcollective: (object)

conf: (object)

public-cert: (string) Optional value of server public certificate which will be written to /etc/mcollective/ssl/server-public.pem.

private-cert: (string) Optional value of server private certificate which will be written to /etc/mcollective/ssl/server-private.pem.

^.+$: (boolean/integer/string) Optional config key: value pairs which will be appended to /etc/mcollective/server.cfg.

Examples:

# Provide server private and public key and provide the following
# config settings in /etc/mcollective/server.cfg:
# loglevel: debug
# plugin.stomp.host: dbhost

# WARNING WARNING WARNING
# The ec2 metadata service is a network service, and thus is
# readable by non-root users on the system
# (ie: 'ec2metadata --user-data')
# If you want security for this, please use include-once + SSL urls
mcollective:
  conf:
    loglevel: debug
    plugin.stomp.host: dbhost
    public-cert: |
        -------BEGIN CERTIFICATE--------
        <cert data>
        -------END CERTIFICATE--------
    private-cert: |
        -------BEGIN CERTIFICATE--------
        <cert data>
        -------END CERTIFICATE--------

Migrator

Summary: Migrate old versions of cloud-init data to new

This module handles moving old versions of cloud-init data to newer ones. Currently, it only handles renaming cloud-init’s per-frequency semaphore files to canonicalized name and renaming legacy semaphore names to newer ones. This module is enabled by default, but can be disabled by specifying migrate: false in config.

Internal name: cc_migrator

Module frequency: always

Supported distros: all

Config schema:

migrate: (boolean) Whether to migrate legacy cloud-init semaphores to new format. Default: true.

Examples:

# Do not migrate cloud-init semaphores
migrate: false

Mounts

Summary: Configure mount points and swap files

This module can add or remove mountpoints from /etc/fstab as well as configure swap. The mounts config key takes a list of fstab entries to add. Each entry is specified as a list of [ fs_spec, fs_file, fs_vfstype, fs_mntops, fs-freq, fs_passno ]. For more information on these options, consult the manual for /etc/fstab. When specifying the fs_spec, if the device name starts with one of xvd, sd, hd, or vd, the leading /dev may be omitted.

Any mounts that do not appear to either an attached block device or network resource will be skipped with a log like “Ignoring nonexistent mount …”.

Cloud-init will attempt to add the following mount directives if available and unconfigured in /etc/fstab:

mounts:
    - ["ephemeral0", "/mnt", "auto","defaults,nofail,x-systemd.requires=cloud-init.service", "0", "2"]
    - ["swap", "none", "swap", "sw", "0", "0"]

In order to remove a previously listed mount, an entry can be added to the mounts list containing fs_spec for the device to be removed but no mountpoint (i.e. [ swap ] or [ swap, null ]).

The mount_default_fields config key allows default options to be specified for the values in a mounts entry that are not specified, aside from the fs_spec and the fs_file. If specified, this must be a list containing 6 values. It defaults to:

mount_default_fields: [none, none, "auto","defaults,nofail,x-systemd.requires=cloud-init.service", "0", "2"]

Non-systemd init systems will vary in mount_default_fields.

Swap files can be configured by setting the path to the swap file to create with filename, the size of the swap file with size maximum size of the swap file if using an size: auto with maxsize. By default no swap file is created.

Internal name: cc_mounts

Module frequency: once-per-instance

Supported distros: all

Config schema:

mounts: (array of array) List of lists. Each inner list entry is a list of /etc/fstab mount declarations of the format: [ fs_spec, fs_file, fs_vfstype, fs_mntops, fs-freq, fs_passno ]. A mount declaration with less than 6 items will get remaining values from mount_default_fields. A mount declaration with only fs_spec and no fs_file mountpoint will be skipped.

mount_default_fields: (array of (string/null)) Default mount configuration for any mount entry with less than 6 options provided. When specified, 6 items are required and represent /etc/fstab entries. Default: defaults,nofail,x-systemd.requires=cloud-init.service,_netdev.

swap: (object)

filename: (string) Path to the swap file to create.

size: (auto/integer/string) The size in bytes of the swap file, ‘auto’ or a human-readable size abbreviation of the format <float_size><units> where units are one of B, K, M, G or T.

maxsize: (integer/string) The maxsize in bytes of the swap file.

Examples:

# Mount ephemeral0 with "noexec" flag, /dev/sdc with mount_default_fields,
# and /dev/xvdh with custom fs_passno "0" to avoid fsck on the mount.
# Also provide an automatically sized swap with a max size of 10485760
# bytes.
mounts:
    - [ /dev/ephemeral0, /mnt, auto, "defaults,noexec" ]
    - [ sdc, /opt/data ]
    - [ xvdh, /opt/data, auto, "defaults,nofail", "0", "0" ]
mount_default_fields: [None, None, auto, "defaults,nofail", "0", "2"]
swap:
    filename: /my/swapfile
    size: auto
    maxsize: 10485760

# --- Example2 ---
# Create a 2 GB swap file at /swapfile using human-readable values
swap:
    filename: /swapfile
    size: 2G
    maxsize: 2G

NTP

Summary: enable and configure ntp

Handle ntp configuration. If ntp is not installed on the system and ntp configuration is specified, ntp will be installed. If there is a default ntp config file in the image or one is present in the distro’s ntp package, it will be copied to a file with .dist appended to the filename before any changes are made. A list of ntp pools and ntp servers can be provided under the ntp config key. If no ntp servers or pools are provided, 4 pools will be used in the format {0-3}.{distro}.pool.ntp.org.

Internal name: cc_ntp

Module frequency: once-per-instance

Supported distros: almalinux, alpine, centos, cloudlinux, debian, eurolinux, fedora, miraclelinux, openEuler, openmandriva, opensuse, photon, rhel, rocky, sles, ubuntu, virtuozzo

Activate only on keys: ntp

Config schema:

ntp: (null/object)

pools: (array of string) List of ntp pools. If both pools and servers are empty, 4 default pool servers will be provided of the format {0-3}.{distro}.pool.ntp.org. NOTE: for Alpine Linux when using the Busybox NTP client this setting will be ignored due to the limited functionality of Busybox’s ntpd.

servers: (array of string) List of ntp servers. If both pools and servers are empty, 4 default pool servers will be provided with the format {0-3}.{distro}.pool.ntp.org.

ntp_client: (string) Name of an NTP client to use to configure system NTP. When unprovided or ‘auto’ the default client preferred by the distribution will be used. The following built-in client names can be used to override existing configuration defaults: chrony, ntp, ntpdate, systemd-timesyncd.

enabled: (boolean) Attempt to enable ntp clients if set to True. If set to False, ntp client will not be configured or installed.

config: (object) Configuration settings or overrides for the ntp_client specified.

confpath: (string) The path to where the ntp_client configuration is written.

check_exe: (string) The executable name for the ntp_client. For example, ntp service check_exe is ‘ntpd’ because it runs the ntpd binary.

packages: (array of string) List of packages needed to be installed for the selected ntp_client.

service_name: (string) The systemd or sysvinit service name used to start and stop the ntp_client service.

template: (string) Inline template allowing users to define their own ntp_client configuration template. The value must start with ‘## template:jinja’ to enable use of templating support. .

Examples:

# Override ntp with chrony configuration on Ubuntu
ntp:
  enabled: true
  ntp_client: chrony  # Uses cloud-init default chrony configuration

# --- Example2 ---
# Provide a custom ntp client configuration
ntp:
  enabled: true
  ntp_client: myntpclient
  config:
     confpath: /etc/myntpclient/myntpclient.conf
     check_exe: myntpclientd
     packages:
       - myntpclient
     service_name: myntpclient
     template: |
         ## template:jinja
         # My NTP Client config
         {% if pools -%}# pools{% endif %}
         {% for pool in pools -%}
         pool {{pool}} iburst
         {% endfor %}
         {%- if servers %}# servers
         {% endif %}
         {% for server in servers -%}
         server {{server}} iburst
         {% endfor %}
  pools: [0.int.pool.ntp.org, 1.int.pool.ntp.org, ntp.myorg.org]
  servers:
    - ntp.server.local
    - ntp.ubuntu.com
    - 192.168.23.2

Package Update Upgrade Install

Summary: Update, upgrade, and install packages

This module allows packages to be updated, upgraded or installed during boot. If any packages are to be installed or an upgrade is to be performed then the package cache will be updated first. If a package installation or upgrade requires a reboot, then a reboot can be performed if package_reboot_if_required is specified.

Internal name: cc_package_update_upgrade_install

Module frequency: once-per-instance

Supported distros: all

Activate only on keys: apt_update, package_update, apt_upgrade, package_upgrade, packages

Config schema:

packages: (array of (array of string/string)) A list of packages to install. Each entry in the list can be either a package name or a list with two entries, the first being the package name and the second being the specific package version to install.

package_update: (boolean) Set true to update packages. Happens before upgrade or install. Default: false.

package_upgrade: (boolean) Set true to upgrade packages. Happens before install. Default: false.

package_reboot_if_required: (boolean) Set true to reboot the system if required by presence of /var/run/reboot-required. Default: false.

apt_update: (boolean) DEPRECATED: Dropped after April 2027. Use package_update. Default: false.

apt_upgrade: (boolean) DEPRECATED: Dropped after April 2027. Use package_upgrade. Default: false.

apt_reboot_if_required: (boolean) DEPRECATED: Dropped after April 2027. Use package_reboot_if_required. Default: false.

Examples:

packages:
  - pwgen
  - pastebinit
  - [libpython3.8, 3.8.10-0ubuntu1~20.04.2]
package_update: true
package_upgrade: true
package_reboot_if_required: true

Phone Home

Summary: Post data to url

This module can be used to post data to a remote host after boot is complete. If the post url contains the string $INSTANCE_ID it will be replaced with the id of the current instance. Either all data can be posted or a list of keys to post. Available keys are:

  • pub_key_dsa

  • pub_key_rsa

  • pub_key_ecdsa

  • pub_key_ed25519

  • instance_id

  • hostname

  • fdqn

Data is sent as x-www-form-urlencoded arguments.

Example HTTP POST:

POST / HTTP/1.1
Content-Length: 1337
User-Agent: Cloud-Init/21.4
Accept-Encoding: gzip, deflate
Accept: */*
Content-Type: application/x-www-form-urlencoded

pub_key_dsa=dsa_contents&pub_key_rsa=rsa_contents&pub_key_ecdsa=ecdsa_contents&pub_key_ed25519=ed25519_contents&instance_id=i-87018aed&hostname=myhost&fqdn=myhost.internal

Internal name: cc_phone_home

Module frequency: once-per-instance

Supported distros: all

Activate only on keys: phone_home

Config schema:

phone_home: (object)

url: (string) The URL to send the phone home data to.

post: (all/array) A list of keys to post or all. Default: all.

tries: (integer) The number of times to try sending the phone home data. Default: 10.

Examples:

phone_home:
    url: http://example.com/$INSTANCE_ID/
    post: all

# --- Example2 ---
phone_home:
    url: http://example.com/$INSTANCE_ID/
    post:
        - pub_key_dsa
        - pub_key_rsa
        - pub_key_ecdsa
        - pub_key_ed25519
        - instance_id
        - hostname
        - fqdn
    tries: 5

Power State Change

Summary: Change power state

This module handles shutdown/reboot after all config modules have been run. By default it will take no action, and the system will keep running unless a package installation/upgrade requires a system reboot (e.g. installing a new kernel) and package_reboot_if_required is true.

Using this module ensures that cloud-init is entirely finished with modules that would be executed.

An example to distinguish delay from timeout:

If you delay 5 (5 minutes) and have a timeout of 120 (2 minutes), then the max time until shutdown will be 7 minutes, though it could be as soon as 5 minutes. Cloud-init will invoke ‘shutdown +5’ after the process finishes, or when ‘timeout’ seconds have elapsed.

Note

With Alpine Linux any message value specified is ignored as Alpine’s halt, poweroff, and reboot commands do not support broadcasting a message.

Internal name: cc_power_state_change

Module frequency: once-per-instance

Supported distros: all

Activate only on keys: power_state

Config schema:

power_state: (object)

delay: (integer/now) Time in minutes to delay after cloud-init has finished. Can be now or an integer specifying the number of minutes to delay. Default: now. DEPRECATED: Use of string for this value will be dropped after April 2027. Use now or integer type.

mode: (poweroff/reboot/halt) Must be one of poweroff, halt, or reboot.

message: (string) Optional message to display to the user when the system is powering off or rebooting.

timeout: (integer) Time in seconds to wait for the cloud-init process to finish before executing shutdown. Default: 30.

condition: (string/boolean/array) Apply state change only if condition is met. May be boolean true (always met), false (never met), or a command string or list to be executed. For command formatting, see the documentation for cc_runcmd. If exit code is 0, condition is met, otherwise not. Default: true.

Examples:

power_state:
    delay: now
    mode: poweroff
    message: Powering off
    timeout: 2
    condition: true

# --- Example2 ---
power_state:
    delay: 30
    mode: reboot
    message: Rebooting machine
    condition: test -f /var/tmp/reboot_me

Puppet

Summary: Install, configure and start puppet

This module handles puppet installation and configuration. If the puppet key does not exist in global configuration, no action will be taken. If a config entry for puppet is present, then by default the latest version of puppet will be installed. If the puppet config key exists in the config archive, this module will attempt to start puppet even if no installation was performed.

The module also provides keys for configuring the new puppet 4 paths and installing the puppet package from the puppetlabs repositories: https://docs.puppet.com/puppet/4.2/reference/whered_it_go.html The keys are package_name, conf_file, ssl_dir and csr_attributes_path. If unset, their values will default to ones that work with puppet 3.x and with distributions that ship modified puppet 4.x that uses the old paths.

Internal name: cc_puppet

Module frequency: once-per-instance

Supported distros: all

Activate only on keys: puppet

Config schema:

puppet: (object)

install: (boolean) Whether or not to install puppet. Setting to false will result in an error if puppet is not already present on the system. Default: true.

version: (string) Optional version to pass to the installer script or package manager. If unset, the latest version from the repos will be installed.

install_type: (packages/aio) Valid values are packages and aio. Agent packages from the puppetlabs repositories can be installed by setting aio. Based on this setting, the default config/SSL/CSR paths will be adjusted accordingly. Default: packages.

collection: (string) Puppet collection to install if install_type is aio. This can be set to one of puppet (rolling release), puppet6, puppet7 (or their nightly counterparts) in order to install specific release streams.

aio_install_url: (string) If install_type is aio, change the url of the install script.

cleanup: (boolean) Whether to remove the puppetlabs repo after installation if install_type is aio Default: true.

conf_file: (string) The path to the puppet config file. Default depends on install_type.

ssl_dir: (string) The path to the puppet SSL directory. Default depends on install_type.

csr_attributes_path: (string) The path to the puppet csr attributes file. Default depends on install_type.

package_name: (string) Name of the package to install if install_type is packages. Default: puppet.

exec: (boolean) Whether or not to run puppet after configuration finishes. A single manual run can be triggered by setting exec to true, and additional arguments can be passed to puppet agent via the exec_args key (by default the agent will execute with the --test flag). Default: false.

exec_args: (array of string) A list of arguments to pass to ‘puppet agent’ if ‘exec’ is true Default: ['--test'].

start_service: (boolean) By default, the puppet service will be automatically enabled after installation and set to automatically start on boot. To override this in favor of manual puppet execution set start_service to false.

conf: (object) Every key present in the conf object will be added to puppet.conf. As such, section names should be one of: main, server, agent or user and keys should be valid puppet configuration options. The configuration is specified as a dictionary containing high-level <section> keys and lists of <key>=<value> pairs within each section. The certname key supports string substitutions for %i and %f, corresponding to the instance id and fqdn of the machine respectively.

ca_cert is a special case. It won’t be added to puppet.conf. It holds the puppetserver certificate in pem format. It should be a multi-line string (using the | yaml notation for multi-line strings).

main: (object)

server: (object)

agent: (object)

user: (object)

ca_cert: (string)

csr_attributes: (object) create a csr_attributes.yaml file for CSR attributes and certificate extension requests. See https://puppet.com/docs/puppet/latest/config_file_csr_attributes.html.

custom_attributes: (object)

extension_requests: (object)

Examples:

puppet:
    install: true
    version: "7.7.0"
    install_type: "aio"
    collection: "puppet7"
    aio_install_url: 'https://git.io/JBhoQ'
    cleanup: true
    conf_file: "/etc/puppet/puppet.conf"
    ssl_dir: "/var/lib/puppet/ssl"
    csr_attributes_path: "/etc/puppet/csr_attributes.yaml"
    exec: true
    exec_args: ['--test']
    conf:
        agent:
            server: "puppetserver.example.org"
            certname: "%i.%f"
        ca_cert: |
            -----BEGIN CERTIFICATE-----
            MIICCTCCAXKgAwIBAgIBATANBgkqhkiG9w0BAQUFADANMQswCQYDVQQDDAJjYTAe
            Fw0xMDAyMTUxNzI5MjFaFw0xNTAyMTQxNzI5MjFaMA0xCzAJBgNVBAMMAmNhMIGf
            MA0GCSqGSIb3DQEBAQUAA4GNADCBiQKBgQCu7Q40sm47/E1Pf+r8AYb/V/FWGPgc
            b014OmNoX7dgCxTDvps/h8Vw555PdAFsW5+QhsGr31IJNI3kSYprFQcYf7A8tNWu
            1MASW2CfaEiOEi9F1R3R4Qlz4ix+iNoHiUDTjazw/tZwEdxaQXQVLwgTGRwVa+aA
            qbutJKi93MILLwIDAQABo3kwdzA4BglghkgBhvhCAQ0EKxYpUHVwcGV0IFJ1Ynkv
            T3BlblNTTCBHZW5lcmF0ZWQgQ2VydGlmaWNhdGUwDwYDVR0TAQH/BAUwAwEB/zAd
            BgNVHQ4EFgQUu4+jHB+GYE5Vxo+ol1OAhevspjAwCwYDVR0PBAQDAgEGMA0GCSqG
            SIb3DQEBBQUAA4GBAH/rxlUIjwNb3n7TXJcDJ6MMHUlwjr03BDJXKb34Ulndkpaf
            +GAlzPXWa7bO908M9I8RnPfvtKnteLbvgTK+h+zX1XCty+S2EQWk29i2AdoqOTxb
            hppiGMp0tT5Havu4aceCXiy2crVcudj3NFciy8X66SoECemW9UYDCb9T5D0d
            -----END CERTIFICATE-----
    csr_attributes:
        custom_attributes:
            1.2.840.113549.1.9.7: 342thbjkt82094y0uthhor289jnqthpc2290
        extension_requests:
            pp_uuid: ED803750-E3C7-44F5-BB08-41A04433FE2E
            pp_image_name: my_ami_image
            pp_preshared_key: 342thbjkt82094y0uthhor289jnqthpc2290

# --- Example2 ---
puppet:
    install_type: "packages"
    package_name: "puppet"
    exec: false

Resizefs

Summary: Resize filesystem

Resize a filesystem to use all avaliable space on partition. This module is useful along with cc_growpart and will ensure that if the root partition has been resized the root filesystem will be resized along with it. By default, cc_resizefs will resize the root partition and will block the boot process while the resize command is running. Optionally, the resize operation can be performed in the background while cloud-init continues running modules. This can be enabled by setting resize_rootfs to noblock. This module can be disabled altogether by setting resize_rootfs to false.

Internal name: cc_resizefs

Module frequency: always

Supported distros: all

Config schema:

resize_rootfs: (true/false/noblock) Whether to resize the root partition. noblock will resize in the background. Default: true.

Examples:

resize_rootfs: false  # disable root filesystem resize operation
# --- Example2 ---
resize_rootfs: noblock  # runs resize operation in the background

Resolv Conf

Summary: Configure resolv.conf

This module is intended to manage resolv.conf in environments where early configuration of resolv.conf is necessary for further bootstrapping and/or where configuration management such as puppet or chef own DNS configuration. As Debian/Ubuntu will, by default, utilize resolvconf, and similarly Red Hat will use sysconfig, this module is likely to be of little use unless those are configured correctly.

When using a Config Drive and a RHEL-like system, resolv.conf will also be managed automatically due to the available information provided for DNS servers in the Networking Config Version 2 format. For those that with to have different settings, use this module.

In order for the resolv_conf section to be applied, manage_resolv_conf must be set true.

Note

For Red Hat with sysconfig, be sure to set PEERDNS=no for all DHCP enabled NICs.

Note

And, in Ubuntu/Debian it is recommended that DNS be configured via the standard /etc/network/interfaces configuration file.

Internal name: cc_resolv_conf

Module frequency: once-per-instance

Supported distros: alpine, fedora, opensuse, photon, rhel, sles

Activate only on keys: manage_resolv_conf

Config schema:

manage_resolv_conf: (boolean) Whether to manage the resolv.conf file. resolv_conf block will be ignored unless this is set to true. Default: false.

resolv_conf: (object)

nameservers: (array) A list of nameservers to use to be added as nameserver lines.

searchdomains: (array) A list of domains to be added search line.

domain: (string) The domain to be added as domain line.

sortlist: (array) A list of IP addresses to be added to sortlist line.

options: (object) Key/value pairs of options to go under options heading. A unary option should be specified as true.

Examples:

manage_resolv_conf: true
resolv_conf:
  nameservers:
    - 8.8.8.8
    - 8.8.4.4
  searchdomains:
    - foo.example.com
    - bar.example.com
  domain: example.com
  sortlist:
    - 10.0.0.1/255
    - 10.0.0.2
  options:
    rotate: true
    timeout: 1

Red Hat Subscription

Summary: Register Red Hat Enterprise Linux based system

Register a Red Hat system either by username and password or activation and org. Following a successful registration, you can:

  • auto-attach subscriptions

  • set the service level

  • add subscriptions based on pool id

  • enable/disable yum repositories based on repo id

  • alter the rhsm_baseurl and server-hostname in /etc/rhsm/rhs.conf.

Internal name: cc_rh_subscription

Module frequency: once-per-instance

Supported distros: fedora, rhel

Activate only on keys: rh_subscription

Config schema:

rh_subscription: (object)

username: (string) The username to use. Must be used with password. Should not be used with activation-key or org.

password: (string) The password to use. Must be used with username. Should not be used with activation-key or org.

activation-key: (string) The activation key to use. Must be used with org. Should not be used with username or password.

org: (integer) The organization number to use. Must be used with activation-key. Should not be used with username or password.

auto-attach: (boolean) Whether to attach subscriptions automatically.

service-level: (string) The service level to use when subscribing to RH repositories. auto-attach must be true for this to be used.

add-pool: (array of string) A list of pools ids add to the subscription.

enable-repo: (array of string) A list of repositories to enable.

disable-repo: (array of string) A list of repositories to disable.

rhsm-baseurl: (string) Sets the baseurl in /etc/rhsm/rhsm.conf.

server-hostname: (string) Sets the serverurl in /etc/rhsm/rhsm.conf.

Examples:

rh_subscription:
    username: joe@foo.bar
    ## Quote your password if it has symbols to be safe
    password: '1234abcd'

# --- Example2 ---
rh_subscription:
    activation-key: foobar
    org: 12345

# --- Example3 ---
rh_subscription:
    activation-key: foobar
    org: 12345
    auto-attach: true
    service-level: self-support
    add-pool:
      - 1a1a1a1a1a1a1a1a1a1a1a1a1a1a1a1a
      - 2b2b2b2b2b2b2b2b2b2b2b2b2b2b2b2b
    enable-repo:
      - repo-id-to-enable
      - other-repo-id-to-enable
    disable-repo:
      - repo-id-to-disable
      - other-repo-id-to-disable
    # Alter the baseurl in /etc/rhsm/rhsm.conf
    rhsm-baseurl: http://url
    # Alter the server hostname in /etc/rhsm/rhsm.conf
    server-hostname: foo.bar.com

RightScale Userdata

Summary: Support rightscale configuration hooks

This module adds support for RightScale configuration hooks to cloud-init. RightScale adds an entry in the format CLOUD_INIT_REMOTE_HOOK=http://... to ec2 user-data. This module checks for this line in the raw userdata and retrieves any scripts linked by the RightScale user data and places them in the user scripts configuration directory, to be run later by cc_scripts_user.

Note

the CLOUD_INIT_REMOTE_HOOK config variable is present in the raw ec2 user data only, not in any cloud-config parts

Raw user data schema:

CLOUD_INIT_REMOTE_HOOK=<url>

Internal name: cc_rightscale_userdata

Module frequency: once-per-instance

Supported distros: all

Rsyslog

Summary: Configure system logging via rsyslog

This module configures remote system logging using rsyslog.

Configuration for remote servers can be specified in configs, but for convenience it can be specified as key value pairs in remotes.

Internal name: cc_rsyslog

Module frequency: once-per-instance

Supported distros: all

Activate only on keys: rsyslog

Config schema:

rsyslog: (object)

config_dir: (string) The directory where rsyslog configuration files will be written. Default: /etc/rsyslog.d.

config_filename: (string) The name of the rsyslog configuration file. Default: 20-cloud-config.conf.

configs: (array of (string/object)) Each entry in configs is either a string or an object. Each config entry contains a configuration string and a file to write it to. For config entries that are an object, filename sets the target filename and content specifies the config string to write. For config entries that are only a string, the string is used as the config string to write. If the filename to write the config to is not specified, the value of the config_filename key is used. A file with the selected filename will be written inside the directory specified by config_dir.

Each object in configs list supports the following keys:

filename: (string)

content: (string)

remotes: (object) Each key is the name for an rsyslog remote entry. Each value holds the contents of the remote config for rsyslog. The config consists of the following parts:

  • filter for log messages (defaults to *.*)

  • optional leading @ or @@, indicating udp and tcp respectively (defaults to @, for udp)

  • ipv4 or ipv6 hostname or address. ipv6 addresses must be in [::1] format, (e.g. @[fd00::1]:514)

  • optional port number (defaults to 514)

This module will provide sane defaults for any part of the remote entry that is not specified, so in most cases remote hosts can be specified just using <name>: <address>.

service_reload_command: (auto/array) The command to use to reload the rsyslog service after the config has been updated. If this is set to auto, then an appropriate command for the distro will be used. This is the default behavior. To manually set the command, use a list of command args (e.g. [systemctl, restart, rsyslog]).

Examples:

rsyslog:
    remotes:
        maas: 192.168.1.1
        juju: 10.0.4.1
    service_reload_command: auto

# --- Example2 ---
rsyslog:
    config_dir: /opt/etc/rsyslog.d
    config_filename: 99-late-cloud-config.conf
    configs:
        - "*.* @@192.158.1.1"
        - content: "*.*   @@192.0.2.1:10514"
          filename: 01-example.conf
        - content: |
            *.*   @@syslogd.example.com
    remotes:
        maas: 192.168.1.1
        juju: 10.0.4.1
    service_reload_command: [your, syslog, restart, command]

Runcmd

Summary: Run arbitrary commands

Run arbitrary commands at a rc.local like time-frame with output to the console. Each item can be either a list or a string. The item type affects how it is executed:

  • If the item is a string, it will be interpreted by sh.

  • If the item is a list, the items will be executed as if passed to execve(3) (with the first arg as the command).

Note that the runcmd module only writes the script to be run later. The module that actually runs the script is scripts-user in the Final boot stage.

Note

all commands must be proper yaml, so you have to quote any characters yaml would eat (‘:’ can be problematic)

Note

when writing files, do not use /tmp dir as it races with systemd-tmpfiles-clean LP: #1707222. Use /run/somedir instead.

Internal name: cc_runcmd

Module frequency: once-per-instance

Supported distros: all

Activate only on keys: runcmd

Config schema:

runcmd: (array of (array of string/string/null))

Examples:

runcmd:
    - [ ls, -l, / ]
    - [ sh, -xc, "echo $(date) ': hello world!'" ]
    - [ sh, -c, echo "=========hello world'=========" ]
    - ls -l /root
    - [ wget, "http://example.org", -O, /tmp/index.html ]

Salt Minion

Summary: Setup and run salt minion

This module installs, configures and starts salt minion. If the salt_minion key is present in the config parts, then salt minion will be installed and started. Configuration for salt minion can be specified in the conf key under salt_minion. Any conf values present there will be assigned in /etc/salt/minion. The public and private keys to use for salt minion can be specified with public_key and private_key respectively. Optionally if you have a custom package name, service name or config directory you can specify them with pkg_name, service_name and config_dir.

Salt keys can be manually generated by: salt-key --gen-keys=GEN_KEYS, where GEN_KEYS is the name of the keypair, e.g. ‘minion’. The keypair will be copied to /etc/salt/pki on the minion instance.

Internal name: cc_salt_minion

Module frequency: once-per-instance

Supported distros: all

Activate only on keys: salt_minion

Config schema:

salt_minion: (object)

pkg_name: (string) Package name to install. Default: salt-minion.

service_name: (string) Service name to enable. Default: salt-minion.

config_dir: (string) Directory to write config files to. Default: /etc/salt.

conf: (object) Configuration to be written to config_dir/minion.

grains: (object) Configuration to be written to config_dir/grains.

public_key: (string) Public key to be used by the salt minion.

private_key: (string) Private key to be used by salt minion.

pki_dir: (string) Directory to write key files. Default: config_dir/pki/minion.

Examples:

salt_minion:
    pkg_name: salt-minion
    service_name: salt-minion
    config_dir: /etc/salt
    conf:
        master: salt.example.com
    grains:
        role:
            - web
    public_key: |
        ------BEGIN PUBLIC KEY-------
        <key data>
        ------END PUBLIC KEY-------
    private_key: |
        ------BEGIN PRIVATE KEY------
        <key data>
        ------END PRIVATE KEY-------
    pki_dir: /etc/salt/pki/minion

Scripts Per Boot

Summary: Run per boot scripts

Any scripts in the scripts/per-boot directory on the datasource will be run every time the system boots. Scripts will be run in alphabetical order. This module does not accept any config keys.

Internal name: cc_scripts_per_boot

Module frequency: always

Supported distros: all

Scripts Per Instance

Summary: Run per instance scripts

Any scripts in the scripts/per-instance directory on the datasource will be run when a new instance is first booted. Scripts will be run in alphabetical order. This module does not accept any config keys.

Some cloud platforms change instance-id if a significant change was made to the system. As a result per-instance scripts will run again.

Internal name: cc_scripts_per_instance

Module frequency: once-per-instance

Supported distros: all

Scripts Per Once

Summary: Run one time scripts

Any scripts in the scripts/per-once directory on the datasource will be run only once. Changes to the instance will not force a re-run. The only way to re-run these scripts is to run the clean subcommand and reboot. Scripts will be run in alphabetical order. This module does not accept any config keys.

Internal name: cc_scripts_per_once

Module frequency: once

Supported distros: all

Scripts User

Summary: Run user scripts

This module runs all user scripts. User scripts are not specified in the scripts directory in the datasource, but rather are present in the scripts dir in the instance configuration. Any cloud-config parts with a #! will be treated as a script and run. Scripts specified as cloud-config parts will be run in the order they are specified in the configuration. This module does not accept any config keys.

Internal name: cc_scripts_user

Module frequency: once-per-instance

Supported distros: all

Scripts Vendor

Summary: Run vendor scripts

On select Datasources, vendors have a channel for the consumption of all supported user data types via a special channel called vendor data. Any scripts in the scripts/vendor directory in the datasource will be run when a new instance is first booted. Scripts will be run in alphabetical order. This module allows control over the execution of vendor data.

Internal name: cc_scripts_vendor

Module frequency: once-per-instance

Supported distros: all

Config schema:

vendor_data: (object)

enabled: (boolean) Whether vendor data is enabled or not. Default: true. DEPRECATED: Use of string for this value is DEPRECATED. Use a boolean value instead.

prefix: (string/array of (string/integer)) The command to run before any vendor scripts. Its primary use case is for profiling a script, not to prevent its run.

Examples:

vendor_data:
  enabled: true
  prefix: /usr/bin/ltrace

# --- Example2 ---
vendor_data:
  enabled: true
  prefix: [timeout, 30]

# --- Example3 ---
# Vendor data will not be processed
vendor_data:
  enabled: false

Seed Random

Summary: Provide random seed data

All cloud instances started from the same image will produce very similar data when they are first booted as they are all starting with the same seed for the kernel’s entropy keyring. To avoid this, random seed data can be provided to the instance either as a string or by specifying a command to run to generate the data.

Configuration for this module is under the random_seed config key. If the cloud provides its own random seed data, it will be appended to data before it is written to file.

If the command key is specified, the given command will be executed. This will happen after file has been populated. That command’s environment will contain the value of the file key as RANDOM_SEED_FILE. If a command is specified that cannot be run, no error will be reported unless command_required is set to true.

Internal name: cc_seed_random

Module frequency: once-per-instance

Supported distros: all

Config schema:

random_seed: (object)

file: (string) File to write random data to. Default: /dev/urandom.

data: (string) This data will be written to file before data from the datasource. When using a multiline value or specifying binary data, be sure to follow yaml syntax and use the | and !binary yaml format specifiers when appropriate.

encoding: (raw/base64/b64/gzip/gz) Used to decode data provided. Allowed values are raw, base64, b64, gzip, or gz. Default: raw.

command: (array of string) Execute this command to seed random. The command will have RANDOM_SEED_FILE in its environment set to the value of file above.

command_required: (boolean) If true, and command is not available to be run then an exception is raised and cloud-init will record failure. Otherwise, only debug error is mentioned. Default: false.

Examples:

random_seed:
  file: /dev/urandom
  data: my random string
  encoding: raw
  command: ['sh', '-c', 'dd if=/dev/urandom of=$RANDOM_SEED_FILE']
  command_required: true

# --- Example2 ---
# To use 'pollinate' to gather data from a remote entropy
# server and write it to '/dev/urandom', the following
# could be used:
random_seed:
  file: /dev/urandom
  command: ["pollinate", "--server=http://local.polinate.server"]
  command_required: true

Set Hostname

Summary: Set hostname and FQDN

This module handles setting the system hostname and fully qualified domain name (FQDN). If preserve_hostname is set, then the hostname will not be altered.

A hostname and FQDN can be provided by specifying a full domain name under the FQDN key. Alternatively, a hostname can be specified using the hostname key, and the FQDN of the cloud will be used. If a FQDN specified with the hostname key, it will be handled properly, although it is better to use the fqdn config key. If both fqdn and hostname are set, the prefer_fqdn_over_hostname will force the use of FQDN in all distros when true, and when false it will force the short hostname. Otherwise, the hostname to use is distro-dependent.

Note

cloud-init performs no hostname input validation before sending the hostname to distro-specific tools, and most tools will not accept a trailing dot on the FQDN.

This module will run in the init-local stage before networking is configured if the hostname is set by metadata or user data on the local system.

This will occur on datasources like nocloud and ovf where metadata and user data are available locally. This ensures that the desired hostname is applied before any DHCP requests are performed on these platforms where dynamic DNS is based on initial hostname.

Internal name: cc_set_hostname

Module frequency: always

Supported distros: all

Config schema:

preserve_hostname: (boolean) If true, the hostname will not be changed. Default: false.

hostname: (string) The hostname to set.

fqdn: (string) The fully qualified domain name to set.

prefer_fqdn_over_hostname: (boolean) If true, the fqdn will be used if it is set. If false, the hostname will be used. If unset, the result is distro-dependent.

Examples:

preserve_hostname: true
# --- Example2 ---
hostname: myhost
fqdn: myhost.example.com
prefer_fqdn_over_hostname: true

Set Passwords

Summary: Set user passwords and enable/disable SSH password auth

This module consumes three top-level config keys: ssh_pwauth, chpasswd and password.

The ssh_pwauth config key determines whether or not sshd will be configured to accept password authentication.

The chpasswd config key accepts a dictionary containing either or both of users and expire. The users key is used to assign a password to a corresponding pre-existing user. The expire key is used to set whether to expire all user passwords specified by this module, such that a password will need to be reset on the user’s next login.

Note

Prior to cloud-init 22.3, the expire key only applies to plain text (including RANDOM) passwords. Post 22.3, the expire key applies to both plain text and hashed passwords.

password config key is used to set the default user’s password. It is ignored if the chpasswd users is used. Note: the list keyword is deprecated in favor of users.

Internal name: cc_set_passwords

Module frequency: once-per-instance

Supported distros: all

Config schema:

ssh_pwauth: (boolean) Sets whether or not to accept password authentication. true will enable password auth. false will disable. Default is to leave the value unchanged. DEPRECATED: Use of non-boolean values for this field is DEPRECATED and will result in an error in a future version of cloud-init.

chpasswd: (object)

expire: (boolean) Whether to expire all user passwords such that a password will need to be reset on the user’s next login. Default: true.

users: (array of object) Replaces the deprecated list key. This key represents a list of existing users to set passwords for. Each item under users contains the following required keys: name and password or in the case of a randomly generated password, name and type. The type key has a default value of hash, and may alternatively be set to text or RANDOM.

list: (string/array) DEPRECATED: List of username:password pairs. Each user will have the corresponding password set. A password can be randomly generated by specifying RANDOM or R as a user’s password. A hashed password, created by a tool like mkpasswd, can be specified. A regex (r'\$(1|2a|2y|5|6)(\$.+){2}') is used to determine if a password value should be treated as a hash.

Use of a multiline string for this field is DEPRECATED and will result in an error in a future version of cloud-init.

password: (string) Set the default user’s password. Ignored if chpasswd list is used.

Examples:

# Set a default password that would need to be changed
# at first login
ssh_pwauth: true
password: password1

# --- Example2 ---
# Disable ssh password authentication
# Don't require users to change their passwords on next login
# Set the password for user1 to be 'password1' (OS does hashing)
# Set the password for user2 to a pre-hashed password
# Set the password for user3 to be a randomly generated password,
#   which will be written to the system console
ssh_pwauth: false
chpasswd:
  expire: false
  users:
    - name: user1
      password: password1
      type: text
    - name: user2
      password: $6$rounds=4096$5DJ8a9WMTEzIo5J4$Yms6imfeBvf3Yfu84mQBerh18l7OR1Wm1BJXZqFSpJ6BVas0AYJqIjP7czkOaAZHZi1kxQ5Y1IhgWN8K9NgxR1
    - name: user3
      type: RANDOM

Snap

Summary: Install, configure and manage snapd and snap packages

This module provides a simple configuration namespace in cloud-init to both setup snapd and install snaps.

Note

Both assertions and commands values can be either a dictionary or a list. If these configs are provided as a dictionary, the keys are only used to order the execution of the assertions or commands and the dictionary is merged with any vendor-data snap configuration provided. If a list is provided by the user instead of a dict, any vendor-data snap configuration is ignored.

The assertions configuration option is a dictionary or list of properly-signed snap assertions which will run before any snap commands. They will be added to snapd’s assertion database by invoking snap ack <aggregate_assertion_file>.

Snap commands is a dictionary or list of individual snap commands to run on the target system. These commands can be used to create snap users, install snaps and provide snap configuration.

Note

If ‘side-loading’ private/unpublished snaps on an instance, it is best to create a snap seed directory and seed.yaml manifest in /var/lib/snapd/seed/ which snapd automatically installs on startup.

Internal name: cc_snap

Module frequency: once-per-instance

Supported distros: ubuntu

Activate only on keys: snap

Config schema:

snap: (object)

assertions: (object/array of string) Properly-signed snap assertions which will run before and snap commands.

commands: (object/array of (string/array of string)) Snap commands to run on the target system.

Examples:

snap:
    assertions:
      00: |
        signed_assertion_blob_here
      02: |
        signed_assertion_blob_here
    commands:
      00: snap create-user --sudoer --known <snap-user>@mydomain.com
      01: snap install canonical-livepatch
      02: canonical-livepatch enable <AUTH_TOKEN>

# --- Example2 ---
# Convenience: the snap command can be omitted when specifying commands
# as a list and 'snap' will automatically be prepended.
# The following commands are equivalent:
snap:
  commands:
    00: ['install', 'vlc']
    01: ['snap', 'install', 'vlc']
    02: snap install vlc
    03: 'snap install vlc'

# --- Example3 ---
# You can use a list of commands
snap:
  commands:
    - ['install', 'vlc']
    - ['snap', 'install', 'vlc']
    - snap install vlc
    - 'snap install vlc'

# --- Example4 ---
# You can use a list of assertions
snap:
  assertions:
    - signed_assertion_blob_here
    - |
      signed_assertion_blob_here

Spacewalk

Summary: Install and configure spacewalk

This module installs spacewalk and applies basic configuration. If the spacewalk config key is present spacewalk will be installed. The server to connect to after installation must be provided in the server in spacewalk configuration. A proxy to connect through and a activation key may optionally be specified.

For more information about spacewalk see: https://fedorahosted.org/spacewalk/

Internal name: cc_spacewalk

Module frequency: once-per-instance

Supported distros: rhel, fedora

Activate only on keys: spacewalk

Config schema:

spacewalk: (object)

server: (string) The Spacewalk server to use.

proxy: (string) The proxy to use when connecting to Spacewalk.

activation_key: (string) The activation key to use when registering with Spacewalk.

Examples:

spacewalk:
  server: <url>
  proxy: <proxy host>
  activation_key: <key>

SSH

Summary: Configure SSH and SSH keys

This module handles most configuration for SSH and both host and authorized SSH keys.

Authorized Keys

Authorized keys are a list of public SSH keys that are allowed to connect to a user account on a system. They are stored in .ssh/authorized_keys in that account’s home directory. Authorized keys for the default user defined in users can be specified using ssh_authorized_keys. Keys should be specified as a list of public keys.

Note

see the cc_set_passwords module documentation to enable/disable SSH password authentication

Root login can be enabled/disabled using the disable_root config key. Root login options can be manually specified with disable_root_opts.

Supported public key types for the ssh_authorized_keys are:

Note

this list has been filtered out from the supported keytypes of OpenSSH source, where the sigonly keys are removed. Please see ssh_util for more information.

dsa, rsa, ecdsa and ed25519 are added for legacy, as they are valid public keys in some old distros. They can possibly be removed in the future when support for the older distros are dropped

Host Keys

Host keys are for authenticating a specific instance. Many images have default host SSH keys, which can be removed using ssh_deletekeys.

Host keys can be added using the ssh_keys configuration key.

When host keys are generated the output of the ssh-keygen command(s) can be displayed on the console using the ssh_quiet_keygen configuration key.

Note

when specifying private host keys in cloud-config, care should be taken to ensure that the communication between the data source and the instance is secure

If no host keys are specified using ssh_keys, then keys will be generated using ssh-keygen. By default one public/private pair of each supported host key type will be generated. The key types to generate can be specified using the ssh_genkeytypes config flag, which accepts a list of host key types to use. For each host key type for which this module has been instructed to create a keypair, if a key of the same type is already present on the system (i.e. if ssh_deletekeys was false), no key will be generated.

Supported host key types for the ssh_keys and the ssh_genkeytypes config flags are:

  • dsa

  • ecdsa

  • ed25519

  • rsa

Unsupported host key types for the ssh_keys and the ssh_genkeytypes config flags are:

  • ecdsa-sk

  • ed25519-sk

Internal name: cc_ssh

Module frequency: once-per-instance

Supported distros: all

Config schema:

ssh_keys: (object) A dictionary entries for the public and private host keys of each desired key type. Entries in the ssh_keys config dict should have keys in the format <key type>_private, <key type>_public, and, optionally, <key type>_certificate, e.g. rsa_private: <key>, rsa_public: <key>, and rsa_certificate: <key>. Not all key types have to be specified, ones left unspecified will not be used. If this config option is used, then separate keys will not be automatically generated. In order to specify multiline private host keys and certificates, use yaml multiline syntax.

<key_type>: (string)

ssh_authorized_keys: (array of string) The SSH public keys to add .ssh/authorized_keys in the default user’s home directory.

ssh_deletekeys: (boolean) Remove host SSH keys. This prevents re-use of a private host key from an image with default host SSH keys. Default: true.

ssh_genkeytypes: (array of string) The SSH key types to generate. Default: [rsa, dsa, ecdsa, ed25519].

disable_root: (boolean) Disable root login. Default: true.

disable_root_opts: (string) Disable root login options. If disable_root_opts is specified and contains the string $USER, it will be replaced with the username of the default user. Default: no-port-forwarding,no-agent-forwarding,no-X11-forwarding,command="echo 'Please login as the user \"$USER\" rather than the user \"$DISABLE_USER\".';echo;sleep 10;exit 142".

allow_public_ssh_keys: (boolean) If true, will import the public SSH keys from the datasource’s metadata to the user’s .ssh/authorized_keys file. Default: true.

ssh_quiet_keygen: (boolean) If true, will suppress the output of key generation to the console. Default: false.

ssh_publish_hostkeys: (object)

enabled: (boolean) If true, will read host keys from /etc/ssh/*.pub and publish them to the datasource (if supported). Default: true.

blacklist: (array of string) The SSH key types to ignore when publishing. Default: [dsa].

Examples:

ssh_keys:
  rsa_private: |
    -----BEGIN RSA PRIVATE KEY-----
    MIIBxwIBAAJhAKD0YSHy73nUgysO13XsJmd4fHiFyQ+00R7VVu2iV9Qco
    ...
    -----END RSA PRIVATE KEY-----
  rsa_public: ssh-rsa AAAAB3NzaC1yc2EAAAABIwAAAGEAoPRhIfLvedSDKw7Xd ...
  rsa_certificate: |
    ssh-rsa-cert-v01@openssh.com AAAAIHNzaC1lZDI1NTE5LWNlcnQt ...
  dsa_private: |
    -----BEGIN DSA PRIVATE KEY-----
    MIIBxwIBAAJhAKD0YSHy73nUgysO13XsJmd4fHiFyQ+00R7VVu2iV9Qco
    ...
    -----END DSA PRIVATE KEY-----
  dsa_public: ssh-dsa AAAAB3NzaC1yc2EAAAABIwAAAGEAoPRhIfLvedSDKw7Xd ...
  dsa_certificate: |
    ssh-dsa-cert-v01@openssh.com AAAAIHNzaC1lZDI1NTE5LWNlcnQt ...
ssh_authorized_keys:
  - ssh-rsa AAAAB3NzaC1yc2EAAAABIwAAAGEA3FSyQwBI6Z+nCSjUU ...
  - ssh-rsa AAAAB3NzaC1yc2EAAAABIwAAAQEA3I7VUf2l5gSn5uavROsc5HRDpZ ...
ssh_deletekeys: true
ssh_genkeytypes: [rsa, dsa, ecdsa, ed25519]
disable_root: true
disable_root_opts: no-port-forwarding,no-agent-forwarding,no-X11-forwarding
allow_public_ssh_keys: true
ssh_quiet_keygen: true
ssh_publish_hostkeys:
  enabled: true
  blacklist: [dsa]

SSH AuthKey Fingerprints

Summary: Log fingerprints of user SSH keys

Write fingerprints of authorized keys for each user to log. This is enabled by default, but can be disabled using no_ssh_fingerprints. The hash type for the keys can be specified, but defaults to sha256.

Internal name: cc_ssh_authkey_fingerprints

Module frequency: once-per-instance

Supported distros: all

Config schema:

no_ssh_fingerprints: (boolean) If true, SSH fingerprints will not be written. Default: false.

authkey_hash: (string) The hash type to use when generating SSH fingerprints. Default: sha256.

Examples:

no_ssh_fingerprints: true
# --- Example2 ---
authkey_hash: sha512

SSH Import ID

Summary: Import SSH id

This module imports SSH keys from either a public keyserver, usually launchpad or github using ssh-import-id. Keys are referenced by the username they are associated with on the keyserver. The keyserver can be specified by prepending either lp: for launchpad or gh: for github to the username.

Internal name: cc_ssh_import_id

Module frequency: once-per-instance

Supported distros: ubuntu, debian

Config schema:

ssh_import_id: (array of string)

Examples:

ssh_import_id:
 - user
 - gh:user
 - lp:user

Timezone

Summary: Set the system timezone

Sets the system timezone based on the value provided.

Internal name: cc_timezone

Module frequency: once-per-instance

Supported distros: all

Activate only on keys: timezone

Config schema:

timezone: (string) The timezone to use as represented in /usr/share/zoneinfo.

Examples:

timezone: US/Eastern

Ubuntu Advantage

Summary: Configure Ubuntu Advantage support services

Attach machine to an existing Ubuntu Advantage support contract and enable or disable support services such as Livepatch, ESM, FIPS and FIPS Updates. When attaching a machine to Ubuntu Advantage, one can also specify services to enable. When the ‘enable’ list is present, any named service will supplement the contract-default enabled services.

Note that when enabling FIPS or FIPS updates you will need to schedule a reboot to ensure the machine is running the FIPS-compliant kernel. See Power State Change for information on how to configure cloud-init to perform this reboot.

Internal name: cc_ubuntu_advantage

Module frequency: once-per-instance

Supported distros: ubuntu

Activate only on keys: ubuntu_advantage, ubuntu-advantage

Config schema:

ubuntu_advantage: (object)

enable: (array of string) Optional list of ubuntu-advantage services to enable. Any of: cc-eal, cis, esm-infra, fips, fips-updates, livepatch. By default, a given contract token will automatically enable a number of services, use this list to supplement which services should additionally be enabled. Any service unavailable on a given Ubuntu release or unentitled in a given contract will remain disabled.

token: (string) Required contract token obtained from https://ubuntu.com/advantage to attach.

config: (object) Configuration settings or override Ubuntu Advantage config.

http_proxy: (string) Ubuntu Advantage HTTP Proxy URL.

https_proxy: (string) Ubuntu Advantage HTTPS Proxy URL.

global_apt_http_proxy: (string) HTTP Proxy URL used for all APT repositories on a system. Stored at /etc/apt/apt.conf.d/90ubuntu-advantage-aptproxy.

global_apt_https_proxy: (string) HTTPS Proxy URL used for all APT repositories on a system. Stored at /etc/apt/apt.conf.d/90ubuntu-advantage-aptproxy.

ua_apt_http_proxy: (string) HTTP Proxy URL used only for Ubuntu Advantage APT repositories. Stored at /etc/apt/apt.conf.d/90ubuntu-advantage-aptproxy.

ua_apt_https_proxy: (string) HTTPS Proxy URL used only for Ubuntu Advantage APT repositories. Stored at /etc/apt/apt.conf.d/90ubuntu-advantage-aptproxy.

Examples:

# Attach the machine to an Ubuntu Advantage support contract with a
# UA contract token obtained from https://ubuntu.com/advantage.
ubuntu_advantage:
  token: <ua_contract_token>

# --- Example2 ---
# Attach the machine to an Ubuntu Advantage support contract enabling
# only fips and esm services. Services will only be enabled if
# the environment supports said service. Otherwise warnings will
# be logged for incompatible services specified.
ubuntu_advantage:
  token: <ua_contract_token>
  enable:
  - fips
  - esm

# --- Example3 ---
# Attach the machine to an Ubuntu Advantage support contract and enable
# the FIPS service.  Perform a reboot once cloud-init has
# completed.
power_state:
  mode: reboot
ubuntu_advantage:
  token: <ua_contract_token>
  enable:
  - fips

# --- Example4 ---
# Set a http(s) proxy before attaching the machine to an
# Ubuntu Advantage support contract and enabling the FIPS service.
ubuntu_advantage:
  token: <ua_contract_token>
  config:
    http_proxy: 'http://some-proxy:8088'
    https_proxy: 'https://some-proxy:8088'
    global_apt_https_proxy: 'http://some-global-apt-proxy:8088/'
    global_apt_http_proxy: 'https://some-global-apt-proxy:8088/'
    ua_apt_http_proxy: 'http://10.0.10.10:3128'
    ua_apt_https_proxy: 'https://10.0.10.10:3128'
  enable:
  - fips

Ubuntu Drivers

Summary: Interact with third party drivers in Ubuntu.

This module interacts with the ‘ubuntu-drivers’ command to install third party driver packages.

Internal name: cc_ubuntu_drivers

Module frequency: once-per-instance

Supported distros: ubuntu

Activate only on keys: drivers

Config schema:

drivers: (object)

nvidia: (object)

license-accepted: (boolean) Do you accept the NVIDIA driver license?.

version: (string) The version of the driver to install (e.g. “390”, “410”). Defaults to the latest version.

Examples:

drivers:
  nvidia:
    license-accepted: true

Update Etc Hosts

Summary: Update the hosts file (usually /etc/hosts)

This module will update the contents of the local hosts database (hosts file; usually /etc/hosts) based on the hostname/fqdn specified in config. Management of the hosts file is controlled using manage_etc_hosts. If this is set to false, cloud-init will not manage the hosts file at all. This is the default behavior.

If set to true, cloud-init will generate the hosts file using the template located in /etc/cloud/templates/hosts.tmpl. In the /etc/cloud/templates/hosts.tmpl template, the strings $hostname and $fqdn will be replaced with the hostname and fqdn respectively.

If manage_etc_hosts is set to localhost, then cloud-init will not rewrite the hosts file entirely, but rather will ensure that a entry for the fqdn with a distribution dependent ip is present (i.e. ping <hostname> will ping 127.0.0.1 or 127.0.1.1 or other ip).

Note

if manage_etc_hosts is set true, the contents of the hosts file will be updated every boot. To make any changes to the hosts file persistent they must be made in /etc/cloud/templates/hosts.tmpl

Note

for instructions on specifying hostname and fqdn, see documentation for cc_set_hostname

Internal name: cc_update_etc_hosts

Module frequency: always

Supported distros: all

Activate only on keys: manage_etc_hosts

Config schema:

manage_etc_hosts: (true/false/localhost) Whether to manage /etc/hosts on the system. If true, render the hosts file using /etc/cloud/templates/hosts.tmpl replacing $hostname and $fdqn. If localhost, append a 127.0.1.1 entry that resolves from FQDN and hostname every boot. Default: false. DEPRECATED: Value template will be dropped after April 2027. Use true instead.

fqdn: (string) Optional fully qualified domain name to use when updating /etc/hosts. Preferred over hostname if both are provided. In absence of hostname and fqdn in cloud-config, the local-hostname value will be used from datasource metadata.

hostname: (string) Hostname to set when rendering /etc/hosts. If fqdn is set, the hostname extracted from fqdn overrides hostname.

Examples:

# Do not update or manage /etc/hosts at all. This is the default behavior.
#
# Whatever is present at instance boot time will be present after boot.
# User changes will not be overwritten.
manage_etc_hosts: false

# --- Example2 ---
# Manage /etc/hosts with cloud-init.
# On every boot, /etc/hosts will be re-written from
# ``/etc/cloud/templates/hosts.tmpl``.
#
# The strings '$hostname' and '$fqdn' are replaced in the template
# with the appropriate values either from the config-config ``fqdn`` or
# ``hostname`` if provided. When absent, the cloud metadata will be
# checked for ``local-hostname` which can be split into <hostname>.<fqdn>.
#
# To make modifications persistent across a reboot, you must modify
# ``/etc/cloud/templates/hosts.tmpl``.
manage_etc_hosts: true

# --- Example3 ---
# Update /etc/hosts every boot providing a "localhost" 127.0.1.1 entry
# with the latest hostname and fqdn as provided by either IMDS or
# cloud-config.
# All other entries will be left as is.
# 'ping `hostname`' will ping 127.0.1.1
manage_etc_hosts: localhost

Update Hostname

Summary: Update hostname and fqdn

This module will update the system hostname and fqdn. If preserve_hostname is set true, then the hostname will not be altered.

Note

for instructions on specifying hostname and fqdn, see documentation for cc_set_hostname

Internal name: cc_update_hostname

Module frequency: always

Supported distros: all

Config schema:

preserve_hostname: (boolean) Do not update system hostname when true. Default: false.

prefer_fqdn_over_hostname: (boolean) By default, it is distro-dependent whether cloud-init uses the short hostname or fully qualified domain name when both local-hostname` and ``fqdn are both present in instance metadata. When set true, use fully qualified domain name if present as hostname instead of short hostname. When set false, use hostname config value if present, otherwise fallback to fqdn.

Examples:

# By default: when ``preserve_hostname`` is not specified cloud-init
# updates ``/etc/hostname`` per-boot based on the cloud provided
# ``local-hostname`` setting. If you manually change ``/etc/hostname``
# after boot cloud-init will no longer modify it.
#
# This default cloud-init behavior is equivalent to this cloud-config:
preserve_hostname: false

# --- Example2 ---
# Prevent cloud-init from updating the system hostname.
preserve_hostname: true

# --- Example3 ---
# Prevent cloud-init from updating ``/etc/hostname``
preserve_hostname: true

# --- Example4 ---
# Set hostname to "external.fqdn.me" instead of "myhost"
fqdn: external.fqdn.me
hostname: myhost
prefer_fqdn_over_hostname: true

# --- Example5 ---
# Set hostname to "external" instead of "external.fqdn.me" when
# cloud metadata provides the ``local-hostname``: "external.fqdn.me".
prefer_fqdn_over_hostname: false

Users and Groups

Summary: Configure users and groups

This module configures users and groups. For more detailed information on user options, see the Including users and groups config example.

Groups to add to the system can be specified under the groups key as a string of comma-separated groups to create, or a list. Each item in the list should either contain a string of a single group to create, or a dictionary with the group name as the key and string of a single user as a member of that group or a list of users who should be members of the group.

Note

Groups are added before users, so any users in a group list must already exist on the system.

Users to add can be specified as a string or list under the users key. Each entry in the list should either be a string or a dictionary. If a string is specified, that string can be comma-separated usernames to create or the reserved string default which represents the primary admin user used to access the system. The default user varies per distribution and is generally configured in /etc/cloud/cloud.cfg by the default_user key.

Each users dictionary item must contain either a name or snapuser key, otherwise it will be ignored. Omission of default as the first item in the users list skips creation the default user. If no users key is provided the default behavior is to create the default user via this config:

users:
- default

Note

Specifying a hash of a user’s password with passwd is a security risk if the cloud-config can be intercepted. SSH authentication is preferred.

Note

If specifying a sudo rule for a user, ensure that the syntax for the rule is valid, as it is not checked by cloud-init.

Note

Most of these configuration options will not be honored if the user already exists. The following options are the exceptions; they are applied to already-existing users: plain_text_passwd, hashed_passwd, lock_passwd, sudo, ssh_authorized_keys, ssh_redirect_user.

The user key can be used to override the default_user configuration defined in /etc/cloud/cloud.cfg. The user value should be a dictionary which supports the same config keys as the users dictionary items.

Internal name: cc_users_groups

Module frequency: once-per-instance

Supported distros: all

Config schema:

groups: (string/object/array of (string/object))

Each object in groups list supports the following keys:

<group_name>: (string/array of string) Optional string of single username or a list of usernames to add to the group.

user: (string/object) The user dictionary values override the default_user configuration from /etc/cloud/cloud.cfg. The user dictionary keys supported for the default_user are the same as the users schema.

users: (string/object/array of (string/array of string/object))

Each object in users list supports the following keys:

name: (string) The user’s login name. Required otherwise user creation will be skipped for this user.

expiredate: (string) Optional. Date on which the user’s account will be disabled. Default: null.

gecos: (string) Optional comment about the user, usually a comma-separated string of real name and contact information.

groups: (string/object/array) Optional comma-separated string of groups to add the user to.

homedir: (string) Optional home dir for user. Default: /home/<username>.

inactive: (string) Optional string representing the number of days until the user is disabled. .

lock-passwd: (boolean) DEPRECATED: Dropped after April 2027. Use lock_passwd. Default: true.

lock_passwd: (boolean) Disable password login. Default: true.

no_create_home: (boolean) Do not create home directory. Default: false.

no_log_init: (boolean) Do not initialize lastlog and faillog for user. Default: false.

no_user_group: (boolean) Do not create group named after user. Default: false.

passwd: (string) Hash of user password applied when user does not exist. This will NOT be applied if the user already exists. To generate this hash, run: mkpasswd –method=SHA-512 –rounds=4096. Note: While hashed password is better than plain text, using passwd in user-data represents a security risk as user-data could be accessible by third-parties depending on your cloud platform.

hashed_passwd: (string) Hash of user password to be applied. This will be applied even if the user is pre-existing. To generate this hash, run: mkpasswd –method=SHA-512 –rounds=4096. Note: While hashed_password is better than plain_text_passwd, using passwd in user-data represents a security risk as user-data could be accessible by third-parties depending on your cloud platform.

plain_text_passwd: (string) Clear text of user password to be applied. This will be applied even if the user is pre-existing. There are many more secure options than using plain text passwords, such as ssh_import_id or hashed_passwd. Do not use this in production as user-data and your password can be exposed.

create_groups: (boolean) Boolean set false to disable creation of specified user groups. Default: true.

primary_group: (string) Primary group for user. Default: <username>.

selinux_user: (string) SELinux user for user’s login. Default to default SELinux user.

shell: (string) Path to the user’s login shell. The default is to set no shell, which results in a system-specific default being used.

snapuser: (string) Specify an email address to create the user as a Snappy user through snap create-user. If an Ubuntu SSO account is associated with the address, username and SSH keys will be requested from there.

ssh_authorized_keys: (array of string) List of SSH keys to add to user’s authkeys file. Can not be combined with ssh_redirect_user.

ssh_import_id: (array of string) List of SSH IDs to import for user. Can not be combined with ssh_redirect_user.

ssh_redirect_user: (boolean) Boolean set to true to disable SSH logins for this user. When specified, all cloud meta-data public SSH keys will be set up in a disabled state for this username. Any SSH login as this username will timeout and prompt with a message to login instead as the default_username for this instance. Default: false. This key can not be combined with ssh_import_id or ssh_authorized_keys.

system: (boolean) Optional. Create user as system user with no home directory. Default: false.

sudo: (string/null) Sudo rule to use or false. Absence of a sudo value or null will result in no sudo rules added for this user. DEPRECATED: The value false will be dropped after April 2027. Use null or no sudo key instead.

uid: (integer) The user’s ID. Default is next available value. DEPRECATED: The use of string type will be dropped after April 2027. Use an integer instead.

Examples:

# Add the ``default_user`` from /etc/cloud/cloud.cfg.
# This is also the default behavior of cloud-init when no `users` key
# is provided.
users:
- default

# --- Example2 ---
# Add the 'admingroup' with members 'root' and 'sys' and an empty
# group cloud-users.
groups:
- admingroup: [root,sys]
- cloud-users

# --- Example3 ---
# Skip creation of the <default> user and only create newsuper.
# Password-based login is rejected, but the github user TheRealFalcon
# and the launchpad user falcojr can SSH as newsuper. The default
# shell for newsuper is bash instead of system default.
users:
- name: newsuper
  gecos: Big Stuff
  groups: users, admin
  sudo: ALL=(ALL) NOPASSWD:ALL
  shell: /bin/bash
  lock_passwd: true
  ssh_import_id:
    - lp:falcojr
    - gh:TheRealFalcon

# --- Example4 ---
# On a system with SELinux enabled, add youruser and set the
# SELinux user to 'staff_u'. When omitted on SELinux, the system will
# select the configured default SELinux user.
users:
- default
- name: youruser
  selinux_user: staff_u

# --- Example5 ---
# To redirect a legacy username to the <default> user for a
# distribution, ssh_redirect_user will accept an SSH connection and
# emit a message telling the client to ssh as the <default> user.
# SSH clients will get the message:
users:
- default
- name: nosshlogins
  ssh_redirect_user: true

# --- Example6 ---
# Override any ``default_user`` config in /etc/cloud/cloud.cfg with
# supplemental config options.
# This config will make the default user to mynewdefault and change
# the user to not have sudo rights.
ssh_import_id: [chad.smith]
user:
  name: mynewdefault
  sudo: null

Wireguard

Summary: Module to configure Wireguard tunnel

Wireguard module provides a dynamic interface for configuring Wireguard (as a peer or server) in an easy way.

This module takes care of:
  • writing interface configuration files

  • enabling and starting interfaces

  • installing wireguard-tools package

  • loading wireguard kernel module

  • executing readiness probes

What’s a readiness probe?

The idea behind readiness probes is to ensure Wireguard connectivity before continuing the cloud-init process. This could be useful if you need access to specific services like an internal APT Repository Server (e.g Landscape) to install/update packages.

Example:

An edge device can’t access the internet but uses cloud-init modules which will install packages (e.g landscape, packages, ubuntu_advantage). Those modules will fail due to missing internet connection. The “wireguard” module fixes that problem as it waits until all readinessprobes (which can be arbitrary commands - e.g. checking if a proxy server is reachable over Wireguard network) are finished before continuing the cloud-init “config” stage.

Note

In order to use DNS with Wireguard you have to install resolvconf package or symlink it to systemd’s resolvectl, otherwise wg-quick commands will throw an error message that executable resolvconf is missing which leads wireguard module to fail.

Internal name: cc_wireguard

Module frequency: once-per-instance

Supported distros: ubuntu

Activate only on keys: wireguard

Config schema:

wireguard: (null/object)

interfaces: (array of object)

Each object in interfaces list supports the following keys:

name: (string) Name of the interface. Typically wgx (example: wg0).

config_path: (string) Path to configuration file of Wireguard interface.

content: (string) Wireguard interface configuration. Contains key, peer, .

readinessprobe: (array of string) List of shell commands to be executed as probes.

Examples:

# Configure one or more WG interfaces and provide optional readinessprobes
wireguard:
  interfaces:
    - name: wg0
      config_path: /etc/wireguard/wg0.conf
      content: |
        [Interface]
        PrivateKey = <private_key>
        Address = <address>
        [Peer]
        PublicKey = <public_key>
        Endpoint = <endpoint_ip>:<endpoint_ip_port>
        AllowedIPs = <allowedip1>, <allowedip2>, ...
    - name: wg1
      config_path: /etc/wireguard/wg1.conf
      content: |
        [Interface]
        PrivateKey = <private_key>
        Address = <address>
        [Peer]
        PublicKey = <public_key>
        Endpoint = <endpoint_ip>:<endpoint_ip_port>
        AllowedIPs = <allowedip1>
  readinessprobe:
    - 'systemctl restart service'
    - 'curl https://webhook.endpoint/example'
    - 'nc -zv some-service-fqdn 443'

Write Files

Summary: write arbitrary files

Write out arbitrary content to files, optionally setting permissions. Parent folders in the path are created if absent. Content can be specified in plain text or binary. Data encoded with either base64 or binary gzip data can be specified and will be decoded before being written. For empty file creation, content can be omitted.

Note

if multiline data is provided, care should be taken to ensure that it follows yaml formatting standards. to specify binary data, use the yaml option !!binary

Note

Do not write files under /tmp during boot because of a race with systemd-tmpfiles-clean that can cause temp files to get cleaned during the early boot process. Use /run/somedir instead to avoid race LP:1707222.

Internal name: cc_write_files

Module frequency: once-per-instance

Supported distros: all

Activate only on keys: write_files

Config schema:

write_files: (array of object)

Each object in write_files list supports the following keys:

path: (string) Path of the file to which content is decoded and written.

content: (string) Optional content to write to the provided path. When content is present and encoding is not ‘text/plain’, decode the content prior to writing. Default: ''.

owner: (string) Optional owner:group to chown on the file. Default: root:root.

permissions: (string) Optional file permissions to set on path represented as an octal string ‘0###’. Default: 0o644.

encoding: (gz/gzip/gz+base64/gzip+base64/gz+b64/gzip+b64/b64/base64/text/plain) Optional encoding type of the content. Default is text/plain and no content decoding is performed. Supported encoding types are: gz, gzip, gz+base64, gzip+base64, gz+b64, gzip+b64, b64, base64.

append: (boolean) Whether to append content to existing file if path exists. Default: false.

defer: (boolean) Defer writing the file until ‘final’ stage, after users were created, and packages were installed. Default: false.

Examples:

# Write out base64 encoded content to /etc/sysconfig/selinux
write_files:
- encoding: b64
  content: CiMgVGhpcyBmaWxlIGNvbnRyb2xzIHRoZSBzdGF0ZSBvZiBTRUxpbnV4...
  owner: root:root
  path: /etc/sysconfig/selinux
  permissions: '0644'

# --- Example2 ---
# Appending content to an existing file
write_files:
- content: |
    15 * * * * root ship_logs
  path: /etc/crontab
  append: true

# --- Example3 ---
# Provide gziped binary content
write_files:
- encoding: gzip
  content: !!binary |
      H4sIAIDb/U8C/1NW1E/KzNMvzuBKTc7IV8hIzcnJVyjPL8pJ4QIA6N+MVxsAAAA=
  path: /usr/bin/hello
  permissions: '0755'

# --- Example4 ---
# Create an empty file on the system
write_files:
- path: /root/CLOUD_INIT_WAS_HERE

# --- Example5 ---
# Defer writing the file until after the package (Nginx) is
# installed and its user is created alongside
write_files:
- path: /etc/nginx/conf.d/example.com.conf
  content: |
    server {
        server_name example.com;
        listen 80;
        root /var/www;
        location / {
            try_files $uri $uri/ $uri.html =404;
        }
    }
  owner: 'nginx:nginx'
  permissions: '0640'
  defer: true

Yum Add Repo

Summary: Add yum repository configuration to the system

Add yum repository configuration to /etc/yum.repos.d. Configuration files are named based on the opaque dictionary key under the yum_repos they are specified with. If a config file already exists with the same name as a config entry, the config entry will be skipped.

Internal name: cc_yum_add_repo

Module frequency: once-per-instance

Supported distros: almalinux, centos, cloudlinux, eurolinux, fedora, openEuler, openmandriva, photon, rhel, rocky, virtuozzo

Activate only on keys: yum_repos

Config schema:

yum_repo_dir: (string) The repo parts directory where individual yum repo config files will be written. Default: /etc/yum.repos.d.

yum_repos: (object)

<repo_name>: (object) Object keyed on unique yum repo IDs. The key used will be used to write yum repo config files in yum_repo_dir/<repo_key_id>.repo.

baseurl: (string) URL to the directory where the yum repository’s ‘repodata’ directory lives.

name: (string) Optional human-readable name of the yum repo.

enabled: (boolean) Whether to enable the repo. Default: true.

<yum_config_option>: (integer/boolean/string) Any supported yum repository configuration options will be written to the yum repo config file. See: man yum.conf.

Examples:

yum_repos:
  my_repo:
    baseurl: http://blah.org/pub/epel/testing/5/$basearch/
yum_repo_dir: /store/custom/yum.repos.d

# --- Example2 ---
# Enable cloud-init upstream's daily testing repo for EPEL 8 to
# install latest cloud-init from tip of `main` for testing.
yum_repos:
  cloud-init-daily:
    name: Copr repo for cloud-init-dev owned by @cloud-init
    baseurl: https://download.copr.fedorainfracloud.org/results/@cloud-init/cloud-init-dev/epel-8-$basearch/
    type: rpm-md
    skip_if_unavailable: true
    gpgcheck: true
    gpgkey: https://download.copr.fedorainfracloud.org/results/@cloud-init/cloud-init-dev/pubkey.gpg
    enabled_metadata: 1

# --- Example3 ---
# Add the file /etc/yum.repos.d/epel_testing.repo which can then
# subsequently be used by yum for later operations.
yum_repos:
# The name of the repository
 epel-testing:
   baseurl: https://download.copr.fedorainfracloud.org/results/@cloud-init/cloud-init-dev/pubkey.gpg
   enabled: false
   failovermethod: priority
   gpgcheck: true
   gpgkey: file:///etc/pki/rpm-gpg/RPM-GPG-KEY-EPEL
   name: Extra Packages for Enterprise Linux 5 - Testing

# --- Example4 ---
# Any yum repo configuration can be passed directly into
# the repository file created. See: man yum.conf for supported
# config keys.
#
# Write /etc/yum.conf.d/my-package-stream.repo with gpgkey checks
# on the repo data of the repository enabled.
yum_repos:
  my package stream:
    baseurl: http://blah.org/pub/epel/testing/5/$basearch/
    mirrorlist: http://some-url-to-list-of-baseurls
    repo_gpgcheck: 1
    enable_gpgcheck: true
    gpgkey: https://url.to.ascii-armored-gpg-key

Zypper Add Repo

Summary: Configure zypper behavior and add zypper repositories

Zypper behavior can be configured using the config key, which will modify /etc/zypp/zypp.conf. The configuration writer will only append the provided configuration options to the configuration file. Any duplicate options will be resolved by the way the zypp.conf INI file is parsed.

Note

Setting configdir is not supported and will be skipped.

The repos key may be used to add repositories to the system. Beyond the required id and baseurl attributions, no validation is performed on the repos entries. It is assumed the user is familiar with the zypper repository file format.

Internal name: cc_zypper_add_repo

Module frequency: always

Supported distros: opensuse, sles

Activate only on keys: zypper

Config schema:

zypper: (object)

repos: (array of object)

Each object in repos list supports the following keys:

id: (string) The unique id of the repo, used when writing /etc/zypp/repos.d/<id>.repo.

baseurl: (string) The base repositoy URL.

config: (object) Any supported zypo.conf key is written to /etc/zypp/zypp.conf.

Examples:

zypper:
  repos:
    - id: opensuse-oss
      name: os-oss
      baseurl: http://dl.opensuse.org/dist/leap/v/repo/oss/
      enabled: 1
      autorefresh: 1
    - id: opensuse-oss-update
      name: os-oss-up
      baseurl: http://dl.opensuse.org/dist/leap/v/update
      # any setting per
      # https://en.opensuse.org/openSUSE:Standards_RepoInfo
      # enable and autorefresh are on by default
  config:
    reposdir: /etc/zypp/repos.dir
    servicesdir: /etc/zypp/services.d
    download.use_deltarpm: true
    # any setting in /etc/zypp/zypp.conf