from dataclasses import dataclass from anydi import singleton from fansifter_common.auth.account import Account from fansifter_common.auth.requests import AuthRequest from fansifter_common.auth.services import AuthService from fansifter_common.auth.types import Permission from dmp.adapters.db import DefaultDB from dmp.app_connections.services import AdsConnectionService from dmp.tiktok.exceptions import ( TikTokAdAccountNotFoundError, TikTokUserAdAccountNotFoundError, ) from dmp.tiktok.models import TikTokAdReportingConnection from dmp.tiktok.repositories import ( TikTokAdAccountRepository, TikTokUserAdAccountRepository, ) from dmp.tiktok.services import ( TikTokAdReportingConnectionService, TikTokUserConnectionService, ) @dataclass class DeleteTikTokAdAccountsRequest(AuthRequest): ad_account_id: str vendor_id: int subaccount_id: int @property def account(self) -> Account: return Account(vendor_id=self.vendor_id, subaccount_id=self.subaccount_id) @singleton class DeleteTikTokAdAccountsHandler: permission = Permission("ad_account", "delete") def __init__( self, db: DefaultDB, auth_service: AuthService, ad_account_repository: TikTokAdAccountRepository, user_ad_account_repository: TikTokUserAdAccountRepository, user_connection_service: TikTokUserConnectionService, ad_reporting_connection_service: TikTokAdReportingConnectionService, ads_connection_service: AdsConnectionService, ) -> None: self.db = db self.auth_service = auth_service self.ad_account_repository = ad_account_repository self.user_ad_account_repository = user_ad_account_repository self.user_connection_service = user_connection_service self.ad_reporting_connection_service = ad_reporting_connection_service self.ads_connection_service = ads_connection_service def handle(self, request: DeleteTikTokAdAccountsRequest) -> None: self.auth_service.check_account_resource( request.identity_id, permission=self.permission, resource_id=request.ad_account_id, account=request.account, ) with self.db.transaction(): if not self.ad_account_repository.exists_by_id(request.ad_account_id): raise TikTokAdAccountNotFoundError users_ad_accounts = ( self.user_ad_account_repository.find_by_ad_account_id_and_account( ad_account_id=request.ad_account_id, vendor_id=request.vendor_id, subaccount_id=request.subaccount_id, ) ) if not users_ad_accounts: raise TikTokUserAdAccountNotFoundError all_ad_reporting_connections: list[TikTokAdReportingConnection] = [] # Delete user ad account ad_account = users_ad_accounts[0].ad_account for user_ad_account in users_ad_accounts: self.user_ad_account_repository.delete(user_ad_account) # Remove ad account from user connection self.user_connection_service.delete_user_ad_accounts( identity_id=user_ad_account.identity_id, ad_account=ad_account ) # Remove ad account from ad reporting connection ad_reporting_connections = ( self.ad_reporting_connection_service.delete_user_ad_accounts( identity_id=user_ad_account.identity_id, ad_account=ad_account ) ) if ad_reporting_connections: all_ad_reporting_connections.extend(ad_reporting_connections) for ad_reporting_connection in all_ad_reporting_connections: self.ads_connection_service.delete_fivetran_ad_account( ad_reporting_connection, ad_account.external_id ) return None