Welcome to today’s article on how to install, configure and use Ansible AWX on Kubernetes / OpenShift Cluster. Ansible AWX is a popular web-based platform created to provide a user-friendly interface for Ansible automation operations. AWX is built on top of the Ansible project and it gives you a centralized management for all Ansible inventories and playbooks.
From the dashboard you can manage inventory, run and schedule Ansible playbooks, monitor job activity and execution results. The built-in RBAC (role-based access control) is used for managing access to resources within AWX platform. An integration with other tools such as Git for version control is also possible.
Key features of Ansible AWX:
- Centralized management: It offers centralized management for Ansible playbooks and inventories for ease of administration.
- Role-based access control: With the built-in RBAC you can ensure there is a secure and efficient management of automation tasks.
- Web-based user interface: AWX comes with an intuitive user-friendly web interface for managing Ansible playbooks, inventory, and automation tasks.
- Third-party integrations: Integration with other tools such as Git for version control can be done making it easy to manage and track changes to Ansible playbooks over time.
- Reporting and analytics: AWX has reporting and analytics capabilities for tracking performance and gains from its use.
Run Ansible AWX on Kubernetes / OpenShift Cluster
In this section we’ll cover the full process of installing Ansible AWX on Kubernetes / OpenShift Cluster. A major pre-requisite for this operation is existing Kubernetes / OpenShift cluster.
Step 1: Deploy Kubernetes Cluster
You can use existing articles on our website to setup a cluster.
- Deploy Kubernetes on KVM using Flatcar Container Linux
- Deploy Kubernetes Cluster with Ansible & Kubespray
- Install Kubernetes Cluster on Ubuntu with kubeadm
- Install Kubernetes Cluster on Rocky Linux 8 with Kubeadm & CRI-O
- Deploy Lightweight Kubernetes Cluster in 5 minutes with K3s
- How To Deploy Highly Available Kubernetes Cluster Using k3sup
Once the cluster is deployed and running confirm using kubectl command:
$ kubectl cluster-info
Kubernetes control plane is running at https://api.k8s.cloudlabske.io:6443
To further debug and diagnose cluster problems, use 'kubectl cluster-info dump'.Step 2: Deploy MetalLB / Ingress solution
For Kubernetes clusters deployed on your on-prem infrastructure you’ll need a solution that provides Load Balancing feature and Ingress solution. For managed Kubernetes clusters such as ones provided by cloud providers like EKS, AKS and GKE, a manual setup is not required for LB.
We have existing articles on this setup.
- How To Deploy MetalLB Load Balancer on Kubernetes Cluster
- Deploy Nginx Ingress Controller on Kubernetes using Helm Chart
Step 3: Configure Persistent Storage Solution
We’ll need persistent storage for AWX data. Any solution integrated to Kubernetes can be used for this. Refer to some of the guides available in our website.
- Configure NFS as Kubernetes Persistent Volume Storage
- Deploy and Manage MinIO Storage on Kubernetes
- How To Deploy Rook Ceph Storage on Kubernetes Cluster
- Deploy and Use OpenEBS Container Storage on Kubernetes
In this setup we’re using NFS storage class to automatically provision persistent volumes on Kubernetes.
$ kubectl get sc
NAME PROVISIONER RECLAIMPOLICY VOLUMEBINDINGMODE ALLOWVOLUMEEXPANSION AGE
nfs-01 (default) nfs-provisioner-01 Delete Immediate true 53dThis will be used when deploying AWX on Kubernetes / OpenShift cluster.
Step 4: Deploy AWX Operator on Kubernetes
We shall use the AWX Kubernetes Operator meant to be deployed in your Kubernetes cluster(s) and can manage one or more AWX instances in any namespace.
Install git and make tools:
### Ubuntu / Debian ###
sudo apt update
sudo apt install git build-essential curl jq -y
### RHEL based systems ###
sudo yum -y install epel-release
sudo yum group install "Development Tools"
sudo yum install curl jqUse git to clone Operator project source to your workstation with kubectl configured.
$ git clone https://github.com/ansible/awx-operator.git
Cloning into 'awx-operator'...
remote: Enumerating objects: 7925, done.
remote: Counting objects: 100% (403/403), done.
remote: Compressing objects: 100% (256/256), done.
remote: Total 7925 (delta 187), reused 316 (delta 121), pack-reused 7522
Receiving objects: 100% (7925/7925), 2.19 MiB | 739.00 KiB/s, done.
Resolving deltas: 100% (4498/4498), done.Next we create a namespace where operator will be deployed. We’ll name this awx:
export NAMESPACE=awx
kubectl create ns ${NAMESPACE}Set current context to value set in NAMESPACE variable:
# kubectl config set-context --current --namespace=$NAMESPACE
Context "default" modified.Switch to awx-operator directory:
cd awx-operator/Save the latest version from AWX Operator releases as RELEASE_TAG variable then checkout to the branch.
RELEASE_TAG=`curl -s https://api.github.com/repos/ansible/awx-operator/releases/latest | grep tag_name | cut -d '"' -f 4`
echo $RELEASE_TAG
git checkout $RELEASE_TAGInstall AWX Operator into your Kubernetes cluster:
export NAMESPACE=awx
make deploySuccessful execution output:
namespace/awx configured
customresourcedefinition.apiextensions.k8s.io/awxbackups.awx.ansible.com created
customresourcedefinition.apiextensions.k8s.io/awxrestores.awx.ansible.com created
customresourcedefinition.apiextensions.k8s.io/awxs.awx.ansible.com created
serviceaccount/awx-operator-controller-manager created
role.rbac.authorization.k8s.io/awx-operator-awx-manager-role created
role.rbac.authorization.k8s.io/awx-operator-leader-election-role created
clusterrole.rbac.authorization.k8s.io/awx-operator-metrics-reader created
clusterrole.rbac.authorization.k8s.io/awx-operator-proxy-role created
rolebinding.rbac.authorization.k8s.io/awx-operator-awx-manager-rolebinding created
rolebinding.rbac.authorization.k8s.io/awx-operator-leader-election-rolebinding created
clusterrolebinding.rbac.authorization.k8s.io/awx-operator-proxy-rolebinding created
configmap/awx-operator-awx-manager-config created
service/awx-operator-controller-manager-metrics-service created
deployment.apps/awx-operator-controller-manager createdWait for the operator pod creation to be successful. The status should be running
$ kubectl get pods -w
NAME READY STATUS RESTARTS AGE
awx-operator-controller-manager-65b875f4bf-757vt 0/2 ContainerCreating 0 68sStep 5: Install Ansible AWX on Kubernetes
With the AWX operator running we can use it to install AWX instance on the cluster. But first we have to create static data PVC – Ref AWX data persistence:
cat <<EOF | kubectl create -f -
apiVersion: v1
kind: PersistentVolumeClaim
metadata:
name: awx-static-data-pvc
namespace: awx
spec:
accessModes:
- ReadWriteOnce
storageClassName: nfs-01
resources:
requests:
storage: 10Gi
EOFConfirm if the PVC is created successfully.
$ kubectl get pvc
NAME STATUS VOLUME CAPACITY ACCESS MODES STORAGECLASS AGE
awx-static-data-pvc Bound pvc-184cec87-8447-4055-a672-55fe264acb27 10Gi RWO nfs-01 28sNow create AWX deployment file. See example below.
$ vim awx-deployment.yml
---
apiVersion: awx.ansible.com/v1beta1
kind: AWX
metadata:
name: awx
spec:
service_type: nodeport
projects_persistence: true
projects_storage_access_mode: ReadWriteOnce
web_extra_volume_mounts: |
- name: static-data
mountPath: /var/lib/projects
extra_volumes: |
- name: static-data
persistentVolumeClaim:
claimName: awx-static-data-pvcIf the service_type is not specified, the ClusterIP service will be used for your AWX Tower service. The service_type supported options are: ClusterIP, LoadBalancer and NodePort.
Apply configuration file.
$ kubectl apply -f awx-deployment.yml
awx.awx.ansible.com/awx createdGive it a few seconds and AWX instance will be deployed and running:
$ kubectl get pods -l "app.kubernetes.io/managed-by=awx-operator" -w
NAME READY STATUS RESTARTS AGE
awx-74bd7c8bc-4mqbb 4/4 Running 0 15m
awx-postgres-13-0 1/1 Running 0 31mYou can track the installation process at the operator pod logs:
kubectl logs -f deployments/awx-operator-controller-manager -c awx-managerListing PVCs in the namespace:
$ kubectl get pvc
NAME STATUS VOLUME CAPACITY ACCESS MODES STORAGECLASS AGE
awx-projects-claim Bound pvc-188c3463-65c0-4265-a00d-2a8573894ca7 8Gi RWO nfs-01 33m
awx-static-data-pvc Bound pvc-184cec87-8447-4055-a672-55fe264acb27 10Gi RWO nfs-01 49m
postgres-13-awx-postgres-13-0 Bound pvc-84b68384-3c9c-4f81-bfab-f083c1cf10cd 8Gi RWO nfs-01 36mChecking AWX Container’s logs
The awx-xxx-yyy pod will have four containers, namely:
- redis
- awx-web
- awx-task
- awx-ee
As can be seen from below command output:
#