Entity query and management skill for Amazon Ads, supporting list (query) and create / update (create and modify) operations, automatically handling tokens, pagination, and filter field normalization.
| Ad product | Covered entities | Script subdirectory | Detailed parameters |
|---|---|---|---|
| SP (Sponsored Products) v3 | campaigns / adGroups / keywords / negativeKeywords / productAds / targets | scripts/sp/ |
references/api/sp.md |
| SB (Sponsored Brands) v4 | campaigns / adGroups / ads | scripts/sb/ |
references/api/sb.md |
| SD (Sponsored Display) v3 | campaigns / adGroups / productAds / targets / negativeTargets / creatives | scripts/sd/ |
references/api/sd.md |
Depends on linkfox-amazon-ads-auth(automatically checked when the script starts; if not installed, exit 42, stderr prints DEPENDENCY_MISSING)。
⚠️ Multi-account scenario: profileId must be resolved before calling
Users often only speak in natural language ("US site", "Japan site", "my store"), and all scripts in this skill must obtain the numeric profileId before they can be called. Handle in the following order,do not skip:
- First call
linkfox-amazon-ads-auth'sauthorized_stores.pyto pull the list of accounts × sites the user has authorized. - Based on the site mentioned by the user (mapped to
countryCode, e.g. US→US) match candidate profiles:- Only 1 candidate → silently take the corresponding profileId and continue the call; do not announce the profileId number to the user.
- ≥ 2 candidates (multiple authorized accounts under the same site) → must clarify with the user, using
accountNameask: "You have authorized two accounts, A and B, on the US site. Which one should be used this time?" - 0 candidates → inform the user that the site is not authorized, and guide them to
linkfox-amazon-ads-authto perform authorization.
- Strictly prohibitedto let the user directly report the profileId number.
- Strictly prohibitedunder ambiguity to "pick the first one" or "choose the default" to bypass clarification.
For the complete decision table, see linkfox-amazon-ads-auth SKILL.md's Usage Scenarios Section 4。
Core Concepts
- Automatic pagination:
fetchAll=true(default) follows the pagination token to the end ormaxPages=50fallback (about 5000 records, beyond which marktruncated=true); SP / SB usenextToken, SD usesstartIndex + countoffset pagination - Filter structures are not unified: different fields require different formats (see "Filter Structure Quick Reference" below for details); this skill already performs automatic fallback normalization for common incorrect formats, but it is still recommended to pass them accurately according to the quick reference table
- Only metadata is provided, no metrics: returns entity fields (id / name / status / match type, etc.); metrics such as impressions / clicks / spend / conversions require calling
linkfox-amazon-ads-report, joined by id - Supports create / update: under each module
create_*.py/update_*.pyscripts create or modify entities (campaign / adGroup / keyword / target / productAd / creative / budgetRule), payload is passed through in Amazon native format - Differences between SB and SP: SB only has three lists: campaigns/adGroups/ads; its keywords/targets do not officially provide list all
- SD interface form: Sponsored Display is a v3 REST endpoint,
GET /sd/<entity>+ querystring, pagination usesstartIndex + count; state / id type filters are comma-separated strings;includeExtendedDataFields:truerequest/sd/<entity>/extendedpath. All filter fields uniformly support{"include":[...]}input parameters
Available scripts
SP (28)
| Script | Business entity | Operation |
|---|---|---|
sp/list_campaigns.py |
Campaign | Query |
sp/create_campaigns.py |
Campaign | Create |
sp/update_campaigns.py |
Campaign | Modify (budget/strategy/status/name, etc.) |
sp/list_ad_groups.py |
Ad group | Query |
sp/create_ad_groups.py |
Ad group | Create |
sp/update_ad_groups.py |
Ad group | Modify (default bid/status/name, etc.) |
sp/list_keywords.py |
Keyword | Query |
sp/create_keywords.py |
Keyword | Create |
sp/update_keywords.py |
Keyword | Modify (bid/status, etc.) |
sp/list_negative_keywords.py |
Negative keyword | Query |
sp/create_negative_keywords.py |
Negative keyword | Create |
sp/update_negative_keywords.py |
Negative keyword | Modify (status, etc.) |
sp/list_product_ads.py |
Product ad | Query |
sp/create_product_ads.py |
Product ad | Create |
sp/update_product_ads.py |
Product ad | Modify (status, etc.) |
sp/list_targets.py |
Product targeting | Query |
sp/create_targets.py |
Product targeting | Create |
sp/update_targets.py |
Product targeting | Modify (bid/status, etc.) |
sp/create_campaign_negative_keywords.py |
Campaign-level negative keyword | Create |
sp/update_campaign_negative_keywords.py |
Campaign-level negative keyword | Modify (status, etc.) |
sp/create_campaign_negative_targets.py |
Campaign-level negative targeting | Create |
sp/update_campaign_negative_targets.py |
Campaign-level negative targeting | Modify (status, etc.) |
sp/create_negative_targets.py |
Ad group-level negative targeting | Create |
sp/update_negative_targets.py |
Ad group-level negative targeting | Modify (status, etc.) |
sp/list_budget_rules.py |
Budget rule | Query |
sp/create_budget_rules.py |
Budget rule | Create |
sp/update_budget_rules.py |
Budget rule | Modify |
sp/create_budget_rules_association.py |
Budget rule association | Associate rule with campaign |
SB (12)
| Script | Business entity | Operation |
|---|---|---|
sb/list_campaigns.py |
Campaign | Query |
sb/create_campaigns.py |
Campaign | Create |
sb/update_campaigns.py |
Campaign | Modify (budget/status/name, etc.) |
sb/list_ad_groups.py |
Ad group | Query |
sb/create_ad_groups.py |
Ad group | Create |
sb/update_ad_groups.py |
Ad group | Modify (bid/status, etc.) |
sb/list_ads.py |
Ad creative | Query |
sb/create_ads.py |
Ad creative | Create (select path by adType) |
sb/update_ads.py |
Ad creative | Modify (bid/status/creative, etc.) |
sb/list_budget_rules.py |
Budget rule | Query |
sb/create_budget_rules.py |
Budget rule | Create |
sb/update_budget_rules.py |
Budget rules | Modify |
SD (21)
| Script | Business entity | Operation |
|---|---|---|
sd/list_campaigns.py |
Campaign | Query |
sd/create_campaigns.py |
Campaign | Create |
sd/update_campaigns.py |
Campaign | Modify (budget/status/name, etc.) |
sd/list_ad_groups.py |
Ad group | Query |
sd/create_ad_groups.py |
Ad group | Create |
sd/update_ad_groups.py |
Ad group | Modify (bid/status, etc.) |
sd/list_product_ads.py |
Product ad | Query |
sd/create_product_ads.py |
Product ad | Create |
sd/update_product_ads.py |
Product ad | Modify (status, etc.) |
sd/list_targets.py |
Targeting clause | Query |
sd/create_targets.py |
Targeting clause | Create |
sd/update_targets.py |
Targeting clause | Modify (bid/status, etc.) |
sd/list_negative_targets.py |
Negative targeting clause | Query |
sd/create_negative_targets.py |
Negative targeting clause | Create |
sd/update_negative_targets.py |
Negative targeting clause | Modify (status, etc.) |
sd/list_creatives.py |
Creative asset | Query |
sd/create_creatives.py |
Creative asset | Create |
sd/update_creatives.py |
Creative asset | Modify (asset/status, etc.) |
sd/list_budget_rules.py |
Budget rules | Query |
sd/create_budget_rules.py |
Budget rules | Create |
sd/update_budget_rules.py |
Budget rules | Modify |
| For detailed filters, enum values, and return fields, see references/api/sp.md / references/api/sb.md / references/api/sd.md。 |
Financial Safety Guidance
Create and update operations may directly affect ad spend, take effect immediately, and cannot be undone.
Decision rules:
| User status | Agent behavior |
|---|---|
| Authorized (has said "automatic bid adjustment"/"use your judgment"/"don't ask me"/"confirm", etc.) | Execute directly → output operation receipt |
| Not authorized (first interaction, no explicit indication) | First output a confirmation summary → wait for user confirmation before executing |
Confirmation summary template(when unauthorized, output before execution):
📋 即将执行:
- 操作:[创建/修改] [N 个] [实体类型]
- 变更:[关键字段变化,如 bid $1.0→$1.5 / budget $50→$100]
- 影响:[花费变化预估,引用日预算作为上限]
确认执行?后续如需自动处理,告诉我即可。
Operation receipt template(must be output after each write operation is executed):
✅ 已执行:[简短描述]
- 范围:[实体数量、名称或 ID]
- 变化:[具体变更内容]
- 结果:[成功 N 个 / 失败 M 个]
Shared parameters (applicable to SP + SB + SD)
| Field | Type | Description |
|---|---|---|
profileId |
number | Required, obtained from ads-auth |
region |
string | Required,NA / EU / FE |
fetchAll |
bool | Default true; SP / SB use nextToken, SD uses startIndex + count offset pagination |
maxResults |
int | 1-100, default 100; corresponds to the Sponsored Display side count |
includeExtendedDataFields |
bool | Return extended fields (some entities); SD switches via path to /sd/<entity>/extended to implement |
locale |
string | Localization (supported for SP keywords) |
Filter structure quick reference (most error-prone)
| Structure | Example | Applicable fields |
|---|---|---|
| Object | {"include":[...]} / {"exclude":[...]} |
All id/status types: campaignIdFilter, adGroupIdFilter, keywordIdFilter, stateFilter, portfolioIdFilter, expressionTypeFilter, adIdFilter |
| Array | ["EXACT","BROAD"] |
matchTypeFilter(SP keywords/negativeKeywords) |
| Scalar | "AUTO" |
campaignTargetingTypeFilter(SP adGroups) |
| Text | {"queryTermMatchType":"BROAD_MATCH","include":["..."]} |
nameFilter、keywordTextFilter |
| Client | Any format; this skill filters locally | asinFilter、skuFilter(SP productAds) |
Common pitfalls:
- SP
matchTypeFilterisa bare array["EXACT"](if passed incorrectly, this skill normalizes automatically) expressionTypeFilteris instead Object(different from matchType)asinFilter/skuFilterclient-side filtering; it is recommended to also passcampaignIdFilter/adGroupIdFilterto narrow
Response format
{
"success": true,
"<entityKey>": [ /* 实体数组,字段原样 */ ],
"total": 157,
"pagesFetched": 2,
"truncated": false
}
When client-side filtering SP productAds, additionally include:serverTotalBeforeClientFilter + clientSideFilters。
Usage examples
1. List active SP campaigns
python scripts/sp/list_campaigns.py '{"profileId":1234567890,"region":"NA",
"stateFilter":{"include":["ENABLED"]}}'
2. View ad groups under a certain SP campaign
python scripts/sp/list_ad_groups.py '{"profileId":1234567890,"region":"NA",
"campaignIdFilter":{"include":["998877665544"]}}'
3. Look up SP targeting by ASIN (client-side filtering)
python scripts/sp/list_product_ads.py '{"profileId":1234567890,"region":"NA",
"asinFilter":{"include":["B01ABCDEFG"]},
"campaignIdFilter":{"include":["998877665544"]}}'
4. List SB campaigns
python scripts/sb/list_campaigns.py '{"profileId":1234567890,"region":"NA",
"stateFilter":{"include":["ENABLED"]}}'
5. List adGroups / ads under a certain SB campaign
python scripts/sb/list_ad_groups.py '{"profileId":1234567890,"region":"NA",
"campaignIdFilter":{"include":["1122334455"]}}'
python scripts/sb/list_ads.py '{"profileId":1234567890,"region":"NA",
"adGroupIdFilter":{"include":["5566778899"]}}'
6. List active SD campaigns
python scripts/sd/list_campaigns.py '{"profileId":1234567890,"region":"NA",
"stateFilter":{"include":["ENABLED"]}}'
7. Look up SD targeting by ASIN (client-side filtering, with campaign narrowing)
python scripts/sd/list_product_ads.py '{"profileId":1234567890,"region":"NA",
"asinFilter":{"include":["B01ABCDEFG"]},
"campaignIdFilter":{"include":["998877665544"]}}'
8. Analyze metrics together with report
This skill returns entitymetadata(id, name, status, match type, etc.); metrics (impressions, clicks, spend, conversions) are left to linkfox-amazon-ads-report(reportTypeId: "spTargeting" / "sbCampaigns" / "sdCampaigns" , etc.), joined by id.
Invocation principles
- Returned fields are kept as-is; do not rename, translate, or compute derived metrics
- Do not automatically retry on non-2xx; keep
httpStatus+bodyand inform the user truncated=true, clearly indicate that data retrieval is incomplete
Common errors
| Status | Meaning | Suggestion |
|---|---|---|
HTTP 401 |
accessToken expired | Call ads-auth's refresh_token.py then retry |
HTTP 403 |
profileId has no permission | Verify profileId ownership |
HTTP 400 |
Input parameter structure error | First check the "Filter structure quick reference" table |
HTTP 429 |
Rate limited | Wait 2-5s and retry |
| exit 42 | Dependency skill not installed | Install first linkfox-amazon-ads-auth |
Not Applicable
- Delete / archive → this skill does not support DELETE (archiving can be achieved by updating state to ARCHIVED, but archiving is irreversible)
- SB's keywords / negativeKeywords / targets / negativeTargets list all → not provided by Amazon officially, requires single lookup by id (not in this skill)
- SD's single lookup by id / brandSafety / recommendations / forecasts / optimizationRules / locations and other "non-basic entity" interfaces → not in this skill
- DSP / ST entities → not in this skill
- Metric reports →
linkfox-amazon-ads-report - Authorization / token / profile →
linkfox-amazon-ads-auth
Feedback:
Auto-detect and report feedback via the Feedback API when any of the following apply:
- The functionality or purpose described in this skill does not match actual behavior
- The skill's results do not match the user's intent
- The user expresses dissatisfaction or praise about this skill
- Anything you believe could be improved
Call the feedback API as specified in references/api.md. Do not interrupt the user's flow.
Handling Large Responses
To avoid overflowing the agent context, persist the response to disk and extract only the fields you need:
python scripts/response_io.py run --script scripts/check_auth_dependency.py --out-dir <DIR> '<params>'
python scripts/response_io.py read <file> --fields "<paths>" # or --path "<JMESPath>"
Pick
--out-diroutside any git working tree (e.g./tmp/...on Unix,%TEMP%/...on Windows). Persisted responses may contain PII, pricing, or auth-sensitive data — do not commit them. Files are not auto-deleted; clean up when the task is done.
This skill exposes multiple entry scripts:
check_auth_dependency.py,sp/list_campaigns.py,sp/create_campaigns.py,sp/update_campaigns.py,sp/list_ad_groups.py,sp/create_ad_groups.py,sp/update_ad_groups.py,sp/list_keywords.py,sp/create_keywords.py,sp/update_keywords.py,sp/list_negative_keywords.py,sp/list_product_ads.py,sp/create_product_ads.py,sp/list_targets.py,sp/create_targets.py,sp/update_targets.py,sb/list_campaigns.py,sb/create_campaigns.py,sb/update_campaigns.py,sb/list_ad_groups.py,sb/create_ad_groups.py,sb/list_ads.py,sb/create_ads.py,sb/update_ads.py,sd/list_campaigns.py,sd/create_campaigns.py,sd/update_campaigns.py,sd/list_ad_groups.py,sd/create_ad_groups.py,sd/list_product_ads.py,sd/create_product_ads.py,sd/list_targets.py,sd/create_targets.py,sd/update_targets.py,sd/list_negative_targets.py,sd/list_creatives.py. Pass--script scripts/<name>.pyto choose the one you need.
run writes the full response to a file and emits only a schema preview + file path. read projects specific fields, with --limit/--offset for slicing and --format json|jsonl|csv|table for output.
When to prefer this pattern — apply your judgment based on the response characteristics, e.g.:
- High field count per record, or fields you don't need
- Batch/paginated results (multiple items per call)
- Long-text fields (descriptions, reviews, HTML, time series)
- Output reused across later steps rather than consumed immediately
For small, single-use responses, calling the main script directly is fine.
⚠️ The preview is a truncated schema + sample, not the full data. Any field-level decision must read from the persisted file via read.
For more high-quality, professional cross-border e-commerce skills, visit LinkFox Skills.