ios_user: Add support for multiple sshkeys (#51173)
* Add support for multiple sshkeys Signed-off-by: NilashishC <nilashishchakraborty8@gmail.com> * Fix CI Signed-off-by: NilashishC <nilashishchakraborty8@gmail.com> * Add the keys at on go Signed-off-by: NilashishC <nilashishchakraborty8@gmail.com> * Update tests Signed-off-by: NilashishC <nilashishchakraborty8@gmail.com>
This commit is contained in:
parent
99a4a3dc33
commit
69dd03d472
2 changed files with 49 additions and 18 deletions
|
@ -102,8 +102,9 @@ options:
|
|||
aliases: ['role']
|
||||
sshkey:
|
||||
description:
|
||||
- Specifies the SSH public key to configure
|
||||
for the given username. This argument accepts a valid SSH key value.
|
||||
- Specifies one or more SSH public key(s) to configure
|
||||
for the given username.
|
||||
- This argument accepts a valid SSH key value.
|
||||
version_added: "2.7"
|
||||
nopassword:
|
||||
description:
|
||||
|
@ -139,6 +140,14 @@ EXAMPLES = """
|
|||
sshkey: "{{ lookup('file', '~/.ssh/id_rsa.pub') }}"
|
||||
state: present
|
||||
|
||||
- name: create a new user with multiple keys
|
||||
ios_user:
|
||||
name: ansible
|
||||
sshkey:
|
||||
- "{{ lookup('file', '~/.ssh/id_rsa.pub') }}"
|
||||
- "{{ lookup('file', '~/path/to/public_key') }}"
|
||||
state: present
|
||||
|
||||
- name: remove all users except admin
|
||||
ios_user:
|
||||
purge: yes
|
||||
|
@ -210,19 +219,17 @@ commands:
|
|||
- username ansible secret password
|
||||
- username admin secret admin
|
||||
"""
|
||||
from copy import deepcopy
|
||||
|
||||
import re
|
||||
import base64
|
||||
import hashlib
|
||||
|
||||
import re
|
||||
from copy import deepcopy
|
||||
from functools import partial
|
||||
|
||||
from ansible.module_utils.basic import AnsibleModule
|
||||
from ansible.module_utils.network.common.utils import remove_default_spec
|
||||
from ansible.module_utils.network.ios.ios import get_config, load_config
|
||||
from ansible.module_utils.six import iteritems
|
||||
from ansible.module_utils.network.ios.ios import ios_argument_spec, check_args
|
||||
from ansible.module_utils.six import iteritems
|
||||
|
||||
|
||||
def validate_privilege(value, module):
|
||||
|
@ -275,7 +282,8 @@ def map_obj_to_commands(updates, module):
|
|||
command.append('ip ssh pubkey-chain')
|
||||
if x:
|
||||
command.append('username %s' % want['name'])
|
||||
command.append('key-hash %s' % x)
|
||||
for item in x:
|
||||
command.append('key-hash %s' % item)
|
||||
command.append('exit')
|
||||
else:
|
||||
command.append('no username %s' % want['name'])
|
||||
|
@ -324,10 +332,15 @@ def parse_view(data):
|
|||
return match.group(1)
|
||||
|
||||
|
||||
def parse_sshkey(data):
|
||||
match = re.search(r'key-hash (\S+ \S+(?: .+)?)$', data, re.M)
|
||||
if match:
|
||||
return match.group(1)
|
||||
def parse_sshkey(data, user):
|
||||
sshregex = r'username %s(\n\s+key-hash .+$)+' % user
|
||||
sshcfg = re.search(sshregex, data, re.M)
|
||||
key_list = []
|
||||
if sshcfg:
|
||||
match = re.findall(r'key-hash (\S+ \S+(?: .+)?)$', sshcfg.group(), re.M)
|
||||
if match:
|
||||
key_list = match
|
||||
return key_list
|
||||
|
||||
|
||||
def parse_privilege(data):
|
||||
|
@ -356,9 +369,6 @@ def map_config_to_obj(module):
|
|||
regex = r'username %s .+$' % user
|
||||
cfg = re.findall(regex, data, re.M)
|
||||
cfg = '\n'.join(cfg)
|
||||
sshregex = r'username %s\n\s+key-hash .+$' % user
|
||||
sshcfg = re.findall(sshregex, data, re.M)
|
||||
sshcfg = '\n'.join(sshcfg)
|
||||
obj = {
|
||||
'name': user,
|
||||
'state': 'present',
|
||||
|
@ -366,7 +376,7 @@ def map_config_to_obj(module):
|
|||
'configured_password': None,
|
||||
'hashed_password': None,
|
||||
'password_type': parse_password_type(cfg),
|
||||
'sshkey': parse_sshkey(sshcfg),
|
||||
'sshkey': parse_sshkey(data, user),
|
||||
'privilege': parse_privilege(cfg),
|
||||
'view': parse_view(cfg)
|
||||
}
|
||||
|
@ -423,13 +433,21 @@ def map_params_to_obj(module):
|
|||
item['nopassword'] = get_value('nopassword')
|
||||
item['privilege'] = get_value('privilege')
|
||||
item['view'] = get_value('view')
|
||||
item['sshkey'] = sshkey_fingerprint(get_value('sshkey'))
|
||||
item['sshkey'] = render_key_list(get_value('sshkey'))
|
||||
item['state'] = get_value('state')
|
||||
objects.append(item)
|
||||
|
||||
return objects
|
||||
|
||||
|
||||
def render_key_list(ssh_keys):
|
||||
key_list = []
|
||||
if ssh_keys:
|
||||
for item in ssh_keys:
|
||||
key_list.append(sshkey_fingerprint(item))
|
||||
return key_list
|
||||
|
||||
|
||||
def update_objects(want, have):
|
||||
updates = list()
|
||||
for entry in want:
|
||||
|
@ -463,7 +481,7 @@ def main():
|
|||
privilege=dict(type='int'),
|
||||
view=dict(aliases=['role']),
|
||||
|
||||
sshkey=dict(),
|
||||
sshkey=dict(type='list'),
|
||||
|
||||
state=dict(default='present', choices=['present', 'absent'])
|
||||
)
|
||||
|
|
|
@ -128,3 +128,16 @@ class TestIosUserModule(TestIosModule):
|
|||
]
|
||||
result = self.execute_module(changed=True, commands=commands)
|
||||
self.assertEqual(result['commands'], commands)
|
||||
|
||||
def test_ios_user_set_sshkey_multiple(self):
|
||||
set_module_args(dict(name='ansible', sshkey=['dGVzdA==', 'eHWacB2==']))
|
||||
commands = [
|
||||
'ip ssh pubkey-chain',
|
||||
'username ansible',
|
||||
'key-hash ssh-rsa 098F6BCD4621D373CADE4E832627B4F6',
|
||||
'key-hash ssh-rsa A019918340A1E9183388D9A675603036',
|
||||
'exit',
|
||||
'exit'
|
||||
]
|
||||
result = self.execute_module(changed=True, commands=commands)
|
||||
self.assertEqual(result['commands'], commands)
|
||||
|
|
Loading…
Reference in a new issue