Vous automatisez vos tâches d’administration système répétitives avec Ansible depuis un sure temps déjà. Vous avez renvoyé des providers problématiques, déployé des objets sur Kubernetes, mis à jour des systèmes et effectué des redémarrages progressifs. Peut-être avez-vous même déployé et configuré des providers en utilisant des rôles que vous avez trouvés sur Galaxie Ansible. Cependant, c’est finalement arrivé. Vous ne trouvez pas de rôle sur Ansible Galaxy qui fasse ce que vous voulez (vous avez coché, n’est-ce pas ?), ou vous avez été chargé d’écrire un rôle pour l’software de votre organisation. Quelle que soit la raison, il est temps pour vous d’écrire votre propre rôle. Remark faites-vous cela d’une manière où vous pouvez être sûr que votre rôle fonctionne comme prévu ? Cet article répondra à cette query en fournissant des conseils sur la meilleure façon de commencer à développer des rôles Ansible.
Infrastructure en tant que code et DevOps
Avant de plonger dans les détails, il serait utile de définir une terminologie. Ansible relève de la infrastructure en tant que code (IaC) parapluie à outils. IaC est le processus de gestion et de provisionnement des ressources informatiques through des fichiers de définition lisibles par machine. Cette approche permet de stocker la configuration de l’infrastructure dans git, en bénéficiant de tous les avantages, y compris la création de branches, l’historique, les politiques de révision et d’approbation, and so forth.
DevOps est l’ensemble des pratiques qui combinent le développement de logiciels (dev) et les opérations informatiques (ops) pour raccourcir le cycle de vie du développement et fournir une livraison proceed des logiciels. Les outils IaC sont une pièce du puzzle qui permet aux organisations d’adopter une approche DevOps. Le processus DevOps est généralement décrit comme swimsuit :
Determine 1 : La boucle DevOps Infinity.
Il est utile d’avoir ce processus à l’esprit lors du développement de vos rôles Ansible, automotive en tant que logiciels, ils peuvent également bénéficier d’une approche DevOps.
Rôles Ansibles
Dans Ansible, les rôles sont une méthode de chargement automatique de certaines variables, tâches, fichiers, modèles et gestionnaires basés sur une construction de fichiers connue. Le regroupement du contenu par rôles permet un partage et une réutilisation faciles. L’Ansible Documentation sur les rôles décrit la construction du fichier et d’autres considérations.
Lors du développement de rôles, vous devrez faire face à diverses préoccupations, notamment le(s) système(s) d’exploitation et la(les) model(s) que vous prendrez en cost et si vous n’avez besoin que d’un seul nœud ou si vous devez cibler un cluster de machines. Il est également souvent vital de repartir d’un nouvel état chaque fois que vous réexécutez votre rôle tout en le développant pour vous assurer que (1) vos rôles se terminent avec succès lors de leur première exécution et (2) les modifications apportées lors des exécutions précédentes n’affectent pas le résultat. . Vous devez également vérifier que votre rôle est idempotent pour vous assurer que, quel que soit le nombre de fois qu’il est exécuté, vous obtenez le même résultat. Il est également vital de vérifier que les choses ne doivent être modifiées que si elles doivent l’être. Par exemple, un service ne doit être redémarré que si des changements de configuration justifient un redémarrage.
La dernière selected à considérer est de savoir remark vérifier que votre rôle a fait ce que vous aviez l’intention de faire. Se connecter à un nœud cible et vérifier manuellement est certainement une façon de le faire. Cependant, il est préférable d’écrire des assessments qui peuvent être exécutés automatiquement après votre rôle Ansible pour vérifier l’état réel.
Pour automatiser ces sorts de assessments, vous aurez besoin d’un hôte cible (ou d’un ensemble d’hôtes) et vous devrez détruire et recréer cet hôte (ou cet ensemble d’hôtes) constamment pendant le processus de développement. Vous serez également responsable de la gestion des connexions à l’hôte (ou aux hôtes) dans l’un des systèmes pris en cost par Ansible. méthodes. De plus, vous devez passer à l’outil de take a look at que vous avez choisi et gérer sa connexion au(x) nœud(s). La gestion de cette infrastructure de développement et de take a look at peut être fastidieuse et consommera une grande partie du temps qui pourrait être mieux consacré aux fonctionnalités de rôle.
Entrez la molécule
Molécule est un projet visant à faciliter le développement et le take a look at des rôles Ansible en traitant l’ensemble des préoccupations décrites précédemment et en rationalisant l’ensemble du processus de développement des rôles. Jumeler Molécule avec Docker automotive son fournisseur vous permet de développer rapidement et facilement vos rôles sur n’importe quel nombre de systèmes d’exploitation et de variations fraîchement déployés simultanément. Molecule dispose également d’une vérification d’idempotence intégrée et d’une prise en cost de diverses méthodes de take a look at de vérification.
Pour commencer, installez d’abord Docker. Alors en supposant que vous avez pip3installez Molecule et les dépendances de help :
pip3 set up yamllint ansible molecule(docker) docker pytest-testinfra
Avec Molecule et ses dépendances installées, il est temps de commencer à développer un rôle Ansible. Molecule peut vous aider ici en créant pour vous la construction de fichiers de votre rôle et les propres fichiers de configuration requis par Molecule :
$ molecule init function maheckathorn.instance -d docker
$ tree
.
├── README.md
├── defaults
│ └── foremost.yml
├── recordsdata
├── handlers
│ └── foremost.yml
├── meta
│ └── foremost.yml
├── molecule
│ └── default
│ ├── converge.yml
│ ├── molecule.yml
│ └── confirm.yml
├── duties
│ └── foremost.yml
├── templates
├── assessments
│ ├── stock
│ └── take a look at.yml
└── vars
└── foremost.yml
10 directories, 11 recordsdata
Au sein de la File Moléculeles fichiers suivants ont des objectifs spécifiques :
converge.yml
est le fichier playbook qui contient l’appel pour votre rôle. Molecule invoquera ce playbook avecansible-playbook
et exécutez-le sur une occasion créée par le pilote, qui est Docker dans notre scénario.molecule.yml
est le level d’entrée de configuration central pour Molecule. Avec ce fichier, vous pouvez configurer chaque outil que Molecule utilisera lors du take a look at de votre rôle.confirm.yml
est le fichier Ansible utilisé pour les assessments automotive Ansible est la valeur par défaut vérificateur, ce qui vous permet d’écrire des assessments spécifiques sur l’état du conteneur une fois l’exécution de votre rôle terminée. D’autres outils de vérification sont disponibles (notez que TestInfra était le vérificateur par défaut avant Molecule model 3).
Le molecule.yml
contient différentes sections pour configurer le comportement des composants de la molécule :
- Le dépendance directeur—La molécule utilise Galaxie par défaut pour résoudre vos dépendances de rôle.
- Le conducteur fournisseur. Utilisations de la molécule Docker par défaut. Molecule utilise le pilote pour déléguer la tâche de création d’situations.
- Le peluche commande-Molecule peut appeler des commandes externes pour s’assurer que les meilleures pratiques sont encouragées. Remarque : Ansible-lint n’est pas inclus avec la molécule ou la molécule (peluche).
- Le plates-formes définitions—Molecule s’appuie sur cela pour savoir quelles situations créer et nommer et pour identifier à quel groupe appartient chaque occasion. Si vous devez tester votre rôle par rapport à plusieurs distributions populaires (CentOS, Fedora, Debian), vous pouvez le spécifier dans cette part.
- Le fournisseur—Molecule ne fournit qu’un provisionneur Ansible. Ansible gère le cycle de vie de l’occasion en fonction de cette configuration.
- Le scénario définition—Molecule s’appuie sur cette configuration pour contrôler l’ordre de séquence des scénarios.
- Le vérificateur cadre— Molecule utilise Ansible par défaut pour fournir un moyen d’écrire des assessments de vérification d’état spécifiques (tels que des assessments de fumée de déploiement) sur l’occasion cible.
Il existe de nombreuses choices pour configurer ces sections afin de répondre à vos besoins. Cependant, s’en tenir à un fichier de configuration commun à tous les projets permet de définir des attentes commonplace. Ce qui swimsuit est basé sur Le commun de Jeff Geerling molecule.yml
déposer:
https://github.com/cmu-sei/ansible-role-silk/blob/grasp/molecule/default/molecule.yml
---
dependency:
identify: galaxy
driver:
identify: docker
platforms:
- identify: occasion
picture: "geerlingguy/docker-${MOLECULE_DISTRO:-centos7}-ansible:newest"
command: ${MOLECULE_DOCKER_COMMAND:-""}
volumes:
- /sys/fs/cgroup:/sys/fs/cgroup:ro
privileged: true
pre_build_image: true
env:
http_proxy: "${http_proxy}"
https_proxy: "${https_proxy}"
no_proxy: "${no_proxy} "
provisioner:
identify: ansible
playbooks:
converge: ${MOLECULE_PLAYBOOK:-converge.yml}
verifier:
identify: testinfra
choices:
v: 1
L’élément clé à noter dans ce fichier est l’utilisation de Conteneur(s) Docker de Jeff Geerling comme supply d’picture, la configuration de Testinfra comme vérificateur, et la variable d’environnement MOLECULE_DISTRO avec centos7 comme valeur par défaut. Les photos Docker prédéfinies personnalisées contiennent déjà Python, Ansible et systemd. Ils aident à accélérer les assessments en n’ayant pas besoin que Molecule fasse quoi que ce soit pour utiliser l’picture autre que de la récupérer. La variable d’environnement MOLECULE_DISTRO vous permet de tester facilement par rapport à d’autres sorts et variations de système d’exploitation en :
$ MOLECULE_DISTRO=ubuntu1804 molecule take a look at
D’autres photos prédéfinies sont répertoriées ici.
Enfin, le vérificateur Testinfra configure Molecule pour utiliser Testinfra pour les assessments de vérification, ce qui était la valeur par défaut avant la model 3 de la molécule. Si vous développez des rôles avec des assessments de vérification depuis un sure temps, il est utile de pouvoir configurer ce paramètre, ce qui signifie le répertoire de assessments créé par la molécule est inutile. Vous pouvez également modifier votre fichier converge.yml pour qu’il ressemble à ceci :
https://github.com/cmu-sei/ansible-role-silk/blob/grasp/molecule/default/converge.yml
---
- identify: Converge
hosts: all
roles:
- function: "{ basename }"
surroundings:
http_proxy: "{{ lookup('env', 'http_proxy') }}"
https_proxy: "{{ lookup('env', 'https_proxy') }}"
no_proxy: "{{ lookup('env', 'no_proxy') }}"
Cette configuration permet d’éviter les problèmes de intégration proceed/déploiement continu (CI/CD) et traite également des problèmes d’espace de noms de projet Ansible.
Avec Molecule configuré, nous pouvons exécuter le scénario Molecule complet par défaut, qui est une suite de assessments pour votre nouveau rôle :
$ molecule take a look at
INFO default state of affairs take a look at matrix: dependency, lint, cleanup, destroy, syntax, create, put together, converge, idempotence, side_effect, confirm, cleanup, destroy
INFO Performing prerun...
INFO Set ANSIBLE_LIBRARY=/Customers/maheckathorn/.cache/ansible-compat/50d858/modules:/Customers/maheckathorn/.ansible/plugins/modules:/usr/share/ansible/plugins/modules
INFO Set ANSIBLE_COLLECTIONS_PATH=/Customers/maheckathorn/.cache/ansible-compat/50d858/collections:/Customers/maheckathorn/.ansible/collections:/usr/share/ansible/collections
INFO Set ANSIBLE_ROLES_PATH=/Customers/maheckathorn/.cache/ansible-compat/50d858/roles:/Customers/maheckathorn/.ansible/roles:/usr/share/ansible/roles:/and so forth/ansible/roles
INFO Utilizing /Customers/maheckathorn/.cache/ansible-compat/50d858/roles/maheckathorn.instance symlink to present repository with a purpose to allow Ansible to seek out the function utilizing its anticipated full identify.
INFO Working default > dependency
WARNING Skipping, lacking the necessities file.
WARNING Skipping, lacking the necessities file.
INFO Working default > lint
INFO Lint is disabled.
INFO Working default > cleanup
WARNING Skipping, cleanup playbook not configured.
INFO Working default > destroy
INFO Sanity checks: 'docker'
PLAY (Destroy) *****************************************************************
TASK (Destroy molecule occasion(s)) ********************************************
modified: (localhost) => (merchandise=occasion)
TASK (Wait as an illustration(s) deletion to finish) *******************************
FAILED - RETRYING: (localhost): Wait as an illustration(s) deletion to finish (300 retries left).
okay: (localhost) => (merchandise=occasion)
TASK (Delete docker networks(s)) ***********************************************
PLAY RECAP *********************************************************************
localhost : okay=2 modified=1 unreachable=0 failed=0 skipped=1 rescued=0 ignored=0
INFO Working default > syntax
playbook: /Customers/maheckathorn/take a look at/instance/molecule/default/converge.yml
INFO Working default > create
PLAY (Create) ******************************************************************
TASK (Log right into a Docker registry) **********************************************
skipping: (localhost) => (merchandise=None)
skipping: (localhost)
TASK (Verify presence of customized Dockerfiles) ************************************
okay: (localhost) => (merchandise={'command': '', 'env': '', 'picture': 'geerlingguy/docker-centos7-ansible:newest', 'identify': 'occasion', 'pre_build_image': True, 'privileged': True, 'volumes': ('/sys/fs/cgroup:/sys/fs/cgroup:ro')})
TASK (Create Dockerfiles from picture names) *************************************
skipping: (localhost) => (merchandise={'command': '', 'env': '', 'picture': 'geerlingguy/docker-centos7-ansible:newest', 'identify': 'occasion', 'pre_build_image': True, 'privileged': True, 'volumes': ('/sys/fs/cgroup:/sys/fs/cgroup:ro')})
TASK (Uncover native Docker photos) ********************************************
okay: (localhost) => (merchandise={'modified': False, 'skipped': True, 'skip_reason': 'Conditional consequence was False', 'merchandise': {'command': '', 'env': '', 'picture': 'geerlingguy/docker-centos7-ansible:newest', 'identify': 'occasion', 'pre_build_image': True, 'privileged': True, 'volumes': ('/sys/fs/cgroup:/sys/fs/cgroup:ro')}, 'ansible_loop_var': 'merchandise', 'i': 0, 'ansible_index_var': 'i'})
TASK (Construct an Ansible suitable picture (new)) *********************************
skipping: (localhost) => (merchandise=molecule_local/geerlingguy/docker-centos7-ansible:newest)
TASK (Create docker community(s)) ************************************************
TASK (Decide the CMD directives) ********************************************
okay: (localhost) => (merchandise={'command': '', 'env': '', 'picture': 'geerlingguy/docker-centos7-ansible:newest', 'identify': 'occasion', 'pre_build_image': True, 'privileged': True, 'volumes': ('/sys/fs/cgroup:/sys/fs/cgroup:ro')})
TASK (Create molecule occasion(s)) *********************************************
modified: (localhost) => (merchandise=occasion)
TASK (Wait as an illustration(s) creation to finish) *******************************
FAILED - RETRYING: (localhost): Wait as an illustration(s) creation to finish (300 retries left).
modified: (localhost) => (merchandise={'failed': 0, 'began': 1, 'completed': 0, 'ansible_job_id': '429858788464.21737', 'results_file': '/Customers/maheckathorn/.ansible_async/429858788464.21737', 'modified': True, 'merchandise': {'command': '', 'env': '', 'picture': 'geerlingguy/docker-centos7-ansible:newest', 'identify': 'occasion', 'pre_build_image': True, 'privileged': True, 'volumes': ('/sys/fs/cgroup:/sys/fs/cgroup:ro')}, 'ansible_loop_var': 'merchandise'})
PLAY RECAP *********************************************************************
localhost : okay=5 modified=2 unreachable=0 failed=0 skipped=4 rescued=0 ignored=0
INFO Working default > put together
WARNING Skipping, put together playbook not configured.
INFO Working default > converge
PLAY (Converge) ****************************************************************
TASK (Gathering Information) *********************************************************
okay: (occasion)
PLAY RECAP *********************************************************************
occasion : okay=1 modified=0 unreachable=0 failed=0 skipped=0 rescued=0 ignored=0
INFO Working default > idempotence
PLAY (Converge) ****************************************************************
TASK (Gathering Information) *********************************************************
okay: (occasion)
PLAY RECAP *********************************************************************
occasion : okay=1 modified=0 unreachable=0 failed=0 skipped=0 rescued=0 ignored=0
INFO Idempotence accomplished efficiently.
INFO Working default > side_effect
WARNING Skipping, facet impact playbook not configured.
INFO Working default > confirm
WARNING Skipping, no assessments discovered.
INFO Working default > cleanup
WARNING Skipping, cleanup playbook not configured.
INFO Working default > destroy
PLAY (Destroy) *****************************************************************
TASK (Destroy molecule occasion(s)) ********************************************
modified: (localhost) => (merchandise=occasion)
TASK (Wait as an illustration(s) deletion to finish) *******************************
FAILED - RETRYING: (localhost): Wait as an illustration(s) deletion to finish (300 retries left).
modified: (localhost) => (merchandise=occasion)
TASK (Delete docker networks(s)) ***********************************************
PLAY RECAP *********************************************************************
localhost : okay=2 modified=2 unreachable=0 failed=0 skipped=1 rescued=0 ignored=0
INFO Pruning additional recordsdata from state of affairs ephemeral listing
Puisque nous avons montré beaucoup de résultats ci-dessus, décomposons ce qui se passe ici. Immédiatement après avoir exécuté le take a look at Molecule, nous obtenons une sortie nous indiquant quelles étapes du processus de take a look at vont être exécutées :
INFO default state of affairs take a look at matrix: dependency, lint, cleanup, destroy, syntax, create, put together, converge, idempotence, side_effect, confirm, cleanup, destroy
Comme le montre cette sortie, Molecule exécute par défaut ces étapes dans le cadre de la matrice de take a look at dans l’ordre indiqué. Chaque fois que nous voyons un
INFO Working default >
ligne dans la sortie, nous examinons une étape différente dans la matrice en cours d’exécution. Si vous parcourez la sortie, vous verrez que de nombreuses étapes sont en fait ignorées par défaut. Par exemple:
INFO Working default > dependency
WARNING Skipping, lacking the necessities file.
Dans notre exemple, la première étape de la matrice où Molecule en fait fait quelque selected est l’étape de destruction. À cette étape, Molecule interagit avec le pilote configuré, dans notre cas Docker, et tente de détruire tous les environnements de take a look at précédents pour s’assurer qu’un nouvel environnement de take a look at propre est utilisé. La molécule interagit avec le Démon Docker et détruit tout conteneur en cours d’exécution avec notre nom défini à partir de notre molecule.yml
déposer:
platforms:
- identify: occasion
Si un conteneur en cours d’exécution portant ce nom n’existe pas actuellement, comme dans notre cas, il passe simplement à autre selected. La prochaine étape à laquelle Molecule fait réellement quelque selected est l’étape de création. À ce stade du processus, la molécule interagit avec le pilote et tente de créer un environnement de take a look at à l’aide du pilote que nous lui avons indiqué et configuré de la manière décrite dans la part plate-forme de molecule.yml :
driver:
identify: docker
platforms:
- identify: occasion
picture: "geerlingguy/docker-${MOLECULE_DISTRO:-centos7}-ansible:newest"
command: ${MOLECULE_DOCKER_COMMAND:-""}
volumes:
- /sys/fs/cgroup:/sys/fs/cgroup:ro
privileged: true
pre_build_image: true
env:
http_proxy: "${http_proxy}"
https_proxy: "${https_proxy}"
no_proxy: "${no_proxy} "
Puisque nous utilisons Docker, Molecule gère l’extraction de l’picture du conteneur que nous avons définie, définit les choices d’exécution de Docker et exécute le conteneur en arrière-plan. Les lignes suivantes montrent la création réussie de notre environnement de take a look at souhaité :
TASK (Wait as an illustration(s) creation to finish) *******************************
FAILED - RETRYING: (localhost): Wait as an illustration(s) creation to finish (300 retries left).
modified: (localhost) => (merchandise={'failed': 0, 'began': 1, 'completed': 0, 'ansible_job_id': '429858788464.21737', 'results_file': '/Customers/maheckathorn/.ansible_async/429858788464.21737', 'modified': True, 'merchandise': {'command': '', 'env': '' '}, 'picture': 'geerlingguy/docker-centos7-ansible:newest', 'identify': 'occasion', 'pre_build_image': True, 'privileged': True, 'volumes': ('/sys/fs/cgroup:/sys/fs/cgroup:ro')}, 'ansible_loop_var': 'merchandise'})
Avec notre environnement de take a look at maintenant en place, Molecule passe à l’exécution de l’étape de convergence du processus, qui exécute commodément le playbook nommé converge.yml
que nous avons défini précédemment. Ce playbook dirige notre rôle. À l’heure actuelle, notre rôle ne fait rien, comme le montre cette sortie :
INFO Working default > converge
PLAY (Converge) ****************************************************************
TASK (Gathering Information) *********************************************************
okay: (occasion)
PLAY RECAP *********************************************************************
occasion : okay=1 modified=0 unreachable=0 failed=0 skipped=0 rescued=0 ignored=0
Ce que cela montre, cependant, c’est que Molecule a pu se connecter avec succès à notre environnement de take a look at. Immédiatement après une étape de convergence réussie, Molecule teste automatiquement notre rôle pour l’idempotence. Cela consiste à relancer notre playbook converge.yml et à s’assurer que rien n’a été changé.
Si nous avions défini des assessments Testinfra, l’étape de vérification les aurait exécutés :
INFO Working default > confirm
WARNING Skipping, no assessments discovered.
Un exemple de code Testinfra easy peut être vu dans le Référentiel github Ansible SiLK:
import os
import testinfra.utils.ansible_runner
testinfra_hosts = testinfra.utils.ansible_runner.AnsibleRunner(
os.environ('MOLECULE_INVENTORY_FILE')).get_hosts('all')
def test_silk_version(host):
model = "3.19.2"
command = """/usr/native/bin/silk_config --silk-version"""
cmd = host.run(command)
assert model in cmd.stdout
Dans ce cas, Molecule exécuterait ce code Python sur l’hôte Docker et Testinfra se chargerait de se connecter à l’environnement de take a look at, d’exécuter les assessments et de renvoyer la sortie à la molécule. Le take a look at que nous exécutons vérifie simplement si la model de Soie installé dans l’environnement de take a look at est 3.19.2. Si nos assessments réussissent, Molecule considère l’étape de vérification comme un succès et passe à autre selected. La dernière selected que Molecule fait lors d’un take a look at est de nettoyer après lui-même en réexécutant l’étape de destruction.
Automatisation de la confiance
Comme le souligne notre exemple ci-dessus, Molecule est succesful de rationaliser votre processus de développement de rôle Ansible. Il met en place et démantèle rapidement et facilement des environnements de take a look at configurables et gère les assessments d’idempotence et de vérification. Cependant, cette publication de weblog ne fait qu’effleurer la floor de ce dont Molecule est succesful.
Par exemple, la gestion d’un environnement de take a look at en cluster est un jeu d’enfant en ajoutant simplement une autre occasion nommée à la part plate-forme du molecule.yml
déposer. Tester sur différents systèmes d’exploitation et différentes variations de système d’exploitation est également une easy commande de réglage. L’ajout de préparations aux nœuds de take a look at qui, pour une raison ou une autre, doivent se produire en dehors du rôle est easy grâce à l’inclusion de l’étape de préparation (en ajoutant un put together.yml
livret de jeu). Il est également facile d’ajouter des dépendances de rôle en créant un necessities.yml
fichier dans le répertoire Molecule.
Enfin, l’ensemble du processus est easy à déplacer vers un système CI/CD. Le ci.yml dans le référentiel Ansible SiLK montre remark procéder avec les actions Github, mais le processus est suffisamment moveable pour être facilement recréé à l’aide de la plate-forme CI/CD de votre choix. Si vous n’utilisez pas Molecule pour développer vos rôles Ansible, vous risquez de ralentir considérablement votre cadence de développement et de réduire la qualité de votre code Ansible. L’écriture de rôles Ansible avec l’aide de Molecule rend très possible que vous puissiez être sûr que votre rôle fait ce que vous voulez, ce qui conduit à un code de meilleure qualité et à une réduction de la frustration des utilisateurs.