From 2355d1af8344b3bab0bff0ade201d06bf2b1b007 Mon Sep 17 00:00:00 2001 From: feng <1304903146@qq.com> Date: Thu, 27 Oct 2022 18:53:10 +0800 Subject: [PATCH] perf: gather accounts --- .../change_secret/database/mysql/main.yml | 4 + .../database/postgresql/main.yml | 8 +- .../change_secret/host/aix/main.yml | 59 ++++++++++---- .../host/{linux => posix}/main.yml | 4 +- .../host/{linux => posix}/manifest.yml | 4 +- apps/assets/automations/endpoint.py | 5 +- .../automations/gather_accounts/__init__.py | 0 .../gather_accounts/database/mysql/main.yml | 22 ++++++ .../database/mysql/manifest.yml | 6 ++ .../database/postgresql/main.yml | 23 ++++++ .../database/postgresql/manifest.yml | 6 ++ .../automations/gather_accounts/filter.py | 56 +++++++++++++ .../gather_accounts/host/posix/main.yml | 14 ++++ .../gather_accounts/host/posix/manifest.yml | 7 ++ .../gather_accounts/host/windows/main.yml | 18 +++++ .../gather_accounts/host/windows/manifest.yml | 7 ++ .../automations/gather_accounts/manager.py | 45 +++++++++++ .../gather_facts/database/mysql/main.yml | 2 +- .../gather_facts/database/postgresql/main.yml | 4 +- .../gather_facts/host/posix/main.yml | 2 +- apps/assets/automations/ping/manager.py | 78 ++----------------- apps/assets/const/automation.py | 2 +- apps/assets/const/types.py | 1 + .../migrations/0111_auto_20221027_1053.py | 29 +++++++ apps/assets/models/automations/__init__.py | 1 + apps/assets/models/automations/base.py | 3 +- .../models/automations/gather_accounts.py | 15 ++++ apps/ops/ansible/inventory.py | 6 +- 28 files changed, 328 insertions(+), 103 deletions(-) rename apps/assets/automations/change_secret/host/{linux => posix}/main.yml (95%) rename apps/assets/automations/change_secret/host/{linux => posix}/manifest.yml (52%) create mode 100644 apps/assets/automations/gather_accounts/__init__.py create mode 100644 apps/assets/automations/gather_accounts/database/mysql/main.yml create mode 100644 apps/assets/automations/gather_accounts/database/mysql/manifest.yml create mode 100644 apps/assets/automations/gather_accounts/database/postgresql/main.yml create mode 100644 apps/assets/automations/gather_accounts/database/postgresql/manifest.yml create mode 100644 apps/assets/automations/gather_accounts/filter.py create mode 100644 apps/assets/automations/gather_accounts/host/posix/main.yml create mode 100644 apps/assets/automations/gather_accounts/host/posix/manifest.yml create mode 100644 apps/assets/automations/gather_accounts/host/windows/main.yml create mode 100644 apps/assets/automations/gather_accounts/host/windows/manifest.yml create mode 100644 apps/assets/automations/gather_accounts/manager.py create mode 100644 apps/assets/migrations/0111_auto_20221027_1053.py create mode 100644 apps/assets/models/automations/gather_accounts.py diff --git a/apps/assets/automations/change_secret/database/mysql/main.yml b/apps/assets/automations/change_secret/database/mysql/main.yml index 39560a383..c76b53b08 100644 --- a/apps/assets/automations/change_secret/database/mysql/main.yml +++ b/apps/assets/automations/change_secret/database/mysql/main.yml @@ -27,6 +27,7 @@ password: "{{ account.secret }}" host: "%" when: db_info is succeeded + register: change_info - name: Verify password community.mysql.mysql_info: @@ -35,3 +36,6 @@ login_host: "{{ jms_asset.address }}" login_port: "{{ jms_asset.port }}" filter: version + when: + - db_info is succeeded + - change_info is succeeded \ No newline at end of file diff --git a/apps/assets/automations/change_secret/database/postgresql/main.yml b/apps/assets/automations/change_secret/database/postgresql/main.yml index 816d4c0e2..40c326704 100644 --- a/apps/assets/automations/change_secret/database/postgresql/main.yml +++ b/apps/assets/automations/change_secret/database/postgresql/main.yml @@ -1,8 +1,8 @@ - hosts: postgre gather_facts: no vars: -# ansible_python_interpreter: /usr/local/bin/python - ansible_python_interpreter: /Users/xiaofeng/Desktop/jumpserver/venv/bin/python + ansible_python_interpreter: /usr/local/bin/python + tasks: - name: Test PostgreSQL connection community.postgresql.postgresql_ping: @@ -37,4 +37,6 @@ login_host: "{{ jms_asset.address }}" login_port: "{{ jms_asset.port }}" db: "{{ jms_asset.database }}" - when: db_info is succeeded and change_info is changed + when: + - db_info is succeeded + - change_info is succeeded diff --git a/apps/assets/automations/change_secret/host/aix/main.yml b/apps/assets/automations/change_secret/host/aix/main.yml index 41e093df8..1a4e6a6a4 100644 --- a/apps/assets/automations/change_secret/host/aix/main.yml +++ b/apps/assets/automations/change_secret/host/aix/main.yml @@ -1,29 +1,58 @@ - hosts: demo + gather_facts: no tasks: - - name: ping + - name: Test privileged account ansible.builtin.ping: - - #- name: print variables - # debug: - # msg: "Username: {{ account.username }}, Password: {{ account.password }}" + # + # - name: print variables + # debug: + # msg: "Username: {{ account.username }}, Secret: {{ account.secret }}, Secret type: {{ secret_type }}" - name: Change password - user: + ansible.builtin.user: name: "{{ account.username }}" - password: "{{ account.password | password_hash('des') }}" + password: "{{ account.secret | password_hash('sha512') }}" update_password: always - when: account.password + when: secret_type == "password" - - name: Change public key - authorized_key: + - name: create user If it already exists, no operation will be performed + ansible.builtin.user: + name: "{{ account.username }}" + when: secret_type == "ssh_key" + + - name: remove jumpserver ssh key + ansible.builtin.lineinfile: + dest: "{{ kwargs.dest }}" + regexp: "{{ kwargs.regexp }}" + state: absent + when: + - secret_type == "ssh_key" + - kwargs.strategy == "set_jms" + + - name: Change SSH key + ansible.builtin.authorized_key: user: "{{ account.username }}" - key: "{{ account.public_key }}" - state: present - when: account.public_key + key: "{{ account.secret }}" + exclusive: "{{ kwargs.exclusive }}" + when: secret_type == "ssh_key" + + - name: Refresh connection + ansible.builtin.meta: reset_connection - name: Verify password ansible.builtin.ping: + become: no vars: ansible_user: "{{ account.username }}" - ansible_pass: "{{ account.password }}" - ansible_ssh_connection: paramiko + ansible_password: "{{ account.secret }}" + ansible_become: no + when: secret_type == "password" + + - name: Verify SSH key + ansible.builtin.ping: + become: no + vars: + ansible_user: "{{ account.username }}" + ansible_ssh_private_key_file: "{{ account.private_key_path }}" + ansible_become: no + when: secret_type == "ssh_key" diff --git a/apps/assets/automations/change_secret/host/linux/main.yml b/apps/assets/automations/change_secret/host/posix/main.yml similarity index 95% rename from apps/assets/automations/change_secret/host/linux/main.yml rename to apps/assets/automations/change_secret/host/posix/main.yml index d295079ba..1a4e6a6a4 100644 --- a/apps/assets/automations/change_secret/host/linux/main.yml +++ b/apps/assets/automations/change_secret/host/posix/main.yml @@ -25,7 +25,9 @@ dest: "{{ kwargs.dest }}" regexp: "{{ kwargs.regexp }}" state: absent - when: secret_type == "ssh_key" and kwargs.strategy == "set_jms" + when: + - secret_type == "ssh_key" + - kwargs.strategy == "set_jms" - name: Change SSH key ansible.builtin.authorized_key: diff --git a/apps/assets/automations/change_secret/host/linux/manifest.yml b/apps/assets/automations/change_secret/host/posix/manifest.yml similarity index 52% rename from apps/assets/automations/change_secret/host/linux/manifest.yml rename to apps/assets/automations/change_secret/host/posix/manifest.yml index afd9b9671..491fb14a2 100644 --- a/apps/assets/automations/change_secret/host/linux/manifest.yml +++ b/apps/assets/automations/change_secret/host/posix/manifest.yml @@ -1,5 +1,5 @@ -id: change_secret_linux -name: Change password for Linux +id: change_secret_posix +name: Change secret for posix category: host type: - unix diff --git a/apps/assets/automations/endpoint.py b/apps/assets/automations/endpoint.py index 0efbc55ea..11330370a 100644 --- a/apps/assets/automations/endpoint.py +++ b/apps/assets/automations/endpoint.py @@ -1,8 +1,6 @@ -# from .backup.manager import AccountBackupExecutionManager -# -# from .change_secret.manager import ChangeSecretManager from .gather_facts.manager import GatherFactsManager +from .gather_accounts.manager import GatherAccountsManager from ..const import AutomationTypes @@ -10,6 +8,7 @@ class ExecutionManager: manager_type_mapper = { AutomationTypes.change_secret: ChangeSecretManager, AutomationTypes.gather_facts: GatherFactsManager, + AutomationTypes.gather_accounts: GatherAccountsManager, } def __init__(self, execution): diff --git a/apps/assets/automations/gather_accounts/__init__.py b/apps/assets/automations/gather_accounts/__init__.py new file mode 100644 index 000000000..e69de29bb diff --git a/apps/assets/automations/gather_accounts/database/mysql/main.yml b/apps/assets/automations/gather_accounts/database/mysql/main.yml new file mode 100644 index 000000000..fc61d26fc --- /dev/null +++ b/apps/assets/automations/gather_accounts/database/mysql/main.yml @@ -0,0 +1,22 @@ +- hosts: mysql + gather_facts: no + vars: +# ansible_python_interpreter: /usr/local/bin/python + ansible_python_interpreter: /Users/xiaofeng/Desktop/jumpserver/venv/bin/python + + tasks: + - name: Get info + community.mysql.mysql_info: + login_user: "{{ jms_account.username }}" + login_password: "{{ jms_account.secret }}" + login_host: "{{ jms_asset.address }}" + login_port: "{{ jms_asset.port }}" + filter: users + register: db_info + + - name: Define info by set_fact + set_fact: + info: "{{ db_info.users }}" + + - debug: + var: info diff --git a/apps/assets/automations/gather_accounts/database/mysql/manifest.yml b/apps/assets/automations/gather_accounts/database/mysql/manifest.yml new file mode 100644 index 000000000..e69cca67b --- /dev/null +++ b/apps/assets/automations/gather_accounts/database/mysql/manifest.yml @@ -0,0 +1,6 @@ +id: gather_accounts_mysql +name: Gather account from MySQL +category: database +type: + - mysql +method: gather_accounts diff --git a/apps/assets/automations/gather_accounts/database/postgresql/main.yml b/apps/assets/automations/gather_accounts/database/postgresql/main.yml new file mode 100644 index 000000000..c5680f6b3 --- /dev/null +++ b/apps/assets/automations/gather_accounts/database/postgresql/main.yml @@ -0,0 +1,23 @@ +- hosts: postgresql + gather_facts: no + vars: +# ansible_python_interpreter: /usr/local/bin/python + ansible_python_interpreter: /Users/xiaofeng/Desktop/jumpserver/venv/bin/python + + tasks: + - name: Get info + community.postgresql.postgresql_info: + login_user: "{{ jms_account.username }}" + login_password: "{{ jms_account.secret }}" + login_host: "{{ jms_asset.address }}" + login_port: "{{ jms_asset.port }}" + login_db: "{{ jms_asset.database }}" + filter: "roles" + register: db_info + + - name: Define info by set_fact + set_fact: + info: "{{ db_info.roles }}" + + - debug: + var: info diff --git a/apps/assets/automations/gather_accounts/database/postgresql/manifest.yml b/apps/assets/automations/gather_accounts/database/postgresql/manifest.yml new file mode 100644 index 000000000..3e563053a --- /dev/null +++ b/apps/assets/automations/gather_accounts/database/postgresql/manifest.yml @@ -0,0 +1,6 @@ +id: gather_accounts_postgresql +name: Gather account for PostgreSQL +category: database +type: + - postgresql +method: gather_accounts diff --git a/apps/assets/automations/gather_accounts/filter.py b/apps/assets/automations/gather_accounts/filter.py new file mode 100644 index 000000000..0c8f32536 --- /dev/null +++ b/apps/assets/automations/gather_accounts/filter.py @@ -0,0 +1,56 @@ +from django.utils import timezone + +__all__ = ['GatherAccountsFilter'] + + +# TODO 后期会挪到playbook中 +class GatherAccountsFilter: + + def __init__(self, tp): + self.tp = tp + + @staticmethod + def mysql_filter(info): + result = {} + for _, user_dict in info.items(): + for username, data in user_dict.items(): + if data.get('account_locked') == 'N': + result[username] = {} + return result + + @staticmethod + def postgresql_filter(info): + result = {} + for username in info: + result[username] = {} + return result + + @staticmethod + def posix_filter(info): + result = {} + for line in info: + data = line.split('@') + if len(data) != 3: + continue + username, address, dt = data + date = timezone.datetime.strptime(f'{dt} +0800', '%b %d %H:%M:%S %Y %z') + result[username] = {'address': address, 'date': date} + return result + + @staticmethod + def windows_filter(info): + # TODO + result = {} + return result + + def run(self, method_id_meta_mapper, info): + run_method_name = None + for k, v in method_id_meta_mapper.items(): + if self.tp not in v['type']: + continue + run_method_name = k.replace(f'{v["method"]}_', '') + + if not run_method_name: + return info + + return getattr(self, f'{run_method_name}_filter')(info) diff --git a/apps/assets/automations/gather_accounts/host/posix/main.yml b/apps/assets/automations/gather_accounts/host/posix/main.yml new file mode 100644 index 000000000..97326431d --- /dev/null +++ b/apps/assets/automations/gather_accounts/host/posix/main.yml @@ -0,0 +1,14 @@ +- hosts: demo + gather_facts: no + tasks: + - name: Gather posix account + ansible.builtin.win_shell: + cmd: net user + register: result + + - name: Define info by set_fact + ansible.builtin.set_fact: + info: "{{ result.stdout_lines }}" + + - debug: + var: info \ No newline at end of file diff --git a/apps/assets/automations/gather_accounts/host/posix/manifest.yml b/apps/assets/automations/gather_accounts/host/posix/manifest.yml new file mode 100644 index 000000000..a761c9796 --- /dev/null +++ b/apps/assets/automations/gather_accounts/host/posix/manifest.yml @@ -0,0 +1,7 @@ +id: gather_accounts_posix +name: Gather posix account +category: host +type: + - linux + - unix +method: gather_accounts diff --git a/apps/assets/automations/gather_accounts/host/windows/main.yml b/apps/assets/automations/gather_accounts/host/windows/main.yml new file mode 100644 index 000000000..377ffd10a --- /dev/null +++ b/apps/assets/automations/gather_accounts/host/windows/main.yml @@ -0,0 +1,18 @@ +- hosts: windows + gather_facts: yes + tasks: + - name: Get info + set_fact: + info: + arch: "{{ ansible_architecture2 }}" + distribution: "{{ ansible_distribution }}" + distribution_version: "{{ ansible_distribution_version }}" + kernel: "{{ ansible_kernel }}" + vendor: "{{ ansible_system_vendor }}" + model: "{{ ansible_product_name }}" + sn: "{{ ansible_product_serial }}" + cpu_vcpus: "{{ ansible_processor_vcpus }}" + memory: "{{ ansible_memtotal_mb }}" + + - debug: + var: info diff --git a/apps/assets/automations/gather_accounts/host/windows/manifest.yml b/apps/assets/automations/gather_accounts/host/windows/manifest.yml new file mode 100644 index 000000000..ffc2ef7ee --- /dev/null +++ b/apps/assets/automations/gather_accounts/host/windows/manifest.yml @@ -0,0 +1,7 @@ +id: gather_accounts_windows +name: Gather account windows +version: 1 +method: gather_accounts +category: host +type: + - windows diff --git a/apps/assets/automations/gather_accounts/manager.py b/apps/assets/automations/gather_accounts/manager.py new file mode 100644 index 000000000..d6881f96c --- /dev/null +++ b/apps/assets/automations/gather_accounts/manager.py @@ -0,0 +1,45 @@ +from common.utils import get_logger +from assets.const import AutomationTypes +from orgs.utils import tmp_to_org +from .filter import GatherAccountsFilter +from ...models import Account, GatheredUser +from ..base.manager import BasePlaybookManager + +logger = get_logger(__name__) + + +class GatherAccountsManager(BasePlaybookManager): + def __init__(self, *args, **kwargs): + super().__init__(*args, **kwargs) + self.host_asset_mapper = {} + + @classmethod + def method_type(cls): + return AutomationTypes.gather_accounts + + def host_callback(self, host, asset=None, **kwargs): + super().host_callback(host, asset=asset, **kwargs) + self.host_asset_mapper[host['name']] = asset + return host + + def filter_success_result(self, host, result): + result = GatherAccountsFilter(host).run(self.method_id_meta_mapper, result) + return result + + def on_host_success(self, host, result): + info = result.get('debug', {}).get('res', {}).get('info', {}) + asset = self.host_asset_mapper.get(host) + org_id = asset.org_id + if asset and info: + result = self.filter_success_result(host, info) + with tmp_to_org(org_id): + GatheredUser.objects.filter(asset=asset, present=True).update(present=False) + for username, data in result.items(): + defaults = {'asset': asset, 'present': True, 'username': username} + if data.get('date'): + defaults['date_last_login'] = data['date'] + if data.get('address'): + defaults['ip_last_login'] = data['address'][:32] + GatheredUser.objects.update_or_create(defaults=defaults, asset=asset, username=username) + else: + logger.error("Not found info, task name must be 'Get info': {}".format(host)) diff --git a/apps/assets/automations/gather_facts/database/mysql/main.yml b/apps/assets/automations/gather_facts/database/mysql/main.yml index c4e90835e..8ba210283 100644 --- a/apps/assets/automations/gather_facts/database/mysql/main.yml +++ b/apps/assets/automations/gather_facts/database/mysql/main.yml @@ -13,7 +13,7 @@ filter: version register: db_info - - name: Define Mysql info by set_fact + - name: Define info by set_fact set_fact: info: version: "{{ db_info.version.full }}" diff --git a/apps/assets/automations/gather_facts/database/postgresql/main.yml b/apps/assets/automations/gather_facts/database/postgresql/main.yml index 55731a4fa..82adcdc16 100644 --- a/apps/assets/automations/gather_facts/database/postgresql/main.yml +++ b/apps/assets/automations/gather_facts/database/postgresql/main.yml @@ -1,4 +1,4 @@ -- hosts: postgre +- hosts: postgresql gather_facts: no vars: ansible_python_interpreter: /usr/local/bin/python @@ -13,7 +13,7 @@ login_db: "{{ jms_asset.database }}" register: db_info - - name: Define Postgresql info by set_fact + - name: Define info by set_fact set_fact: info: version: "{{ db_info.server_version.raw }}" diff --git a/apps/assets/automations/gather_facts/host/posix/main.yml b/apps/assets/automations/gather_facts/host/posix/main.yml index f42635458..81aef9aac 100644 --- a/apps/assets/automations/gather_facts/host/posix/main.yml +++ b/apps/assets/automations/gather_facts/host/posix/main.yml @@ -1,4 +1,4 @@ -- hosts: website +- hosts: demo gather_facts: yes tasks: - name: Get info diff --git a/apps/assets/automations/ping/manager.py b/apps/assets/automations/ping/manager.py index 36017438b..84712fb44 100644 --- a/apps/assets/automations/ping/manager.py +++ b/apps/assets/automations/ping/manager.py @@ -1,75 +1,9 @@ -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 +from common.utils import get_logger +from assets.const import AutomationTypes 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) - self.playbooks = [] - - def inventory_kwargs(self): - return { - 'host_callback': 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] - method_playbook_dir_path = method['dir'] - method_playbook_dir_name = os.path.basename(method_playbook_dir_path) - sub_playbook_dir = os.path.join(os.path.dirname(self.playbook_path), method_playbook_dir_name) - shutil.copytree(method_playbook_dir_path, sub_playbook_dir) - sub_playbook_path = os.path.join(sub_playbook_dir, 'main.yml') - - with open(sub_playbook_path, 'r') as f: - host_playbook_play = yaml.safe_load(f) - - if isinstance(host_playbook_play, list): - host_playbook_play = host_playbook_play[0] - - step = 10 - hosts_grouped = [host_names[i:i+step] for i in range(0, len(host_names), step)] - for i, hosts in enumerate(hosts_grouped): - plays = [] - play = deepcopy(host_playbook_play) - play['hosts'] = ':'.join(hosts) - plays.append(play) - - playbook_path = os.path.join(sub_playbook_dir, 'part_{}.yml'.format(i)) - with open(playbook_path, 'w') as f: - yaml.safe_dump(plays, f) - self.playbooks.append(playbook_path) - - playbook.append({ - 'name': method['name'] + ' for part {}'.format(i), - 'import_playbook': os.path.join(method_playbook_dir_name, 'part_{}.yml'.format(i)) - }) - - with open(self.playbook_path, 'w') as f: - yaml.safe_dump(playbook, f) - - print("Generate playbook done: " + self.playbook_path) - - def get_runner(self): - return PlaybookRunner( - self.inventory_path, - self.playbook_path, - self.runtime_dir - ) + +logger = get_logger(__name__) +class PingManager(BasePlaybookManager): + pass diff --git a/apps/assets/const/automation.py b/apps/assets/const/automation.py index 54b3cc019..6b3b6dbd4 100644 --- a/apps/assets/const/automation.py +++ b/apps/assets/const/automation.py @@ -15,7 +15,7 @@ class AutomationTypes(TextChoices): push_account = 'push_account', _('Create account') change_secret = 'change_secret', _('Change secret') verify_account = 'verify_account', _('Verify account') - gather_account = 'gather_account', _('Gather account') + gather_accounts = 'gather_accounts', _('Gather accounts') class SecretStrategy(TextChoices): diff --git a/apps/assets/const/types.py b/apps/assets/const/types.py index b77872ad0..f9cf83b85 100644 --- a/apps/assets/const/types.py +++ b/apps/assets/const/types.py @@ -166,6 +166,7 @@ class AllTypes(ChoicesMixin): data['protocols'] = protocols automation = constraints.get('automation', {}) + enable_fields = {k: v for k, v in automation.items() if k.endswith('_enabled')} for k, v in enable_fields.items(): auto_item = k.replace('_enabled', '') diff --git a/apps/assets/migrations/0111_auto_20221027_1053.py b/apps/assets/migrations/0111_auto_20221027_1053.py new file mode 100644 index 000000000..093ddb115 --- /dev/null +++ b/apps/assets/migrations/0111_auto_20221027_1053.py @@ -0,0 +1,29 @@ +# Generated by Django 3.2.14 on 2022-10-27 02:53 + +from django.db import migrations, models +import django.db.models.deletion + + +class Migration(migrations.Migration): + + dependencies = [ + ('assets', '0110_auto_20221021_1506'), + ] + + operations = [ + migrations.CreateModel( + name='GatherAccountsAutomation', + fields=[ + ('baseautomation_ptr', models.OneToOneField(auto_created=True, on_delete=django.db.models.deletion.CASCADE, parent_link=True, primary_key=True, serialize=False, to='assets.baseautomation')), + ], + options={ + 'verbose_name': 'Gather asset accounts', + }, + bases=('assets.baseautomation',), + ), + migrations.AlterField( + model_name='baseautomation', + name='type', + field=models.CharField(choices=[('ping', 'Ping'), ('gather_facts', 'Gather facts'), ('push_account', 'Create account'), ('change_secret', 'Change secret'), ('verify_account', 'Verify account'), ('gather_accounts', 'Gather accounts')], max_length=16, verbose_name='Type'), + ), + ] diff --git a/apps/assets/models/automations/__init__.py b/apps/assets/models/automations/__init__.py index 77a885b1b..1c62bbddd 100644 --- a/apps/assets/models/automations/__init__.py +++ b/apps/assets/models/automations/__init__.py @@ -3,3 +3,4 @@ from .discovery_account import * from .push_account import * from .verify_secret import * from .gather_facts import * +from .gather_accounts import * diff --git a/apps/assets/models/automations/base.py b/apps/assets/models/automations/base.py index 1f9e1ac04..aabfd241f 100644 --- a/apps/assets/models/automations/base.py +++ b/apps/assets/models/automations/base.py @@ -10,6 +10,7 @@ from orgs.mixins.models import OrgModelMixin from ops.mixin import PeriodTaskModelMixin from assets.models import Node, Asset from assets.tasks import execute_automation +from assets.const import AutomationTypes class BaseAutomation(CommonModelMixin, PeriodTaskModelMixin, OrgModelMixin): @@ -20,7 +21,7 @@ class BaseAutomation(CommonModelMixin, PeriodTaskModelMixin, OrgModelMixin): assets = models.ManyToManyField( 'assets.Asset', blank=True, verbose_name=_("Assets") ) - type = models.CharField(max_length=16, verbose_name=_('Type')) + type = models.CharField(max_length=16, choices=AutomationTypes.choices, verbose_name=_('Type')) is_active = models.BooleanField(default=True, verbose_name=_("Is active")) comment = models.TextField(blank=True, verbose_name=_('Comment')) diff --git a/apps/assets/models/automations/gather_accounts.py b/apps/assets/models/automations/gather_accounts.py new file mode 100644 index 000000000..861031af4 --- /dev/null +++ b/apps/assets/models/automations/gather_accounts.py @@ -0,0 +1,15 @@ +from django.utils.translation import ugettext_lazy as _ + +from assets.const import AutomationTypes +from .base import BaseAutomation + +__all__ = ['GatherAccountsAutomation'] + + +class GatherAccountsAutomation(BaseAutomation): + def save(self, *args, **kwargs): + self.type = AutomationTypes.gather_accounts + super().save(*args, **kwargs) + + class Meta: + verbose_name = _("Gather asset accounts") diff --git a/apps/ops/ansible/inventory.py b/apps/ops/ansible/inventory.py index c544cfcd6..35344ad6a 100644 --- a/apps/ops/ansible/inventory.py +++ b/apps/ops/ansible/inventory.py @@ -106,7 +106,7 @@ class JMSInventory: 'jms_asset': { 'id': str(asset.id), 'name': asset.name, 'address': asset.address, 'type': asset.type, 'category': asset.category, - 'protocol': asset.protocol, 'port': asset.port, + 'protocol': asset.protocol, 'port': asset.port,'database': '', 'protocols': [{'name': p.name, 'port': p.port} for p in protocols], }, 'jms_account': { @@ -117,6 +117,10 @@ class JMSInventory: ansible_config = dict(automation.ansible_config) ansible_connection = ansible_config.get('ansible_connection', 'ssh') host.update(ansible_config) + + if platform.category == 'database': + host['jms_asset']['database'] = asset.database.db_name + gateway = None if asset.domain: gateway = asset.domain.select_gateway()