Skip to main content
This guide assumes you finished Connect in five minutes and have a buyer account. It moves from reading sellers to launching a campaign, and shows where your code must take responsibility for durability.

1. Start with seller discovery

Discovery is read-only and safe to run as often as you like.
search
Each result carries the seller’s channels, markets, whether your account already buys from it, and whether it needs anything before it can transact (for example an account mapping). An empty list is a valid answer. To change which sellers receive your briefs, call save_connection with one intent per call:

2. Give the loop a durable owner

A model’s memory is not a database. Before your agent writes anything, decide where these live:
  • the person’s request and any approvals they gave;
  • the active customerId and advertiser id;
  • every Semicola id you create (cmp_…, exe_…, sfp1:…, mb_…);
  • the idempotencyKey for each write you attempted, and whether it finished.
When the process restarts, read those ids back and ask Semicola for the current state with get before deciding what to do next.

3. Add buying steps

1

Advertiser

save_advertiser with a name, brand domain and primary currency. If a fact is missing you get needs_input; ask the person, do not guess. Use sandbox: true while you build.
2

Draft campaign

save_campaign with the brief, flight, budget and an idempotencyKey. Save the returned campaignId and revision.
3

Request proposals

request_proposals with campaignId, expectedCampaignRevision and a new idempotencyKey. It returns at once with an execution id and a status of running.
4

Collect results

Poll with get or call request_proposals again with the same key and a resultCursor to page through what has arrived. Each seller reports quoted, products or failed.
5

Refine

refine_proposal with the proposalId and plain instructions, optionally keepProductIds, dropProductIds or a budgetDelta. The seller may decline parts of the request.
6

Stage

save_media_buy with fromProposalId for each proposal the person picked. Nothing is booked.
7

Launch, with the person

save_campaign with desiredPhase: "active" returns pending_confirmation. Show the summary; only after the person approves, call again with confirmLaunch: true. See the Campaign object guide.

Resuming a proposal request

Only one execution runs per buyer at a time. If your process dies mid-request, do not start a new one: call request_proposals again with the same idempotencyKey and you get the existing execution back, including everything that has arrived since.

Recovering from interrupted writes

If a write times out or the connection drops, the write may still have happened. Read the object first. If it is unchanged, retry with the same idempotencyKey. If it changed, compare it with what you intended, then decide. After a REVISION_CONFLICT, re-read and re-decide rather than retrying with a bumped number.

4. Test the boundaries

  • Run the whole loop against a sandbox advertiser: sellers answer, buys are placed, delivery is simulated, and no money moves.
  • Test the empty cases: no sellers, a seller that fails, an execution where every seller passes.
  • Test that your agent stops at pending_confirmation and needs_input instead of pushing through.
  • Test resuming after a restart at every step above.

Errors

Codes, partial results and safe retries.

v3 Tool Catalog

Every input field for the tools used here.