diff --git a/apps/accounts/serializers/account/template.py b/apps/accounts/serializers/account/template.py index 45190f051..e9804876b 100644 --- a/apps/accounts/serializers/account/template.py +++ b/apps/accounts/serializers/account/template.py @@ -1,3 +1,5 @@ +from django.db.utils import IntegrityError + from accounts.models import AccountTemplate, Account from assets.models import Asset from common.serializers import SecretReadableMixin @@ -9,37 +11,66 @@ class AccountTemplateSerializer(BaseAccountSerializer): model = AccountTemplate @staticmethod - def bulk_update_accounts(instance, diff): + def account_save(data, account): + for field, value in data.items(): + setattr(account, field, value) + try: + account.save(update_fields=list(data.keys())) + except IntegrityError: + pass + + # TODO 数据库访问的太多了 后期优化 + def bulk_update_accounts(self, instance, diff): accounts = Account.objects.filter(source_id=instance.id) if not accounts: return - secret_type = diff.pop('secret_type', None) diff.pop('secret', None) + name = diff.pop('name', None) + username = diff.pop('username', None) + secret_type = diff.pop('secret_type', None) update_accounts = [] for account in accounts: for field, value in diff.items(): setattr(account, field, value) update_accounts.append(account) + if update_accounts: Account.objects.bulk_update(update_accounts, diff.keys()) - if secret_type is None: - return + if name: + for account in accounts: + data = {'name': name} + self.account_save(data, account) - update_accounts = [] + if secret_type and username: + asset_ids_supports = self.get_asset_ids_supports(accounts, secret_type) + for account in accounts: + asset_id = account.asset_id + if asset_id not in asset_ids_supports: + data = {'username': username} + self.account_save(data, account) + continue + data = {'username': username, 'secret_type': secret_type, 'secret': instance.secret} + self.account_save(data, account) + elif secret_type: + asset_ids_supports = self.get_asset_ids_supports(accounts, secret_type) + for account in accounts: + asset_id = account.asset_id + if asset_id not in asset_ids_supports: + continue + data = {'secret_type': secret_type, 'secret': instance.secret} + self.account_save(data, account) + elif username: + for account in accounts: + data = {'username': username} + self.account_save(data, account) + + @staticmethod + def get_asset_ids_supports(accounts, secret_type): asset_ids = accounts.values_list('asset_id', flat=True) secret_type_supports = Asset.get_secret_type_assets(asset_ids, secret_type) - asset_ids_supports = [asset.id for asset in secret_type_supports] - for account in accounts: - asset_id = account.asset_id - if asset_id not in asset_ids_supports: - continue - account.secret_type = secret_type - account.secret = instance.secret - update_accounts.append(account) - if update_accounts: - Account.objects.bulk_update(update_accounts, ['secret', 'secret_type']) + return [asset.id for asset in secret_type_supports] def update(self, instance, validated_data): diff = {