Ansible fails to pull docker image from aws ecr (registry) - amazon-ec2

ansible: 2.3, trying to pull image with docker_container step.
Did all the steps of amazon-ecr-credential-helper
still when ansible in the docker_container step it fails on
message: unauthorized: authentication required
Thing is that on the remote machine I'm able to pull the image manually.
I have only one user there (ec2-user of aws) - so it's seems like ansible thing. thoughts?

So, you have configured amazon-ecr-credential-helper for the ec2-user on remote machine, and the images can be pulled manually. While, executing the playbook, I think that you are executing the play as root or with become: yes.
If you are executing the playbook with become: yes, then the image pull would fail because, the task is executed as root.

Related

How to visualize the ansible-playbook run command in a web UI format

I have an ansible yaml file and mentioned all the hosts in a different file. When I run a playbook in cli, I would like to visualize in which of the hosts, the ansible play is successful and in which of the hosts the play is unsuccessful in a web UI. Are there any tools/apps that can solves this issue.
You are asking for Ansible Tower (paid) or AWX (free). These two are the same thing actually (AWX is an upstream branch of Tower). With both you can run playbooks using web UI and there is some indication if there were failed hosts.

Is it possible to call ansible or ansible-playbook directly on a target host using a script or ansible itself?

I need to know if it's possible to call / execute ansible playbooks from the target machine. I think i saw a vendor do it or at least something similar. they downloaded a script and it did ran the playbook.
if this is possible how would it be done?
my goal is to run ansible as a centralized server in aws to perform tasks in mulitple environments. most are behind firewalls, any reccomendations/thoughts would be appreciated.
Sure. If your host will install Ansible on target and feed it with all the playbooks the you can run it as any other executable. Should you do that is another story but technically there's no obstacle.
You can run ansible and ansible playbook as you would any other binary on the target's $PATH, so any tool that facilitates running remote commands would work.
Because you are in AWS, one way might be to use AWS System's Manager.
If you wanted to use Ansible itself to do this you could use the shell or command modules:
- hosts: target
become: false
gather_facts: false
tasks:
- name: ansible in ansible
command: ansible --version
- name: ansible-playbook in ansible
command: ansible-playbook --version
Though, as with any situation where you reach for the shell or command modules, you have to be vigilant to maintain playbook idempotency yourself.
If you're requirement is just the ability to execute Ansible commands remotely, you might look into AWX which is the upstream project for Red Hat's Ansible Tower. It wraps ansible in a nice user interface to allow you to trigger Ansible playbooks remotely and with nice-to-haves like RBAC.
If you're ok with executing tasks remotely over ssh take a look at Sparrowdo it has out of the box facilities to run bash scripts ( read ansible executable ) remotely from one master host to another. Or you can even use it to install all the ansible dependencies or whatever you need to do for your scope.

Ansible command to trigger registration on another server

I can't find any documentation on how to include a secondary server in a playbook.
If for instance, I want to install sssd on SERVERA and register with a FreeIPA server.
On the FreeIPA server (only), I need to:
get a Kerberos ticket (via kinit)
check if SERVERA is already in IPA instance
delete SERVERA from IPA if true
Since this is an installation playbook run against SERVERA, it doesn't seem right to include the IPA server in the hostlist...but nor can I see any "third party servers" module?
I presume you are searching for the delegate_to option, which allows you to delegate a task to a host that is not in the hostlist.
Often used to run things on the localhost (host running ansible), it can also be used to push a task to a host not in hostlist. The host has to be in the inventory file though.
Example:
- name: Ping the other host
ping:
delegate_to: otherhost.com # This is where you set it
More info: http://docs.ansible.com/ansible/latest/user_guide/playbooks_delegation.html#delegation

Ansible execute command locally and then on remote server

I am trying to start a server using ansible shell module with ipmitools and then do configuration change on that server once its up.
Server with ansible installed also has ipmitools.
On server with ansible i need to execute ipmitools to start target server and then execute playbooks on it.
Is there a way to execute local ipmi commands on server running ansible to start target server through ansible and then execute all playbooks over ssh on target server.
You can run any command locally by providing the delegate_to parameter.
- shell: ipmitools ...
delegate_to: localhost
If ansible complains about connecting to localhost via ssh, you need to add an entry in your inventory like this:
localhost ansible_connection=local
or in host_vars/localhost:
ansible_connection: local
See behavioral parameters.
Next, you're going to need to wait until the server is booted and accessible though ssh. Here is an article from Ansible covering this topic and this is the task they have listed:
- name: Wait for Server to Restart
local_action:
wait_for
host={{ inventory_hostname }}
port=22
delay=15
timeout=300
sudo: false
If that doesn't work (since it is an older article and I think I previously had issues with this solution) you can look into the answers of this SO question.

Ansible How to replay notifications

Currently I am switching from puppet to Ansible and I am a bit confused with some concepts or at least how ansible works.
Some info on the setup:
I am using the examples from Ansible Best Practices and have structured my project similar with several roles (playbooks) and so on.
I am using Vagrant for provisioning and the box is Saucy64 VBox.
Where the Confusion comes:
When I provision, and I run ansible, tasks start to execute, then the stack of notifications.
Example:
Last task:
TASK: [mysql | delete anonymous MySQL server user for localhost] **************
<127.0.0.1> REMOTE_MODULE mysql_user user='' state=absent
changed: [default] => {"changed": true, "item": "", "user": ""}
Then first notification:
NOTIFIED: [timezone | update tzdata] ******************************************
<127.0.0.1> REMOTE_MODULE command /usr/sbin/dpkg-reconfigure --frontend noninteractive tzdata
changed: [default] => {"changed": true, "cmd": ["/usr/sbin/dpkg-reconfigure", "--frontend", "noninteractive", "tzdata"], "delta": "0:00:00.224081", "end": "2014-02-03 22:34:48.508961", "item": "", "rc": 0, "start": "2014-02-03 22:34:48.284880", "stderr": "\nCurrent default time zone: 'Europe/Amsterdam'\nLocal time is now: Mon Feb 3 22:34:48 CET 2014.\nUniversal Time is now: Mon Feb 3 21:34:48 UTC 2014.", "stdout": ""}
Now this is all fine. As the roles increase more and more notifications stuck up.
Now here comes the problem.
When a notification fails the provisioning stops as usual. But then the notification stack is empty!
This means that all notifications that where after the faulty one will not be executed!
If that is so then if you changed a vhosts setting for apache and had a notification for the apache service to reload then this would get lost.
Let's give an example (pseudo lang):
- name: Install Apache Modules
notify: Restart Apache
- name: Enable Vhosts
notify: Reload Apache
- name: Install PHP
command: GGGGGG # throws an error
When the above executes:
Apache modules are installed
Vhosts are enables
PHP tries to istall and fails
Script exits
(Where are the notifications?)
Now at this point all seems logical but again Ansible tries to be clever (no!*) stacks notifications and thus reload and restart apache will result in a single restart of apache run at the end of provisioning. That means that all notifications will fail!!!
Now up to here for some people this is fine as well. They will say hey just re-run the provisioning and the notifications will fire up, thus apache will be finally reloaded and site will be up again. This is not the case.
On the second run of the script after the code for installing php is corrected the notifications will not run due to design. Why?
This is why:
Ansible will have the tasks that executed successfully, marked as "Done/Green" thus not registering any notifications for these tasks. The provisioning will be successful and in order to trigger the notification and thus the apache restart you can do one of the following:
Run a direct command to the server via ansible or ssh
Edit the script to trigger the task
Add a separate task for that
Destroy instance of box and reprovision
This is quite frustrating because requires total cleanup of the box, or do I not understand something correctly with Ansible?
Is there another way to 'reclaim'/replay/force the notifications to execute?
Clever would be either to mark the task as incomplete and then restart the notifications or keep a separate queue with the notifications as tasks of their own.*
Yeah, that's one of the shortcomings of Ansible to say compared to Puppet. Puppet is declarative and doesn't error out like Ansible (or Chef) for that matter. It has its positives and negatives, for example Puppet takes a little bit of time before it starts running because it needs to compile its catalog.
So, you are right if your Ansible script errors out then your notification updates won't happen. The only way we've gotten around it is by using conditional statements. In your playbook you can do something like this:
- name: My cool playbook
hosts: all
vars:
force_tasks: 0
tasks:
- name: Apache install
action: apt pkg=$item state=latest
with_items:
- apache2
- apache2-mpm-prefork
- name: Restart apache
action: service name=apache2 state=restart
when: force_tasks
Then when you run your playbook you can pass force_tasks as an environment variable:
ansible-playbook -i my_inventory -e "force_tasks=True" my_ansible_playbook.yml
You can accomplish this in similar fashion with tags.
Run ansible-playbook with the --force-handlers flag. This tells Ansible to run any queued handlers even if a task fails and further processing stops. The Ansible developers plan to add this as an option to the ansible.cfg file so it can be set globally and forgotten about. I don't know what the time frame for that is.

Resources