ansible-role-kubernetes is a free, open source orchestration & scheduling project written in Jinja and released under MIT. It has 626 GitHub stars, 279 forks and 6 open issues, and was last pushed 2 months ago. On this registry it ranks #123 of 130 tracked projects in Orchestration & Scheduling, with 5 head-to-head comparisons available.

What is ansible-role-kubernetes?

ansible-role-kubernetes is an MIT-licensed Ansible role that installs Kubernetes on Linux hosts using kubeadm, aimed at operators who already manage their servers with Ansible and want a repeatable, role-based path from bare machines to a working cluster.

What it is

The role lives in the Ansible ecosystem and is published on Ansible Galaxy as geerlingguy.kubernetes. It installs the Kubernetes package set on Linux hosts, runs kubeadm init on the host designated as the control plane, and runs kubeadm join on hosts designated as nodes. It is written in Jinja, ships configuration templates, and is exercised by a GitHub Actions CI workflow on every push. The repository carries 627 stars and 281 forks, with 6 open issues.

The concrete problem it solves is the manual per-host setup sequence that kubeadm clusters otherwise require. Instead of installing kubelet, kubectl, kubeadm, and kubernetes-cni by hand on each machine and then invoking the correct kubeadm command with the right flags, an operator declares the hosts in an inventory and lets the role apply the same steps in the same order. It replaces the hand-run command sequence and the ad-hoc shell scripts that usually surround it.

Key capabilities

  • Installs the package list defined in kubernetes_packages (kubelet, kubectl, kubeadm, kubernetes-cni), with per-package name and state control so packages can be present, absent, or latest.
  • Switches host behaviour with kubernetes_role, set to control_plane by default or to node, which decides whether kubeadm init or kubeadm join runs on that host.
  • Pins versions through kubernetes_version (default '1.32') for apt on Debian and for the value passed to kubeadm, and through kubernetes_version_rhel_package for Red Hat and CentOS.
  • Runs kubeadm init with a config file at kubernetes_kubeadm_kubelet_config_file_path, defaulting to /etc/kubernetes/kubeadm-kubelet-config.yaml, and creates the directory if it is missing.
  • Generates the config file skeleton through templates/kubeadm-kubelet-config.j2, so the apiVersion and kind fields are supplied by the role rather than by the operator.
  • Splits configuration across kubernetes_config_init_configuration (kind: InitConfiguration), kubernetes_config_cluster_configuration (kind: ClusterConfiguration, including networking.podSubnet and kubernetesVersion), and kubernetes_config_kubelet_configuration (cgroupDriver, set to systemd, or cgroupfs when Docker is the runtime).
  • Keeps backward compatibility with older releases through kubernetes_apiserver_advertise_address, kubernetes_pod_network.cidr, and kubernetes_version_kubeadm, which now feed the config file instead of command-line options.

Who uses it and how

  • Teams that already run Ansible for server configuration and want cluster bring-up to sit in the same playbook and repository as the rest of their host management.
  • Operators building clusters on bare metal or virtual machines, where the control plane and worker hosts are ordinary Linux machines under their own control.
  • Administrators who pair it with geerlingguy.containerd, the recommended role for installing a container runtime, since the role expects a compatible CRI to be present already.
  • Docker-based setups, where the operator changes kubernetes_config_kubelet_configuration to cgroupDriver: cgroupfs to match the runtime.
  • Single-inventory clusters, where one host is marked as the control plane and the remaining hosts are marked as nodes.

Getting started

Install the role from Ansible Galaxy as geerlingguy.kubernetes and reference it from a playbook, after installing a compatible container runtime, for which geerlingguy.containerd is recommended.

How it compares

The facts name no paid products this role replaces and no competing role. The only related tool named is geerlingguy.containerd, which is a companion rather than a rival: it installs the container runtime that this role requires before the Kubernetes packages and kubeadm commands can work. On that basis the role stands alone in this registry as the Kubernetes installation role.

When to use it — and when not to

A self-hoster must operate an Ansible control node, the target Linux hosts, and a compatible container runtime installed separately, because the role does not supply a CRI. The documented surface stops at package installation and at kubeadm init and kubeadm join, so anyone expecting managed control-plane upgrades or a hosted option will not find one here. It is also a poor fit for environments without Ansible, since a series of one-off plays would defeat the purpose, and for anyone unwilling to keep the kubelet cgroupDriver aligned with the chosen runtime.

project readme (upstream, from github) — read inline

Ansible Role: Kubernetes

CI

An Ansible Role that installs Kubernetes on Linux.

Requirements

Requires a compatible Container Runtime; recommended role for CRI installation: geerlingguy.containerd.

Role Variables

Available variables are listed below, along with default values (see defaults/main.yml):

kubernetes_packages:
  - name: kubelet
    state: present
  - name: kubectl
    state: present
  - name: kubeadm
    state: present
  - name: kubernetes-cni
    state: present

Kubernetes packages to be installed on the server. You can either provide a list of package names, or set name and state to have more control over whether the package is present, absent, latest, etc.

kubernetes_version: '1.32'
kubernetes_version_rhel_package: '1.32'

The minor version of Kubernetes to install. The plain kubernetes_version is used to pin an apt package version on Debian, and as the Kubernetes version passed into the kubeadm init command (see kubernetes_version_kubeadm). The kubernetes_version_rhel_package variable must be a specific Kubernetes release, and is used to pin the version on Red Hat / CentOS servers.

kubernetes_role: control_plane

Whether the particular server will serve as a Kubernetes control_plane (default) or node. The control plane will have kubeadm init run on it to intialize the entire K8s control plane, while nodes will have kubeadm join run on them to join them to the control_plane.

Variables to configure kubeadm and kubelet with kubeadm init through a config file (recommended)

With this role, kubeadm init will be run with --config .

kubernetes_kubeadm_kubelet_config_file_path: '/etc/kubernetes/kubeadm-kubelet-config.yaml'

Path for ``. If the directory does not exist, this role will create it.

The following variables are parsed as options to . To understand its syntax, see kubelet-integration and kubeadm-config-file . The skeleton (apiVersion, kind) of the config file will be created by this role, so do not define them within the variables. (See templates/kubeadm-kubelet-config.j2).

kubernetes_config_init_configuration:
  localAPIEndpoint:
    advertiseAddress: "{{ kubernetes_apiserver_advertise_address | default(ansible_default_ipv4.address, true) }}"

Defines the options under kind: InitConfiguration. Including kubernetes_apiserver_advertise_address here is for backward-compatibilty to older versions of this role, where kubernetes_apiserver_advertise_address was used with a command-line-option.

kubernetes_config_cluster_configuration:
  networking:
    podSubnet: "{{ kubernetes_pod_network.cidr }}"
  kubernetesVersion: "{{ kubernetes_version_kubeadm }}"

Options under kind: ClusterConfiguration. Including kubernetes_pod_network.cidr and kubernetes_version_kubeadm here are for backward-compatibilty to older versions of this role, where they were used with command-line-options.

kubernetes_config_kubelet_configuration:
  cgroupDriver: systemd

Options to configure kubelet on any nodes in your cluster through the kubeadm init process. For syntax options read the kubelet config file and kubelet integration documentation.

NOTE: This is the recommended way to do the kubelet-configuration. Most command-line-options are deprecated.

NOTE: The recommended cgroupDriver depends on your Container Runtime. When using this role with Docker instead of containerd, this value should be changed to cgroupfs.

kubernetes_config_kube_proxy_configuration: {}

Options to configure kubelet's proxy configuration in the KubeProxyConfiguration section of the kubelet configuration.

Variables to configure kubeadm and kubelet through command-line-options

kubernetes_kubelet_extra_args: ""
kubernetes_kubelet_extra_args_config_file: /etc/default/kubelet

Extra args to pass to kubelet during startup. E.g. to allow kubelet to start up even if there is swap is enabled on your server, set this to: "--fail-swap-on=false". Or to specify the node-ip advertised by kubelet, set this to "--node-ip={{ ansible_host }}". This option is deprecated. Please use kubernetes_config_kubelet_configuration instead.

kubernetes_kubeadm_init_extra_opts: ""

Extra args to pass to kubeadm init during K8s control plane initialization. E.g. to specify extra Subject Alternative Names for API server certificate, set this to: "--apiserver-cert-extra-sans my-custom.host"

kubernetes_join_command_extra_opts: ""

Extra args to pass to the generated kubeadm join command during K8s node initialization. E.g. to ignore certain preflight errors like swap being enabled, set this to: --ignore-preflight-errors=Swap

Additional variables

kubernetes_allow_pods_on_control_plane: true

Whether to remove the taint that denies pods from being deployed to the Kubernetes control plane. If you have a single-node cluster, this should definitely be True. Otherwise, set to False if you want a dedicated Kubernetes control plane which doesn't run any other pods.

kubernetes_pod_network:
  # Flannel CNI.
  cni: 'flannel'
  cidr: '10.244.0.0/16'
  #
  # Calico CNI.
  # cni: 'calico'
  # cidr: '192.168.0.0/16'
  #
  # Weave CNI.
  # cni: 'weave'
  # cidr: '192.168.0.0/16'

This role currently supports flannel (default), calico or weave for cluster pod networking. Choose only one for your cluster; converting between them is not done automatically and could result in broken networking; if you need to switch from one to another, it should be done outside of this role.

kubernetes_apiserver_advertise_address: ''`
kubernetes_version_kubeadm: 'stable-{{ kubernetes_version }}'`
kubernetes_ignore_preflight_errors: 'all'

Options passed to kubeadm init when initializing the Kubernetes control plane. The kubernetes_apiserver_advertise_address defaults to ansible_default_ipv4.address if it's left empty.

kubernetes_apt_release_channel: "stable"
kubernetes_apt_repository: "https://pkgs.k8s.io/core:/{{ kubernetes_apt_release_channel }}:/v{{ kubernetes_version }}/deb/"

Apt repository options for Kubernetes installation.

kubernetes_yum_base_url: "https://pkgs.k8s.io/core:/stable:/v{{ kubernetes_version }}/rpm/"
kubernetes_yum_gpg_key: "https://pkgs.k8s.io/core:/stable:/v{{ kubernetes_version }}/rpm/repodata/repomd.xml.key"
kubernetes_yum_gpg_check: true
kubernetes_yum_repo_gpg_check: true

Yum repository options for Kubernetes installation. You can change kubernete_yum_gpg_key to a different url if you are behind a firewall or provide a trustworthy mirror. Usually in combination with changing kubernetes_yum_base_url as well.

kubernetes_flannel_manifest_file: https://raw.githubusercontent.com/coreos/flannel/master/Documentation/kube-flannel.yml

Flannel manifest file to apply to the Kubernetes cluster to enable networking. You can copy your own files to your server and apply them instead, if you need to customize the Flannel networking configuration.

kubernetes_calico_manifest_file: https://projectcalico.docs.tigera.io/manifests/calico.yaml

Calico manifest file to apply to the Kubernetes cluster (if using Calico instead of Flannel).

Dependencies

None.

Example Playbooks

Single node (control-plane-only) cluster

- hosts: all

  vars:
    kubernetes_allow_pods_on_control_plane: true

  roles:
    - geerlingguy.docker
    - geerlingguy.kubernetes

Two or more nodes (single control-plane) cluster

Control plane inventory vars:

kubernetes_role: "control_plane"

Node(s) inventory vars:

kubernetes_role: "node"

Playbook:

- hosts: all

  vars:
    kubernetes_allow_pods_on_control_plane: true

  roles:
    - geerlingguy.docker
    - geerlingguy.kubernetes

Then, log into the Kubernetes control plane, and run kubectl get nodes as root, and you should see a list of all the servers.

License

MIT / BSD

Author Information

This role was created in 2018 by Jeff Geerling, author of Ansible for DevOps.

Frequently asked questions

Is ansible-role-kubernetes free to use?

ansible-role-kubernetes is open source under the MIT licence. There is no licence fee and no seat count — you can self-host it or, where the project offers one, pay a vendor for a managed version instead.

What does ansible-role-kubernetes do?

Ansible Role - Kubernetes

What is ansible-role-kubernetes written in?

ansible-role-kubernetes is primarily written in Jinja. Its source is publicly available at https://github.com/geerlingguy/ansible-role-kubernetes, and it has 626 GitHub stars.