Prévenir simultanée déploie avec Ansible
Quelqu'un dans mon équipe peut faire un SSH sur notre déploiement du serveur, et à partir de là, exécuter une Ansible playbook de pousser le nouveau code pour les machines.
Nous sommes inquiets de ce qui va se passer si deux personnes tentent de faire se déploie simultanément. Nous aimerions faire en sorte que le playbook sera un échec si quelqu'un d'autre est en train de l'exécuter.
Des suggestions pour savoir comment faire cela? La solution standard est d'utiliser un fichier pid, mais Ansible n'a pas intégré la prise en charge de ces.
Vous devez vous connecter pour publier un commentaire.
Vous pourriez écrire un wrapper pour ansible commandes comme :
Définir cette fonction dans le
~/.bashrc
de vos utilisateurs sur le déploiement de la boîte et vous êtes fixés.Vous pouvez faire de même pour le
ansible
commande si vous le souhaitez, mais la question étant de savoir que je ne suis pas sûr que c'est nécessaire.EDIT: a Réécrit avec le gestionnaire de signal pour éviter de verrouiller le fichier balançant autour de si les utilisateurs appuyez sur Ctrl-C.
EDIT2: correction d'une faute
[ -e $lock ] || (echo $SSH_CLIENT | cut -f1 -d' ' > $lock)
(et adapter le script en conséquence), ce qui prend moins d'une milliseconde. Dans la pratique, semble tout à fait raisonnable. Ou écrire le fichier de verrouillage avec restriction permanente afin qu'un autre utilisateur ne peut pas le remplacer. Dans l'ensemble de sûr, c'est un hack au mieux. Rundeck l'air cool.flock -x $HOME/.ansible_lock -c 'ansible-playbook ...'
Personnellement, j'utilise RunDeck ( http://rundeck.org/ ) comme un wrapper autour de mon Ansible tablettes playbook pour de multiples raisons:
Il y a beaucoup plus de bonnes raisons, bien sûr, mais mes doigts sont fatigués de frappe 😉
J'ai mis cela dans mon principal playbook, après
lock_file_path
: C'est un fichier dont l'existence indique qu'il est actuellement en cours d'exécution ansible déployer, ou il y avait un déploiement avant, qui l'a abandonnée pour une raison quelconque.force_ignore_lock
: La valeur par défaut est false, la réinitialisation par un indicateur d'option que vous pouvez définir dans une ligne de commande wrapper pour ansible. Il permet ansible pour continuer avec la déployer.Ce que cela ne
pre_tasks
La première
pre_task
vérifie si lelock_file_path
existe, et enregistre le résultat dans un registre appelélock_file
.La tâche suivante puis vérifie si le fichier existe, et si la personne le déploiement a choisi de l'ignorer (j'espère qu'après la communication avec d'autres coéquipiers). Si non, le travail échoue avec un message d'erreur utile.
Si l'utilisateur choisit de passer à la déployer, même si il y avait un
lock_file
, la tâche suivante supprime lelock_file
et en crée une nouvelle. Les autres tâches dans le rôle sélectionné puis continuer joyeusement.post_tasks
C'est un crochet appelé immédiatement après que toutes les tâches dans le déploiement ont été achevés. La tâche ici supprime le
lock_file
, permettant à la personne suivante à déployer heureusement, sans aucun problème.when: lock_file.stat.exists|bool and not force_ignore_lock|bool
. Il utilise laforce_ignore_lock
variable qui peut être situé dans un indicateur de ligne de commande à un script écrit en python par exemple à l'aide de clic. Exemple: `@deploy.command() @click.option('--force', help="Ignore the lock file that prevents parallel deploys, \ if a previous deploy was aborted.", is_flag=True, default=False) def backend(api_server, force): """Deploys the backend application.""" if force: ignore_lock = 'true' else: ignore_lock = 'false' extra_vars = { 'force_ignore_lock': ignore_lock } call_ansible(api_server, 'api_server.yml', json.dumps(extra_vars))
Avez-vous envisagé de mettre en
maxsyslogins
dans les limites.conf? Vous pouvez limiter ce groupe.C'est un peu plus grave que ce que vous avez demandé. Vous pourriez vouloir essayer sur une machine virtuelle en premier. Notez qu'aucune de déployeurs aurez accès si il y a d'autres utilisateurs sur le système à tous, le 1 limite n'est pas juste compter les chargés de déploiement. Aussi, si tant qu'utilisateur, vous multiplex de vos connexions ssh (ControlMaster auto), vous serez toujours en mesure de se connecter plusieurs fois; il est d'autres utilisateurs qui seraient verrouillés.
Vous pouvez utiliser le troupeau de commande, qui va envelopper votre commande avec un système de fichiers basé sur troupeau(2):
Étirable toutefois, il convient à vos utilisateurs le meilleur. Cela laissera une persistante fichier de verrouillage dans /tmp, mais notez qu'il est pas sûr de le supprimer[1]. C'est atomique, et très simple.
Wrapper les scripts ne sont pas utiles lors de travaux de déploiement pourrait être exécuté à partir de construire plusieurs hôtes. Pour ce genre de cas, le verrouillage doit être gérée par le playbook.
Ansible a maintenant un wait_for module, qui peut être utilisé pour le verrouillage. Voici un court exemple (sans considération de verrous périmés):
Ansible va vérifier le fichier de verrouillage pour un délai configurable période, et puis si il n'est pas retiré dans ce délai.
Vous pouvez également utiliser simple variante de wrapper:
J'aurais l'air dans un système distribué, mécanisme de verrouillage comme gardienne d'animaux que je voudrais inclure un rôle, comme il est un
znode
module. Distribué à des fins de haute disponibilité et de l'écriture de verrouillage de la cible nœuds.Le rôle serait d'écrire un znode de le nom de la cible sous
/deployment/
au début et à la supprimer par la suite. Si le verrou existe déjà, vous pouvez échouer et de lancer un message dans unblock
.