perf: 修改改密

This commit is contained in:
ibuler
2022-10-09 20:54:11 +08:00
committed by 老广
parent f921f12171
commit 4e5a7a0a25
83 changed files with 413 additions and 652 deletions

View File

@@ -0,0 +1 @@
from .methods import platform_automation_methods

View File

@@ -0,0 +1,14 @@
## all connection vars
hostname asset_name=name asset_type=type asset_primary_protocol=ssh asset_primary_port=22 asset_protocols=[]
## local connection
hostname ansible_connection=local
## local connection with gateway
hostname ansible_connection=ssh ansible_user=gateway.username ansible_port=gateway.port ansible_host=gateway.host ansible_ssh_private_key_file=gateway.key
## ssh connection for windows
hostname ansible_connection=ssh ansible_shell_type=powershell/cmd ansible_user=windows.username ansible_port=windows.port ansible_host=windows.host ansible_ssh_private_key_file=windows.key
## ssh connection
hostname ansible_user=user ansible_password=pass ansible_host=host ansible_port=port ansible_ssh_private_key_file=key ssh_args="-o StrictHostKeyChecking=no"

View File

@@ -0,0 +1,70 @@
import os
from django.conf import settings
from django.utils import timezone
from ops.ansible import JMSInventory
class BasePlaybookManager:
ansible_account_policy = 'privileged_first'
def __init__(self, execution):
self.execution = execution
self.automation = execution.automation
def get_grouped_assets(self):
return self.automation.all_assets_group_by_platform()
@property
def playbook_dir_path(self):
ansible_dir = settings.ANSIBLE_DIR
path = os.path.join(
ansible_dir, self.automation.type, self.automation.name,
timezone.now().strftime('%Y%m%d_%H%M%S')
)
return path
@property
def inventory_path(self):
return os.path.join(self.playbook_dir_path, 'inventory', 'hosts.json')
@property
def playbook_path(self):
return os.path.join(self.playbook_dir_path, 'project', 'main.yml')
def generate(self):
self.prepare_playbook_dir()
self.generate_inventory()
self.generate_playbook()
def prepare_playbook_dir(self):
inventory_dir = os.path.dirname(self.inventory_path)
playbook_dir = os.path.dirname(self.playbook_path)
for d in [inventory_dir, playbook_dir]:
if not os.path.exists(d):
os.makedirs(d, exist_ok=True, mode=0o755)
def inventory_kwargs(self):
raise NotImplemented
def generate_inventory(self):
inventory = JMSInventory(
assets=self.automation.get_all_assets(),
account_policy=self.ansible_account_policy,
**self.inventory_kwargs()
)
inventory.write_to_file(self.inventory_path)
print("Generate inventory done: {}".format(self.inventory_path))
def generate_playbook(self):
raise NotImplemented
def get_runner(self):
raise NotImplemented
def run(self, **kwargs):
self.generate()
runner = self.get_runner()
return runner.run(**kwargs)

View File

@@ -0,0 +1,29 @@
- hosts: demo
tasks:
- name: ping
ping:
#- name: print variables
# debug:
# msg: "Username: {{ account.username }}, Password: {{ account.password }}"
- name: Change password
user:
name: "{{ account.username }}"
password: "{{ account.password | password_hash('des') }}"
update_password: always
when: account.password
- name: Change public key
authorized_key:
user: "{{ account.username }}"
key: "{{ account.public_key }}"
state: present
when: account.public_key
- name: Verify password
ping:
vars:
ansible_user: "{{ account.username }}"
ansible_pass: "{{ account.password }}"
ansible_ssh_connection: paramiko

View File

@@ -0,0 +1,29 @@
- hosts: demo
tasks:
- name: ping
ping:
#- name: print variables
# debug:
# msg: "Username: {{ account.username }}, Password: {{ account.password }}"
- name: Change password
user:
name: "{{ account.username }}"
password: "{{ account.password | password_hash('des') }}"
update_password: always
when: account.password
- name: Change public key
authorized_key:
user: "{{ account.username }}"
key: "{{ account.public_key }}"
state: present
when: account.public_key
- name: Verify password
ping:
vars:
ansible_user: "{{ account.username }}"
ansible_pass: "{{ account.password }}"
ansible_ssh_connection: paramiko

View File

@@ -0,0 +1,2 @@
# all base inventory in base/base_inventory.txt
asset_name(ip)_account_username account={"username": "", "password": "xxx"} ...base_inventory_vars

View File

@@ -0,0 +1,29 @@
- hosts: demo
tasks:
- name: ping
ping:
#- name: print variables
# debug:
# msg: "Username: {{ account.username }}, Password: {{ account.password }}"
- name: Change password
user:
name: "{{ account.username }}"
password: "{{ account.password | password_hash('des') }}"
update_password: always
when: account.password
- name: Change public key
authorized_key:
user: "{{ account.username }}"
key: "{{ account.public_key }}"
state: present
when: account.public_key
- name: Verify password
ping:
vars:
ansible_user: "{{ account.username }}"
ansible_pass: "{{ account.password }}"
ansible_ssh_connection: paramiko

View File

@@ -0,0 +1,29 @@
- hosts: demo
tasks:
- name: Test privileged account
ping:
#- name: print variables
# debug:
# msg: "Username: {{ account.username }}, Password: {{ account.password }}"
- name: Change password
user:
name: "{{ account.username }}"
password: "{{ account.password | password_hash('des') }}"
update_password: always
when: account.secret_type == 'password'
- name: Change public key
authorized_key:
user: "{{ account.username }}"
key: "{{ account.public_key }}"
state: present
when: account.public_key
- name: Verify password
ping:
vars:
ansible_user: "{{ account.username }}"
ansible_pass: "{{ account.password }}"
ansible_ssh_connection: paramiko

View File

@@ -0,0 +1,29 @@
- hosts: demo
tasks:
- name: ping
ping:
#- name: print variables
# debug:
# msg: "Username: {{ account.username }}, Password: {{ account.password }}"
- name: Change password
user:
name: "{{ account.username }}"
password: "{{ account.password | password_hash('des') }}"
update_password: always
when: account.password
- name: Change public key
authorized_key:
user: "{{ account.username }}"
key: "{{ account.public_key }}"
state: present
when: account.public_key
- name: Verify password
ping:
vars:
ansible_user: "{{ account.username }}"
ansible_pass: "{{ account.password }}"
ansible_ssh_connection: paramiko

View File

@@ -0,0 +1,91 @@
import os
import shutil
from copy import deepcopy
from collections import defaultdict
import yaml
from django.utils.translation import gettext as _
from ops.ansible import PlaybookRunner, JMSInventory
from ..base.manager import BasePlaybookManager
from assets.automations.methods import platform_automation_methods
class ChangePasswordManager(BasePlaybookManager):
def __init__(self, *args, **kwargs):
super().__init__(*args, **kwargs)
self.id_method_mapper = {
method['id']: method
for method in platform_automation_methods
}
self.method_hosts_mapper = defaultdict(list)
def host_duplicator(self, host, asset=None, account=None, platform=None, **kwargs):
accounts = asset.accounts.all()
if account:
accounts = accounts.exclude(id=account.id)
if '*' not in self.automation.accounts:
accounts = accounts.filter(username__in=self.automation.accounts)
automation = platform.automation
change_password_enabled = automation and \
automation.change_password_enabled and \
automation.change_password_method and \
automation.change_password_method in self.id_method_mapper
if not change_password_enabled:
host.exclude = _('Change password disabled')
return [host]
hosts = []
for account in accounts:
h = deepcopy(host)
h['name'] += '_' + account.username
h['account'] = {
'name': account.name,
'username': account.username,
'secret_type': account.secret_type,
'secret': account.secret,
}
hosts.append(h)
self.method_hosts_mapper[automation.change_password_method].append(h['name'])
return hosts
def inventory_kwargs(self):
return {
'host_duplicator': self.host_duplicator
}
def generate_playbook(self):
playbook = []
for method_id, host_names in self.method_hosts_mapper.items():
method = self.id_method_mapper[method_id]
playbook_dir_path = method['dir']
playbook_dir_name = os.path.dirname(playbook_dir_path)
shutil.copytree(playbook_dir_path, self.playbook_dir_path)
sub_playbook_path = os.path.join(self.playbook_dir_path, playbook_dir_name, 'main.yml')
with open(sub_playbook_path, 'r') as f:
host_playbook_play = yaml.safe_load(f)
plays = []
for name in host_names:
play = deepcopy(host_playbook_play)
play['hosts'] = name
plays.append(play)
with open(sub_playbook_path, 'w') as f:
yaml.safe_dump(plays, f, default_flow_style=False)
playbook.append({
'name': method['name'],
'import_playbook': playbook_dir_name + '/' + 'main.yml'
})
with open(self.playbook_path, 'w') as f:
yaml.safe_dump(playbook, f, default_flow_style=False)
print("Generate playbook done: " + self.playbook_path)

View File

@@ -0,0 +1,7 @@
# from .backup.manager import AccountBackupExecutionManager
#
#
class ExecutionManager:
manager_type = {
}

View File

@@ -1,5 +1,6 @@
import os
import yaml
import json
from functools import partial
BASE_DIR = os.path.dirname(os.path.abspath(__file__))
@@ -62,4 +63,4 @@ platform_automation_methods = get_platform_automation_methods()
if __name__ == '__main__':
print(get_platform_automation_methods())
print(json.dumps(platform_automation_methods, indent=4))

View File

@@ -38,7 +38,7 @@ class AllTypes(ChoicesMixin):
@classmethod
def set_automation_methods(cls, category, tp, constraints):
from assets.playbooks import filter_platform_methods
from assets.automations import filter_platform_methods
automation = constraints.get('automation', {})
automation_methods = {}
for item, enabled in automation.items():

View File

@@ -10,6 +10,7 @@ from .gathered_user import *
from .favorite_asset import *
from .account import *
from .backup import *
from .automations import *
from ._user import *
# 废弃以下
# from ._authbook import *

View File

@@ -4,6 +4,7 @@
import logging
import uuid
from collections import defaultdict
from django.db import models
from django.db.models import Q
@@ -41,6 +42,12 @@ class AssetQuerySet(models.QuerySet):
def has_protocol(self, name):
return self.filter(protocols__contains=name)
def group_by_platform(self) -> dict:
groups = defaultdict(list)
for asset in self.all():
groups[asset.platform].append(asset)
return groups
class NodesRelationMixin:
NODES_CACHE_KEY = 'ASSET_NODES_{}'
@@ -126,6 +133,22 @@ class Asset(AbsConnectivity, NodesRelationMixin, JMSOrgBaseModel):
names.append(n.name + ':' + n.value)
return names
@lazyproperty
def primary_protocol(self):
return self.protocols.first()
@lazyproperty
def protocol(self):
if not self.primary_protocol:
return 'none'
return self.primary_protocol.name
@lazyproperty
def port(self):
if not self.primary_protocol:
return 0
return self.primary_protocol.port
@property
def protocols_as_list(self):
return [{'name': p.name, 'port': p.port} for p in self.protocols.all()]

View File

@@ -1,6 +1,7 @@
from django.utils.translation import ugettext_lazy as _
from ops.const import StrategyChoice
from ops.ansible.runner import PlaybookRunner
from .base import BaseAutomation

View File

@@ -8,16 +8,17 @@ from common.db.fields import EncryptJsonDictTextField
from orgs.mixins.models import OrgModelMixin, JMSOrgBaseModel
from ops.mixin import PeriodTaskModelMixin
from ops.tasks import execute_automation_strategy
from ops.task_handlers import ExecutionManager
from assets.models import Node, Asset
from assets.automations.endpoint import ExecutionManager
class BaseAutomation(JMSOrgBaseModel, PeriodTaskModelMixin):
accounts = models.JSONField(default=list, verbose_name=_("Accounts"))
nodes = models.ManyToManyField(
'assets.Node', related_name='automation_strategy', blank=True, verbose_name=_("Nodes")
'assets.Node', blank=True, verbose_name=_("Nodes")
)
assets = models.ManyToManyField(
'assets.Asset', related_name='automation_strategy', blank=True, verbose_name=_("Assets")
'assets.Asset', blank=True, verbose_name=_("Assets")
)
type = models.CharField(max_length=16, verbose_name=_('Type'))
comment = models.TextField(blank=True, verbose_name=_('Comment'))
@@ -25,6 +26,17 @@ class BaseAutomation(JMSOrgBaseModel, PeriodTaskModelMixin):
def __str__(self):
return self.name + '@' + str(self.created_by)
def get_all_assets(self):
nodes = self.nodes.all()
node_asset_ids = Node.get_nodes_all_assets(*nodes).values_list('id', flat=True)
direct_asset_ids = self.assets.all().values_list('id', flat=True)
asset_ids = set(list(direct_asset_ids) + list(node_asset_ids))
return Asset.objects.filter(id__in=asset_ids)
def all_assets_group_by_platform(self):
assets = self.get_all_assets().prefetch_related('platform')
return assets.group_by_platform()
def get_register_task(self):
name = "automation_strategy_period_{}".format(str(self.id)[:8])
task = execute_automation_strategy.name
@@ -40,13 +52,15 @@ class BaseAutomation(JMSOrgBaseModel, PeriodTaskModelMixin):
'nodes': list(self.assets.all().values_list('id', flat=True)),
}
def execute(self, trigger):
def execute(self, trigger=Trigger.manual):
try:
eid = current_task.request.id
except AttributeError:
eid = str(uuid.uuid4())
execution = AutomationStrategyExecution.objects.create(
id=eid, strategy=self, snapshot=self.to_attr_json(), trigger=trigger
execution = AutomationExecution.objects.create(
id=eid, strategy=self, trigger=trigger,
snapshot=self.to_attr_json(),
)
return execution.start()
@@ -55,22 +69,22 @@ class BaseAutomation(JMSOrgBaseModel, PeriodTaskModelMixin):
verbose_name = _("Automation plan")
class AutomationStrategyExecution(OrgModelMixin):
class AutomationExecution(OrgModelMixin):
id = models.UUIDField(default=uuid.uuid4, primary_key=True)
date_created = models.DateTimeField(auto_now_add=True)
timedelta = models.FloatField(default=0.0, verbose_name=_('Time'), null=True)
date_start = models.DateTimeField(auto_now_add=True, verbose_name=_('Date start'))
automation = models.ForeignKey(
'BaseAutomation', related_name='executions', on_delete=models.CASCADE,
verbose_name=_('Automation strategy')
)
status = models.CharField(max_length=16, default='pending')
date_created = models.DateTimeField(auto_now_add=True, verbose_name=_('Date created'))
date_start = models.DateTimeField(null=True, verbose_name=_('Date start'), db_index=True)
date_finished = models.DateTimeField(null=True, verbose_name=_("Date finished"))
snapshot = EncryptJsonDictTextField(
default=dict, blank=True, null=True, verbose_name=_('Automation snapshot')
)
strategy = models.ForeignKey(
'BaseAutomation', related_name='execution', on_delete=models.CASCADE,
verbose_name=_('Automation strategy')
)
trigger = models.CharField(
max_length=128, default=Trigger.manual, choices=Trigger.choices, verbose_name=_('Trigger mode')
max_length=128, default=Trigger.manual, choices=Trigger.choices,
verbose_name=_('Trigger mode')
)
class Meta:
@@ -83,28 +97,3 @@ class AutomationStrategyExecution(OrgModelMixin):
def start(self):
manager = ExecutionManager(execution=self)
return manager.run()
class AutomationStrategyTask(OrgModelMixin):
id = models.UUIDField(default=uuid.uuid4, primary_key=True)
asset = models.ForeignKey(
'assets.Asset', on_delete=models.CASCADE, verbose_name=_('Asset')
)
account = models.ForeignKey(
'assets.Account', on_delete=models.CASCADE, verbose_name=_('Account')
)
is_success = models.BooleanField(default=False, verbose_name=_('Is success'))
timedelta = models.FloatField(default=0.0, null=True, verbose_name=_('Time'))
date_start = models.DateTimeField(auto_now_add=True, verbose_name=_('Date start'))
reason = models.CharField(max_length=1024, blank=True, null=True, verbose_name=_('Reason'))
execution = models.ForeignKey(
'AutomationStrategyExecution', related_name='task', on_delete=models.CASCADE,
verbose_name=_('Automation strategy execution')
)
class Meta:
verbose_name = _('Automation strategy task')
@property
def handler_type(self):
return self.execution.snapshot['type']

View File

@@ -2,7 +2,7 @@ from django.db import models
from django.utils.translation import ugettext_lazy as _
from common.db import fields
from ops.const import SSHKeyStrategy, PasswordStrategy, StrategyChoice
from ops.const import PasswordStrategy, StrategyChoice
from ops.utils import generate_random_password
from .base import BaseAutomation

View File

@@ -1,33 +0,0 @@
import os
import time
import shutil
from typing import List
from django.conf import settings
from assets.models import Asset
class BaseRunner:
src_filepath: str
def __init__(self, assets: List[Asset], strategy):
self.assets = assets
self.strategy = strategy
self.temp_folder = self.temp_folder_path()
@staticmethod
def temp_folder_path():
project_dir = settings.PROJECT_DIR
tmp_dir = os.path.join(project_dir, 'tmp')
filepath = os.path.join(tmp_dir, str(time.time()))
return filepath
def del_temp_folder(self):
shutil.rmtree(self.temp_folder)
def generate_temp_playbook(self):
src = self.src_filepath
dst = os.path.join(self.temp_folder, self.strategy)
shutil.copytree(src, dst)
return dst

View File

@@ -1,47 +0,0 @@
import os
import tempfile
import shutil
from typing import List
from django.conf import settings
from assets.models import Asset
class BasePlaybookGenerator:
def __init__(self, assets: list[Asset], strategy, ansible_connection='ssh'):
self.assets = assets
self.strategy = strategy
self.playbook_dir = self.temp_folder_path()
def generate(self):
self.prepare_playbook_dir()
self.generate_inventory()
self.generate_playbook()
def prepare_playbook_dir(self):
pass
def generate_inventory(self):
pass
def generate_playbook(self):
pass
@property
def base_dir(self):
tmp_dir = os.path.join(settings.PROJECT_DIR, 'tmp')
path = os.path.join(tmp_dir, self.strategy)
return path
def temp_folder_path(self):
return tempfile.mkdtemp(dir=self.base_dir)
def del_temp_folder(self):
shutil.rmtree(self.playbook_dir)
def generate_temp_playbook(self):
src = self.src_filepath
dst = os.path.join(self.temp_folder, self.strategy)
shutil.copytree(src, dst)
return dst

View File

@@ -1,10 +0,0 @@
{% for account in accounts %}
- hosts: {{ account.asset.name }}
vars:
account:
username: {{ account.username }}
password: {{ account.password }}
public_key: {{ account.public_key }}
roles:
- change_password
{% endfor %}

View File

@@ -1,27 +0,0 @@
- name: ping
ping:
#- name: print variables
# debug:
# msg: "Username: {{ account.username }}, Password: {{ account.password }}"
- name: Change password
user:
name: "{{ account.username }}"
password: "{{ account.password | password_hash('des') }}"
update_password: always
when: account.password
- name: Change public key
authorized_key:
user: "{{ account.username }}"
key: "{{ account.public_key }}"
state: present
when: account.public_key
- name: Verify password
ping:
vars:
ansible_user: "{{ account.username }}"
ansible_pass: "{{ account.password }}"
ansible_ssh_connection: paramiko

View File

@@ -1,10 +0,0 @@
{% for account in accounts %}
- hosts: {{ account.asset.name }}
vars:
account:
username: {{ account.username }}
password: {{ account.password }}
public_key: {{ account.public_key }}
roles:
- change_password
{% endfor %}

View File

@@ -1,27 +0,0 @@
- name: ping
ping:
#- name: print variables
# debug:
# msg: "Username: {{ account.username }}, Password: {{ account.password }}"
- name: Change password
user:
name: "{{ account.username }}"
password: "{{ account.password | password_hash('des') }}"
update_password: always
when: account.password
- name: Change public key
authorized_key:
user: "{{ account.username }}"
key: "{{ account.public_key }}"
state: present
when: account.public_key
- name: Verify password
ping:
vars:
ansible_user: "{{ account.username }}"
ansible_pass: "{{ account.password }}"
ansible_ssh_connection: paramiko

View File

@@ -1,10 +0,0 @@
{% for account in accounts %}
- hosts: {{ account.asset.name }}
vars:
account:
username: {{ account.username }}
password: {{ account.password }}
public_key: {{ account.public_key }}
roles:
- change_password
{% endfor %}

View File

@@ -1,27 +0,0 @@
- name: ping
ping:
#- name: print variables
# debug:
# msg: "Username: {{ account.username }}, Password: {{ account.password }}"
- name: Change password
user:
name: "{{ account.username }}"
password: "{{ account.password | password_hash('des') }}"
update_password: always
when: account.password
- name: Change public key
authorized_key:
user: "{{ account.username }}"
key: "{{ account.public_key }}"
state: present
when: account.public_key
- name: Verify password
ping:
vars:
ansible_user: "{{ account.username }}"
ansible_pass: "{{ account.password }}"
ansible_ssh_connection: paramiko

View File

@@ -1,8 +0,0 @@
- hosts: all
vars:
account:
username: {{ account.username }}
password: {{ account.password }}
public_key: {{ account.public_key }}
roles:
- change_password

View File

@@ -1,23 +0,0 @@
- name: Check connection
ping:
- name: Change password
user:
name: "{{ account.username }}"
password: "{{ account.password | password_hash('sha512') }}"
update_password: always
when: account.password
- name: Change public key
authorized_key:
user: "{{ account.username }}"
key: "{{ account.public_key }}"
state: present
when: account.public_key
- name: Verify password
ping:
vars:
ansible_user: "{{ account.username }}"
ansible_pass: "{{ account.password }}"
ansible_ssh_connection: paramiko

View File

@@ -1,10 +0,0 @@
{% for account in accounts %}
- hosts: {{ account.asset.name }}
vars:
account:
username: {{ account.username }}
password: {{ account.password }}
public_key: {{ account.public_key }}
roles:
- change_password
{% endfor %}

View File

@@ -1,27 +0,0 @@
- name: ping
ping:
#- name: print variables
# debug:
# msg: "Username: {{ account.username }}, Password: {{ account.password }}"
- name: Change password
user:
name: "{{ account.username }}"
password: "{{ account.password | password_hash('des') }}"
update_password: always
when: account.password
- name: Change public key
authorized_key:
user: "{{ account.username }}"
key: "{{ account.public_key }}"
state: present
when: account.public_key
- name: Verify password
ping:
vars:
ansible_user: "{{ account.username }}"
ansible_pass: "{{ account.password }}"
ansible_ssh_connection: paramiko

View File

@@ -1,13 +0,0 @@
- hosts: centos
gather_facts: no
vars:
account:
username: web
password: test123
tasks:
- name: Verify password
ping:
vars:
ansible_user: "{{ account.username }}"
ansible_pass: "{{ account.password }}"

View File

@@ -1,10 +0,0 @@
id: ansible_posix_ping
name: Ansible posix ping
description: Ansible ping
category: host
type:
- linux
- unix
- macos
- bsd
method: verify_account

View File

@@ -1,13 +0,0 @@
- hosts: centos
gather_facts: no
vars:
account:
username: web
password: test123
tasks:
- name: Verify password
win_ping:
vars:
ansible_user: "{{ account.username }}"
ansible_pass: "{{ account.password }}"

View File

@@ -1,6 +0,0 @@
id: ansible_win_ping
name: Ansible win ping
category: host
type:
- windows
method: verify_account

View File

@@ -1,12 +0,0 @@
- hosts: all
vars:
connection_type: ssh
password:
value: {{ password }}
public_key:
value: {{ jms_key }}
exclusive: {{ exclusive }}
key_strategy: {{ key_strategy }}
private_key_file: {{ private_key_file }}
roles:
- linux

View File

@@ -1,36 +0,0 @@
- name: Check connection
ping:
- name: Change password
user:
name: "{{ item }}"
password: "{{ password.value | password_hash('sha512') }}"
update_password: always
with_items: "{{ usernames }}"
when: "{{ password.value }}"
- name: Change public key
authorized_key:
user: "{{ item }}"
key: "{{ lookup('file', id_rsa.pub) }}"
state: present
exclusive: "{{ public_key.exclusive }}"
with_items: "{{ usernames }}"
when: "{{ public_key.value and key_strategy != 'set_jms' }}"
- name: Change public key
lineinfile:
user: "{{ item }}"
dest: /home/{{ item }}/.ssh/authorized_keys regexp='.*{{ public_key.value }}$
state: absent
with_items: "{{ usernames }}"
when: "{{ public_key.value and key_strategy == 'set_jms' }}"
- name: Verify user
ping:
vars:
ansible_user: "{{ item }}"
ansible_pass: "{{ password.value }}"
ansible_ssh_private_key_file: "{{ private_key_file }}"
ansible_connection: "{{ connection_type | default('ssh') }}"
with_items: "{{ usernames }}"

View File

@@ -1,5 +0,0 @@
- hosts: all
vars:
connection_type: ssh
roles:
- linux

View File

@@ -1,8 +0,0 @@
- name: Verify user
ping:
vars:
ansible_user: "{{ item.username }}"
ansible_pass: "{{ item.username }}"
ansible_connection: "{{ connection_type | default('ssh') }}"
ansible_ssh_private_key_file: "{{ item.private_key_file }}"
with_items: "{{ account_info }}"

View File

@@ -1 +0,0 @@
from .endpoint import *

View File

@@ -1,10 +0,0 @@
from .backup.manager import AccountBackupExecutionManager
class ExecutionManager:
manager_type = {
'backup': AccountBackupExecutionManager
}
def __new__(cls, execution):
return AccountBackupExecutionManager(execution)