#!/usr/bin/env python3
"""ACAO 3 - Criar campanha de MARCA isolada em PAUSED. Autorizado por Renato.
Estrutura: budget R$20/dia, Search puro (sem partners/display), geo BR, idiomas
iguais SEARSH CLOUD (en/es/pt), Max Conversoes sem tCPA, 1 ad group, keywords
EXACT (marca) + PHRASE opcionais, 2 RSAs, shared negative list 12186910123.
Tudo via mutate atomico. Confirma por releitura."""
import json, uuid
from google.ads.googleads.client import GoogleAdsClient

TOK = json.load(open('/opt/mia/config/google_ads_tokens.json'))
CUSTOMER_ID = "2186917336"
NEG_LIST_RES = "customers/2186917336/sharedSets/12186910123"
FINAL_URL = "https://www.px3lab.com.br/cloud-photorf/"
BUDGET_MICROS = 20_000_000  # R$20/dia
cfg = {"developer_token": TOK["developer_token"],"client_id": TOK["client_id"],
       "client_secret": TOK["client_secret"],"refresh_token": TOK["refresh_token"],
       "login_customer_id": TOK["mcc_id"],"use_proto_plus": True}
client = GoogleAdsClient.load_from_dict(cfg)

goa = client.get_service("GoogleAdsService")

# temp resource ids
budget_tmp   = "-1"
campaign_tmp = "-2"
adgroup_tmp  = "-3"

def rn(entity, tmp):
    return f"customers/{CUSTOMER_ID}/{entity}/{tmp}"

ops = []

# 1) BUDGET
budget_op = client.get_type("MutateOperation")
b = budget_op.campaign_budget_operation.create
b.resource_name = rn("campaignBudgets", budget_tmp)
b.name = f"[BRAND] Cloudphotorf budget {uuid.uuid4().hex[:6]}"
b.amount_micros = BUDGET_MICROS
b.delivery_method = client.enums.BudgetDeliveryMethodEnum.STANDARD
b.explicitly_shared = False
ops.append(budget_op)

# 2) CAMPAIGN (PAUSED, Search puro, Max Conversoes sem tCPA)
camp_op = client.get_type("MutateOperation")
c = camp_op.campaign_operation.create
c.resource_name = rn("campaigns", campaign_tmp)
c.name = "[SEARCH][PX3][BRAND] Cloudphotorf"
c.status = client.enums.CampaignStatusEnum.PAUSED
c.advertising_channel_type = client.enums.AdvertisingChannelTypeEnum.SEARCH
c.campaign_budget = rn("campaignBudgets", budget_tmp)
c.maximize_conversions.target_cpa_micros = 0  # sem tCPA
c.contains_eu_political_advertising = client.enums.EuPoliticalAdvertisingStatusEnum.DOES_NOT_CONTAIN_EU_POLITICAL_ADVERTISING
c.network_settings.target_google_search = True
c.network_settings.target_search_network = False  # brand: so Google Search, sem partners
c.network_settings.target_content_network = False
c.network_settings.target_partner_search_network = False
ops.append(camp_op)

# 3) CAMPAIGN CRITERIA: geo BR (2076) + idiomas 1000/1003/1014
geo_op = client.get_type("MutateOperation")
g = geo_op.campaign_criterion_operation.create
g.campaign = rn("campaigns", campaign_tmp)
g.location.geo_target_constant = "geoTargetConstants/2076"
ops.append(geo_op)
for lang in ["1000","1003","1014"]:
    lop = client.get_type("MutateOperation")
    l = lop.campaign_criterion_operation.create
    l.campaign = rn("campaigns", campaign_tmp)
    l.language.language_constant = f"languageConstants/{lang}"
    ops.append(lop)

# 4) CAMPAIGN SHARED SET (negative list)
css_op = client.get_type("MutateOperation")
css = css_op.campaign_shared_set_operation.create
css.campaign = rn("campaigns", campaign_tmp)
css.shared_set = NEG_LIST_RES
ops.append(css_op)

# 5) AD GROUP
ag_op = client.get_type("MutateOperation")
ag = ag_op.ad_group_operation.create
ag.resource_name = rn("adGroups", adgroup_tmp)
ag.name = "Brand - Cloudphotorf"
ag.campaign = rn("campaigns", campaign_tmp)
ag.type_ = client.enums.AdGroupTypeEnum.SEARCH_STANDARD
ag.status = client.enums.AdGroupStatusEnum.ENABLED
ops.append(ag_op)

# 6) KEYWORDS
exact_kws = ["cloudphotorf","cloud photorf","photorf","photo rf","px3 cloudphotorf","px3 photorf"]
phrase_kws = ["cloudphotorf px3","photorf px3"]
for kw in exact_kws:
    kop = client.get_type("MutateOperation")
    k = kop.ad_group_criterion_operation.create
    k.ad_group = rn("adGroups", adgroup_tmp)
    k.status = client.enums.AdGroupCriterionStatusEnum.ENABLED
    k.keyword.text = kw
    k.keyword.match_type = client.enums.KeywordMatchTypeEnum.EXACT
    ops.append(kop)
for kw in phrase_kws:
    kop = client.get_type("MutateOperation")
    k = kop.ad_group_criterion_operation.create
    k.ad_group = rn("adGroups", adgroup_tmp)
    k.status = client.enums.AdGroupCriterionStatusEnum.ENABLED
    k.keyword.text = kw
    k.keyword.match_type = client.enums.KeywordMatchTypeEnum.PHRASE
    ops.append(kop)

# 7) RSAs (2)
def add_rsa(headlines, descriptions, path1, path2):
    op = client.get_type("MutateOperation")
    a = op.ad_group_ad_operation.create
    a.ad_group = rn("adGroups", adgroup_tmp)
    a.status = client.enums.AdGroupAdStatusEnum.ENABLED
    a.ad.final_urls.append(FINAL_URL)
    for h in headlines:
        ai = client.get_type("AdTextAsset"); ai.text = h
        a.ad.responsive_search_ad.headlines.append(ai)
    for d in descriptions:
        ai = client.get_type("AdTextAsset"); ai.text = d
        a.ad.responsive_search_ad.descriptions.append(ai)
    a.ad.responsive_search_ad.path1 = path1
    a.ad.responsive_search_ad.path2 = path2
    ops.append(op)

# RSA 1 - foco marca/reconhecimento
add_rsa(
    headlines=[
        "Cloud PhotoRF Oficial",            # <=30
        "PX3 Lab | Cloud PhotoRF",
        "PhotoRF Reconhecimento Facial",
        "Separe Fotos por Rosto com IA",
        "Software PhotoRF pra Fotografo",
        "Cloud PhotoRF da PX3 Lab",
        "Entregue Fotos Mais Rapido",
        "IA que Separa Fotos por Rosto",
        "PhotoRF pra Formatura/Evento",
        "Teste o Cloud PhotoRF",
        "Reconhecimento Facial de Fotos",
        "PX3 Lab Cloud PhotoRF",
    ],
    descriptions=[
        "Cloud PhotoRF da PX3 Lab: separe milhares de fotos por rosto com IA. Fale no WhatsApp.",
        "Software oficial de reconhecimento facial pra fotografo de formatura e eventos.",
        "Entregue as fotos certas pra cada cliente em minutos. Conheca o Cloud PhotoRF.",
        "PX3 Lab: tecnologia de separacao de fotos por rosto. Peca uma demonstracao.",
    ],
    path1="cloud-photorf", path2="px3lab",
)

# RSA 2 - foco beneficio/fotografo
add_rsa(
    headlines=[
        "PhotoRF: Fotos por Rosto",
        "PX3 Lab Reconhecimento Facial",
        "Software pra Fotografo",
        "Separacao de Fotos com IA",
        "Cloud PhotoRF - Site Oficial",
        "Chega de Separar Foto na Mao",
        "PhotoRF pra Formatura",
        "IA de Fotos da PX3 Lab",
        "Cloud PhotoRF Reconhece Rostos",
        "Fotografo: Ganhe Tempo com IA",
        "Solucao PX3 Cloud PhotoRF",
        "PhotoRF para Fotografos",
    ],
    descriptions=[
        "Fotografo de formatura: separe fotos por rosto automaticamente com o Cloud PhotoRF.",
        "PX3 Lab. IA que reconhece rostos e organiza suas fotos por cliente. Fale conosco.",
        "Menos tempo separando, mais tempo fotografando. Conheca o Cloud PhotoRF da PX3.",
        "Reconhecimento facial profissional pra entregar fotos rapido. Peca demonstracao.",
    ],
    path1="photorf", path2="px3lab",
)

# EXECUTAR mutate atomico
resp = goa.mutate(customer_id=CUSTOMER_ID, mutate_operations=ops)
print("=== MUTATE OK - resultados ===")
campaign_id = None
for res in resp.mutate_operation_responses:
    which = res._pb.WhichOneof("response")
    val = getattr(res, which)
    rname = val.resource_name
    print(f"  {which}: {rname}")
    if which == "campaign_result":
        campaign_id = rname.split("/")[-1]

print()
print("CAMPAIGN_ID:", campaign_id)
with open("/opt/mia/workspace/clientes/px3lab/ads/_brand_campaign_id.txt","w") as f:
    f.write(campaign_id or "")
