Manage bastion SSH known_hosts file
This attempts to manage the SSH host keys of all the hosts in the inventory. The idea here is each host in the inventory will add a ansible_ssh_host_key_ecdsa_public variable, then when we first run our bastion playbook we'll properly populate the local known_hosts file each time. Change-Id: I26e328192a7127086e514dc62a27cb946a77440b Depends-On: https://review.openstack.org/643408 Signed-off-by: Paul Belanger <pabelanger@redhat.com>
This commit is contained in:
parent
6f7db58426
commit
1d490a3729
@ -69,6 +69,10 @@ def bootstrap_server(server, key, name, group, keep, timeout):
|
||||
ansible_user = None
|
||||
|
||||
print("--- Running initial configuration on host %s ---" % ip)
|
||||
host_key = utils.nodescan(ip)
|
||||
if not host_key:
|
||||
raise Exception("Unable to find ssh-ecdsa SSH host key")
|
||||
|
||||
for username in ['ubuntu', 'centos']:
|
||||
ssh_client = utils.ssh_connect(
|
||||
ip, username, ssh_kwargs, timeout=timeout)
|
||||
@ -87,9 +91,10 @@ def bootstrap_server(server, key, name, group, keep, timeout):
|
||||
with open(runner.hosts, 'w') as inventory_file:
|
||||
inventory_file.write(
|
||||
"[{group}]\n{host} ansible_host={ip} "
|
||||
"ansible_user={user}".format(
|
||||
"ansible_user={user} "
|
||||
"ansible_ssh_host_key_ed25519_public={host_key}".format(
|
||||
group=group, host=name, ip=server.interface_ip,
|
||||
user=ansible_user))
|
||||
user=ansible_user, host_key=host_key))
|
||||
|
||||
project_dir = os.path.join(
|
||||
SCRIPT_DIR, '..', 'playbooks', 'bootstrap-ansible')
|
||||
|
@ -15,6 +15,7 @@
|
||||
# limitations under the License.
|
||||
|
||||
import socket
|
||||
import subprocess
|
||||
import time
|
||||
|
||||
import paramiko
|
||||
@ -32,6 +33,30 @@ def iterate_timeout(max_seconds, purpose):
|
||||
raise Exception("Timeout waiting for %s" % purpose)
|
||||
|
||||
|
||||
def nodescan(ip, port=22, timeout=60):
|
||||
"""Scan the IP address for public SSH keys.
|
||||
|
||||
Returns SSH host key
|
||||
"""
|
||||
|
||||
key = None
|
||||
output = None
|
||||
for count in iterate_timeout(
|
||||
timeout, "connection to %s on port %s" % (ip, port)):
|
||||
|
||||
try:
|
||||
output = subprocess.check_output(
|
||||
['ssh-keyscan', '-t', 'ed25519', '-p', str(port), str(ip)])
|
||||
if output:
|
||||
break
|
||||
except Exception as e:
|
||||
print("ssh-keyscan failure: %s", e)
|
||||
|
||||
key = output.split()[2].decode('utf8')
|
||||
|
||||
return key
|
||||
|
||||
|
||||
def ssh_connect(ip, username, connect_kwargs={}, timeout=60):
|
||||
# HPcloud may return errno 111 for about 30 seconds after adding the IP
|
||||
for count in iterate_timeout(timeout, "ssh access"):
|
||||
|
@ -12,6 +12,15 @@
|
||||
# License for the specific language governing permissions and limitations
|
||||
# under the License.
|
||||
---
|
||||
- name: Configure bastion SSH known_hosts
|
||||
hosts: bastion:!disabled
|
||||
gather_facts: false
|
||||
tasks:
|
||||
- name: Ensure SSH host keys are known
|
||||
template:
|
||||
dest: ~/.ssh/known_hosts
|
||||
src: bastion/root/.ssh/known_hosts.j2
|
||||
|
||||
- name: Bootstrap all hosts
|
||||
hosts: all:!disabled
|
||||
tasks:
|
||||
|
@ -0,0 +1,10 @@
|
||||
# This file is generated by Ansible
|
||||
# DO NOT EDIT THIS FILE BY HAND -- YOUR CHANGES WILL BE OVERWRITTEN
|
||||
#
|
||||
{% for host in groups['all'] %}
|
||||
{% if hostvars[host].ansible_host is defined %}
|
||||
{% if hostvars[host].ansible_ssh_host_key_ed25519_public is defined %}
|
||||
{{ hostvars[host].ansible_host }} ssh-ed25519 {{ hostvars[host].ansible_ssh_host_key_ed25519_public }}
|
||||
{% endif %}
|
||||
{% endif %}
|
||||
{% endfor %}
|
Loading…
x
Reference in New Issue
Block a user