line_item_update
Edit a Line Item. A real change returns that Line Item to draft, and no other.
Ask the agent to change one Line Item: its channel, its objective, its money, its audience, its dates, its ad account or its persona.
“Raise the Meta Line Item of the spring sale Campaign Plan to €3,000, and add the Netherlands.”
The agent reads the Campaign Plan to get the id and the revision of the Line Item. Then it calls line_item_update with only the fields that change. You see the Line Item as it is now. A real change returns a validated Line Item to draft. The approval of the Campaign Plan stays. A campaign that the Line Item created on Meta does not change.
Plan a campaign walks the whole job.
Reference
Update a Line Item. Omit a field to leave it alone; send null to clear it. Pass base_revision from campaign_plan_get. Any real change returns a validated line to draft, and only that line — the plan’s own approval stands. The provider objects the line already created are untouched: a live campaign is never altered from here.
Input
| Argument | Type | Required | Description |
|---|---|---|---|
advertiser_id |
string or null | no | null unlinks the ad account. |
age_max |
integer, 0 to 120 or null | no | |
age_min |
integer, 0 to 120 or null | no | |
base_revision |
integer | yes | The revision of the Line Item, as you last read it: the revision of that Line Item in lineItems of campaign_plan_get. It is not the revision of the Campaign Plan. It guards against a write over a change that another person made after your read. |
budget |
number, at least 0 or null | no | |
campaign_plan_name |
string | yes | The Campaign Plan slug — its stable per-organization handle. |
channel |
one of meta, tiktok, snapchat, google_search, google_pmax, google_display, youtube, programmatic_display, linkedin, x |
no | |
countries |
array of (string, 2 characters) | no | The array is the value — send [] to clear the geography. |
end_date |
string or null | no | null makes the line inherit the plan’s end, which can flip its budget between a total and a daily rate. That is allowed, and it returns the line to draft. |
gender |
one of all, men, women or null |
no | |
line_item_id |
string | yes | The Line Item id, as returned by campaign_plan_get. |
objective |
one of awareness, engagement, leads, sales, traffic, app_promotion |
no | |
persona_name |
string or null | no | A persona slug, looked up on the brand this plan is for; null clears it. |
start_date |
string or null | no |
Output
A successful call returns this object in structuredContent.
| Field | Type | Always present | Description |
|---|---|---|---|
lineItem |
object | yes | A Line Item: one thing that the Campaign Plan buys. |
lineItem.advertiserId |
string or null | yes | The ad account that the Line Item runs through, acc_…, or null. |
lineItem.ageMax |
number or null | yes | The highest age, or null for no upper bound. |
lineItem.ageMin |
number or null | yes | The lowest age, or null for no lower bound. |
lineItem.budget |
number or null | yes | The amount in whole units of the currency of the Campaign Plan, or null when it is not set. unit tells how to read it. |
lineItem.campaignPlanId |
string | yes | The id of the Campaign Plan that holds the Line Item, cpl_…. |
lineItem.channel |
one of meta, tiktok, snapchat, google_search, google_pmax, google_display, youtube, programmatic_display, linkedin, x |
yes | What the Line Item buys, in planning words. A channel is not a provider. |
lineItem.countries |
array of string | yes | ISO 3166-1 alpha-2 codes. An empty list means that the geography is not decided. |
lineItem.createdAt |
number | yes | Milliseconds since the Unix epoch, UTC. |
lineItem.createdBy |
string | yes | The user who added the Line Item, usr_…. |
lineItem.effectiveEndDate |
string or null | yes | The end that applies: the end date of the Line Item, else the end date of the Campaign Plan. null when neither has one. |
lineItem.effectiveStartDate |
string or null | yes | The start that applies: the start date of the Line Item, else the start date of the Campaign Plan. null when neither has one. |
lineItem.endDate |
string or null | yes | The end date of the Line Item itself, or null when the Line Item uses the end date of the Campaign Plan. |
lineItem.executable |
boolean | yes | true when AdCrunch can create objects for this channel today. It is not a promise that a create succeeds. |
lineItem.executions |
array of object | yes | The provider objects that the Line Item created, as line_item_record_execution recorded them. The list does not tell whether the Line Item is complete. |
lineItem.executions[].advertiserId |
string | yes | The ad account that holds the object, acc_…. |
lineItem.executions[].createdAt |
number | yes | When AdCrunch recorded the object, in milliseconds since the Unix epoch, UTC. |
lineItem.executions[].entityId |
string | yes | The id of the object on the provider, with no prefix. get_entity and list_entities use the same id. |
lineItem.executions[].entityType |
string | yes | The word of the provider for the level of the object, such as campaign, adset or ad. |
lineItem.executions[].id |
string | yes | The id of the record, exe_…. |
lineItem.executions[].mutationWorkflowId |
string or null | yes | The workflowId of the change that created the object, or null when the record names none. |
lineItem.executions[].provider |
one of meta, gads, tiktok, x, openai, snapchat, dv360 |
yes | The provider of the object. |
lineItem.gender |
one of all, men, women or null |
yes | The gender of the audience, or null when it is not decided. null executes as all. |
lineItem.id |
string | yes | The id of the Line Item, lni_…. |
lineItem.objective |
one of awareness, engagement, leads, sales, traffic, app_promotion |
yes | What the Line Item is for. |
lineItem.personaId |
string or null | yes | The Persona that explains the audience, psn_…, or null. The countries, the ages and the gender are what execute. |
lineItem.provider |
one of meta, gads, tiktok, x, openai, snapchat, dv360 or null |
yes | The provider that sells the channel, or null when AdCrunch has no integration for it. |
lineItem.revision |
number | yes | The revision of the Line Item. It increments when the Line Item changes. Send it as base_revision to line_item_update, line_item_delete or line_item_validate. |
lineItem.startDate |
string or null | yes | The start date of the Line Item itself, or null when the Line Item uses the start date of the Campaign Plan. |
lineItem.status |
one of draft, validated |
yes | validated when a person cleared the Line Item to run, by line_item_validate or by the approval of the Campaign Plan. A real change to the Line Item returns it to draft. |
lineItem.unit |
one of total, daily |
yes | How to read budget. total when the Line Item has an effective end date: the budget is for the whole period. daily when it has none: the budget is for each day. |
lineItem.updatedAt |
number or null | yes | When the Line Item last changed, or null when it never changed. |
Failure codes
A failed call has isError set, and structuredContent.error holds one of these codes. Errors describes the shape of a failed call.
not_foundinvalid_countriesinvalid_age_rangeinvalid_amountinvalid_windowpersona_not_in_brandadvertiser_not_ownedrevision_mismatchforbiddeninvalid_requestinternal_error
Scope
The token must hold campaign_plan:write. Auth & scopes lists each scope.
Annotations
A client reads these hints. A hint that the tool does not declare has the default value of the MCP specification.
- Writes. The tool can change data.
- Destructive. The tool can make a change that you cannot undo. A client can ask you to confirm before it calls the tool.
- Not idempotent. A second call with the same arguments can change more.
- Closed world. The tool reads and writes the data of AdCrunch only.
Example
The arguments:
{
"base_revision": 2,
"budget": 3000,
"campaign_plan_name": "spring-sale",
"countries": [
"FR",
"BE",
"NL"
],
"line_item_id": "lni_2d9e77"
}
The result, in structuredContent:
{
"lineItem": {
"advertiserId": "acc_1203456789012345",
"ageMax": 44,
"ageMin": 25,
"budget": 3000,
"campaignPlanId": "cpl_4e1a08",
"channel": "meta",
"countries": [
"FR",
"BE",
"NL"
],
"createdAt": 1768435200000,
"createdBy": "usr_5d2b71",
"effectiveEndDate": "2026-05-31",
"effectiveStartDate": "2026-03-01",
"endDate": null,
"executable": true,
"executions": [],
"gender": "all",
"id": "lni_2d9e77",
"objective": "sales",
"personaId": "psn_8c4a20",
"provider": "meta",
"revision": 3,
"startDate": null,
"status": "draft",
"unit": "total",
"updatedAt": 1769644800000
}
}