Skip to main content

Paid-media campaign lifecycle

Erdo can read a connected ad account in full — campaigns, spend, status, keywords — and it can also act on a campaign: pause it, enable it, or change its daily budget. The lifecycle endpoints expose exactly those three actions over /v1 (and the matching MCP tools), so an external product or script can drive a decision the evidence argues for instead of someone performing it by hand in the provider’s console. Every lifecycle call goes through the same approval gate that governs agent-proposed changes. There is one gated path into a customer’s ad account, not two: the /v1 call files the very action an agent’s tool would file — same action key, same input, same deduplication — and a caller with an API key is never more trusted than an agent. Supported providers: google_ads. Any other provider is rejected with an unimplemented error rather than silently ignored.

The two outcomes

What happens depends on whether your organization has granted a standing always-approve policy for the action (the same standing grant you create by choosing “always allow” when deciding an agent’s approval):
  • No standing policy — propose. The call does not touch the provider. It files a pending approval request and returns status: "pending_approval" with the approval_request_id — accepted, not performed (202 semantics, expressed in the body). The approval appears in the activity feed and on GET /v1/approvals, stamped with subject_resource_type: "paid_media_campaign" and the campaign’s external id so you can list everything awaiting decision about one campaign. When a human approves it — feed, CLI, or POST /v1/approvals/{id}/decide — the exact stored action executes, under the approver’s identity. A rejection is terminal and nothing reaches the provider.
  • Standing policy — execute. The call executes immediately through the same integration handler an agent-run approval would execute, and returns status: "executed" with the provider’s result.
Re-proposing the same change while one is pending folds onto the existing request instead of filing a duplicate — including a budget change with a different amount, which is still “the same decision to review” and updates the pending card rather than stacking a second one.

Set campaign status

  • externalID (path) — the provider’s campaign id.
  • providergoogle_ads.
  • customer_id — the provider account the campaign belongs to (campaign ids are only unique within an account). Required.
  • statuspaused or enabled. Removal is deliberately not exposed: deleting a campaign is destructive, not lifecycle.
  • reason (optional) — shown on the approval card as the why beside the what, so the approver reads the evidence, not just the action.

Set campaign daily budget

  • daily_budget_micros — the new daily budget in micros of the account currency (50000000 = $50.00). Must be positive.

Response

or, when a standing policy covers the action:

Following up on a pending action

List what is awaiting decision about one campaign:
Decide it:
Approving with a broader scope (always_org, with parameter constraints) creates the standing policy that makes subsequent identical calls execute immediately — see Approvals and Autonomy.

MCP tools

The same capability is available as MCP tools:
  • erdo_set_paid_media_campaign_status — provider, customer id, campaign id, paused/enabled, optional reason.
  • erdo_set_paid_media_campaign_budget — provider, customer id, campaign id, daily budget in micros, optional reason.