Creative Testing
Run multi-creative campaigns to test variations
Multi-creative campaigns (creative testing)
For creative A/B testing, don't spin up one campaign per creative, that fragments the budget across parallel ad sets and none of them exit Meta's learning phase (~50 conversions/week required). Instead, pass creatives[] on POST /v1/ads/create to get 1 campaign → 1 ad set → N ads sharing the same budget, targeting, and schedule. Meta's delivery algorithm allocates budget across the creatives inside the single ad set.
const result = await zernio.ads.createStandaloneAd({
body: {
accountId: 'acc_metaads_123',
adAccountId: 'act_1234567890',
name: 'Spring Launch',
goal: 'traffic',
budgetAmount: 100,
budgetType: 'daily',
countries: ['AR'],
ageMin: 25,
ageMax: 45,
creatives: [
{ headline: 'Spring - 30% off', body: 'Limited time.', imageUrl: 'https://cdn.example.com/a.jpg', linkUrl: 'https://example.com/a', callToAction: 'SHOP_NOW' },
{ headline: 'Just for you', body: 'Curated picks.', imageUrl: 'https://cdn.example.com/b.jpg', linkUrl: 'https://example.com/b', callToAction: 'SHOP_NOW' },
{ headline: 'Free shipping', body: 'This week only.', imageUrl: 'https://cdn.example.com/c.jpg', linkUrl: 'https://example.com/c', callToAction: 'SHOP_NOW' },
],
},
});result = client.ads.create_standalone_ad(
account_id="acc_metaads_123",
ad_account_id="act_1234567890",
name="Spring Launch",
goal="traffic",
budget_amount=100,
budget_type="daily",
countries=["AR"],
age_min=25,
age_max=45,
creatives=[
{"headline": "Spring - 30% off", "body": "Limited time.", "imageUrl": "https://cdn.example.com/a.jpg", "linkUrl": "https://example.com/a", "callToAction": "SHOP_NOW"},
{"headline": "Just for you", "body": "Curated picks.", "imageUrl": "https://cdn.example.com/b.jpg", "linkUrl": "https://example.com/b", "callToAction": "SHOP_NOW"},
{"headline": "Free shipping", "body": "This week only.", "imageUrl": "https://cdn.example.com/c.jpg", "linkUrl": "https://example.com/c", "callToAction": "SHOP_NOW"},
],
)curl -X POST "https://zernio.com/api/v1/ads/create" \
-H "Authorization: Bearer YOUR_API_KEY" \
-H "Content-Type: application/json" \
-d '{
"accountId": "acc_metaads_123",
"adAccountId": "act_1234567890",
"name": "Spring Launch",
"goal": "traffic",
"budgetAmount": 100,
"budgetType": "daily",
"countries": ["AR"],
"ageMin": 25,
"ageMax": 45,
"creatives": [
{ "headline": "Spring - 30% off", "body": "Limited time.", "imageUrl": "https://cdn.example.com/a.jpg", "linkUrl": "https://example.com/a", "callToAction": "SHOP_NOW" },
{ "headline": "Just for you", "body": "Curated picks.", "imageUrl": "https://cdn.example.com/b.jpg", "linkUrl": "https://example.com/b", "callToAction": "SHOP_NOW" },
{ "headline": "Free shipping", "body": "This week only.", "imageUrl": "https://cdn.example.com/c.jpg", "linkUrl": "https://example.com/c", "callToAction": "SHOP_NOW" }
]
}'Returns { ads: [...], platformCampaignId, platformAdSetId, message }, N Ad documents sharing the same platformCampaignId + platformAdSetId. Each ad's name is "<name> #N" (e.g. "Spring Launch #1", "Spring Launch #2"). To add more creatives later without spinning up a new campaign, use the attach shape below.
Meta-only today. Non-Meta platforms return 400.