adside 0.0.0-stage → 0.1.0

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
@@ -0,0 +1,25 @@
1
+ #!/usr/bin/env node
2
+ import{Command as e}from"commander";import{createHash as t,randomBytes as n,randomUUID as r}from"node:crypto";import{chmod as i,mkdir as a,open as o,readFile as s,rename as c,rm as l,stat as u,utimes as d,writeFile as f}from"node:fs/promises";import{createWriteStream as p,openAsBlob as m}from"node:fs";import h from"node:path";import{pipeline as g}from"node:stream/promises";import{spawn as _}from"node:child_process";import{createInterface as v}from"node:readline/promises";import y from"node:os";import{createServer as b}from"node:http";async function x(e,t,n){let r=e.commands.find(e=>e.id===t);if(!r||r.transport.type!==`rest`)throw Error(`Missing REST contract: ${t}`);let i=await e.callRest(r.transport.method,r.transport.path,n,{auth:r.transport.auth,parameters:r.options,contentType:r.transport.requestContentType});if(i.kind!==`json`)throw Error(`Expected JSON from ${t}`);return S(i.data)}function S(e){if(!e||typeof e!=`object`||Array.isArray(e))throw Error(`Invalid API response`);return e}function C(e){if(typeof e!=`string`||!e)throw Error(`Invalid API response`);return e}const ee={".csv":`text/csv`,".xlsx":`application/vnd.openxmlformats-officedocument.spreadsheetml.sheet`,".png":`image/png`,".jpg":`image/jpeg`,".jpeg":`image/jpeg`,".webp":`image/webp`,".gif":`image/gif`,".mp4":`video/mp4`,".mov":`video/quicktime`,".webm":`video/webm`,".zip":`application/zip`};async function w(e,t,n,r,i=`library`){let a=r??ee[h.extname(n).toLowerCase()];if(!a)throw Error(`Cannot infer the media type; supply --content-type`);let o=await m(n,{type:a}),s=await x(e,`assets.uploads.create`,{workspaceId:t,filename:h.basename(n),contentType:a,sizeBytes:o.size,purpose:i}),c=C(s.assetId),l=new URL(C(s.uploadUrl));if(l.protocol!==`https:`||l.username||l.password)throw Error(`Upload ticket must use HTTPS`);let u=Object.fromEntries(Object.entries(S(s.headers)).map(([e,t])=>[e,C(t)])),d=await fetch(l,{method:`PUT`,headers:u,body:o,redirect:`error`});if(!d.ok)throw Error(`Asset ${c}: upload failed (HTTP ${d.status})`);await d.body?.cancel();try{return await x(e,`assets.uploads.complete`,{workspaceId:t,assetId:c})}catch(e){throw Error(`Upload stored; retry adside assets uploads complete --workspace-id ${t} --asset-id ${c}: ${e instanceof Error?e.message:`finalization failed`}`)}}async function te(e,t,n,r){return await T(C(S((await x(e,`assets.get`,{workspaceId:t,assetId:n})).asset).url),r),{assetId:n,saved_to:r}}async function T(e,t){let n=new URL(e);if(n.protocol!==`https:`||n.username||n.password)throw Error(`Asset download URL must use HTTPS`);let r=await fetch(n,{redirect:`error`});if(!r.ok||!r.body)throw Error(`Download failed (HTTP ${r.status})`);await g(ne(r.body),p(t,{flags:`wx`}))}async function*ne(e){let t=e.getReader();try{for(;;){let{value:e,done:n}=await t.read();if(n)return;yield e}}finally{await t.cancel(),t.releaseLock()}}const re={".pdf":`application/pdf`,".docx":`application/vnd.openxmlformats-officedocument.wordprocessingml.document`,".pptx":`application/vnd.openxmlformats-officedocument.presentationml.presentation`,".md":`text/markdown`,".txt":`text/plain`,".eml":`message/rfc822`,".zip":`application/zip`};async function ie(e,t,n,r={}){let i=r.contentType??re[h.extname(n).toLowerCase()];if(!i)throw Error(`Cannot infer the document type; supply --content-type`);let a=await m(n,{type:i}),o=`organizationId`in t,s=await x(e,o?`brain.orgUpload`:`brain.upload`,{...t,filename:h.basename(n),contentType:i,sizeBytes:a.size}),c=new URL(C(s.uploadUrl));if(c.protocol!==`https:`||c.username||c.password)throw Error(`Upload ticket must use HTTPS`);let l=Object.fromEntries(Object.entries(S(s.headers)).map(([e,t])=>[e,C(t)])),u=await fetch(c,{method:`PUT`,headers:l,body:a,redirect:`error`});if(!u.ok)throw Error(`Document upload failed (HTTP ${u.status})`);let d=S(await u.json());return x(e,o?`brain.orgIngest`:`brain.ingest`,{...t,tier:o?`org`:`workspace`,instructions:r.instructions,registration:{kind:`blob`,blobUrl:C(d.url),blobPathname:C(s.pathname),filename:h.basename(n),mimeType:i,sizeBytes:a.size}})}const ae=`0.1.0`;async function oe(e,t){if(process.env.ADSIDE_AUTH===`proxy`)return{fromLogin:!1};if(process.env.ADSIDE_CREDENTIAL_FILE){let e=JSON.parse(await s(process.env.ADSIDE_CREDENTIAL_FILE,`utf8`));if(typeof e.token!=`string`||!e.token)throw Error(`Invalid Adside execution credential file`);return{token:e.token,fromLogin:!1}}if(e.apiKey)return{token:e.apiKey,fromLogin:!1};if(e.login)return{token:await e.login.accessToken(),fromLogin:!0};throw Error(e.missingCredentialMessage??`ADSIDE_API_KEY is required for this command (${t})`)}function E(e,t){return{commands:t,async callRest(t,n,r={},i={}){let{token:a,fromLogin:o}=await oe(e,i.auth??`user`),s=new URLSearchParams,c={},l={Accept:`application/json`,"User-Agent":`adside-cli/${ae}`};for(let[e,a]of Object.entries(r)){if(a===void 0)continue;let r=i.parameters?.find(t=>t.name===e)?.location??(t===`GET`?`query`:`body`);if(r===`path`){if(typeof a!=`string`&&typeof a!=`number`||[`.`,`..`].includes(String(a)))throw Error(`Invalid path parameter ${e}`);n=n.replaceAll(`{${e}}`,encodeURIComponent(String(a)))}else if(r===`query`)for(let t of Array.isArray(a)?a:[a])s.append(e,typeof t==`object`?JSON.stringify(t):String(t));else if(r===`header`){if([`authorization`,`host`,`cookie`,`content-length`,`x-adside-user-id`,`x-adside-organization-id`,`x-adside-workspace-id`,`x-adside-execution-id`,`x-adside-tool-policy`,`x-adside-routine-task-id`,`x-adside-bulk-upload-job-id`,`x-adside-approved-operation`].includes(e.toLowerCase()))throw Error(`Reserved header ${e}`);l[e]=String(a)}else c[e]=a}if(/\{[^}]+\}/.test(n))throw Error(`Missing path parameter in ${n}`);let u=new URL(n,e.apiGatewayUrl);if(u.origin!==new URL(e.apiGatewayUrl).origin)throw Error(`REST endpoint must use the configured API origin`);for(let[e,t]of s)u.searchParams.append(e,t);let d;if(t!==`GET`&&Object.keys(c).length)if(i.contentType===`multipart/form-data`){let e=new FormData;for(let[t,n]of Object.entries(c))if(i.fileFields?.includes(t)){let r=String(n);e.append(t,await m(r,{type:typeof c.mime_type==`string`?c.mime_type:`application/octet-stream`}),h.basename(r))}else e.append(t,typeof n==`object`?JSON.stringify(n):String(n));d=e}else l[`Content-Type`]=`application/json`,d=JSON.stringify(c);let f=e=>fetch(u,{method:t,headers:e?{...l,Authorization:`Bearer ${e}`}:l,body:d,redirect:`error`}),p=await f(a);if(p.status===401&&o&&a&&e.login&&(await p.body?.cancel(),p=await f(await e.login.refreshAfterRejection(a))),!p.ok)throw await ce(p);let g=p.headers.get(`content-type`);return p.status===204?{kind:`json`,data:null,contentType:g,status:p.status}:g?.includes(`json`)?{kind:`json`,data:await p.json(),contentType:g,status:p.status}:g?.startsWith(`text/`)?{kind:`text`,data:await p.text(),contentType:g,status:p.status}:{kind:`binary`,data:new Uint8Array(await p.arrayBuffer()),contentType:g,status:p.status}}}}var se=class extends Error{constructor(e,t){super(e),this.status=t,this.name=`ApiHttpError`}};async function ce(e){let t=await e.text(),n=t,r;try{let e=JSON.parse(t);r=typeof e.confirmationToken==`string`?e.confirmationToken:void 0,n=[e.code,e.error??e.message??e.summary,e.details&&JSON.stringify(e.details)].filter(Boolean).join(`: `)}catch{}return new se(`HTTP ${e.status}: ${n.slice(0,2e3)||e.statusText}`+(r?`\nconfirmationToken=${r}`:``),e.status)}function le(e){return{apiKey:process.env.ADSIDE_API_KEY,workspaceId:process.env.ADSIDE_WORKSPACE_ID||void 0,apiGatewayUrl:ue(process.env.API_GATEWAY_URL||`https://api.adside.ai`),output:de(e)}}function ue(e){return e.replace(/\/+$/,``)}function de(e){if(!e||e===`json`)return`json`;if(e===`text`)return`text`;throw Error(`Invalid output format "${e}". Use "json" or "text".`)}const D={name:`referenceFile`,flag:`--reference-file`,value:`<file>`,repeatable:!0,description:`Upload a local image, video or .zip as a creative reference (repeatable)`},O={name:`wait`,flag:`--wait`,description:`Wait for the job to finish, 30 s per request, up to --wait-timeout`},k={name:`waitTimeout`,flag:`--wait-timeout`,value:`<duration>`,description:`How long --wait may take: 90s, 14m or seconds (default 15m)`},A={name:`out`,flag:`--out`,value:`<file>`,description:`Download the finished output to a new file (never overwrites one)`},fe={name:`inputReference`,flag:`--input-reference`,value:`<ref>`,repeatable:!0,description:`A reference image: a local file (uploaded), an https URL or an asset ID (repeatable)`},pe={name:`firstFrame`,flag:`--first-frame`,value:`<ref>`,description:`The clip's first frame: a local file (uploaded), an https URL or an asset ID`},me={name:`lastFrame`,flag:`--last-frame`,value:`<ref>`,description:`The clip's last frame, with --first-frame, for a model that takes one: a local file (uploaded), an https URL or an asset ID`},he={"creatives.create":[D],"creatives.edit":[D],"creatives.add":[D],"creatives.messages.create":[D],"media.images.generate":[fe,O,k,A],"media.images.get":[O,k,A],"media.videos.generate":[pe,me,O,k,A],"media.videos.get":[O,k,A]};function ge(e){return he[e]??[]}const j={completed:0,error:1,ended:2,stillRunning:3},M=new Set([`completed`,`failed`,`cancelled`,`expired`]);function _e(e){let t=/^(\d+(?:\.\d+)?)(s|m|h)?$/.exec(e.trim());if(!t)throw Error(`Invalid --wait-timeout "${e}": use 90s, 14m or a number of seconds`);let n={s:1e3,m:6e4,h:36e5}[t[2]??`s`]??1e3;return Math.round(Number(t[1])*n)}async function N(e,t){if(await t.isFile(e)){let n=await t.upload(e);return t.stderr(`inputAssetId=${n}`),{type:`asset`,assetId:n}}return/^https:\/\//i.test(e)?{type:`image_url`,imageUrl:{url:e}}:{type:`asset`,assetId:e}}async function ve(e,t,n){let r=t.inputReference??[];if(r.length){if(e.inputReferences!==void 0)throw Error(`Use --input-reference or --input-references, not both`);let t=[];for(let e of r)t.push(await N(e,n));e.inputReferences=t}if(t.firstFrame!==void 0||t.lastFrame!==void 0){if(e.frameImages!==void 0)throw Error(`Use --first-frame and --last-frame or --frame-images, not both`);let r=[];t.firstFrame!==void 0&&r.push({...await N(t.firstFrame,n),frameType:`first_frame`}),t.lastFrame!==void 0&&r.push({...await N(t.lastFrame,n),frameType:`last_frame`}),e.frameImages=r}}function ye(e){return e instanceof se&&e.status>=500||e instanceof TypeError}async function P(e,t){for(let n=0;;n++)try{return await t()}catch(t){if(n>=3||!ye(t))throw t;e.stderr(`retrying (${n+1}/3): ${t instanceof Error?t.message:String(t)}`),await e.sleep(1e3*2**n)}}function be(e){if(e&&typeof e==`object`&&`id`in e&&typeof e.id==`string`&&`status`in e&&typeof e.status==`string`){let t=`outputs`in e&&Array.isArray(e.outputs)?e.outputs:[];return{id:e.id,status:e.status,outputs:t}}throw Error(`The API answered without a media job`)}function xe(e,t){return e===`completed`?j.completed:M.has(e)?j.ended:t?j.stillRunning:j.completed}function Se(e){return/^media\.(images|videos)\.(generate|get)$/.test(e)}function F(e){return/^[\w@%+=:,./-]+$/.test(e)?e:`'${e.replace(/'/g,`'\\''`)}'`}function Ce(e,t,n,r){let[,i]=e.split(`.`);return[`adside media ${i} get`,...typeof t==`string`?[`--workspace-id ${F(t)}`]:[],`--job-id ${F(n)} --wait`,...r===void 0?[]:[`--out ${F(r)}`]].join(` `)}async function we(e,t,n,r){let i=e.endsWith(`.generate`),a=e.replace(/\.generate$/,`.get`);if(n.waitTimeout!==void 0&&!n.wait)throw Error(`--wait-timeout needs --wait`);if(n.out!==void 0&&i&&!n.wait)throw Error(`--out needs --wait on generate, or use get`);if(!i&&(n.inputReference?.length||n.firstFrame!==void 0))throw Error(`Input flags go with generate`);if(n.out!==void 0&&await r.isFile(n.out))throw Error(`${n.out} already exists; choose a new file for --out`);i&&await ve(t,n,r);let o=r.now()+(n.waitTimeout?_e(n.waitTimeout):9e5),s=()=>Math.max(0,Math.min(30,Math.floor((o-r.now())/1e3))),c={...t,...n.wait?{waitSeconds:s()}:{}},l=await P(r,()=>r.call(e,c)),u=be(l);for(;n.wait&&!M.has(u.status)&&r.now()<o;){let e=s();if(e<1)break;l=await P(r,()=>r.call(a,{workspaceId:t.workspaceId,jobId:u.id,waitSeconds:e})),u=be(l)}let d=xe(u.status,!!n.wait);if(n.out!==void 0){let e=u.outputs?.[0]?.url;if(u.status!==`completed`)r.stderr(`job ${u.id} is ${u.status}; nothing saved to ${n.out}`);else if(typeof e!=`string`)r.stderr(`job ${u.id} completed without an output to download`),d=j.error;else try{await r.download(e,n.out),r.stderr(`saved_to=${n.out}`)}catch(e){r.stderr(`download failed: ${e instanceof Error?e.message:String(e)}`),d=j.error}}return n.wait&&!M.has(u.status)&&r.stderr(`job ${u.id} is still ${u.status}; to keep waiting without paying again, run: ${Ce(e,t.workspaceId,u.id,n.out)}`),{job:l,exitCode:d}}const Te=new Set([`credits.ledger`]);function Ee(t,n){let r=new e;r.name(`adside`).description(`Adside product and advertising-platform commands`).version(`${ae} (contracts ${t.contractHash.slice(0,12)})`).option(`--output <format>`,`Output format: json or text`,`json`),ke(r,t.commands,n),De(r,t.commands,n),n?.register(r,t.commands),r.parseAsync(process.argv).catch(We)}function I(e,t){let n=le(e);return t?t.configure(n):Promise.resolve(n)}async function L(e){return process.env.ADSIDE_WORKSPACE_ID||(await e?.defaults())?.workspaceId}function De(e,t,n){let r=e.commands.find(e=>e.name()===`assets`);for(let e of[`upload`,`download`]){let i=r.command(e).description(e===`upload`?`Upload a local media file and publish it in the asset library`:`Download an asset to a new local file`).option(`--workspace-id <id>`,`Workspace (defaults to ADSIDE_WORKSPACE_ID)`);e===`upload`?i.requiredOption(`--file <file>`,`Local media or tabular file`).option(`--purpose <purpose>`,`library or attachment (CSV/XLSX audience input)`,`library`).option(`--content-type <type>`,`Media MIME type (inferred from extension by default)`):i.requiredOption(`--asset-id <id>`,`Asset to download`).requiredOption(`--out <file>`,`Destination file (must not exist)`),i.action(async()=>{let r=i.optsWithGlobals(),a=R(r.output),o=E(await I(a,n),t),s=z(r.workspaceId??await L(n),`--workspace-id`);V(e===`upload`?await w(o,s,z(r.file,`--file`),B(r.contentType),Oe(r.purpose)):await te(o,s,z(r.assetId,`--asset-id`),z(r.out,`--out`)),a)})}let i=e.commands.find(e=>e.name()===`brain`).command(`upload`).description(`Upload a local document and start Brain ingestion`).requiredOption(`--file <file>`,`PDF, DOCX, PPTX, Markdown, text, email or ZIP`).option(`--workspace-id <id>`,`Workspace (defaults to ADSIDE_WORKSPACE_ID)`).option(`--organization-id <id>`,`Write to the organization Brain instead (admin required)`).option(`--content-type <type>`,`Document MIME type`).option(`--instructions <text>`,`Filing instructions`);i.action(async()=>{let e=i.optsWithGlobals(),r=R(e.output),a=e.organizationId?{organizationId:z(e.organizationId,`--organization-id`)}:{workspaceId:z(e.workspaceId??await L(n),`--workspace-id`)};V(await ie(E(await I(r,n),t),a,z(e.file,`--file`),{contentType:B(e.contentType),instructions:B(e.instructions)}),r)})}function Oe(e){if(e===`library`||e===`attachment`)return e;throw Error(`--purpose must be library or attachment`)}function ke(e,t,n){let i=new Map;for(let a of t)for(let o of[a.path,...a.aliases??[]]){let c={...a,path:o},l=Ae(e,i,c);l.description(c.summary),c.description&&l.addHelpText(`after`,`\n${c.description}\n`),l.option(`--input-file <file>`,`Read a JSON object of parameters from a file`),l.option(`--json <json>`,`Provide parameters as a JSON object`);let u=ge(c.id);for(let e of u)je(l,e);let d=u.some(e=>e.name===`referenceFile`);for(let e of c.options)Ne(l,e);if(c.output.kind!==`json`&&l.option(`--out <file>`,`Write the response body to a file`),c.examples.length>0){let e=c.examples.map(e=>` ${e.description}\n ${e.command}`).join(`
3
+ `);l.addHelpText(`after`,`Examples:\n${e}\n`)}l.action(async(e,i)=>{let a=i.optsWithGlobals(),o=R(a.output),l=B(a.out),u=await I(o,n),f=E(u,t),p=B(a.inputFile),m=B(a.json);if(p&&m)throw Error(`Use --json or --input-file, not both`);let h=p?JSON.parse(await s(p,`utf8`)):m?JSON.parse(m):{};if(!h||typeof h!=`object`||Array.isArray(h))throw Error(`Input must be a JSON object`);let g={...h,...Fe(c,a)},_=e=>c.options.some(t=>t.name===e);_(`workspaceId`)&&!Te.has(c.id)&&g.workspaceId===void 0&&(g.workspaceId=await L(n)),_(`organizationId`)&&g.organizationId===void 0&&(g.organizationId=(await n?.defaults())?.organizationId),c.generateRequestId&&g.requestId===void 0&&(g.requestId=r());for(let e of c.options)if(e.required&&g[e.name]===void 0)throw Error(`Missing required parameter: ${e.flag}`);let v=c.options.filter(e=>e.valueType===`file`).map(e=>e.name);if(c.generateRequestId&&process.stderr.write(`requestId=${String(g.requestId)}\n`),Se(c.id)){let{job:e,exitCode:t}=await we(c.id,g,{wait:a.wait===!0,waitTimeout:B(a.waitTimeout),out:l,inputReference:Array.isArray(a.inputReference)?a.inputReference.map(String):void 0,firstFrame:B(a.firstFrame),lastFrame:B(a.lastFrame)},Me(f,g));V(e,u.output),process.exitCode=t;return}if(d&&Array.isArray(a.referenceFile)&&a.referenceFile.length){let e=g.references??[];if(!Array.isArray(e)||e.length+a.referenceFile.length>20)throw Error(`A creative request supports at most 20 references`);g.references=[...e];for(let e of a.referenceFile){let t=C(S((await w(f,z(g.workspaceId,`--workspace-id`),z(e,`--reference-file`),void 0,`attachment`)).asset).id);g.references.push({type:`asset`,assetId:t}),process.stderr.write(`referenceAssetId=${t}\n`)}}await Ue(await f.callRest(c.transport.method,c.transport.path,g,{contentType:c.transport.requestContentType,fileFields:v,parameters:c.options,auth:c.transport.auth}),u.output,l)})}}function Ae(e,t,n){let r=e,i=``;for(let e of n.path){i=i?`${i} ${e}`:e;let n=t.get(i);if(n){r=n;continue}let a=r.command(e);t.set(i,a),r=a}return r}function je(e,t){let n=t.value?`${t.flag} ${t.value}`:t.flag;t.repeatable?e.option(n,t.description,(e,t)=>[...t,e],[]):e.option(n,t.description)}function Me(e,t){return{call:(t,n)=>x(e,t,n),upload:async n=>C(S((await w(e,z(t.workspaceId,`--workspace-id`),n,void 0,`attachment`)).asset).id),download:T,isFile:e=>u(e).then(e=>e.isFile(),()=>!1),sleep:e=>new Promise(t=>setTimeout(t,e)),now:()=>Date.now(),stderr:e=>process.stderr.write(`${e}\n`)}}function Ne(e,t){let n=t.valueType===`boolean`?`<boolean>`:t.valueType===`file`?`<file>`:`<value>`,r=`${t.flag} ${n}`,i=Pe(t);e.option(r,i)}function Pe(e){let t=[e.description||Be(e.name)];return e.enum&&e.enum.length>0&&t.push(`Allowed: ${e.enum.join(`, `)}`),e.defaultValue!==void 0&&t.push(`Default: ${String(e.defaultValue)}`),e.required&&t.push(`Required`),t.join(` `)}function Fe(e,t){let n={};for(let r of e.options){let e=t[Ve(r.flag)];e!==void 0&&(n[r.name]=Ie(r,e))}return n}function Ie(e,t){let n=z(t,e.flag);switch(e.valueType){case`boolean`:return Le(n,e.flag);case`number`:return Re(n,e.flag);case`json`:return ze(n,e.flag);default:return n}}function Le(e,t){if(e===`true`)return!0;if(e===`false`)return!1;throw Error(`Invalid boolean for ${t}: "${e}". Use true or false.`)}function Re(e,t){let n=Number(e);if(!Number.isFinite(n))throw Error(`Invalid number for ${t}: "${e}".`);return n}function ze(e,t){try{return JSON.parse(e)}catch(e){let n=e instanceof Error?e.message:`Unknown JSON parse error`;throw Error(`Invalid JSON for ${t}: ${n}`)}}function R(e){if(e!==`json`&&e!==`text`)throw Error(`--output must be json or text`);return e}function z(e,t){if(typeof e!=`string`||e.length===0)throw Error(`Missing required value for ${t}.`);return e}function B(e){return typeof e==`string`&&e.length>0?e:void 0}function Be(e){return e.replace(/_/g,` `)}function Ve(e){return e.replace(/^--/,``).replace(/-([a-z])/g,(e,t)=>t.toUpperCase())}function V(e,t){let n=H(e);if(t===`text`&&typeof e==`string`){process.stdout.write(`${n}\n`);return}process.stdout.write(`${JSON.stringify(n,null,2)}\n`)}function H(e){return Array.isArray(e)?e.map(e=>H(e)):!e||typeof e!=`object`?e:Object.fromEntries(Object.entries(e).map(([e,t])=>[e,He(e)?`[REDACTED]`:H(t)]))}function He(e){let t=e.replace(/[^a-zA-Z0-9]/g,``).toLowerCase();return new Set([`accesstoken`,`refreshtoken`,`idtoken`,`apikey`,`authorization`,`password`,`secret`,`clientsecret`,`appsecret`,`developertoken`]).has(t)||t.endsWith(`accesstoken`)||t.endsWith(`refreshtoken`)||t.endsWith(`idtoken`)||t.endsWith(`apikey`)||t.endsWith(`secret`)}async function Ue(e,t,n){if(e.kind===`json`){V(e.data,t);return}if(e.kind===`text`){if(n){await f(n,e.data,`utf8`),V({saved_to:n,content_type:e.contentType,bytes:Buffer.byteLength(e.data)},t);return}if(t===`text`){process.stdout.write(e.data),e.data.endsWith(`
4
+ `)||process.stdout.write(`
5
+ `);return}V({text:e.data},t);return}if(n){await f(n,e.data),V({saved_to:n,content_type:e.contentType,bytes:e.data.byteLength},t);return}if(process.stdout.isTTY)throw Error(`Binary response detected. Use --out <file> or redirect stdout.`);process.stdout.write(Buffer.from(e.data))}function We(e){let t=e instanceof Error?e.message:`Unknown CLI execution error`;process.stderr.write(`${t}\n`),process.exitCode=1}const Ge={version:`2`,contractHash:`85fb7dd4ce85d82709dc74c9a565a758aad3ad312d89db041867d88a0a9d7f98`,commands:[{id:`ad-comments.capabilities`,path:[`ad-comments`,`capabilities`],summary:`Read moderation capabilities of connected Meta accounts`,description:``,source:`rest`,options:[{name:`workspaceId`,flag:`--workspace-id`,description:``,required:!0,valueType:`string`,location:`path`}],examples:[{description:`Example`,command:`adside ad-comments capabilities --workspace-id <workspaceId>`}],output:{kind:`json`,description:`Read moderation capabilities of connected Meta accounts`},transport:{type:`rest`,method:`GET`,path:`/v1/workspaces/{workspaceId}/ad-comments/capabilities`,auth:`user`}},{id:`ad-comments.hide`,path:[`ad-comments`,`hide`],summary:`Hide an ad comment on Meta`,description:``,source:`rest`,options:[{name:`workspaceId`,flag:`--workspace-id`,description:``,required:!0,valueType:`string`,location:`path`},{name:`surface`,flag:`--surface`,description:``,required:!0,valueType:`string`,enum:[`facebook`,`instagram`],location:`path`},{name:`commentId`,flag:`--comment-id`,description:``,required:!0,valueType:`string`,location:`path`},{name:`confirmationToken`,flag:`--confirmation-token`,description:``,required:!1,valueType:`string`,location:`body`}],examples:[{description:`Example`,command:`adside ad-comments hide --workspace-id <workspaceId> --surface facebook --comment-id <commentId>`}],output:{kind:`json`,description:`Hide an ad comment on Meta`},transport:{type:`rest`,method:`POST`,path:`/v1/workspaces/{workspaceId}/ad-comments/{surface}/{commentId}/hide`,auth:`user`,requestContentType:`application/json`}},{id:`ad-comments.list`,path:[`ad-comments`,`list`],summary:`Read workspace ad comments grouped by post`,description:``,source:`rest`,options:[{name:`workspaceId`,flag:`--workspace-id`,description:``,required:!0,valueType:`string`,location:`path`}],examples:[{description:`Example`,command:`adside ad-comments list --workspace-id <workspaceId>`}],output:{kind:`json`,description:`Read workspace ad comments grouped by post`},transport:{type:`rest`,method:`GET`,path:`/v1/workspaces/{workspaceId}/ad-comments`,auth:`user`}},{id:`ad-comments.reply`,path:[`ad-comments`,`reply`],summary:`Post a reply as the owning Page or Instagram account`,description:``,source:`rest`,options:[{name:`workspaceId`,flag:`--workspace-id`,description:``,required:!0,valueType:`string`,location:`path`},{name:`surface`,flag:`--surface`,description:``,required:!0,valueType:`string`,enum:[`facebook`,`instagram`],location:`path`},{name:`commentId`,flag:`--comment-id`,description:``,required:!0,valueType:`string`,location:`path`},{name:`message`,flag:`--message`,description:``,required:!0,valueType:`string`,location:`body`},{name:`confirmationToken`,flag:`--confirmation-token`,description:``,required:!1,valueType:`string`,location:`body`}],examples:[{description:`Example`,command:`adside ad-comments reply --workspace-id <workspaceId> --surface facebook --comment-id <commentId> --message <message>`}],output:{kind:`json`,description:`Post a reply as the owning Page or Instagram account`},transport:{type:`rest`,method:`POST`,path:`/v1/workspaces/{workspaceId}/ad-comments/{surface}/{commentId}/replies`,auth:`user`,requestContentType:`application/json`}},{id:`ad-comments.unhide`,path:[`ad-comments`,`unhide`],summary:`Restore a hidden ad comment on Meta`,description:``,source:`rest`,options:[{name:`workspaceId`,flag:`--workspace-id`,description:``,required:!0,valueType:`string`,location:`path`},{name:`surface`,flag:`--surface`,description:``,required:!0,valueType:`string`,enum:[`facebook`,`instagram`],location:`path`},{name:`commentId`,flag:`--comment-id`,description:``,required:!0,valueType:`string`,location:`path`},{name:`confirmationToken`,flag:`--confirmation-token`,description:``,required:!1,valueType:`string`,location:`body`}],examples:[{description:`Example`,command:`adside ad-comments unhide --workspace-id <workspaceId> --surface facebook --comment-id <commentId>`}],output:{kind:`json`,description:`Restore a hidden ad comment on Meta`},transport:{type:`rest`,method:`POST`,path:`/v1/workspaces/{workspaceId}/ad-comments/{surface}/{commentId}/unhide`,auth:`user`,requestContentType:`application/json`}},{id:`assets.archive`,path:[`assets`,`archive`],summary:`Archive an asset`,description:``,source:`rest`,options:[{name:`workspaceId`,flag:`--workspace-id`,description:``,required:!0,valueType:`string`,location:`path`},{name:`assetId`,flag:`--asset-id`,description:``,required:!0,valueType:`string`,location:`path`}],examples:[{description:`Example`,command:`adside assets archive --workspace-id <workspaceId> --asset-id <assetId>`}],output:{kind:`json`,description:`Archive an asset`},transport:{type:`rest`,method:`POST`,path:`/v1/workspaces/{workspaceId}/assets/{assetId}/archive`,auth:`user`}},{id:`assets.batch`,path:[`assets`,`batch`],summary:`Look up assets in this workspace by ID`,description:``,source:`rest`,options:[{name:`workspaceId`,flag:`--workspace-id`,description:``,required:!0,valueType:`string`,location:`path`},{name:`ids`,flag:`--ids`,description:``,required:!0,valueType:`json`,location:`body`}],examples:[{description:`Example`,command:`adside assets batch --workspace-id <workspaceId> --ids '{}'`}],output:{kind:`json`,description:`Look up assets in this workspace by ID`},transport:{type:`rest`,method:`POST`,path:`/v1/workspaces/{workspaceId}/assets/batch`,auth:`user`,requestContentType:`application/json`}},{id:`assets.delete`,path:[`assets`,`delete`],summary:`Remove an asset and queue storage cleanup`,description:``,source:`rest`,options:[{name:`workspaceId`,flag:`--workspace-id`,description:``,required:!0,valueType:`string`,location:`path`},{name:`assetId`,flag:`--asset-id`,description:``,required:!0,valueType:`string`,location:`path`},{name:`confirmationToken`,flag:`--confirmation-token`,description:``,required:!1,valueType:`string`,location:`body`}],examples:[{description:`Example`,command:`adside assets delete --workspace-id <workspaceId> --asset-id <assetId>`}],output:{kind:`json`,description:`Remove an asset and queue storage cleanup`},transport:{type:`rest`,method:`DELETE`,path:`/v1/workspaces/{workspaceId}/assets/{assetId}`,auth:`user`,requestContentType:`application/json`}},{id:`assets.get`,path:[`assets`,`get`],summary:`Get an asset and its download URL`,description:``,source:`rest`,options:[{name:`workspaceId`,flag:`--workspace-id`,description:``,required:!0,valueType:`string`,location:`path`},{name:`assetId`,flag:`--asset-id`,description:``,required:!0,valueType:`string`,location:`path`}],examples:[{description:`Example`,command:`adside assets get --workspace-id <workspaceId> --asset-id <assetId>`}],output:{kind:`json`,description:`Get an asset and its download URL`},transport:{type:`rest`,method:`GET`,path:`/v1/workspaces/{workspaceId}/assets/{assetId}`,auth:`user`}},{id:`assets.import-url`,path:[`assets`,`import-url`],summary:`Import a public image or video URL into the asset library`,description:``,source:`rest`,options:[{name:`workspaceId`,flag:`--workspace-id`,description:``,required:!0,valueType:`string`,location:`path`},{name:`url`,flag:`--url`,description:``,required:!0,valueType:`url`,location:`body`},{name:`name`,flag:`--name`,description:``,required:!1,valueType:`string`,location:`body`},{name:`tags`,flag:`--tags`,description:``,required:!1,valueType:`json`,location:`body`}],examples:[{description:`Example`,command:`adside assets import-url --workspace-id <workspaceId> --url https://example.com`}],output:{kind:`json`,description:`Import a public image or video URL into the asset library`},transport:{type:`rest`,method:`POST`,path:`/v1/workspaces/{workspaceId}/assets/imports/url`,auth:`user`,requestContentType:`application/json`}},{id:`assets.list`,path:[`assets`,`list`],summary:`List the workspace's assets, with filters and cursor pagination`,description:``,source:`rest`,options:[{name:`workspaceId`,flag:`--workspace-id`,description:``,required:!0,valueType:`string`,location:`path`},{name:`search`,flag:`--search`,description:``,required:!1,valueType:`string`,location:`query`},{name:`sourceType`,flag:`--source-type`,description:``,required:!1,valueType:`json`,location:`query`},{name:`category`,flag:`--category`,description:``,required:!1,valueType:`json`,location:`query`},{name:`tags`,flag:`--tags`,description:``,required:!1,valueType:`json`,location:`query`},{name:`mediaType`,flag:`--media-type`,description:``,required:!1,valueType:`json`,location:`query`},{name:`dateAddedFrom`,flag:`--date-added-from`,description:``,required:!1,valueType:`string`,location:`query`},{name:`dateAddedTo`,flag:`--date-added-to`,description:``,required:!1,valueType:`string`,location:`query`},{name:`minSizeBytes`,flag:`--min-size-bytes`,description:``,required:!1,valueType:`number`,location:`query`},{name:`maxSizeBytes`,flag:`--max-size-bytes`,description:``,required:!1,valueType:`number`,location:`query`},{name:`status`,flag:`--status`,description:``,required:!1,valueType:`string`,enum:[`PENDING`,`PROCESSING`,`READY`,`FAILED`,`ARCHIVED`,`PENDING_DELETION`],location:`query`},{name:`limit`,flag:`--limit`,description:``,required:!1,valueType:`number`,defaultValue:50,location:`query`},{name:`cursor`,flag:`--cursor`,description:``,required:!1,valueType:`string`,location:`query`},{name:`sortBy`,flag:`--sort-by`,description:``,required:!1,valueType:`string`,defaultValue:`createdAt`,enum:[`createdAt`,`name`,`fileSize`],location:`query`},{name:`sortOrder`,flag:`--sort-order`,description:``,required:!1,valueType:`string`,defaultValue:`desc`,enum:[`asc`,`desc`],location:`query`}],examples:[{description:`Example`,command:`adside assets list --workspace-id <workspaceId>`}],output:{kind:`json`,description:`List the workspace's assets, with filters and cursor pagination`},transport:{type:`rest`,method:`GET`,path:`/v1/workspaces/{workspaceId}/assets`,auth:`user`}},{id:`assets.readiness`,path:[`assets`,`status`],summary:`Check asset processing and upload readiness`,description:``,source:`rest`,options:[{name:`workspaceId`,flag:`--workspace-id`,description:``,required:!0,valueType:`string`,location:`path`},{name:`ids`,flag:`--ids`,description:``,required:!0,valueType:`json`,location:`body`}],examples:[{description:`Example`,command:`adside assets status --workspace-id <workspaceId> --ids '{}'`}],output:{kind:`json`,description:`Check asset processing and upload readiness`},transport:{type:`rest`,method:`POST`,path:`/v1/workspaces/{workspaceId}/assets/status`,auth:`user`,requestContentType:`application/json`}},{id:`assets.tags.list`,path:[`assets`,`tags`,`list`],summary:`List the workspace's most-used asset tags`,description:``,source:`rest`,options:[{name:`workspaceId`,flag:`--workspace-id`,description:``,required:!0,valueType:`string`,location:`path`}],examples:[{description:`Example`,command:`adside assets tags list --workspace-id <workspaceId>`}],output:{kind:`json`,description:`List the workspace's most-used asset tags`},transport:{type:`rest`,method:`GET`,path:`/v1/workspaces/{workspaceId}/assets/tags`,auth:`user`}},{id:`assets.tags.update`,path:[`assets`,`tags`,`update`],summary:`Add or remove asset tags`,description:``,source:`rest`,options:[{name:`workspaceId`,flag:`--workspace-id`,description:``,required:!0,valueType:`string`,location:`path`},{name:`assetId`,flag:`--asset-id`,description:``,required:!0,valueType:`string`,location:`path`},{name:`add`,flag:`--add`,description:``,required:!1,valueType:`json`,location:`body`},{name:`remove`,flag:`--remove`,description:``,required:!1,valueType:`json`,location:`body`}],examples:[{description:`Example`,command:`adside assets tags update --workspace-id <workspaceId> --asset-id <assetId>`}],output:{kind:`json`,description:`Add or remove asset tags`},transport:{type:`rest`,method:`PATCH`,path:`/v1/workspaces/{workspaceId}/assets/{assetId}/tags`,auth:`user`,requestContentType:`application/json`}},{id:`assets.transcription`,path:[`assets`,`transcription`],summary:`Request or read a video transcription`,description:``,source:`rest`,options:[{name:`workspaceId`,flag:`--workspace-id`,description:``,required:!0,valueType:`string`,location:`path`},{name:`assetId`,flag:`--asset-id`,description:``,required:!0,valueType:`string`,location:`path`}],examples:[{description:`Example`,command:`adside assets transcription --workspace-id <workspaceId> --asset-id <assetId>`}],output:{kind:`json`,description:`Request or read a video transcription`},transport:{type:`rest`,method:`POST`,path:`/v1/workspaces/{workspaceId}/assets/{assetId}/transcription`,auth:`user`}},{id:`assets.update`,path:[`assets`,`update`],summary:`Update asset metadata`,description:``,source:`rest`,options:[{name:`workspaceId`,flag:`--workspace-id`,description:``,required:!0,valueType:`string`,location:`path`},{name:`assetId`,flag:`--asset-id`,description:``,required:!0,valueType:`string`,location:`path`},{name:`name`,flag:`--name`,description:``,required:!1,valueType:`string`,location:`body`},{name:`description`,flag:`--description`,description:``,required:!1,valueType:`string`,location:`body`},{name:`category`,flag:`--category`,description:``,required:!1,valueType:`string`,enum:[`UNKNOWN`,`LOGO`,`PRODUCT`,`LIFESTYLE`,`BANNER`,`ICON`,`BACKGROUND`,`SCREENSHOT`,`AD_CREATIVE`,`OTHER`],location:`body`},{name:`tags`,flag:`--tags`,description:``,required:!1,valueType:`json`,location:`body`}],examples:[{description:`Example`,command:`adside assets update --workspace-id <workspaceId> --asset-id <assetId>`}],output:{kind:`json`,description:`Update asset metadata`},transport:{type:`rest`,method:`PATCH`,path:`/v1/workspaces/{workspaceId}/assets/{assetId}`,auth:`user`,requestContentType:`application/json`}},{id:`assets.uploads.complete`,path:[`assets`,`uploads`,`complete`],summary:`Publish an uploaded asset (safe to repeat)`,description:``,source:`rest`,options:[{name:`workspaceId`,flag:`--workspace-id`,description:``,required:!0,valueType:`string`,location:`path`},{name:`assetId`,flag:`--asset-id`,description:``,required:!0,valueType:`string`,location:`path`}],examples:[{description:`Example`,command:`adside assets uploads complete --workspace-id <workspaceId> --asset-id <assetId>`}],output:{kind:`json`,description:`Publish an uploaded asset (safe to repeat)`},transport:{type:`rest`,method:`POST`,path:`/v1/workspaces/{workspaceId}/assets/uploads/{assetId}/complete`,auth:`user`}},{id:`assets.uploads.create`,path:[`assets`,`uploads`,`create`],summary:`Reserve a media upload and return a single-file upload ticket`,description:``,source:`rest`,options:[{name:`workspaceId`,flag:`--workspace-id`,description:``,required:!0,valueType:`string`,location:`path`},{name:`filename`,flag:`--filename`,description:``,required:!0,valueType:`string`,location:`body`},{name:`contentType`,flag:`--content-type`,description:``,required:!0,valueType:`string`,location:`body`},{name:`sizeBytes`,flag:`--size-bytes`,description:``,required:!0,valueType:`number`,location:`body`},{name:`purpose`,flag:`--purpose`,description:``,required:!1,valueType:`string`,defaultValue:`library`,enum:[`library`,`attachment`],location:`body`}],examples:[{description:`Example`,command:`adside assets uploads create --workspace-id <workspaceId> --filename <filename> --content-type <contentType> --size-bytes 1`}],output:{kind:`json`,description:`Reserve a media upload and return a single-file upload ticket`},transport:{type:`rest`,method:`POST`,path:`/v1/workspaces/{workspaceId}/assets/uploads`,auth:`user`,requestContentType:`application/json`}},{id:`audiences.imports.confirm`,path:[`audiences`,`imports`,`confirm`],summary:`Approve the exact mapping and send the customer list to the channel`,description:``,source:`rest`,options:[{name:`workspaceId`,flag:`--workspace-id`,description:``,required:!0,valueType:`string`,location:`path`},{name:`jobId`,flag:`--job-id`,description:``,required:!0,valueType:`string`,location:`path`},{name:`selection`,flag:`--selection`,description:`Column selection. Omit for a prepared CSV to approve its stored identity mapping.`,required:!1,valueType:`json`,location:`body`},{name:`fullNameOrder`,flag:`--full-name-order`,description:``,required:!1,valueType:`string`,defaultValue:`given-first`,enum:[`given-first`,`family-first`],location:`body`},{name:`audienceName`,flag:`--audience-name`,description:``,required:!1,valueType:`string`,location:`body`},{name:`defaultCountryCallingCode`,flag:`--default-country-calling-code`,description:``,required:!1,valueType:`string`,location:`body`},{name:`confirmationToken`,flag:`--confirmation-token`,description:``,required:!1,valueType:`string`,location:`body`}],examples:[{description:`Example`,command:`adside audiences imports confirm --workspace-id <workspaceId> --job-id <jobId>`}],output:{kind:`json`,description:`Approve the exact mapping and send the customer list to the channel`},transport:{type:`rest`,method:`POST`,path:`/v1/workspaces/{workspaceId}/audience-imports/{jobId}/confirm`,auth:`user`,requestContentType:`application/json`}},{id:`audiences.imports.create`,path:[`audiences`,`imports`,`create`],summary:`Prepare an audience import for explicit confirmation`,description:``,source:`rest`,options:[{name:`workspaceId`,flag:`--workspace-id`,description:``,required:!0,valueType:`string`,location:`path`},{name:`assetId`,flag:`--asset-id`,description:``,required:!1,valueType:`string`,location:`body`},{name:`filePath`,flag:`--file-path`,description:``,required:!1,valueType:`string`,location:`body`},{name:`channel`,flag:`--channel`,description:``,required:!0,valueType:`string`,enum:[`META`,`LINKEDIN`],location:`body`},{name:`audienceName`,flag:`--audience-name`,description:``,required:!0,valueType:`string`,location:`body`},{name:`audienceDescription`,flag:`--audience-description`,description:``,required:!1,valueType:`string`,location:`body`},{name:`columnMapping`,flag:`--column-mapping`,description:``,required:!1,valueType:`json`,location:`body`},{name:`fullNameOrder`,flag:`--full-name-order`,description:``,required:!1,valueType:`string`,enum:[`given-first`,`family-first`],location:`body`},{name:`preparedCsv`,flag:`--prepared-csv`,description:`Validate a sandbox-prepared UTF-8 CSV with exact channel identifier headers, split names and international phones. Infer the mapping from those headers.`,required:!1,valueType:`boolean`,location:`body`}],examples:[{description:`Example`,command:`adside audiences imports create --workspace-id <workspaceId> --channel META --audience-name <audienceName>`}],output:{kind:`json`,description:`Prepare an audience import for explicit confirmation`},transport:{type:`rest`,method:`POST`,path:`/v1/workspaces/{workspaceId}/audience-imports`,auth:`user`,requestContentType:`application/json`}},{id:`audiences.imports.get`,path:[`audiences`,`imports`,`get`],summary:`Read audience mapping and import progress`,description:``,source:`rest`,options:[{name:`workspaceId`,flag:`--workspace-id`,description:``,required:!0,valueType:`string`,location:`path`},{name:`jobId`,flag:`--job-id`,description:``,required:!0,valueType:`string`,location:`path`}],examples:[{description:`Example`,command:`adside audiences imports get --workspace-id <workspaceId> --job-id <jobId>`}],output:{kind:`json`,description:`Read audience mapping and import progress`},transport:{type:`rest`,method:`GET`,path:`/v1/workspaces/{workspaceId}/audience-imports/{jobId}`,auth:`user`}},{id:`audiences.imports.list`,path:[`audiences`,`imports`,`list`],summary:`List audience import outcomes`,description:``,source:`rest`,options:[{name:`workspaceId`,flag:`--workspace-id`,description:``,required:!0,valueType:`string`,location:`path`},{name:`take`,flag:`--take`,description:``,required:!1,valueType:`number`,defaultValue:20,location:`query`}],examples:[{description:`Example`,command:`adside audiences imports list --workspace-id <workspaceId>`}],output:{kind:`json`,description:`List audience import outcomes`},transport:{type:`rest`,method:`GET`,path:`/v1/workspaces/{workspaceId}/audience-imports`,auth:`user`}},{id:`audiences.imports.preview`,path:[`audiences`,`imports`,`preview`],summary:`Inspect a CSV or spreadsheet before mapping audience identifiers`,description:``,source:`rest`,options:[{name:`workspaceId`,flag:`--workspace-id`,description:``,required:!0,valueType:`string`,location:`path`},{name:`assetId`,flag:`--asset-id`,description:``,required:!1,valueType:`string`,location:`body`},{name:`filePath`,flag:`--file-path`,description:``,required:!1,valueType:`string`,location:`body`}],examples:[{description:`Example`,command:`adside audiences imports preview --workspace-id <workspaceId>`}],output:{kind:`json`,description:`Inspect a CSV or spreadsheet before mapping audience identifiers`},transport:{type:`rest`,method:`POST`,path:`/v1/workspaces/{workspaceId}/audience-imports/preview`,auth:`user`,requestContentType:`application/json`}},{id:`audiences.imports.retry`,path:[`audiences`,`imports`,`retry`],summary:`Resume a failed import with its immutable approved mapping`,description:``,source:`rest`,options:[{name:`workspaceId`,flag:`--workspace-id`,description:``,required:!0,valueType:`string`,location:`path`},{name:`jobId`,flag:`--job-id`,description:``,required:!0,valueType:`string`,location:`path`},{name:`confirmationToken`,flag:`--confirmation-token`,description:``,required:!1,valueType:`string`,location:`body`}],examples:[{description:`Example`,command:`adside audiences imports retry --workspace-id <workspaceId> --job-id <jobId>`}],output:{kind:`json`,description:`Resume a failed import with its immutable approved mapping`},transport:{type:`rest`,method:`POST`,path:`/v1/workspaces/{workspaceId}/audience-imports/{jobId}/retry`,auth:`user`,requestContentType:`application/json`}},{id:`audit.get`,path:[`audit`,`get`],summary:`Read a campaign change or explicitly uncertain platform activity`,description:``,source:`rest`,options:[{name:`workspaceId`,flag:`--workspace-id`,description:``,required:!0,valueType:`string`,location:`path`},{name:`eventId`,flag:`--event-id`,description:``,required:!0,valueType:`string`,location:`path`}],examples:[{description:`Example`,command:`adside audit get --workspace-id <workspaceId> --event-id <eventId>`}],output:{kind:`json`,description:`Read a campaign change or explicitly uncertain platform activity`},transport:{type:`rest`,method:`GET`,path:`/v1/workspaces/{workspaceId}/audit-events/{eventId}`,auth:`user`}},{id:`audit.list`,path:[`audit`,`list`],summary:`Read campaign audit history with current access to explanations and sources`,description:``,source:`rest`,options:[{name:`workspaceId`,flag:`--workspace-id`,description:``,required:!0,valueType:`string`,location:`path`},{name:`scope`,flag:`--scope`,description:``,required:!1,valueType:`string`,defaultValue:`workspace`,enum:[`workspace`,`organization`],location:`query`},{name:`limit`,flag:`--limit`,description:``,required:!1,valueType:`number`,defaultValue:20,location:`query`},{name:`cursor`,flag:`--cursor`,description:``,required:!1,valueType:`string`,location:`query`},{name:`eventType`,flag:`--event-type`,description:``,required:!1,valueType:`string`,location:`query`},{name:`resourceType`,flag:`--resource-type`,description:``,required:!1,valueType:`string`,location:`query`},{name:`provider`,flag:`--provider`,description:``,required:!1,valueType:`string`,location:`query`},{name:`resourceId`,flag:`--resource-id`,description:``,required:!1,valueType:`string`,location:`query`},{name:`actorUserId`,flag:`--actor-user-id`,description:``,required:!1,valueType:`string`,location:`query`},{name:`from`,flag:`--from`,description:``,required:!1,valueType:`string`,location:`query`},{name:`to`,flag:`--to`,description:``,required:!1,valueType:`string`,location:`query`}],examples:[{description:`Example`,command:`adside audit list --workspace-id <workspaceId>`}],output:{kind:`json`,description:`Read campaign audit history with current access to explanations and sources`},transport:{type:`rest`,method:`GET`,path:`/v1/workspaces/{workspaceId}/audit-events`,auth:`user`}},{id:`bookmarks.add-to-board`,path:[`boards`,`bookmarks`,`add-to-board`],summary:`Add a saved item to another board`,description:``,source:`rest`,options:[{name:`workspaceId`,flag:`--workspace-id`,description:``,required:!0,valueType:`string`,location:`path`},{name:`bookmarkId`,flag:`--bookmark-id`,description:``,required:!0,valueType:`string`,location:`path`},{name:`boardId`,flag:`--board-id`,description:``,required:!0,valueType:`string`,location:`body`}],examples:[{description:`Example`,command:`adside boards bookmarks add-to-board --workspace-id <workspaceId> --bookmark-id <bookmarkId> --board-id <boardId>`}],output:{kind:`json`,description:`Add a saved item to another board`},transport:{type:`rest`,method:`POST`,path:`/v1/workspaces/{workspaceId}/bookmarks/{bookmarkId}/boards`,auth:`user`,requestContentType:`application/json`}},{id:`bookmarks.list`,path:[`boards`,`bookmarks`,`list`],summary:`List saved ads and inspiration`,description:``,source:`rest`,options:[{name:`workspaceId`,flag:`--workspace-id`,description:``,required:!0,valueType:`string`,location:`path`},{name:`kind`,flag:`--kind`,description:``,required:!1,valueType:`string`,enum:[`AD`,`INSPIRATION_ITEM`],location:`query`},{name:`trackedCompanyId`,flag:`--tracked-company-id`,description:``,required:!1,valueType:`string`,location:`query`},{name:`boardId`,flag:`--board-id`,description:``,required:!1,valueType:`string`,location:`query`}],examples:[{description:`Example`,command:`adside boards bookmarks list --workspace-id <workspaceId>`}],output:{kind:`json`,description:`List saved ads and inspiration`},transport:{type:`rest`,method:`GET`,path:`/v1/workspaces/{workspaceId}/bookmarks`,auth:`user`}},{id:`bookmarks.move`,path:[`boards`,`bookmarks`,`move`],summary:`Move a saved item between boards`,description:``,source:`rest`,options:[{name:`workspaceId`,flag:`--workspace-id`,description:``,required:!0,valueType:`string`,location:`path`},{name:`bookmarkId`,flag:`--bookmark-id`,description:``,required:!0,valueType:`string`,location:`path`},{name:`fromBoardId`,flag:`--from-board-id`,description:``,required:!0,valueType:`string`,location:`body`},{name:`toBoardId`,flag:`--to-board-id`,description:``,required:!0,valueType:`string`,location:`body`}],examples:[{description:`Example`,command:`adside boards bookmarks move --workspace-id <workspaceId> --bookmark-id <bookmarkId> --from-board-id <fromBoardId> --to-board-id <toBoardId>`}],output:{kind:`json`,description:`Move a saved item between boards`},transport:{type:`rest`,method:`PATCH`,path:`/v1/workspaces/{workspaceId}/bookmarks/{bookmarkId}`,auth:`user`,requestContentType:`application/json`}},{id:`bookmarks.remove`,path:[`boards`,`bookmarks`,`remove`],summary:`Remove a saved item or board membership`,description:``,source:`rest`,options:[{name:`workspaceId`,flag:`--workspace-id`,description:``,required:!0,valueType:`string`,location:`path`},{name:`bookmarkId`,flag:`--bookmark-id`,description:``,required:!0,valueType:`string`,location:`path`},{name:`boardId`,flag:`--board-id`,description:``,required:!1,valueType:`string`,location:`query`}],examples:[{description:`Example`,command:`adside boards bookmarks remove --workspace-id <workspaceId> --bookmark-id <bookmarkId>`}],output:{kind:`json`,description:`Remove a saved item or board membership`},transport:{type:`rest`,method:`DELETE`,path:`/v1/workspaces/{workspaceId}/bookmarks/{bookmarkId}`,auth:`user`}},{id:`bookmarks.save`,path:[`boards`,`bookmarks`,`save`],summary:`Save an ad or inspiration item to a board`,description:``,source:`rest`,options:[{name:`workspaceId`,flag:`--workspace-id`,description:``,required:!0,valueType:`string`,location:`path`},{name:`kind`,flag:`--kind`,description:``,required:!0,valueType:`string`,enum:[`AD`,`INSPIRATION_ITEM`],location:`body`},{name:`adArchiveId`,flag:`--ad-archive-id`,description:``,required:!1,valueType:`string`,location:`body`},{name:`channel`,flag:`--channel`,description:``,required:!1,valueType:`string`,enum:[`META`,`GOOGLE`,`LINKEDIN`],location:`body`},{name:`trackedCompanyId`,flag:`--tracked-company-id`,description:``,required:!1,valueType:`string`,location:`body`},{name:`boardId`,flag:`--board-id`,description:``,required:!1,valueType:`string`,location:`body`},{name:`comment`,flag:`--comment`,description:``,required:!1,valueType:`string`,location:`body`},{name:`itemId`,flag:`--item-id`,description:``,required:!1,valueType:`string`,location:`body`}],examples:[{description:`Example`,command:`adside boards bookmarks save --workspace-id <workspaceId> --kind AD`}],output:{kind:`json`,description:`Save an ad or inspiration item to a board`},transport:{type:`rest`,method:`POST`,path:`/v1/workspaces/{workspaceId}/bookmarks`,auth:`user`,requestContentType:`application/json`}},{id:`boards.create`,path:[`boards`,`create`],summary:`Create a board`,description:``,source:`rest`,options:[{name:`workspaceId`,flag:`--workspace-id`,description:``,required:!0,valueType:`string`,location:`path`},{name:`name`,flag:`--name`,description:``,required:!0,valueType:`string`,location:`body`}],examples:[{description:`Example`,command:`adside boards create --workspace-id <workspaceId> --name <name>`}],output:{kind:`json`,description:`Create a board`},transport:{type:`rest`,method:`POST`,path:`/v1/workspaces/{workspaceId}/boards`,auth:`user`,requestContentType:`application/json`}},{id:`boards.delete`,path:[`boards`,`delete`],summary:`Delete a non-default board and its exclusive saved ads`,description:``,source:`rest`,options:[{name:`workspaceId`,flag:`--workspace-id`,description:``,required:!0,valueType:`string`,location:`path`},{name:`boardId`,flag:`--board-id`,description:``,required:!0,valueType:`string`,location:`path`},{name:`confirmationToken`,flag:`--confirmation-token`,description:``,required:!1,valueType:`string`,location:`body`}],examples:[{description:`Example`,command:`adside boards delete --workspace-id <workspaceId> --board-id <boardId>`}],output:{kind:`json`,description:`Delete a non-default board and its exclusive saved ads`},transport:{type:`rest`,method:`DELETE`,path:`/v1/workspaces/{workspaceId}/boards/{boardId}`,auth:`user`,requestContentType:`application/json`}},{id:`boards.list`,path:[`boards`,`list`],summary:`List boards and saved-ad counts`,description:``,source:`rest`,options:[{name:`workspaceId`,flag:`--workspace-id`,description:``,required:!0,valueType:`string`,location:`path`}],examples:[{description:`Example`,command:`adside boards list --workspace-id <workspaceId>`}],output:{kind:`json`,description:`List boards and saved-ad counts`},transport:{type:`rest`,method:`GET`,path:`/v1/workspaces/{workspaceId}/boards`,auth:`user`}},{id:`boards.update`,path:[`boards`,`update`],summary:`Rename a board`,description:``,source:`rest`,options:[{name:`workspaceId`,flag:`--workspace-id`,description:``,required:!0,valueType:`string`,location:`path`},{name:`boardId`,flag:`--board-id`,description:``,required:!0,valueType:`string`,location:`path`},{name:`name`,flag:`--name`,description:``,required:!1,valueType:`string`,location:`body`}],examples:[{description:`Example`,command:`adside boards update --workspace-id <workspaceId> --board-id <boardId>`}],output:{kind:`json`,description:`Rename a board`},transport:{type:`rest`,method:`PATCH`,path:`/v1/workspaces/{workspaceId}/boards/{boardId}`,auth:`user`,requestContentType:`application/json`}},{id:`brain.ingest`,path:[`brain`,`ingest`,`create`],summary:`ingest Brain content and document ingestion`,description:``,source:`rest`,options:[{name:`workspaceId`,flag:`--workspace-id`,description:``,required:!0,valueType:`string`,location:`path`},{name:`tier`,flag:`--tier`,description:``,required:!0,valueType:`string`,enum:[`org`,`workspace`],location:`body`},{name:`registration`,flag:`--registration`,description:``,required:!0,valueType:`json`,location:`body`},{name:`instructions`,flag:`--instructions`,description:``,required:!1,valueType:`string`,location:`body`}],examples:[{description:`Example`,command:`adside brain ingest create --workspace-id <workspaceId> --tier org --registration '{}'`}],output:{kind:`json`,description:`ingest Brain content and document ingestion`},transport:{type:`rest`,method:`POST`,path:`/v1/workspaces/{workspaceId}/brain/ingest`,auth:`user`,requestContentType:`application/json`}},{id:`brain.job`,path:[`brain`,`ingest`,`get`],summary:`job Brain content and document ingestion`,description:``,source:`rest`,options:[{name:`workspaceId`,flag:`--workspace-id`,description:``,required:!0,valueType:`string`,location:`path`},{name:`jobId`,flag:`--job-id`,description:``,required:!0,valueType:`string`,location:`path`}],examples:[{description:`Example`,command:`adside brain ingest get --workspace-id <workspaceId> --job-id <jobId>`}],output:{kind:`json`,description:`job Brain content and document ingestion`},transport:{type:`rest`,method:`GET`,path:`/v1/workspaces/{workspaceId}/brain/ingest/jobs/{jobId}`,auth:`user`}},{id:`brain.jobs`,path:[`brain`,`ingest`,`list`],summary:`jobs Brain content and document ingestion`,description:``,source:`rest`,options:[{name:`workspaceId`,flag:`--workspace-id`,description:``,required:!0,valueType:`string`,location:`path`},{name:`tier`,flag:`--tier`,description:``,required:!1,valueType:`string`,enum:[`org`,`workspace`],location:`query`},{name:`status`,flag:`--status`,description:``,required:!1,valueType:`string`,enum:[`PENDING`,`EXTRACTING`,`INGESTING`,`COMPLETED`,`FAILED`],location:`query`},{name:`search`,flag:`--search`,description:``,required:!1,valueType:`string`,location:`query`},{name:`limit`,flag:`--limit`,description:``,required:!1,valueType:`number`,defaultValue:50,location:`query`},{name:`cursor`,flag:`--cursor`,description:``,required:!1,valueType:`string`,location:`query`}],examples:[{description:`Example`,command:`adside brain ingest list --workspace-id <workspaceId>`}],output:{kind:`json`,description:`jobs Brain content and document ingestion`},transport:{type:`rest`,method:`GET`,path:`/v1/workspaces/{workspaceId}/brain/ingest/jobs`,auth:`user`}},{id:`brain.tree`,path:[`brain`,`list`],summary:`tree Brain content and document ingestion`,description:``,source:`rest`,options:[{name:`workspaceId`,flag:`--workspace-id`,description:``,required:!0,valueType:`string`,location:`path`},{name:`tier`,flag:`--tier`,description:``,required:!0,valueType:`string`,enum:[`workspace`,`org`],location:`query`},{name:`path`,flag:`--path`,description:``,required:!1,valueType:`string`,defaultValue:``,location:`query`}],examples:[{description:`Example`,command:`adside brain list --workspace-id <workspaceId> --tier workspace`}],output:{kind:`json`,description:`tree Brain content and document ingestion`},transport:{type:`rest`,method:`GET`,path:`/v1/workspaces/{workspaceId}/brain/tree`,auth:`user`}},{id:`brain.orgIngest`,path:[`brain`,`organization`,`ingest`,`create`],summary:`ingest Brain content and document ingestion`,description:``,source:`rest`,options:[{name:`organizationId`,flag:`--organization-id`,description:``,required:!0,valueType:`string`,location:`path`},{name:`tier`,flag:`--tier`,description:``,required:!0,valueType:`string`,enum:[`org`],location:`body`},{name:`registration`,flag:`--registration`,description:``,required:!0,valueType:`json`,location:`body`},{name:`instructions`,flag:`--instructions`,description:``,required:!1,valueType:`string`,location:`body`}],examples:[{description:`Example`,command:`adside brain organization ingest create --organization-id <organizationId> --tier org --registration '{}'`}],output:{kind:`json`,description:`ingest Brain content and document ingestion`},transport:{type:`rest`,method:`POST`,path:`/v1/organizations/{organizationId}/brain/ingest`,auth:`user`,requestContentType:`application/json`}},{id:`brain.orgJob`,path:[`brain`,`organization`,`ingest`,`get`],summary:`job Brain content and document ingestion`,description:``,source:`rest`,options:[{name:`organizationId`,flag:`--organization-id`,description:``,required:!0,valueType:`string`,location:`path`},{name:`jobId`,flag:`--job-id`,description:``,required:!0,valueType:`string`,location:`path`}],examples:[{description:`Example`,command:`adside brain organization ingest get --organization-id <organizationId> --job-id <jobId>`}],output:{kind:`json`,description:`job Brain content and document ingestion`},transport:{type:`rest`,method:`GET`,path:`/v1/organizations/{organizationId}/brain/ingest/jobs/{jobId}`,auth:`user`}},{id:`brain.orgJobs`,path:[`brain`,`organization`,`ingest`,`list`],summary:`jobs Brain content and document ingestion`,description:``,source:`rest`,options:[{name:`organizationId`,flag:`--organization-id`,description:``,required:!0,valueType:`string`,location:`path`},{name:`tier`,flag:`--tier`,description:``,required:!1,valueType:`string`,enum:[`org`,`workspace`],location:`query`},{name:`status`,flag:`--status`,description:``,required:!1,valueType:`string`,enum:[`PENDING`,`EXTRACTING`,`INGESTING`,`COMPLETED`,`FAILED`],location:`query`},{name:`search`,flag:`--search`,description:``,required:!1,valueType:`string`,location:`query`},{name:`limit`,flag:`--limit`,description:``,required:!1,valueType:`number`,defaultValue:50,location:`query`},{name:`cursor`,flag:`--cursor`,description:``,required:!1,valueType:`string`,location:`query`}],examples:[{description:`Example`,command:`adside brain organization ingest list --organization-id <organizationId>`}],output:{kind:`json`,description:`jobs Brain content and document ingestion`},transport:{type:`rest`,method:`GET`,path:`/v1/organizations/{organizationId}/brain/ingest/jobs`,auth:`user`}},{id:`brain.orgUpload`,path:[`brain`,`organization`,`uploads`,`create`],summary:`upload Brain content and document ingestion`,description:``,source:`rest`,options:[{name:`organizationId`,flag:`--organization-id`,description:``,required:!0,valueType:`string`,location:`path`},{name:`filename`,flag:`--filename`,description:``,required:!0,valueType:`string`,location:`body`},{name:`contentType`,flag:`--content-type`,description:``,required:!0,valueType:`string`,enum:[`application/pdf`,`application/vnd.openxmlformats-officedocument.wordprocessingml.document`,`application/vnd.openxmlformats-officedocument.presentationml.presentation`,`text/plain`,`text/markdown`,`message/rfc822`,`application/zip`,`application/x-zip-compressed`],location:`body`},{name:`sizeBytes`,flag:`--size-bytes`,description:``,required:!0,valueType:`number`,location:`body`}],examples:[{description:`Example`,command:`adside brain organization uploads create --organization-id <organizationId> --filename <filename> --content-type application/pdf --size-bytes 1`}],output:{kind:`json`,description:`upload Brain content and document ingestion`},transport:{type:`rest`,method:`POST`,path:`/v1/organizations/{organizationId}/brain/uploads`,auth:`user`,requestContentType:`application/json`}},{id:`brain.page`,path:[`brain`,`read`],summary:`page Brain content and document ingestion`,description:``,source:`rest`,options:[{name:`workspaceId`,flag:`--workspace-id`,description:``,required:!0,valueType:`string`,location:`path`},{name:`tier`,flag:`--tier`,description:``,required:!0,valueType:`string`,enum:[`workspace`,`org`],location:`query`},{name:`path`,flag:`--path`,description:``,required:!0,valueType:`string`,location:`query`}],examples:[{description:`Example`,command:`adside brain read --workspace-id <workspaceId> --tier workspace --path <path>`}],output:{kind:`json`,description:`page Brain content and document ingestion`},transport:{type:`rest`,method:`GET`,path:`/v1/workspaces/{workspaceId}/brain/page`,auth:`user`}},{id:`brain.remember`,path:[`brain`,`remember`],summary:`Remember durable workspace facts in memory.md; applied in the background`,description:``,source:`rest`,generateRequestId:!0,options:[{name:`workspaceId`,flag:`--workspace-id`,description:``,required:!0,valueType:`string`,location:`path`},{name:`requestId`,flag:`--request-id`,description:`Submission identity (generated automatically if omitted)`,required:!1,valueType:`string`,location:`body`},{name:`facts`,flag:`--facts`,description:`This turn's durable facts and corrections, in plain sentences`,required:!0,valueType:`string`,location:`body`},{name:`topic`,flag:`--topic`,description:`Keep the detail in memory/<topic>.md, e.g. decisions or goals-and-targets`,required:!1,valueType:`string`,location:`body`}],examples:[{description:`Example`,command:`adside brain remember --workspace-id <workspaceId> --facts <facts>`}],output:{kind:`json`,description:`Remember durable workspace facts in memory.md; applied in the background`},transport:{type:`rest`,method:`POST`,path:`/v1/workspaces/{workspaceId}/brain/memory`,auth:`user`,requestContentType:`application/json`}},{id:`brain.search`,path:[`brain`,`search`],summary:`Search Brain pages with bounded keyword scanning`,description:``,source:`rest`,options:[{name:`workspaceId`,flag:`--workspace-id`,description:``,required:!0,valueType:`string`,location:`path`},{name:`query`,flag:`--query`,description:``,required:!0,valueType:`string`,location:`body`},{name:`tiers`,flag:`--tiers`,description:``,required:!1,valueType:`json`,location:`body`},{name:`directory`,flag:`--directory`,description:``,required:!1,valueType:`string`,location:`body`},{name:`maxResults`,flag:`--max-results`,description:``,required:!1,valueType:`number`,defaultValue:10,location:`body`}],examples:[{description:`Example`,command:`adside brain search --workspace-id <workspaceId> --query <query>`}],output:{kind:`json`,description:`Search Brain pages with bounded keyword scanning`},transport:{type:`rest`,method:`POST`,path:`/v1/workspaces/{workspaceId}/brain/search`,auth:`user`,requestContentType:`application/json`}},{id:`brain.upload`,path:[`brain`,`uploads`,`create`],summary:`upload Brain content and document ingestion`,description:``,source:`rest`,options:[{name:`workspaceId`,flag:`--workspace-id`,description:``,required:!0,valueType:`string`,location:`path`},{name:`filename`,flag:`--filename`,description:``,required:!0,valueType:`string`,location:`body`},{name:`contentType`,flag:`--content-type`,description:``,required:!0,valueType:`string`,enum:[`application/pdf`,`application/vnd.openxmlformats-officedocument.wordprocessingml.document`,`application/vnd.openxmlformats-officedocument.presentationml.presentation`,`text/plain`,`text/markdown`,`message/rfc822`,`application/zip`,`application/x-zip-compressed`],location:`body`},{name:`sizeBytes`,flag:`--size-bytes`,description:``,required:!0,valueType:`number`,location:`body`}],examples:[{description:`Example`,command:`adside brain uploads create --workspace-id <workspaceId> --filename <filename> --content-type application/pdf --size-bytes 1`}],output:{kind:`json`,description:`upload Brain content and document ingestion`},transport:{type:`rest`,method:`POST`,path:`/v1/workspaces/{workspaceId}/brain/uploads`,auth:`user`,requestContentType:`application/json`}},{id:`brain.write`,path:[`brain`,`write`],summary:`write Brain content and document ingestion`,description:``,source:`rest`,options:[{name:`workspaceId`,flag:`--workspace-id`,description:``,required:!0,valueType:`string`,location:`path`},{name:`tier`,flag:`--tier`,description:``,required:!0,valueType:`string`,enum:[`org`,`workspace`],location:`body`},{name:`path`,flag:`--path`,description:``,required:!0,valueType:`string`,location:`body`},{name:`content`,flag:`--content`,description:``,required:!0,valueType:`string`,location:`body`},{name:`contentFormat`,flag:`--content-format`,description:``,required:!1,valueType:`string`,defaultValue:`body`,enum:[`body`,`document`],location:`body`},{name:`commitMessage`,flag:`--commit-message`,description:``,required:!1,valueType:`string`,location:`body`}],examples:[{description:`Example`,command:`adside brain write --workspace-id <workspaceId> --tier org --path <path> --content <content>`}],output:{kind:`json`,description:`write Brain content and document ingestion`},transport:{type:`rest`,method:`PUT`,path:`/v1/workspaces/{workspaceId}/brain/page`,auth:`user`,requestContentType:`application/json`}},{id:`brands.details`,path:[`brands`,`details`],summary:`Read the default brand identity, products and capped website evidence`,description:``,source:`rest`,options:[{name:`workspaceId`,flag:`--workspace-id`,description:``,required:!0,valueType:`string`,location:`path`}],examples:[{description:`Example`,command:`adside brands details --workspace-id <workspaceId>`}],output:{kind:`json`,description:`Read the default brand identity, products and capped website evidence`},transport:{type:`rest`,method:`GET`,path:`/v1/workspaces/{workspaceId}/brand-details`,auth:`user`}},{id:`brands.get`,path:[`brands`,`get`],summary:`Get a brand kit`,description:``,source:`rest`,options:[{name:`workspaceId`,flag:`--workspace-id`,description:``,required:!0,valueType:`string`,location:`path`},{name:`brandKitId`,flag:`--brand-kit-id`,description:``,required:!0,valueType:`string`,location:`path`}],examples:[{description:`Example`,command:`adside brands get --workspace-id <workspaceId> --brand-kit-id <brandKitId>`}],output:{kind:`json`,description:`Get a brand kit`},transport:{type:`rest`,method:`GET`,path:`/v1/workspaces/{workspaceId}/brand-kits/{brandKitId}`,auth:`user`}},{id:`brands.list`,path:[`brands`,`list`],summary:`List brand kits`,description:``,source:`rest`,options:[{name:`workspaceId`,flag:`--workspace-id`,description:``,required:!0,valueType:`string`,location:`path`}],examples:[{description:`Example`,command:`adside brands list --workspace-id <workspaceId>`}],output:{kind:`json`,description:`List brand kits`},transport:{type:`rest`,method:`GET`,path:`/v1/workspaces/{workspaceId}/brand-kits`,auth:`user`}},{id:`creatives.by-request-id`,path:[`creatives`,`by-request-id`],summary:`Recover the exact receipt of a create request without resubmitting`,description:``,source:`rest`,options:[{name:`workspaceId`,flag:`--workspace-id`,description:``,required:!0,valueType:`string`,location:`path`},{name:`requestId`,flag:`--request-id`,description:``,required:!0,valueType:`string`,location:`query`}],examples:[{description:`Example`,command:`adside creatives by-request-id --workspace-id <workspaceId> --request-id <requestId>`}],output:{kind:`json`,description:`Recover the exact receipt of a create request without resubmitting`},transport:{type:`rest`,method:`GET`,path:`/v1/workspaces/{workspaceId}/creatives/by-request-id`,auth:`user`}},{id:`creatives.cancel`,path:[`creatives`,`cancel`],summary:`Request cancellation of an exact run, retaining published work`,description:``,source:`rest`,options:[{name:`workspaceId`,flag:`--workspace-id`,description:``,required:!0,valueType:`string`,location:`path`},{name:`dropId`,flag:`--drop-id`,description:``,required:!0,valueType:`string`,location:`path`},{name:`runId`,flag:`--run-id`,description:``,required:!0,valueType:`string`,location:`path`}],examples:[{description:`Example`,command:`adside creatives cancel --workspace-id <workspaceId> --drop-id <dropId> --run-id <runId>`}],output:{kind:`json`,description:`Request cancellation of an exact run, retaining published work`},transport:{type:`rest`,method:`POST`,path:`/v1/workspaces/{workspaceId}/creatives/{dropId}/runs/{runId}/cancel`,auth:`user`}},{id:`creatives.comments.create`,path:[`creatives`,`comments`,`create`],summary:`Pin feedback to a creative revision`,description:``,source:`rest`,options:[{name:`workspaceId`,flag:`--workspace-id`,description:``,required:!0,valueType:`string`,location:`path`},{name:`dropId`,flag:`--drop-id`,description:``,required:!0,valueType:`string`,location:`path`},{name:`creativeId`,flag:`--creative-id`,description:``,required:!0,valueType:`string`,location:`path`},{name:`creativeRevisionId`,flag:`--creative-revision-id`,description:``,required:!0,valueType:`string`,location:`body`},{name:`target`,flag:`--target`,description:``,required:!0,valueType:`json`,location:`body`},{name:`body`,flag:`--body`,description:``,required:!0,valueType:`string`,location:`body`}],examples:[{description:`Example`,command:`adside creatives comments create --workspace-id <workspaceId> --drop-id <dropId> --creative-id <creativeId> --creative-revision-id <creativeRevisionId> --target '{}' --body <body>`}],output:{kind:`json`,description:`Pin feedback to a creative revision`},transport:{type:`rest`,method:`POST`,path:`/v1/workspaces/{workspaceId}/creatives/{dropId}/items/{creativeId}/comments`,auth:`user`,requestContentType:`application/json`}},{id:`creatives.comments.delete`,path:[`creatives`,`comments`,`delete`],summary:`Remove your unsubmitted creative feedback`,description:``,source:`rest`,options:[{name:`workspaceId`,flag:`--workspace-id`,description:``,required:!0,valueType:`string`,location:`path`},{name:`dropId`,flag:`--drop-id`,description:``,required:!0,valueType:`string`,location:`path`},{name:`commentId`,flag:`--comment-id`,description:``,required:!0,valueType:`string`,location:`path`}],examples:[{description:`Example`,command:`adside creatives comments delete --workspace-id <workspaceId> --drop-id <dropId> --comment-id <commentId>`}],output:{kind:`json`,description:`Remove your unsubmitted creative feedback`},transport:{type:`rest`,method:`DELETE`,path:`/v1/workspaces/{workspaceId}/creatives/{dropId}/comments/{commentId}`,auth:`user`}},{id:`creatives.comments.update`,path:[`creatives`,`comments`,`update`],summary:`Update your unsubmitted creative feedback`,description:``,source:`rest`,options:[{name:`workspaceId`,flag:`--workspace-id`,description:``,required:!0,valueType:`string`,location:`path`},{name:`dropId`,flag:`--drop-id`,description:``,required:!0,valueType:`string`,location:`path`},{name:`commentId`,flag:`--comment-id`,description:``,required:!0,valueType:`string`,location:`path`},{name:`body`,flag:`--body`,description:``,required:!0,valueType:`string`,location:`body`}],examples:[{description:`Example`,command:`adside creatives comments update --workspace-id <workspaceId> --drop-id <dropId> --comment-id <commentId> --body <body>`}],output:{kind:`json`,description:`Update your unsubmitted creative feedback`},transport:{type:`rest`,method:`PATCH`,path:`/v1/workspaces/{workspaceId}/creatives/{dropId}/comments/{commentId}`,auth:`user`,requestContentType:`application/json`}},{id:`creatives.copy`,path:[`creatives`,`copy`],summary:`Save export copy against an exact creative revision`,description:``,source:`rest`,options:[{name:`workspaceId`,flag:`--workspace-id`,description:``,required:!0,valueType:`string`,location:`path`},{name:`dropId`,flag:`--drop-id`,description:``,required:!0,valueType:`string`,location:`path`},{name:`creativeId`,flag:`--creative-id`,description:``,required:!0,valueType:`string`,location:`path`},{name:`baseCreativeRevisionId`,flag:`--base-creative-revision-id`,description:``,required:!0,valueType:`string`,location:`body`},{name:`copy`,flag:`--copy`,description:``,required:!0,valueType:`json`,location:`body`}],examples:[{description:`Example`,command:`adside creatives copy --workspace-id <workspaceId> --drop-id <dropId> --creative-id <creativeId> --base-creative-revision-id <baseCreativeRevisionId> --copy '{}'`}],output:{kind:`json`,description:`Save export copy against an exact creative revision`},transport:{type:`rest`,method:`PATCH`,path:`/v1/workspaces/{workspaceId}/creatives/{dropId}/items/{creativeId}/copy`,auth:`user`,requestContentType:`application/json`}},{id:`creatives.create`,path:[`creatives`,`create`],summary:`Start a creative drop; the sandbox reserves and generates its first batch. Omit creative count for Auto (brief quantity, otherwise 5).`,description:``,source:`rest`,generateRequestId:!0,options:[{name:`workspaceId`,flag:`--workspace-id`,description:``,required:!0,valueType:`string`,location:`path`},{name:`requestId`,flag:`--request-id`,description:`Submission identity (generated automatically if omitted)`,required:!1,valueType:`string`,location:`body`},{name:`prompt`,flag:`--prompt`,description:``,required:!0,valueType:`string`,location:`body`},{name:`creativeCount`,flag:`--creative-count`,description:`Exact quantity, overriding the prompt. Omit for Auto: infer from the prompt, or use 5 when unspecified.`,required:!1,valueType:`number`,location:`body`},{name:`references`,flag:`--references`,description:``,required:!1,valueType:`json`,location:`body`}],examples:[{description:`Example`,command:`adside creatives create --workspace-id <workspaceId> --prompt <prompt>`}],output:{kind:`json`,description:`Start a creative drop; the sandbox reserves and generates its first batch. Omit creative count for Auto (brief quantity, otherwise 5).`},transport:{type:`rest`,method:`POST`,path:`/v1/workspaces/{workspaceId}/creatives`,auth:`user`,requestContentType:`application/json`}},{id:`creatives.get`,path:[`creatives`,`get`],summary:`Read stable creative IDs, numbers and current render revisions`,description:``,source:`rest`,options:[{name:`workspaceId`,flag:`--workspace-id`,description:``,required:!0,valueType:`string`,location:`path`},{name:`dropId`,flag:`--drop-id`,description:``,required:!0,valueType:`string`,location:`path`}],examples:[{description:`Example`,command:`adside creatives get --workspace-id <workspaceId> --drop-id <dropId>`}],output:{kind:`json`,description:`Read stable creative IDs, numbers and current render revisions`},transport:{type:`rest`,method:`GET`,path:`/v1/workspaces/{workspaceId}/creatives/{dropId}`,auth:`user`}},{id:`creatives.list`,path:[`creatives`,`list`],summary:`List creative drops and their current rendered previews`,description:``,source:`rest`,options:[{name:`workspaceId`,flag:`--workspace-id`,description:``,required:!0,valueType:`string`,location:`path`},{name:`offset`,flag:`--offset`,description:``,required:!1,valueType:`number`,defaultValue:0,location:`query`},{name:`query`,flag:`--query`,description:``,required:!1,valueType:`string`,location:`query`}],examples:[{description:`Example`,command:`adside creatives list --workspace-id <workspaceId>`}],output:{kind:`json`,description:`List creative drops and their current rendered previews`},transport:{type:`rest`,method:`GET`,path:`/v1/workspaces/{workspaceId}/creatives`,auth:`user`}},{id:`creatives.messages.create`,path:[`creatives`,`messages`,`create`],summary:`Send a live drop conversation input`,description:``,source:`rest`,generateRequestId:!0,options:[{name:`workspaceId`,flag:`--workspace-id`,description:``,required:!0,valueType:`string`,location:`path`},{name:`dropId`,flag:`--drop-id`,description:``,required:!0,valueType:`string`,location:`path`},{name:`requestId`,flag:`--request-id`,description:`Submission identity (generated automatically if omitted)`,required:!1,valueType:`string`,location:`body`},{name:`instruction`,flag:`--instruction`,description:``,required:!0,valueType:`string`,location:`body`},{name:`references`,flag:`--references`,description:``,required:!1,valueType:`json`,location:`body`},{name:`expectedCreativeRevisionIds`,flag:`--expected-creative-revision-ids`,description:``,required:!1,valueType:`json`,location:`body`},{name:`targets`,flag:`--targets`,description:``,required:!1,valueType:`json`,location:`body`},{name:`commentIds`,flag:`--comment-ids`,description:``,required:!1,valueType:`json`,location:`body`}],examples:[{description:`Example`,command:`adside creatives messages create --workspace-id <workspaceId> --drop-id <dropId> --instruction <instruction>`}],output:{kind:`json`,description:`Send a live drop conversation input`},transport:{type:`rest`,method:`POST`,path:`/v1/workspaces/{workspaceId}/creatives/{dropId}/messages`,auth:`user`,requestContentType:`application/json`}},{id:`creatives.messages.list`,path:[`creatives`,`messages`,`list`],summary:`Read the shared drop conversation`,description:``,source:`rest`,options:[{name:`workspaceId`,flag:`--workspace-id`,description:``,required:!0,valueType:`string`,location:`path`},{name:`dropId`,flag:`--drop-id`,description:``,required:!0,valueType:`string`,location:`path`}],examples:[{description:`Example`,command:`adside creatives messages list --workspace-id <workspaceId> --drop-id <dropId>`}],output:{kind:`json`,description:`Read the shared drop conversation`},transport:{type:`rest`,method:`GET`,path:`/v1/workspaces/{workspaceId}/creatives/{dropId}/messages`,auth:`user`}},{id:`creatives.messages.resume`,path:[`creatives`,`messages`,`resume`],summary:`Explicitly resume a held conversation input`,description:``,source:`rest`,options:[{name:`workspaceId`,flag:`--workspace-id`,description:``,required:!0,valueType:`string`,location:`path`},{name:`dropId`,flag:`--drop-id`,description:``,required:!0,valueType:`string`,location:`path`},{name:`messageId`,flag:`--message-id`,description:``,required:!0,valueType:`string`,location:`path`}],examples:[{description:`Example`,command:`adside creatives messages resume --workspace-id <workspaceId> --drop-id <dropId> --message-id <messageId>`}],output:{kind:`json`,description:`Explicitly resume a held conversation input`},transport:{type:`rest`,method:`POST`,path:`/v1/workspaces/{workspaceId}/creatives/{dropId}/messages/{messageId}/resume`,auth:`user`}},{id:`creatives.messages.stop`,path:[`creatives`,`messages`,`stop`],summary:`Stop an exact conversation input`,description:``,source:`rest`,options:[{name:`workspaceId`,flag:`--workspace-id`,description:``,required:!0,valueType:`string`,location:`path`},{name:`dropId`,flag:`--drop-id`,description:``,required:!0,valueType:`string`,location:`path`},{name:`messageId`,flag:`--message-id`,description:``,required:!0,valueType:`string`,location:`path`}],examples:[{description:`Example`,command:`adside creatives messages stop --workspace-id <workspaceId> --drop-id <dropId> --message-id <messageId>`}],output:{kind:`json`,description:`Stop an exact conversation input`},transport:{type:`rest`,method:`POST`,path:`/v1/workspaces/{workspaceId}/creatives/{dropId}/messages/{messageId}/stop`,auth:`user`}},{id:`creatives.revert`,path:[`creatives`,`revert`],summary:`Restore a creative revision without changing other creatives`,description:``,source:`rest`,options:[{name:`workspaceId`,flag:`--workspace-id`,description:``,required:!0,valueType:`string`,location:`path`},{name:`dropId`,flag:`--drop-id`,description:``,required:!0,valueType:`string`,location:`path`},{name:`creativeId`,flag:`--creative-id`,description:``,required:!0,valueType:`string`,location:`path`},{name:`creativeRevisionId`,flag:`--creative-revision-id`,description:``,required:!0,valueType:`string`,location:`body`},{name:`expectedCreativeRevisionId`,flag:`--expected-creative-revision-id`,description:``,required:!0,valueType:`string`,location:`body`}],examples:[{description:`Example`,command:`adside creatives revert --workspace-id <workspaceId> --drop-id <dropId> --creative-id <creativeId> --creative-revision-id <creativeRevisionId> --expected-creative-revision-id <expectedCreativeRevisionId>`}],output:{kind:`json`,description:`Restore a creative revision without changing other creatives`},transport:{type:`rest`,method:`POST`,path:`/v1/workspaces/{workspaceId}/creatives/{dropId}/items/{creativeId}/revert`,auth:`user`,requestContentType:`application/json`}},{id:`creatives.review`,path:[`creatives`,`review`],summary:`Select or discard a creative for campaigns`,description:``,source:`rest`,options:[{name:`workspaceId`,flag:`--workspace-id`,description:``,required:!0,valueType:`string`,location:`path`},{name:`dropId`,flag:`--drop-id`,description:``,required:!0,valueType:`string`,location:`path`},{name:`creativeId`,flag:`--creative-id`,description:``,required:!0,valueType:`string`,location:`path`},{name:`reviewStatus`,flag:`--review-status`,description:``,required:!0,valueType:`string`,enum:[`unreviewed`,`kept`,`discarded`],location:`body`}],examples:[{description:`Example`,command:`adside creatives review --workspace-id <workspaceId> --drop-id <dropId> --creative-id <creativeId> --review-status unreviewed`}],output:{kind:`json`,description:`Select or discard a creative for campaigns`},transport:{type:`rest`,method:`PATCH`,path:`/v1/workspaces/{workspaceId}/creatives/{dropId}/items/{creativeId}/review`,auth:`user`,requestContentType:`application/json`}},{id:`creatives.revisions.get`,path:[`creatives`,`revisions`,`get`],summary:`Read a historical creative revision and its published media and copy`,description:``,source:`rest`,options:[{name:`workspaceId`,flag:`--workspace-id`,description:``,required:!0,valueType:`string`,location:`path`},{name:`dropId`,flag:`--drop-id`,description:``,required:!0,valueType:`string`,location:`path`},{name:`creativeId`,flag:`--creative-id`,description:``,required:!0,valueType:`string`,location:`path`},{name:`creativeRevisionId`,flag:`--creative-revision-id`,description:``,required:!0,valueType:`string`,location:`path`}],examples:[{description:`Example`,command:`adside creatives revisions get --workspace-id <workspaceId> --drop-id <dropId> --creative-id <creativeId> --creative-revision-id <creativeRevisionId>`}],output:{kind:`json`,description:`Read a historical creative revision and its published media and copy`},transport:{type:`rest`,method:`GET`,path:`/v1/workspaces/{workspaceId}/creatives/{dropId}/items/{creativeId}/revisions/{creativeRevisionId}`,auth:`user`}},{id:`creatives.runs.by-request-id`,path:[`creatives`,`runs`,`by-request-id`],summary:`Recover the exact receipt of an edit request without resubmitting`,description:``,source:`rest`,options:[{name:`workspaceId`,flag:`--workspace-id`,description:``,required:!0,valueType:`string`,location:`path`},{name:`dropId`,flag:`--drop-id`,description:``,required:!0,valueType:`string`,location:`path`},{name:`requestId`,flag:`--request-id`,description:``,required:!0,valueType:`string`,location:`query`}],examples:[{description:`Example`,command:`adside creatives runs by-request-id --workspace-id <workspaceId> --drop-id <dropId> --request-id <requestId>`}],output:{kind:`json`,description:`Recover the exact receipt of an edit request without resubmitting`},transport:{type:`rest`,method:`GET`,path:`/v1/workspaces/{workspaceId}/creatives/{dropId}/runs/by-request-id`,auth:`user`}},{id:`creatives.status`,path:[`creatives`,`status`],aliases:[[`creatives`,`result`]],summary:`Read an exact run's progress, terminal result and cleanup state`,description:``,source:`rest`,options:[{name:`workspaceId`,flag:`--workspace-id`,description:``,required:!0,valueType:`string`,location:`path`},{name:`dropId`,flag:`--drop-id`,description:``,required:!0,valueType:`string`,location:`path`},{name:`runId`,flag:`--run-id`,description:``,required:!0,valueType:`string`,location:`path`}],examples:[{description:`Example`,command:`adside creatives status --workspace-id <workspaceId> --drop-id <dropId> --run-id <runId>`}],output:{kind:`json`,description:`Read an exact run's progress, terminal result and cleanup state`},transport:{type:`rest`,method:`GET`,path:`/v1/workspaces/{workspaceId}/creatives/{dropId}/runs/{runId}`,auth:`user`}},{id:`credits.balance`,path:[`credits`,`balance`],summary:`Read the organization's media generation credit balance`,description:``,source:`rest`,options:[{name:`organizationId`,flag:`--organization-id`,description:``,required:!0,valueType:`string`,location:`path`}],examples:[{description:`Example`,command:`adside credits balance --organization-id <organizationId>`}],output:{kind:`json`,description:`Read the organization's media generation credit balance`},transport:{type:`rest`,method:`GET`,path:`/v1/organizations/{organizationId}/credits`,auth:`user`}},{id:`credits.ledger`,path:[`credits`,`ledger`],summary:`List where the organization's media generation credit went, newest first`,description:``,source:`rest`,options:[{name:`organizationId`,flag:`--organization-id`,description:``,required:!0,valueType:`string`,location:`path`},{name:`workspaceId`,flag:`--workspace-id`,description:``,required:!1,valueType:`string`,location:`query`},{name:`runId`,flag:`--run-id`,description:``,required:!1,valueType:`string`,location:`query`},{name:`jobId`,flag:`--job-id`,description:``,required:!1,valueType:`string`,location:`query`},{name:`type`,flag:`--type`,description:``,required:!1,valueType:`string`,enum:[`starting_credit`,`top_up`,`charge`,`reversal`,`adjustment`],location:`query`},{name:`cursor`,flag:`--cursor`,description:``,required:!1,valueType:`string`,location:`query`},{name:`limit`,flag:`--limit`,description:``,required:!1,valueType:`number`,defaultValue:50,location:`query`}],examples:[{description:`Example`,command:`adside credits ledger --organization-id <organizationId>`}],output:{kind:`json`,description:`List where the organization's media generation credit went, newest first`},transport:{type:`rest`,method:`GET`,path:`/v1/organizations/{organizationId}/credits/ledger`,auth:`user`}},{id:`google-ads.list_accessible_customers`,path:[`google-ads`,`accessible-customers`,`list`],summary:`List the Google Ads customer account this client is connected to. Always returns that one account — other accounts the credentials can reach belong to other clients and are not available here.`,description:``,source:`rest`,options:[{name:`workspaceId`,flag:`--workspace-id`,description:``,required:!0,valueType:`string`,location:`path`}],examples:[{description:`Example`,command:`adside google-ads accessible-customers list --workspace-id <workspaceId>`}],output:{kind:`json`,description:`List the Google Ads customer account this client is connected to. Always returns that one account — other accounts the credentials can reach belong to other clients and are not available here.`},transport:{type:`rest`,method:`POST`,path:`/v1/workspaces/{workspaceId}/google-ads/accessible-customers/list`,auth:`user`}},{id:`google-ads.list_ad_groups`,path:[`google-ads`,`ad-groups`,`list`],summary:`List ad groups for a campaign with bids, status, and rotation settings.`,description:``,source:`rest`,options:[{name:`workspaceId`,flag:`--workspace-id`,description:``,required:!0,valueType:`string`,location:`path`},{name:`customer_id`,flag:`--customer-id`,description:`Omit it: it defaults to the account this client is connected to, and any other account is refused.`,required:!1,valueType:`string`,location:`body`},{name:`campaign_id`,flag:`--campaign-id`,description:``,required:!0,valueType:`string`,location:`body`},{name:`status`,flag:`--status`,description:``,required:!1,valueType:`string`,enum:[`ENABLED`,`PAUSED`,`REMOVED`],location:`body`},{name:`limit`,flag:`--limit`,description:``,required:!1,valueType:`number`,defaultValue:100,location:`body`}],examples:[{description:`Example`,command:`adside google-ads ad-groups list --workspace-id <workspaceId> --campaign-id <campaign_id>`}],output:{kind:`json`,description:`List ad groups for a campaign with bids, status, and rotation settings.`},transport:{type:`rest`,method:`POST`,path:`/v1/workspaces/{workspaceId}/google-ads/ad-groups/list`,auth:`user`,requestContentType:`application/json`}},{id:`google-ads.list_google_ads`,path:[`google-ads`,`ads`,`list`],summary:`List ads in an ad group with responsive search/display ad details including headlines, descriptions, and ad strength.`,description:``,source:`rest`,options:[{name:`workspaceId`,flag:`--workspace-id`,description:``,required:!0,valueType:`string`,location:`path`},{name:`customer_id`,flag:`--customer-id`,description:`Omit it: it defaults to the account this client is connected to, and any other account is refused.`,required:!1,valueType:`string`,location:`body`},{name:`ad_group_id`,flag:`--ad-group-id`,description:``,required:!0,valueType:`string`,location:`body`},{name:`status`,flag:`--status`,description:``,required:!1,valueType:`string`,enum:[`ENABLED`,`PAUSED`,`REMOVED`],location:`body`},{name:`limit`,flag:`--limit`,description:``,required:!1,valueType:`number`,defaultValue:100,location:`body`}],examples:[{description:`Example`,command:`adside google-ads ads list --workspace-id <workspaceId> --ad-group-id <ad_group_id>`}],output:{kind:`json`,description:`List ads in an ad group with responsive search/display ad details including headlines, descriptions, and ad strength.`},transport:{type:`rest`,method:`POST`,path:`/v1/workspaces/{workspaceId}/google-ads/ads/list`,auth:`user`,requestContentType:`application/json`}},{id:`google-ads.list_asset_group_assets`,path:[`google-ads`,`asset-group-assets`,`list`],summary:`List the assets linked to one Performance Max asset group, including each exact AssetGroupAsset resource name, field type, status, asset ID and image dimensions. Defaults to non-removed links. Use before adding or unlinking assets, and again to verify the result.`,description:``,source:`rest`,options:[{name:`workspaceId`,flag:`--workspace-id`,description:``,required:!0,valueType:`string`,location:`path`},{name:`customer_id`,flag:`--customer-id`,description:`Omit it: it defaults to the account this client is connected to, and any other account is refused.`,required:!1,valueType:`string`,location:`body`},{name:`asset_group_id`,flag:`--asset-group-id`,description:``,required:!0,valueType:`string`,location:`body`},{name:`field_type`,flag:`--field-type`,description:``,required:!1,valueType:`string`,enum:[`HEADLINE`,`LONG_HEADLINE`,`DESCRIPTION`,`BUSINESS_NAME`,`MARKETING_IMAGE`,`SQUARE_MARKETING_IMAGE`,`PORTRAIT_MARKETING_IMAGE`,`TALL_PORTRAIT_MARKETING_IMAGE`,`LOGO`,`LANDSCAPE_LOGO`,`YOUTUBE_VIDEO`,`CALL_TO_ACTION_SELECTION`],location:`body`},{name:`status`,flag:`--status`,description:`Defaults to all non-removed links`,required:!1,valueType:`string`,enum:[`ENABLED`,`PAUSED`,`REMOVED`],location:`body`}],examples:[{description:`Example`,command:`adside google-ads asset-group-assets list --workspace-id <workspaceId> --asset-group-id <asset_group_id>`}],output:{kind:`json`,description:`List the assets linked to one Performance Max asset group, including each exact AssetGroupAsset resource name, field type, status, asset ID and image dimensions. Defaults to non-removed links. Use before adding or unlinking assets, and again to verify the result.`},transport:{type:`rest`,method:`POST`,path:`/v1/workspaces/{workspaceId}/google-ads/asset-group-assets/list`,auth:`user`,requestContentType:`application/json`}},{id:`google-ads.get_asset_group_product_filters`,path:[`google-ads`,`asset-group-product-filters`,`get`],summary:`Read and normalize Merchant Center product filters attached to one Performance Max asset group or every asset group in a campaign.`,description:``,source:`rest`,options:[{name:`workspaceId`,flag:`--workspace-id`,description:``,required:!0,valueType:`string`,location:`path`},{name:`customer_id`,flag:`--customer-id`,description:`Omit it: it defaults to the account this client is connected to, and any other account is refused.`,required:!1,valueType:`string`,location:`body`},{name:`campaign_id`,flag:`--campaign-id`,description:``,required:!1,valueType:`string`,location:`body`},{name:`asset_group_id`,flag:`--asset-group-id`,description:``,required:!1,valueType:`string`,location:`body`}],examples:[{description:`Example`,command:`adside google-ads asset-group-product-filters get --workspace-id <workspaceId>`}],output:{kind:`json`,description:`Read and normalize Merchant Center product filters attached to one Performance Max asset group or every asset group in a campaign.`},transport:{type:`rest`,method:`POST`,path:`/v1/workspaces/{workspaceId}/google-ads/asset-group-product-filters/get`,auth:`user`,requestContentType:`application/json`}},{id:`google-ads.list_asset_groups`,path:[`google-ads`,`asset-groups`,`list`],summary:`List asset groups for a Performance Max campaign with status and final URLs.`,description:``,source:`rest`,options:[{name:`workspaceId`,flag:`--workspace-id`,description:``,required:!0,valueType:`string`,location:`path`},{name:`customer_id`,flag:`--customer-id`,description:`Omit it: it defaults to the account this client is connected to, and any other account is refused.`,required:!1,valueType:`string`,location:`body`},{name:`campaign_id`,flag:`--campaign-id`,description:``,required:!0,valueType:`string`,location:`body`},{name:`status`,flag:`--status`,description:``,required:!1,valueType:`string`,enum:[`ENABLED`,`PAUSED`,`REMOVED`],location:`body`},{name:`limit`,flag:`--limit`,description:``,required:!1,valueType:`number`,defaultValue:100,location:`body`}],examples:[{description:`Example`,command:`adside google-ads asset-groups list --workspace-id <workspaceId> --campaign-id <campaign_id>`}],output:{kind:`json`,description:`List asset groups for a Performance Max campaign with status and final URLs.`},transport:{type:`rest`,method:`POST`,path:`/v1/workspaces/{workspaceId}/google-ads/asset-groups/list`,auth:`user`,requestContentType:`application/json`}},{id:`google-ads.list_assets`,path:[`google-ads`,`assets`,`list`],summary:`List assets (text, image, video, callout, promotion) for a Google Ads account. Filter by type. Search for an identical CALLOUT or PROMOTION before creating one so reusable account assets are not duplicated.`,description:``,source:`rest`,options:[{name:`workspaceId`,flag:`--workspace-id`,description:``,required:!0,valueType:`string`,location:`path`},{name:`customer_id`,flag:`--customer-id`,description:`Omit it: it defaults to the account this client is connected to, and any other account is refused.`,required:!1,valueType:`string`,location:`body`},{name:`type`,flag:`--type`,description:``,required:!1,valueType:`string`,enum:[`TEXT`,`IMAGE`,`YOUTUBE_VIDEO`,`CALLOUT`,`PROMOTION`],location:`body`},{name:`limit`,flag:`--limit`,description:``,required:!1,valueType:`number`,defaultValue:100,location:`body`}],examples:[{description:`Example`,command:`adside google-ads assets list --workspace-id <workspaceId>`}],output:{kind:`json`,description:`List assets (text, image, video, callout, promotion) for a Google Ads account. Filter by type. Search for an identical CALLOUT or PROMOTION before creating one so reusable account assets are not duplicated.`},transport:{type:`rest`,method:`POST`,path:`/v1/workspaces/{workspaceId}/google-ads/assets/list`,auth:`user`,requestContentType:`application/json`}},{id:`google-ads.list_audience_segments`,path:[`google-ads`,`audience-segments`,`list`],summary:"List Google's ready-made audience segments (in-market, affinity, custom). These attach with `audience_id`, and only Performance Max, Demand Gen and App ad groups accept them. For retargeting the client's own site visitors — the usual Display and Search remarketing case — use list_user_lists instead; it is a different resource with a different id.",description:``,source:`rest`,options:[{name:`workspaceId`,flag:`--workspace-id`,description:``,required:!0,valueType:`string`,location:`path`},{name:`customer_id`,flag:`--customer-id`,description:`Omit it: it defaults to the account this client is connected to, and any other account is refused.`,required:!1,valueType:`string`,location:`body`},{name:`limit`,flag:`--limit`,description:``,required:!1,valueType:`number`,defaultValue:100,location:`body`}],examples:[{description:`Example`,command:`adside google-ads audience-segments list --workspace-id <workspaceId>`}],output:{kind:`json`,description:"List Google's ready-made audience segments (in-market, affinity, custom). These attach with `audience_id`, and only Performance Max, Demand Gen and App ad groups accept them. For retargeting the client's own site visitors — the usual Display and Search remarketing case — use list_user_lists instead; it is a different resource with a different id."},transport:{type:`rest`,method:`POST`,path:`/v1/workspaces/{workspaceId}/google-ads/audience-segments/list`,auth:`user`,requestContentType:`application/json`}},{id:`google-ads.get_campaign_ad_schedules`,path:[`google-ads`,`campaign-ad-schedules`,`get`],summary:`Read the complete recurring weekly ad schedule for a Google Ads campaign. Schedules use the account time zone; an empty result means there is no schedule restriction and the campaign is eligible 24/7.`,description:``,source:`rest`,options:[{name:`workspaceId`,flag:`--workspace-id`,description:``,required:!0,valueType:`string`,location:`path`},{name:`customer_id`,flag:`--customer-id`,description:`Omit it: it defaults to the account this client is connected to, and any other account is refused.`,required:!1,valueType:`string`,location:`body`},{name:`campaign_id`,flag:`--campaign-id`,description:``,required:!0,valueType:`string`,location:`body`}],examples:[{description:`Example`,command:`adside google-ads campaign-ad-schedules get --workspace-id <workspaceId> --campaign-id <campaign_id>`}],output:{kind:`json`,description:`Read the complete recurring weekly ad schedule for a Google Ads campaign. Schedules use the account time zone; an empty result means there is no schedule restriction and the campaign is eligible 24/7.`},transport:{type:`rest`,method:`POST`,path:`/v1/workspaces/{workspaceId}/google-ads/campaign-ad-schedules/get`,auth:`user`,requestContentType:`application/json`}},{id:`google-ads.list_campaign_assets`,path:[`google-ads`,`campaign-assets`,`list`],summary:`List callout and promotion assets linked at campaign level. Use this before add_assets_to_campaign to avoid duplicate links, and use it for Performance Max offers that cannot be linked to an asset group.`,description:``,source:`rest`,options:[{name:`workspaceId`,flag:`--workspace-id`,description:``,required:!0,valueType:`string`,location:`path`},{name:`customer_id`,flag:`--customer-id`,description:`Omit it: it defaults to the account this client is connected to, and any other account is refused.`,required:!1,valueType:`string`,location:`body`},{name:`campaign_id`,flag:`--campaign-id`,description:``,required:!0,valueType:`string`,location:`body`},{name:`field_type`,flag:`--field-type`,description:``,required:!1,valueType:`string`,enum:[`CALLOUT`,`PROMOTION`],location:`body`},{name:`status`,flag:`--status`,description:``,required:!1,valueType:`string`,enum:[`ENABLED`,`PAUSED`,`REMOVED`],location:`body`},{name:`limit`,flag:`--limit`,description:``,required:!1,valueType:`number`,defaultValue:100,location:`body`}],examples:[{description:`Example`,command:`adside google-ads campaign-assets list --workspace-id <workspaceId> --campaign-id <campaign_id>`}],output:{kind:`json`,description:`List callout and promotion assets linked at campaign level. Use this before add_assets_to_campaign to avoid duplicate links, and use it for Performance Max offers that cannot be linked to an asset group.`},transport:{type:`rest`,method:`POST`,path:`/v1/workspaces/{workspaceId}/google-ads/campaign-assets/list`,auth:`user`,requestContentType:`application/json`}},{id:`google-ads.list_campaign_budgets`,path:[`google-ads`,`campaign-budgets`,`list`],summary:`List campaign budgets for a Google Ads account with usage information.`,description:``,source:`rest`,options:[{name:`workspaceId`,flag:`--workspace-id`,description:``,required:!0,valueType:`string`,location:`path`},{name:`customer_id`,flag:`--customer-id`,description:`Omit it: it defaults to the account this client is connected to, and any other account is refused.`,required:!1,valueType:`string`,location:`body`},{name:`status`,flag:`--status`,description:``,required:!1,valueType:`string`,enum:[`ENABLED`,`REMOVED`],location:`body`},{name:`limit`,flag:`--limit`,description:``,required:!1,valueType:`number`,defaultValue:100,location:`body`}],examples:[{description:`Example`,command:`adside google-ads campaign-budgets list --workspace-id <workspaceId>`}],output:{kind:`json`,description:`List campaign budgets for a Google Ads account with usage information.`},transport:{type:`rest`,method:`POST`,path:`/v1/workspaces/{workspaceId}/google-ads/campaign-budgets/list`,auth:`user`,requestContentType:`application/json`}},{id:`google-ads.list_campaign_negative_keyword_lists`,path:[`google-ads`,`campaign-negative-keyword-lists`,`list`],summary:`List the negative keyword lists attached to a campaign, with exact link resource names. Performance Max negatives apply to Search and Shopping inventory only. For own-brand variants, consider brand exclusions. Display/Video negative keywords use contextual matching, not Search query matching.`,description:``,source:`rest`,options:[{name:`workspaceId`,flag:`--workspace-id`,description:``,required:!0,valueType:`string`,location:`path`},{name:`customer_id`,flag:`--customer-id`,description:`Omit it: it defaults to the account this client is connected to, and any other account is refused.`,required:!1,valueType:`string`,location:`body`},{name:`campaign_id`,flag:`--campaign-id`,description:``,required:!0,valueType:`string`,location:`body`}],examples:[{description:`Example`,command:`adside google-ads campaign-negative-keyword-lists list --workspace-id <workspaceId> --campaign-id <campaign_id>`}],output:{kind:`json`,description:`List the negative keyword lists attached to a campaign, with exact link resource names. Performance Max negatives apply to Search and Shopping inventory only. For own-brand variants, consider brand exclusions. Display/Video negative keywords use contextual matching, not Search query matching.`},transport:{type:`rest`,method:`POST`,path:`/v1/workspaces/{workspaceId}/google-ads/campaign-negative-keyword-lists/list`,auth:`user`,requestContentType:`application/json`}},{id:`google-ads.list_campaign_negative_keywords`,path:[`google-ads`,`campaign-negative-keywords`,`list`],summary:`List direct negative keyword criteria for one campaign. Shared list members are separate: use list_campaign_negative_keyword_lists. Performance Max negatives apply to Search and Shopping inventory only. For own-brand variants, consider brand exclusions. Display/Video negative keywords use contextual matching, not Search query matching.`,description:``,source:`rest`,options:[{name:`workspaceId`,flag:`--workspace-id`,description:``,required:!0,valueType:`string`,location:`path`},{name:`customer_id`,flag:`--customer-id`,description:`Omit it: it defaults to the account this client is connected to, and any other account is refused.`,required:!1,valueType:`string`,location:`body`},{name:`campaign_id`,flag:`--campaign-id`,description:``,required:!0,valueType:`string`,location:`body`}],examples:[{description:`Example`,command:`adside google-ads campaign-negative-keywords list --workspace-id <workspaceId> --campaign-id <campaign_id>`}],output:{kind:`json`,description:`List direct negative keyword criteria for one campaign. Shared list members are separate: use list_campaign_negative_keyword_lists. Performance Max negatives apply to Search and Shopping inventory only. For own-brand variants, consider brand exclusions. Display/Video negative keywords use contextual matching, not Search query matching.`},transport:{type:`rest`,method:`POST`,path:`/v1/workspaces/{workspaceId}/google-ads/campaign-negative-keywords/list`,auth:`user`,requestContentType:`application/json`}},{id:`google-ads.get_campaign_performance`,path:[`google-ads`,`campaign-performance`,`get`],summary:`Get campaign performance metrics (impressions, clicks, cost, conversions, CTR, CPC). Supports date ranges and segmentation.`,description:``,source:`rest`,options:[{name:`workspaceId`,flag:`--workspace-id`,description:``,required:!0,valueType:`string`,location:`path`},{name:`customer_id`,flag:`--customer-id`,description:`Omit it: it defaults to the account this client is connected to, and any other account is refused.`,required:!1,valueType:`string`,location:`body`},{name:`date_range`,flag:`--date-range`,description:``,required:!1,valueType:`string`,defaultValue:`LAST_30_DAYS`,enum:[`LAST_7_DAYS`,`LAST_14_DAYS`,`LAST_30_DAYS`,`LAST_90_DAYS`,`THIS_MONTH`,`LAST_MONTH`,`CUSTOM`],location:`body`},{name:`start_date`,flag:`--start-date`,description:`YYYY-MM-DD, required when date_range is CUSTOM`,required:!1,valueType:`string`,location:`body`},{name:`end_date`,flag:`--end-date`,description:`YYYY-MM-DD, required when date_range is CUSTOM`,required:!1,valueType:`string`,location:`body`},{name:`campaign_ids`,flag:`--campaign-ids`,description:``,required:!1,valueType:`json`,location:`body`},{name:`metrics`,flag:`--metrics`,description:`Metrics to retrieve, e.g. metrics.impressions, metrics.clicks, metrics.cost_micros`,required:!1,valueType:`json`,location:`body`},{name:`segments`,flag:`--segments`,description:`Segment fields, e.g. segments.date, segments.device`,required:!1,valueType:`json`,location:`body`},{name:`order_by`,flag:`--order-by`,description:``,required:!1,valueType:`string`,location:`body`},{name:`limit`,flag:`--limit`,description:``,required:!1,valueType:`number`,defaultValue:100,location:`body`}],examples:[{description:`Example`,command:`adside google-ads campaign-performance get --workspace-id <workspaceId>`}],output:{kind:`json`,description:`Get campaign performance metrics (impressions, clicks, cost, conversions, CTR, CPC). Supports date ranges and segmentation.`},transport:{type:`rest`,method:`POST`,path:`/v1/workspaces/{workspaceId}/google-ads/campaign-performance/get`,auth:`user`,requestContentType:`application/json`}},{id:`google-ads.list_google_campaigns`,path:[`google-ads`,`campaigns`,`list`],summary:`List campaigns with optional filters for status and type. Includes budget and bidding information.`,description:``,source:`rest`,options:[{name:`workspaceId`,flag:`--workspace-id`,description:``,required:!0,valueType:`string`,location:`path`},{name:`customer_id`,flag:`--customer-id`,description:`Omit it: it defaults to the account this client is connected to, and any other account is refused.`,required:!1,valueType:`string`,location:`body`},{name:`status`,flag:`--status`,description:``,required:!1,valueType:`string`,enum:[`ENABLED`,`PAUSED`,`REMOVED`],location:`body`},{name:`advertising_channel_type`,flag:`--advertising-channel-type`,description:``,required:!1,valueType:`string`,enum:[`SEARCH`,`PERFORMANCE_MAX`,`DISPLAY`,`VIDEO`,`SHOPPING`,`DEMAND_GEN`],location:`body`},{name:`limit`,flag:`--limit`,description:``,required:!1,valueType:`number`,defaultValue:100,location:`body`}],examples:[{description:`Example`,command:`adside google-ads campaigns list --workspace-id <workspaceId>`}],output:{kind:`json`,description:`List campaigns with optional filters for status and type. Includes budget and bidding information.`},transport:{type:`rest`,method:`POST`,path:`/v1/workspaces/{workspaceId}/google-ads/campaigns/list`,auth:`user`,requestContentType:`application/json`}},{id:`google-ads.list_conversion_actions`,path:[`google-ads`,`conversion-actions`,`list`],summary:`List conversion actions, including primary_for_goal, ownership, and value settings. include_in_conversions_metric is deprecated; use primary_for_goal. Custom goals can still bid on secondary actions. Filter status=REMOVED to inspect removed actions.`,description:``,source:`rest`,options:[{name:`workspaceId`,flag:`--workspace-id`,description:``,required:!0,valueType:`string`,location:`path`},{name:`customer_id`,flag:`--customer-id`,description:`Omit it: it defaults to the account this client is connected to, and any other account is refused.`,required:!1,valueType:`string`,location:`body`},{name:`status`,flag:`--status`,description:``,required:!1,valueType:`string`,enum:[`ENABLED`,`REMOVED`,`HIDDEN`],location:`body`},{name:`limit`,flag:`--limit`,description:``,required:!1,valueType:`number`,defaultValue:100,location:`body`}],examples:[{description:`Example`,command:`adside google-ads conversion-actions list --workspace-id <workspaceId>`}],output:{kind:`json`,description:`List conversion actions, including primary_for_goal, ownership, and value settings. include_in_conversions_metric is deprecated; use primary_for_goal. Custom goals can still bid on secondary actions. Filter status=REMOVED to inspect removed actions.`},transport:{type:`rest`,method:`POST`,path:`/v1/workspaces/{workspaceId}/google-ads/conversion-actions/list`,auth:`user`,requestContentType:`application/json`}},{id:`google-ads.list_customer_conversion_goals`,path:[`google-ads`,`customer-conversion-goals`,`list`],summary:`List existing account-default conversion goals, their exact resource names, and biddability. Customer goals affect all primary actions with matching category and origin in campaigns using account defaults. Campaign overrides and custom goals are independent; custom goals can bid on secondary actions.`,description:``,source:`rest`,options:[{name:`workspaceId`,flag:`--workspace-id`,description:``,required:!0,valueType:`string`,location:`path`},{name:`customer_id`,flag:`--customer-id`,description:`Omit it: it defaults to the account this client is connected to, and any other account is refused.`,required:!1,valueType:`string`,location:`body`}],examples:[{description:`Example`,command:`adside google-ads customer-conversion-goals list --workspace-id <workspaceId>`}],output:{kind:`json`,description:`List existing account-default conversion goals, their exact resource names, and biddability. Customer goals affect all primary actions with matching category and origin in campaigns using account defaults. Campaign overrides and custom goals are independent; custom goals can bid on secondary actions.`},transport:{type:`rest`,method:`POST`,path:`/v1/workspaces/{workspaceId}/google-ads/customer-conversion-goals/list`,auth:`user`,requestContentType:`application/json`}},{id:`google-ads.get_customer`,path:[`google-ads`,`customers`,`get`],summary:`Get Google Ads account details including name, currency, timezone, and status.`,description:``,source:`rest`,options:[{name:`workspaceId`,flag:`--workspace-id`,description:``,required:!0,valueType:`string`,location:`path`},{name:`customer_id`,flag:`--customer-id`,description:`Omit it: it defaults to the account this client is connected to, and any other account is refused.`,required:!1,valueType:`string`,location:`body`}],examples:[{description:`Example`,command:`adside google-ads customers get --workspace-id <workspaceId>`}],output:{kind:`json`,description:`Get Google Ads account details including name, currency, timezone, and status.`},transport:{type:`rest`,method:`POST`,path:`/v1/workspaces/{workspaceId}/google-ads/customers/get`,auth:`user`,requestContentType:`application/json`}},{id:`google-ads.get_geo_targets`,path:[`google-ads`,`geo-targets`,`get`],summary:`Search geographic targets by name (countries, regions, cities). Returns geo target constant IDs for campaign targeting.`,description:``,source:`rest`,options:[{name:`workspaceId`,flag:`--workspace-id`,description:``,required:!0,valueType:`string`,location:`path`},{name:`customer_id`,flag:`--customer-id`,description:`Omit it: it defaults to the account this client is connected to, and any other account is refused.`,required:!1,valueType:`string`,location:`body`},{name:`query`,flag:`--query`,description:`Location name to search, e.g. 'New York' or 'France'`,required:!0,valueType:`string`,location:`body`},{name:`country_code`,flag:`--country-code`,description:`ISO country code to filter results, e.g. 'US'`,required:!1,valueType:`string`,location:`body`},{name:`limit`,flag:`--limit`,description:``,required:!1,valueType:`number`,defaultValue:20,location:`body`}],examples:[{description:`Example`,command:`adside google-ads geo-targets get --workspace-id <workspaceId> --query <query>`}],output:{kind:`json`,description:`Search geographic targets by name (countries, regions, cities). Returns geo target constant IDs for campaign targeting.`},transport:{type:`rest`,method:`POST`,path:`/v1/workspaces/{workspaceId}/google-ads/geo-targets/get`,auth:`user`,requestContentType:`application/json`}},{id:`google-ads.suggest_keyword_ad_groups`,path:[`google-ads`,`keyword-ad-groups`,`suggest`],summary:`Ask Google to assign proposed keywords to the most relevant existing ad groups. Pass real IDs returned by list_ad_groups. Returns normalized keyword and match-type suggestions without adding or changing anything.`,description:``,source:`rest`,options:[{name:`workspaceId`,flag:`--workspace-id`,description:``,required:!0,valueType:`string`,location:`path`},{name:`customer_id`,flag:`--customer-id`,description:`Omit it: it defaults to the account this client is connected to, and any other account is refused.`,required:!1,valueType:`string`,location:`body`},{name:`keywords`,flag:`--keywords`,description:``,required:!0,valueType:`json`,location:`body`},{name:`ad_group_ids`,flag:`--ad-group-ids`,description:`Existing ad group IDs from list_ad_groups. Google only suggests among these groups.`,required:!0,valueType:`json`,location:`body`}],examples:[{description:`Example`,command:`adside google-ads keyword-ad-groups suggest --workspace-id <workspaceId> --keywords '{}' --ad-group-ids '{}'`}],output:{kind:`json`,description:`Ask Google to assign proposed keywords to the most relevant existing ad groups. Pass real IDs returned by list_ad_groups. Returns normalized keyword and match-type suggestions without adding or changing anything.`},transport:{type:`rest`,method:`POST`,path:`/v1/workspaces/{workspaceId}/google-ads/keyword-ad-groups/suggest`,auth:`user`,requestContentType:`application/json`}},{id:`google-ads.generate_keyword_ideas`,path:[`google-ads`,`keyword-ideas`,`generate`],summary:`Generate new Google Search keyword ideas from up to 20 seed terms, a public page, both, or a whole site. Returns historical volume, competition and bid estimates without changing the account. Resolve geo and language IDs first; paginate explicitly with next_page_token.`,description:``,source:`rest`,options:[{name:`workspaceId`,flag:`--workspace-id`,description:``,required:!0,valueType:`string`,location:`path`},{name:`customer_id`,flag:`--customer-id`,description:`Omit it: it defaults to the account this client is connected to, and any other account is refused.`,required:!1,valueType:`string`,location:`body`},{name:`seed`,flag:`--seed`,description:`Exactly one seed mode: keywords, one page, both, or a whole site.`,required:!0,valueType:`json`,location:`body`},{name:`geo_target_ids`,flag:`--geo-target-ids`,description:`Geo target IDs from get_geo_targets. Strongly recommended; omitting them requests worldwide ideas.`,required:!1,valueType:`json`,location:`body`},{name:`language_id`,flag:`--language-id`,description:`Language ID from get_languages. Defaults to English (1000).`,required:!1,valueType:`string`,defaultValue:`1000`,location:`body`},{name:`network`,flag:`--network`,description:``,required:!1,valueType:`string`,defaultValue:`GOOGLE_SEARCH`,enum:[`GOOGLE_SEARCH`,`GOOGLE_SEARCH_AND_PARTNERS`],location:`body`},{name:`include_adult_keywords`,flag:`--include-adult-keywords`,description:``,required:!1,valueType:`boolean`,defaultValue:!1,location:`body`},{name:`include_average_cpc`,flag:`--include-average-cpc`,description:``,required:!1,valueType:`boolean`,defaultValue:!0,location:`body`},{name:`include_monthly_volumes`,flag:`--include-monthly-volumes`,description:`Show the monthly volume series returned for every idea.`,required:!1,valueType:`boolean`,defaultValue:!1,location:`body`},{name:`page_size`,flag:`--page-size`,description:`Ideas to return in this call. Deliberately capped below Google's 10,000-result limit to protect agent context.`,required:!1,valueType:`number`,defaultValue:100,location:`body`},{name:`page_token`,flag:`--page-token`,description:`Exact next-page token from a previous call. All other request fields must remain identical.`,required:!1,valueType:`string`,location:`body`}],examples:[{description:`Example`,command:`adside google-ads keyword-ideas generate --workspace-id <workspaceId> --seed '{}'`}],output:{kind:`json`,description:`Generate new Google Search keyword ideas from up to 20 seed terms, a public page, both, or a whole site. Returns historical volume, competition and bid estimates without changing the account. Resolve geo and language IDs first; paginate explicitly with next_page_token.`},transport:{type:`rest`,method:`POST`,path:`/v1/workspaces/{workspaceId}/google-ads/keyword-ideas/generate`,auth:`user`,requestContentType:`application/json`}},{id:`google-ads.get_keyword_performance`,path:[`google-ads`,`keyword-performance`,`get`],summary:`Get keyword-level performance metrics with quality score breakdown (expected CTR, ad relevance, landing page experience).`,description:``,source:`rest`,options:[{name:`workspaceId`,flag:`--workspace-id`,description:``,required:!0,valueType:`string`,location:`path`},{name:`customer_id`,flag:`--customer-id`,description:`Omit it: it defaults to the account this client is connected to, and any other account is refused.`,required:!1,valueType:`string`,location:`body`},{name:`ad_group_id`,flag:`--ad-group-id`,description:``,required:!1,valueType:`string`,location:`body`},{name:`campaign_id`,flag:`--campaign-id`,description:``,required:!1,valueType:`string`,location:`body`},{name:`date_range`,flag:`--date-range`,description:``,required:!1,valueType:`string`,defaultValue:`LAST_30_DAYS`,enum:[`LAST_7_DAYS`,`LAST_14_DAYS`,`LAST_30_DAYS`,`LAST_90_DAYS`,`THIS_MONTH`,`LAST_MONTH`,`CUSTOM`],location:`body`},{name:`start_date`,flag:`--start-date`,description:``,required:!1,valueType:`string`,location:`body`},{name:`end_date`,flag:`--end-date`,description:``,required:!1,valueType:`string`,location:`body`},{name:`limit`,flag:`--limit`,description:``,required:!1,valueType:`number`,defaultValue:100,location:`body`}],examples:[{description:`Example`,command:`adside google-ads keyword-performance get --workspace-id <workspaceId>`}],output:{kind:`json`,description:`Get keyword-level performance metrics with quality score breakdown (expected CTR, ad relevance, landing page experience).`},transport:{type:`rest`,method:`POST`,path:`/v1/workspaces/{workspaceId}/google-ads/keyword-performance/get`,auth:`user`,requestContentType:`application/json`}},{id:`google-ads.forecast_keyword_plan`,path:[`google-ads`,`keyword-plan`,`forecast`],summary:`Forecast cost plus clicks or conversions for a hypothetical Search keyword plan. Supports Manual CPC, Maximize Clicks and Maximize Conversions. This is a read-only estimate and creates no campaigns, ad groups or keywords.`,description:``,source:`rest`,options:[{name:`workspaceId`,flag:`--workspace-id`,description:``,required:!0,valueType:`string`,location:`path`},{name:`customer_id`,flag:`--customer-id`,description:`Omit it: it defaults to the account this client is connected to, and any other account is refused.`,required:!1,valueType:`string`,location:`body`},{name:`ad_groups`,flag:`--ad-groups`,description:`The hypothetical ad-group structure. This does not create anything in Google Ads.`,required:!0,valueType:`json`,location:`body`},{name:`geo_target_ids`,flag:`--geo-target-ids`,description:`Geo target IDs from get_geo_targets.`,required:!1,valueType:`json`,location:`body`},{name:`language_ids`,flag:`--language-ids`,description:``,required:!1,valueType:`json`,location:`body`},{name:`bidding_strategy`,flag:`--bidding-strategy`,description:``,required:!0,valueType:`json`,location:`body`},{name:`currency_code`,flag:`--currency-code`,description:`Omit to use the connected account's currency.`,required:!1,valueType:`string`,location:`body`},{name:`start_date`,flag:`--start-date`,description:`Forecast start in the account time zone. Must be in the future.`,required:!1,valueType:`string`,location:`body`},{name:`end_date`,flag:`--end-date`,description:`Forecast end in the account time zone, no more than one year ahead.`,required:!1,valueType:`string`,location:`body`}],examples:[{description:`Example`,command:`adside google-ads keyword-plan forecast --workspace-id <workspaceId> --ad-groups '{}' --bidding-strategy '{}'`}],output:{kind:`json`,description:`Forecast cost plus clicks or conversions for a hypothetical Search keyword plan. Supports Manual CPC, Maximize Clicks and Maximize Conversions. This is a read-only estimate and creates no campaigns, ad groups or keywords.`},transport:{type:`rest`,method:`POST`,path:`/v1/workspaces/{workspaceId}/google-ads/keyword-plan/forecast`,auth:`user`,requestContentType:`application/json`}},{id:`google-ads.get_keyword_plan_metrics`,path:[`google-ads`,`keyword-plan-metrics`,`get`],summary:`Google Keyword Planner data for keywords that are NOT yet in the account: average monthly searches, top-of-page bid range, competition and average CPC, for pre-launch keyword research. Use this to size conquesting or non-brand terms before committing budget. For keywords already running in the account, use get_keyword_performance instead.`,description:``,source:`rest`,options:[{name:`workspaceId`,flag:`--workspace-id`,description:``,required:!0,valueType:`string`,location:`path`},{name:`customer_id`,flag:`--customer-id`,description:`Omit it: it defaults to the account this client is connected to, and any other account is refused.`,required:!1,valueType:`string`,location:`body`},{name:`keywords`,flag:`--keywords`,description:`The exact terms to measure. Send them all in one call — Google allows only 1 request/second per account, so splitting is slower, not safer.`,required:!0,valueType:`json`,location:`body`},{name:`geo_target_ids`,flag:`--geo-target-ids`,description:`Geo target constant IDs (from get_geo_targets), e.g. '21137' for California. STRONGLY recommended: omitting this returns worldwide volumes, which can be an order of magnitude higher and is almost never what was asked.`,required:!1,valueType:`json`,location:`body`},{name:`language_id`,flag:`--language-id`,description:`Language constant ID (from get_languages). Defaults to '1000' (English).`,required:!1,valueType:`string`,location:`body`},{name:`network`,flag:`--network`,description:`GOOGLE_SEARCH matches what Keyword Planner shows by default.`,required:!1,valueType:`string`,defaultValue:`GOOGLE_SEARCH`,enum:[`GOOGLE_SEARCH`,`GOOGLE_SEARCH_AND_PARTNERS`],location:`body`},{name:`include_average_cpc`,flag:`--include-average-cpc`,description:`Include the historical average CPC alongside the bid range.`,required:!1,valueType:`boolean`,defaultValue:!0,location:`body`},{name:`include_monthly_volumes`,flag:`--include-monthly-volumes`,description:`Include the 12-month volume series per keyword. Off by default: it multiplies the response size by ~12 and is only useful for seasonality.`,required:!1,valueType:`boolean`,defaultValue:!1,location:`body`}],examples:[{description:`Example`,command:`adside google-ads keyword-plan-metrics get --workspace-id <workspaceId> --keywords '{}'`}],output:{kind:`json`,description:`Google Keyword Planner data for keywords that are NOT yet in the account: average monthly searches, top-of-page bid range, competition and average CPC, for pre-launch keyword research. Use this to size conquesting or non-brand terms before committing budget. For keywords already running in the account, use get_keyword_performance instead.`},transport:{type:`rest`,method:`POST`,path:`/v1/workspaces/{workspaceId}/google-ads/keyword-plan-metrics/get`,auth:`user`,requestContentType:`application/json`}},{id:`google-ads.list_keywords`,path:[`google-ads`,`keywords`,`list`],summary:`List keywords for an ad group with match type, quality score, and performance data.`,description:``,source:`rest`,options:[{name:`workspaceId`,flag:`--workspace-id`,description:``,required:!0,valueType:`string`,location:`path`},{name:`customer_id`,flag:`--customer-id`,description:`Omit it: it defaults to the account this client is connected to, and any other account is refused.`,required:!1,valueType:`string`,location:`body`},{name:`ad_group_id`,flag:`--ad-group-id`,description:``,required:!0,valueType:`string`,location:`body`},{name:`status`,flag:`--status`,description:``,required:!1,valueType:`string`,enum:[`ENABLED`,`PAUSED`,`REMOVED`],location:`body`},{name:`limit`,flag:`--limit`,description:``,required:!1,valueType:`number`,defaultValue:100,location:`body`}],examples:[{description:`Example`,command:`adside google-ads keywords list --workspace-id <workspaceId> --ad-group-id <ad_group_id>`}],output:{kind:`json`,description:`List keywords for an ad group with match type, quality score, and performance data.`},transport:{type:`rest`,method:`POST`,path:`/v1/workspaces/{workspaceId}/google-ads/keywords/list`,auth:`user`,requestContentType:`application/json`}},{id:`google-ads.get_languages`,path:[`google-ads`,`languages`,`get`],summary:`Search Google Ads language constants by name or ISO code. Returns the language IDs used for language targeting and for keyword planning.`,description:``,source:`rest`,options:[{name:`workspaceId`,flag:`--workspace-id`,description:``,required:!0,valueType:`string`,location:`path`},{name:`customer_id`,flag:`--customer-id`,description:`Omit it: it defaults to the account this client is connected to, and any other account is refused.`,required:!1,valueType:`string`,location:`body`},{name:`query`,flag:`--query`,description:`Filter by language name or ISO code, e.g. 'Spanish' or 'es'.`,required:!1,valueType:`string`,location:`body`},{name:`limit`,flag:`--limit`,description:``,required:!1,valueType:`number`,defaultValue:200,location:`body`}],examples:[{description:`Example`,command:`adside google-ads languages get --workspace-id <workspaceId>`}],output:{kind:`json`,description:`Search Google Ads language constants by name or ISO code. Returns the language IDs used for language targeting and for keyword planning.`},transport:{type:`rest`,method:`POST`,path:`/v1/workspaces/{workspaceId}/google-ads/languages/get`,auth:`user`,requestContentType:`application/json`}},{id:`google-ads.list_negative_keyword_lists`,path:[`google-ads`,`negative-keyword-lists`,`list`],summary:`List active reusable campaign negative keyword lists with member and campaign counts. Does not include account-level or brand lists.`,description:``,source:`rest`,options:[{name:`workspaceId`,flag:`--workspace-id`,description:``,required:!0,valueType:`string`,location:`path`},{name:`customer_id`,flag:`--customer-id`,description:`Omit it: it defaults to the account this client is connected to, and any other account is refused.`,required:!1,valueType:`string`,location:`body`}],examples:[{description:`Example`,command:`adside google-ads negative-keyword-lists list --workspace-id <workspaceId>`}],output:{kind:`json`,description:`List active reusable campaign negative keyword lists with member and campaign counts. Does not include account-level or brand lists.`},transport:{type:`rest`,method:`POST`,path:`/v1/workspaces/{workspaceId}/google-ads/negative-keyword-lists/list`,auth:`user`,requestContentType:`application/json`}},{id:`google-ads.list_product_filter_values`,path:[`google-ads`,`product-filter-values`,`list`],summary:`List values currently present in a Performance Max campaign's Merchant Center inventory for a supported product filter attribute. Use this before setting filters.`,description:``,source:`rest`,options:[{name:`workspaceId`,flag:`--workspace-id`,description:``,required:!0,valueType:`string`,location:`path`},{name:`customer_id`,flag:`--customer-id`,description:`Omit it: it defaults to the account this client is connected to, and any other account is refused.`,required:!1,valueType:`string`,location:`body`},{name:`campaign_id`,flag:`--campaign-id`,description:``,required:!0,valueType:`string`,location:`body`},{name:`attribute`,flag:`--attribute`,description:``,required:!0,valueType:`string`,enum:[`product_type_l1`,`product_type_l2`,`product_type_l3`,`product_type_l4`,`product_type_l5`,`brand`,`custom_label_0`,`custom_label_1`,`custom_label_2`,`custom_label_3`,`custom_label_4`],location:`body`},{name:`statuses`,flag:`--statuses`,description:``,required:!1,valueType:`json`,location:`body`},{name:`search`,flag:`--search`,description:``,required:!1,valueType:`string`,location:`body`},{name:`limit`,flag:`--limit`,description:``,required:!1,valueType:`number`,defaultValue:100,location:`body`}],examples:[{description:`Example`,command:`adside google-ads product-filter-values list --workspace-id <workspaceId> --campaign-id <campaign_id> --attribute product_type_l1`}],output:{kind:`json`,description:`List values currently present in a Performance Max campaign's Merchant Center inventory for a supported product filter attribute. Use this before setting filters.`},transport:{type:`rest`,method:`POST`,path:`/v1/workspaces/{workspaceId}/google-ads/product-filter-values/list`,auth:`user`,requestContentType:`application/json`}},{id:`google-ads.get_search_terms_report`,path:[`google-ads`,`search-terms-report`,`get`],summary:`Get actual search queries that triggered your ads (vs keywords you're targeting). Essential for negative keyword discovery.`,description:``,source:`rest`,options:[{name:`workspaceId`,flag:`--workspace-id`,description:``,required:!0,valueType:`string`,location:`path`},{name:`customer_id`,flag:`--customer-id`,description:`Omit it: it defaults to the account this client is connected to, and any other account is refused.`,required:!1,valueType:`string`,location:`body`},{name:`campaign_id`,flag:`--campaign-id`,description:``,required:!1,valueType:`string`,location:`body`},{name:`ad_group_id`,flag:`--ad-group-id`,description:``,required:!1,valueType:`string`,location:`body`},{name:`date_range`,flag:`--date-range`,description:``,required:!1,valueType:`string`,defaultValue:`LAST_30_DAYS`,enum:[`LAST_7_DAYS`,`LAST_14_DAYS`,`LAST_30_DAYS`,`LAST_90_DAYS`,`THIS_MONTH`,`LAST_MONTH`,`CUSTOM`],location:`body`},{name:`start_date`,flag:`--start-date`,description:``,required:!1,valueType:`string`,location:`body`},{name:`end_date`,flag:`--end-date`,description:``,required:!1,valueType:`string`,location:`body`},{name:`limit`,flag:`--limit`,description:``,required:!1,valueType:`number`,defaultValue:100,location:`body`}],examples:[{description:`Example`,command:`adside google-ads search-terms-report get --workspace-id <workspaceId>`}],output:{kind:`json`,description:`Get actual search queries that triggered your ads (vs keywords you're targeting). Essential for negative keyword discovery.`},transport:{type:`rest`,method:`POST`,path:`/v1/workspaces/{workspaceId}/google-ads/search-terms-report/get`,auth:`user`,requestContentType:`application/json`}},{id:`google-ads.list_shared_negative_keywords`,path:[`google-ads`,`shared-negative-keywords`,`list`],summary:`List all keyword members of one active shared negative keyword list, including exact resource names for removal.`,description:``,source:`rest`,options:[{name:`workspaceId`,flag:`--workspace-id`,description:``,required:!0,valueType:`string`,location:`path`},{name:`customer_id`,flag:`--customer-id`,description:`Omit it: it defaults to the account this client is connected to, and any other account is refused.`,required:!1,valueType:`string`,location:`body`},{name:`shared_set_id`,flag:`--shared-set-id`,description:``,required:!0,valueType:`string`,location:`body`}],examples:[{description:`Example`,command:`adside google-ads shared-negative-keywords list --workspace-id <workspaceId> --shared-set-id <shared_set_id>`}],output:{kind:`json`,description:`List all keyword members of one active shared negative keyword list, including exact resource names for removal.`},transport:{type:`rest`,method:`POST`,path:`/v1/workspaces/{workspaceId}/google-ads/shared-negative-keywords/list`,auth:`user`,requestContentType:`application/json`}},{id:`google-ads.list_user_lists`,path:[`google-ads`,`user-lists`,`list`],summary:`List the account's remarketing lists — the people who visited the client's own site, as opposed to the ready-made segments Google publishes (those are list_audience_segments). This is what Display and Search retargeting target. Use it to find the id to pass to add_audience_to_campaign as user_list_id, and to check whether a list has enough members: Google will not serve to a list under roughly 100 people.`,description:``,source:`rest`,options:[{name:`workspaceId`,flag:`--workspace-id`,description:``,required:!0,valueType:`string`,location:`path`},{name:`customer_id`,flag:`--customer-id`,description:`Omit it: it defaults to the account this client is connected to, and any other account is refused.`,required:!1,valueType:`string`,location:`body`},{name:`limit`,flag:`--limit`,description:``,required:!1,valueType:`number`,defaultValue:100,location:`body`}],examples:[{description:`Example`,command:`adside google-ads user-lists list --workspace-id <workspaceId>`}],output:{kind:`json`,description:`List the account's remarketing lists — the people who visited the client's own site, as opposed to the ready-made segments Google publishes (those are list_audience_segments). This is what Display and Search retargeting target. Use it to find the id to pass to add_audience_to_campaign as user_list_id, and to check whether a list has enough members: Google will not serve to a list under roughly 100 people.`},transport:{type:`rest`,method:`POST`,path:`/v1/workspaces/{workspaceId}/google-ads/user-lists/list`,auth:`user`,requestContentType:`application/json`}},{id:`google-tag-manager.get_container_config`,path:[`google-tag-manager`,`container-config`,`get`],summary:"Read the tags, triggers and variables of a GTM container, from the published version (`live`) or from a draft workspace.\n\n`live` is what visitors actually execute. A container whose draft holds a perfect setup but was never published tracks nothing, so answer every 'is tracking working' question from `live`.",description:``,source:`rest`,options:[{name:`workspaceId`,flag:`--workspace-id`,description:``,required:!0,valueType:`string`,location:`path`},{name:`container_path`,flag:`--container-path`,description:'The container\'s `path`, as returned by list_gtm_containers — e.g. "accounts/6000123/containers/12345678". Not the GTM-XXXXXX public id.',required:!0,valueType:`string`,location:`body`},{name:`source`,flag:`--source`,description:"`live` reads the published version — what visitors actually execute today, and the only thing that reflects reality. `draft` reads a workspace's unpublished changes. Audit questions are always about `live`; `draft` is for checking work that has not been published yet.",required:!1,valueType:`string`,defaultValue:`live`,enum:[`live`,`draft`],location:`body`},{name:`workspace_path`,flag:`--workspace-path`,description:"Only with source=draft. The workspace `path` to read. Defaults to the container's Default Workspace when omitted.",required:!1,valueType:`string`,location:`body`}],examples:[{description:`Example`,command:`adside google-tag-manager container-config get --workspace-id <workspaceId> --container-path <container_path>`}],output:{kind:`json`,description:"Read the tags, triggers and variables of a GTM container, from the published version (`live`) or from a draft workspace.\n\n`live` is what visitors actually execute. A container whose draft holds a perfect setup but was never published tracks nothing, so answer every 'is tracking working' question from `live`."},transport:{type:`rest`,method:`POST`,path:`/v1/workspaces/{workspaceId}/google-tag-manager/container-config/get`,auth:`user`,requestContentType:`application/json`}},{id:`google-tag-manager.list_gtm_containers`,path:[`google-tag-manager`,`containers`,`list`],summary:`List this client's Google Tag Manager containers. This is the entry point — no other GTM tool can run without a container path from here.
6
+
7
+ Only the GTM account connected for this client is listed. The connected Google login may administer other clients' accounts too; those are never shown and their containers are refused.
8
+
9
+ Read \`usageContext\` before doing anything else: a \`server\` container has a different tag-type namespace, so web tags do not exist in it and their absence is normal rather than a problem.`,description:``,source:`rest`,options:[{name:`workspaceId`,flag:`--workspace-id`,description:``,required:!0,valueType:`string`,location:`path`}],examples:[{description:`Example`,command:`adside google-tag-manager containers list --workspace-id <workspaceId>`}],output:{kind:`json`,description:`List this client's Google Tag Manager containers. This is the entry point — no other GTM tool can run without a container path from here.
10
+
11
+ Only the GTM account connected for this client is listed. The connected Google login may administer other clients' accounts too; those are never shown and their containers are refused.
12
+
13
+ Read \`usageContext\` before doing anything else: a \`server\` container has a different tag-type namespace, so web tags do not exist in it and their absence is normal rather than a problem.`},transport:{type:`rest`,method:`POST`,path:`/v1/workspaces/{workspaceId}/google-tag-manager/containers/list`,auth:`user`}},{id:`google-tag-manager.audit_conversion_tracking`,path:[`google-tag-manager`,`conversion-tracking`,`audit`],summary:"Audit what a GTM container actually deploys for conversion tracking, reading the **published** version.\n\nCovers the container half of the audit: base tags (a Google tag on all pages, and something storing the click id), conversion tags without a firing trigger, paused tags, malformed conversion ids, missing consent settings, and the Meta pixel (base code on all pages, conversion events firing on every page, missing sequencing or event id). It ends with the cross-checks to run next with `list_conversion_actions` and `get_account_pixels` — those need the ad accounts and cannot be answered from the container alone.",description:``,source:`rest`,options:[{name:`workspaceId`,flag:`--workspace-id`,description:``,required:!0,valueType:`string`,location:`path`},{name:`container_path`,flag:`--container-path`,description:'The container\'s `path`, from list_gtm_containers — e.g. "accounts/6000123/containers/12345678".',required:!0,valueType:`string`,location:`body`}],examples:[{description:`Example`,command:`adside google-tag-manager conversion-tracking audit --workspace-id <workspaceId> --container-path <container_path>`}],output:{kind:`json`,description:"Audit what a GTM container actually deploys for conversion tracking, reading the **published** version.\n\nCovers the container half of the audit: base tags (a Google tag on all pages, and something storing the click id), conversion tags without a firing trigger, paused tags, malformed conversion ids, missing consent settings, and the Meta pixel (base code on all pages, conversion events firing on every page, missing sequencing or event id). It ends with the cross-checks to run next with `list_conversion_actions` and `get_account_pixels` — those need the ad accounts and cannot be answered from the container alone."},transport:{type:`rest`,method:`POST`,path:`/v1/workspaces/{workspaceId}/google-tag-manager/conversion-tracking/audit`,auth:`user`,requestContentType:`application/json`}},{id:`linkedin.get_ad_account`,path:[`linkedin`,`ad-accounts`,`get`],summary:`Get details of a LinkedIn Ad Account (name, status, currency, type, serving statuses)`,description:``,source:`rest`,options:[{name:`workspaceId`,flag:`--workspace-id`,description:``,required:!0,valueType:`string`,location:`path`},{name:`account_id`,flag:`--account-id`,description:`LinkedIn Ad Account ID (numeric). Omit it: it defaults to the account this client is connected to, and any other account is refused.`,required:!1,valueType:`string`,location:`body`}],examples:[{description:`Example`,command:`adside linkedin ad-accounts get --workspace-id <workspaceId>`}],output:{kind:`json`,description:`Get details of a LinkedIn Ad Account (name, status, currency, type, serving statuses)`},transport:{type:`rest`,method:`POST`,path:`/v1/workspaces/{workspaceId}/linkedin/ad-accounts/get`,auth:`user`,requestContentType:`application/json`}},{id:`linkedin.list_ad_accounts`,path:[`linkedin`,`ad-accounts`,`list`],summary:`Get the one LinkedIn Ad Account this client is connected to. Every other tool defaults to it, so you rarely need to pass account_id at all — and an account id from anywhere else (memory, an earlier conversation, another client) will be refused.`,description:``,source:`rest`,options:[{name:`workspaceId`,flag:`--workspace-id`,description:``,required:!0,valueType:`string`,location:`path`}],examples:[{description:`Example`,command:`adside linkedin ad-accounts list --workspace-id <workspaceId>`}],output:{kind:`json`,description:`Get the one LinkedIn Ad Account this client is connected to. Every other tool defaults to it, so you rarely need to pass account_id at all — and an account id from anywhere else (memory, an earlier conversation, another client) will be refused.`},transport:{type:`rest`,method:`POST`,path:`/v1/workspaces/{workspaceId}/linkedin/ad-accounts/list`,auth:`user`}},{id:`linkedin.get_ad_segment`,path:[`linkedin`,`ad-segment`,`get`],summary:`Look up one audience segment by its urn:li:adSegment: URN or id. Use this to name a segment found inside a campaign's or saved audience's targeting_criteria: list_ad_segments only returns segments owned by the account in scope, so a segment belonging to a sibling ad account of the same agency appears there as a bare URN. When the segment cannot be read, this says whether it no longer exists or is simply outside this LinkedIn connection's reach — a distinction LinkedIn itself answers with the same 404 for both.`,description:``,source:`rest`,options:[{name:`workspaceId`,flag:`--workspace-id`,description:``,required:!0,valueType:`string`,location:`path`},{name:`segment_id`,flag:`--segment-id`,description:`The segment's numeric id, or the full urn:li:adSegment:… as it appears inside a targeting_criteria.`,required:!0,valueType:`string`,location:`body`}],examples:[{description:`Example`,command:`adside linkedin ad-segment get --workspace-id <workspaceId> --segment-id <segment_id>`}],output:{kind:`json`,description:`Look up one audience segment by its urn:li:adSegment: URN or id. Use this to name a segment found inside a campaign's or saved audience's targeting_criteria: list_ad_segments only returns segments owned by the account in scope, so a segment belonging to a sibling ad account of the same agency appears there as a bare URN. When the segment cannot be read, this says whether it no longer exists or is simply outside this LinkedIn connection's reach — a distinction LinkedIn itself answers with the same 404 for both.`},transport:{type:`rest`,method:`POST`,path:`/v1/workspaces/{workspaceId}/linkedin/ad-segment/get`,auth:`user`,requestContentType:`application/json`}},{id:`linkedin.list_ad_segments`,path:[`linkedin`,`ad-segments`,`list`],summary:`List the audience segments an ad account owns: uploaded contact/company lists (type BULK) and website or engagement retargeting audiences (type RETARGETING). Each result carries the targeting facet its URN belongs under, so it can be dropped straight into a campaign's targeting_criteria. Use this before targeting a matched audience — segment URNs cannot be discovered through search_targeting_facets.`,description:``,source:`rest`,options:[{name:`workspaceId`,flag:`--workspace-id`,description:``,required:!0,valueType:`string`,location:`path`},{name:`account_id`,flag:`--account-id`,description:`LinkedIn Ad Account ID (numeric). Omit it: it defaults to the account this client is connected to, and any other account is refused.`,required:!1,valueType:`string`,location:`body`},{name:`start`,flag:`--start`,description:`Index of the first segment to return (offset paging).`,required:!1,valueType:`number`,defaultValue:0,location:`body`},{name:`count`,flag:`--count`,description:"How many segments to return. LinkedIn defaults to 10 if unset, so this tool asks for 100; check `next_start` in the response for more.",required:!1,valueType:`number`,defaultValue:100,location:`body`}],examples:[{description:`Example`,command:`adside linkedin ad-segments list --workspace-id <workspaceId>`}],output:{kind:`json`,description:`List the audience segments an ad account owns: uploaded contact/company lists (type BULK) and website or engagement retargeting audiences (type RETARGETING). Each result carries the targeting facet its URN belongs under, so it can be dropped straight into a campaign's targeting_criteria. Use this before targeting a matched audience — segment URNs cannot be discovered through search_targeting_facets.`},transport:{type:`rest`,method:`POST`,path:`/v1/workspaces/{workspaceId}/linkedin/ad-segments/list`,auth:`user`,requestContentType:`application/json`}},{id:`linkedin.get_analytics`,path:[`linkedin`,`analytics`,`get`],summary:`Get performance analytics (impressions, clicks, cost, conversions, etc.) for LinkedIn ad entities. Group by account, campaign group, campaign, or creative with daily/monthly/all-time granularity.`,description:``,source:`rest`,options:[{name:`workspaceId`,flag:`--workspace-id`,description:``,required:!0,valueType:`string`,location:`path`},{name:`account_id`,flag:`--account-id`,description:`LinkedIn Ad Account ID. Omit it: it defaults to the account this client is connected to, and any other account is refused.`,required:!1,valueType:`string`,location:`body`},{name:`pivot`,flag:`--pivot`,description:`Dimension to group results by`,required:!0,valueType:`string`,enum:[`ACCOUNT`,`CAMPAIGN_GROUP`,`CAMPAIGN`,`CREATIVE`],location:`body`},{name:`time_granularity`,flag:`--time-granularity`,description:`Time granularity for results`,required:!1,valueType:`string`,defaultValue:`ALL`,enum:[`DAILY`,`MONTHLY`,`ALL`],location:`body`},{name:`date_range_start`,flag:`--date-range-start`,description:`Start date (inclusive)`,required:!0,valueType:`json`,location:`body`},{name:`date_range_end`,flag:`--date-range-end`,description:`End date (inclusive). If omitted, returns data up to now.`,required:!1,valueType:`json`,location:`body`},{name:`campaign_ids`,flag:`--campaign-ids`,description:`Filter by campaign IDs`,required:!1,valueType:`json`,location:`body`},{name:`campaign_group_ids`,flag:`--campaign-group-ids`,description:`Filter by campaign group IDs`,required:!1,valueType:`json`,location:`body`},{name:`creative_ids`,flag:`--creative-ids`,description:`Filter by creative URNs`,required:!1,valueType:`json`,location:`body`},{name:`fields`,flag:`--fields`,description:`Specific metrics to return (max 20). Default: impressions, clicks. Examples: costInLocalCurrency, landingPageClicks, likes, shares, externalWebsiteConversions`,required:!1,valueType:`json`,location:`body`}],examples:[{description:`Example`,command:`adside linkedin analytics get --workspace-id <workspaceId> --pivot ACCOUNT --date-range-start '{}'`}],output:{kind:`json`,description:`Get performance analytics (impressions, clicks, cost, conversions, etc.) for LinkedIn ad entities. Group by account, campaign group, campaign, or creative with daily/monthly/all-time granularity.`},transport:{type:`rest`,method:`POST`,path:`/v1/workspaces/{workspaceId}/linkedin/analytics/get`,auth:`user`,requestContentType:`application/json`}},{id:`linkedin.get_audience_size_estimate`,path:[`linkedin`,`audience-size-estimate`,`get`],summary:`Estimate how many LinkedIn members match a targeting criteria. Returns a rounded member count. Call this BEFORE creating a campaign: LinkedIn accepts a campaign with no targeting at all and stores no audience for it, so an unchecked campaign can be created that cannot reach anyone.`,description:``,source:`rest`,options:[{name:`workspaceId`,flag:`--workspace-id`,description:``,required:!0,valueType:`string`,location:`path`},{name:`targeting_criteria`,flag:`--targeting-criteria`,description:`Targeting criteria with AND/OR structure. Keys are FACET URNs, not bare names: {"include":{"and":[{"or":{"urn:li:adTargetingFacet:locations":["urn:li:geo:105015875"]}}]}}. A bare "locations" key is refused. Same format as campaign targeting; get the URNs from search_targeting_facets.`,required:!0,valueType:`json`,location:`body`}],examples:[{description:`Example`,command:`adside linkedin audience-size-estimate get --workspace-id <workspaceId> --targeting-criteria '{}'`}],output:{kind:`json`,description:`Estimate how many LinkedIn members match a targeting criteria. Returns a rounded member count. Call this BEFORE creating a campaign: LinkedIn accepts a campaign with no targeting at all and stores no audience for it, so an unchecked campaign can be created that cannot reach anyone.`},transport:{type:`rest`,method:`POST`,path:`/v1/workspaces/{workspaceId}/linkedin/audience-size-estimate/get`,auth:`user`,requestContentType:`application/json`}},{id:`linkedin.list_campaign_conversion_rules`,path:[`linkedin`,`campaign-conversion-rules`,`list`],summary:`List which conversion rules are attached to the given campaigns. Use this to answer 'why is this campaign reporting no conversions?' — an unattached rule is credited to nothing. Returns the conversion URNs plus when each was attached; pass those URNs to get_conversion_rule for the detail.`,description:``,source:`rest`,options:[{name:`workspaceId`,flag:`--workspace-id`,description:``,required:!0,valueType:`string`,location:`path`},{name:`campaign_ids`,flag:`--campaign-ids`,description:`Campaign ids (numeric) or urn:li:sponsoredCampaign: URNs to look up.`,required:!0,valueType:`json`,location:`body`}],examples:[{description:`Example`,command:`adside linkedin campaign-conversion-rules list --workspace-id <workspaceId> --campaign-ids '{}'`}],output:{kind:`json`,description:`List which conversion rules are attached to the given campaigns. Use this to answer 'why is this campaign reporting no conversions?' — an unattached rule is credited to nothing. Returns the conversion URNs plus when each was attached; pass those URNs to get_conversion_rule for the detail.`},transport:{type:`rest`,method:`POST`,path:`/v1/workspaces/{workspaceId}/linkedin/campaign-conversion-rules/list`,auth:`user`,requestContentType:`application/json`}},{id:`linkedin.get_campaign_group`,path:[`linkedin`,`campaign-groups`,`get`],summary:'Get the complete configuration for one LinkedIn campaign group, including schedule, budget, audit/version, objective, and delivery settings. Use list_campaign_groups for discovery and this getter only when full detail is required. VOCABULARY: the API\'s `campaignGroup` is what Campaign Manager shows as "Campaign" (campaignGroup="Campaign", campaign="Ad set", creative="Ad"). Say both names when reporting to a user, or they will look in the wrong tab and think nothing happened.',description:``,source:`rest`,options:[{name:`workspaceId`,flag:`--workspace-id`,description:``,required:!0,valueType:`string`,location:`path`},{name:`account_id`,flag:`--account-id`,description:``,required:!1,valueType:`string`,location:`body`},{name:`campaign_group_id`,flag:`--campaign-group-id`,description:`Campaign group ID or urn:li:sponsoredCampaignGroup URN`,required:!0,valueType:`string`,location:`body`}],examples:[{description:`Example`,command:`adside linkedin campaign-groups get --workspace-id <workspaceId> --campaign-group-id <campaign_group_id>`}],output:{kind:`json`,description:'Get the complete configuration for one LinkedIn campaign group, including schedule, budget, audit/version, objective, and delivery settings. Use list_campaign_groups for discovery and this getter only when full detail is required. VOCABULARY: the API\'s `campaignGroup` is what Campaign Manager shows as "Campaign" (campaignGroup="Campaign", campaign="Ad set", creative="Ad"). Say both names when reporting to a user, or they will look in the wrong tab and think nothing happened.'},transport:{type:`rest`,method:`POST`,path:`/v1/workspaces/{workspaceId}/linkedin/campaign-groups/get`,auth:`user`,requestContentType:`application/json`}},{id:`linkedin.list_campaign_groups`,path:[`linkedin`,`campaign-groups`,`list`],summary:'Search and list campaign groups for a LinkedIn Ad Account. Filter by status, name, or test flag. Supports cursor-based pagination. VOCABULARY: the API\'s `campaignGroup` is what Campaign Manager shows as "Campaign" (campaignGroup="Campaign", campaign="Ad set", creative="Ad"). Say both names when reporting to a user, or they will look in the wrong tab and think nothing happened.',description:``,source:`rest`,options:[{name:`workspaceId`,flag:`--workspace-id`,description:``,required:!0,valueType:`string`,location:`path`},{name:`account_id`,flag:`--account-id`,description:`LinkedIn Ad Account ID. Omit it: it defaults to the account this client is connected to, and any other account is refused.`,required:!1,valueType:`string`,location:`body`},{name:`status`,flag:`--status`,description:`Filter by campaign group status`,required:!1,valueType:`string`,enum:[`ACTIVE`,`ARCHIVED`,`CANCELED`,`DRAFT`,`PAUSED`,`PENDING_DELETION`,`REMOVED`],location:`body`},{name:`name`,flag:`--name`,description:`Filter by campaign group name`,required:!1,valueType:`string`,location:`body`},{name:`test`,flag:`--test`,description:`Filter by test (true) or non-test (false) campaign groups`,required:!1,valueType:`boolean`,location:`body`},{name:`sort_order`,flag:`--sort-order`,description:`Sort order by campaign group ID (default: ASCENDING)`,required:!1,valueType:`string`,enum:[`ASCENDING`,`DESCENDING`],location:`body`},{name:`page_size`,flag:`--page-size`,description:`Number of results per page (max 1000)`,required:!1,valueType:`number`,defaultValue:100,location:`body`},{name:`page_token`,flag:`--page-token`,description:`Cursor token for next page of results`,required:!1,valueType:`string`,location:`body`}],examples:[{description:`Example`,command:`adside linkedin campaign-groups list --workspace-id <workspaceId>`}],output:{kind:`json`,description:'Search and list campaign groups for a LinkedIn Ad Account. Filter by status, name, or test flag. Supports cursor-based pagination. VOCABULARY: the API\'s `campaignGroup` is what Campaign Manager shows as "Campaign" (campaignGroup="Campaign", campaign="Ad set", creative="Ad"). Say both names when reporting to a user, or they will look in the wrong tab and think nothing happened.'},transport:{type:`rest`,method:`POST`,path:`/v1/workspaces/{workspaceId}/linkedin/campaign-groups/list`,auth:`user`,requestContentType:`application/json`}},{id:`linkedin.verify_campaign_readiness`,path:[`linkedin`,`campaign-readiness`,`verify`],summary:`Verify campaign readiness by checking serving statuses, budget, targeting, and LinkedIn's cross-field campaign rules (objective/format, optimization target/cost type, Connected TV). Returns a diagnostic report with issues and recommendations.`,description:``,source:`rest`,options:[{name:`workspaceId`,flag:`--workspace-id`,description:``,required:!0,valueType:`string`,location:`path`},{name:`account_id`,flag:`--account-id`,description:`LinkedIn Ad Account ID. Omit it: it defaults to the account this client is connected to, and any other account is refused.`,required:!1,valueType:`string`,location:`body`},{name:`campaign_id`,flag:`--campaign-id`,description:`Specific campaign ID to verify. If omitted, checks all ACTIVE campaigns.`,required:!1,valueType:`string`,location:`body`}],examples:[{description:`Example`,command:`adside linkedin campaign-readiness verify --workspace-id <workspaceId>`}],output:{kind:`json`,description:`Verify campaign readiness by checking serving statuses, budget, targeting, and LinkedIn's cross-field campaign rules (objective/format, optimization target/cost type, Connected TV). Returns a diagnostic report with issues and recommendations.`},transport:{type:`rest`,method:`POST`,path:`/v1/workspaces/{workspaceId}/linkedin/campaign-readiness/verify`,auth:`user`,requestContentType:`application/json`}},{id:`linkedin.get_linkedin_campaign`,path:[`linkedin`,`campaigns`,`get`],summary:'Get the complete configuration for one LinkedIn campaign, including targetingCriteria, version, schedule, optimization, budget, audit stamps, and delivery settings. Use list/search for discovery, then this getter before any targeting update. VOCABULARY: the API\'s `campaign` is what Campaign Manager shows as "Ad set" (campaignGroup="Campaign", campaign="Ad set", creative="Ad"). Say both names when reporting to a user, or they will look in the wrong tab and think nothing happened.',description:``,source:`rest`,options:[{name:`workspaceId`,flag:`--workspace-id`,description:``,required:!0,valueType:`string`,location:`path`},{name:`account_id`,flag:`--account-id`,description:`LinkedIn Ad Account ID. Omit it: it defaults to the connected account.`,required:!1,valueType:`string`,location:`body`},{name:`campaign_id`,flag:`--campaign-id`,description:`Campaign ID or urn:li:sponsoredCampaign URN`,required:!0,valueType:`string`,location:`body`}],examples:[{description:`Example`,command:`adside linkedin campaigns get --workspace-id <workspaceId> --campaign-id <campaign_id>`}],output:{kind:`json`,description:'Get the complete configuration for one LinkedIn campaign, including targetingCriteria, version, schedule, optimization, budget, audit stamps, and delivery settings. Use list/search for discovery, then this getter before any targeting update. VOCABULARY: the API\'s `campaign` is what Campaign Manager shows as "Ad set" (campaignGroup="Campaign", campaign="Ad set", creative="Ad"). Say both names when reporting to a user, or they will look in the wrong tab and think nothing happened.'},transport:{type:`rest`,method:`POST`,path:`/v1/workspaces/{workspaceId}/linkedin/campaigns/get`,auth:`user`,requestContentType:`application/json`}},{id:`linkedin.list_linkedin_campaigns`,path:[`linkedin`,`campaigns`,`list`],summary:`List campaigns for a LinkedIn Ad Account. Filter by status, type, campaign group, or name. Supports cursor-based pagination. Read servingStatuses, not status, to tell whether a campaign is actually delivering: status is what the advertiser set, servingStatuses is LinkedIn's verdict (RUNNABLE, or a *_HOLD explaining why it is not serving). VOCABULARY: the API's \`campaign\` is what Campaign Manager shows as "Ad set" (campaignGroup="Campaign", campaign="Ad set", creative="Ad"). Say both names when reporting to a user, or they will look in the wrong tab and think nothing happened.`,description:``,source:`rest`,options:[{name:`workspaceId`,flag:`--workspace-id`,description:``,required:!0,valueType:`string`,location:`path`},{name:`account_id`,flag:`--account-id`,description:`LinkedIn Ad Account ID. Omit it: it defaults to the account this client is connected to, and any other account is refused.`,required:!1,valueType:`string`,location:`body`},{name:`status`,flag:`--status`,description:`Filter by campaign status`,required:!1,valueType:`string`,enum:[`ACTIVE`,`PAUSED`,`ARCHIVED`,`COMPLETED`,`CANCELED`,`DRAFT`,`PENDING_DELETION`,`REMOVED`],location:`body`},{name:`campaign_group_id`,flag:`--campaign-group-id`,description:`Filter by campaign group ID`,required:!1,valueType:`string`,location:`body`},{name:`type`,flag:`--type`,description:`Filter by campaign type`,required:!1,valueType:`string`,enum:[`TEXT_AD`,`SPONSORED_UPDATES`,`SPONSORED_INMAILS`,`DYNAMIC`],location:`body`},{name:`name`,flag:`--name`,description:`Filter by campaign name`,required:!1,valueType:`string`,location:`body`},{name:`test`,flag:`--test`,description:`Filter by test (true) or non-test (false)`,required:!1,valueType:`boolean`,location:`body`},{name:`sort_order`,flag:`--sort-order`,description:`Sort order by campaign ID (default: ASCENDING)`,required:!1,valueType:`string`,enum:[`ASCENDING`,`DESCENDING`],location:`body`},{name:`page_size`,flag:`--page-size`,description:`Number of results per page (max 1000)`,required:!1,valueType:`number`,defaultValue:100,location:`body`},{name:`page_token`,flag:`--page-token`,description:`Cursor token for next page of results`,required:!1,valueType:`string`,location:`body`}],examples:[{description:`Example`,command:`adside linkedin campaigns list --workspace-id <workspaceId>`}],output:{kind:`json`,description:`List campaigns for a LinkedIn Ad Account. Filter by status, type, campaign group, or name. Supports cursor-based pagination. Read servingStatuses, not status, to tell whether a campaign is actually delivering: status is what the advertiser set, servingStatuses is LinkedIn's verdict (RUNNABLE, or a *_HOLD explaining why it is not serving). VOCABULARY: the API's \`campaign\` is what Campaign Manager shows as "Ad set" (campaignGroup="Campaign", campaign="Ad set", creative="Ad"). Say both names when reporting to a user, or they will look in the wrong tab and think nothing happened.`},transport:{type:`rest`,method:`POST`,path:`/v1/workspaces/{workspaceId}/linkedin/campaigns/list`,auth:`user`,requestContentType:`application/json`}},{id:`linkedin.search_campaigns`,path:[`linkedin`,`campaigns`,`search`],summary:'Search campaigns with multiple filters (IDs, statuses, types, campaign groups). More flexible than list_campaigns for complex queries. As with list_linkedin_campaigns, servingStatuses — not status — says whether a campaign is actually delivering. VOCABULARY: the API\'s `campaign` is what Campaign Manager shows as "Ad set" (campaignGroup="Campaign", campaign="Ad set", creative="Ad"). Say both names when reporting to a user, or they will look in the wrong tab and think nothing happened.',description:``,source:`rest`,options:[{name:`workspaceId`,flag:`--workspace-id`,description:``,required:!0,valueType:`string`,location:`path`},{name:`account_id`,flag:`--account-id`,description:`LinkedIn Ad Account ID. Omit it: it defaults to the account this client is connected to, and any other account is refused.`,required:!1,valueType:`string`,location:`body`},{name:`campaign_ids`,flag:`--campaign-ids`,description:`List of campaign IDs to fetch`,required:!1,valueType:`json`,location:`body`},{name:`statuses`,flag:`--statuses`,description:`Filter by multiple statuses`,required:!1,valueType:`json`,location:`body`},{name:`campaign_group_ids`,flag:`--campaign-group-ids`,description:`Filter by multiple campaign group IDs`,required:!1,valueType:`json`,location:`body`},{name:`types`,flag:`--types`,description:`Filter by multiple campaign types`,required:!1,valueType:`json`,location:`body`},{name:`sort_order`,flag:`--sort-order`,description:`Sort order by campaign ID`,required:!1,valueType:`string`,enum:[`ASCENDING`,`DESCENDING`],location:`body`},{name:`page_size`,flag:`--page-size`,description:`Page size`,required:!1,valueType:`number`,defaultValue:100,location:`body`},{name:`page_token`,flag:`--page-token`,description:`Cursor token for next page`,required:!1,valueType:`string`,location:`body`}],examples:[{description:`Example`,command:`adside linkedin campaigns search --workspace-id <workspaceId>`}],output:{kind:`json`,description:'Search campaigns with multiple filters (IDs, statuses, types, campaign groups). More flexible than list_campaigns for complex queries. As with list_linkedin_campaigns, servingStatuses — not status — says whether a campaign is actually delivering. VOCABULARY: the API\'s `campaign` is what Campaign Manager shows as "Ad set" (campaignGroup="Campaign", campaign="Ad set", creative="Ad"). Say both names when reporting to a user, or they will look in the wrong tab and think nothing happened.'},transport:{type:`rest`,method:`POST`,path:`/v1/workspaces/{workspaceId}/linkedin/campaigns/search`,auth:`user`,requestContentType:`application/json`}},{id:`linkedin.get_conversion_rule`,path:[`linkedin`,`conversion-rule`,`get`],summary:`Get one conversion rule by id, with its attribution settings, value, URL rules, associated campaigns and (for pixel rules) the Insight Tag <img> snippet. Read this before update_conversion_rule so you change only what you mean to — and use it to name a rule id found on a campaign, which list_conversions can only resolve by scanning.`,description:``,source:`rest`,options:[{name:`workspaceId`,flag:`--workspace-id`,description:``,required:!0,valueType:`string`,location:`path`},{name:`conversion_rule_id`,flag:`--conversion-rule-id`,description:`The rule's numeric id, or the full urn:lla:llaPartnerConversion:… as it appears in a campaign's conversion list.`,required:!0,valueType:`string`,location:`body`}],examples:[{description:`Example`,command:`adside linkedin conversion-rule get --workspace-id <workspaceId> --conversion-rule-id <conversion_rule_id>`}],output:{kind:`json`,description:`Get one conversion rule by id, with its attribution settings, value, URL rules, associated campaigns and (for pixel rules) the Insight Tag <img> snippet. Read this before update_conversion_rule so you change only what you mean to — and use it to name a rule id found on a campaign, which list_conversions can only resolve by scanning.`},transport:{type:`rest`,method:`POST`,path:`/v1/workspaces/{workspaceId}/linkedin/conversion-rule/get`,auth:`user`,requestContentType:`application/json`}},{id:`linkedin.list_conversions`,path:[`linkedin`,`conversions`,`list`],summary:"List the conversion rules on a LinkedIn Ad Account: name, type, method, attribution settings, conversion value and enabled status. LinkedIn serves 10 per page, so check `next_start` in the response before concluding you have seen them all.",description:``,source:`rest`,options:[{name:`workspaceId`,flag:`--workspace-id`,description:``,required:!0,valueType:`string`,location:`path`},{name:`account_id`,flag:`--account-id`,description:`LinkedIn Ad Account ID. Omit it: it defaults to the account this client is connected to, and any other account is refused.`,required:!1,valueType:`string`,location:`body`},{name:`start`,flag:`--start`,description:`Index of the first rule to return (offset paging).`,required:!1,valueType:`number`,defaultValue:0,location:`body`},{name:`count`,flag:`--count`,description:"How many rules to return. LinkedIn defaults to 10 if unset, so this tool asks for 100; check `next_start` in the response for more.",required:!1,valueType:`number`,defaultValue:100,location:`body`}],examples:[{description:`Example`,command:`adside linkedin conversions list --workspace-id <workspaceId>`}],output:{kind:`json`,description:"List the conversion rules on a LinkedIn Ad Account: name, type, method, attribution settings, conversion value and enabled status. LinkedIn serves 10 per page, so check `next_start` in the response before concluding you have seen them all."},transport:{type:`rest`,method:`POST`,path:`/v1/workspaces/{workspaceId}/linkedin/conversions/list`,auth:`user`,requestContentType:`application/json`}},{id:`linkedin.get_creative`,path:[`linkedin`,`creatives`,`get`],summary:'Get a creative by ID: its status, review status, serving hold reasons — and the actual content of the ad, read from the post it points at. `post` carries the body text, the headline, the image URN, the landing page and each carousel card. Use it to tell someone what an ad says, or to rebuild one elsewhere. VOCABULARY: the API\'s `creative` is what Campaign Manager shows as "Ad" (campaignGroup="Campaign", campaign="Ad set", creative="Ad"). Say both names when reporting to a user, or they will look in the wrong tab and think nothing happened.',description:``,source:`rest`,options:[{name:`workspaceId`,flag:`--workspace-id`,description:``,required:!0,valueType:`string`,location:`path`},{name:`account_id`,flag:`--account-id`,description:`LinkedIn Ad Account ID. Omit it: it defaults to the account this client is connected to, and any other account is refused.`,required:!1,valueType:`string`,location:`body`},{name:`creative_id`,flag:`--creative-id`,description:`Creative ID or URN (e.g. '120491345' or 'urn:li:sponsoredCreative:120491345')`,required:!0,valueType:`string`,location:`body`}],examples:[{description:`Example`,command:`adside linkedin creatives get --workspace-id <workspaceId> --creative-id <creative_id>`}],output:{kind:`json`,description:'Get a creative by ID: its status, review status, serving hold reasons — and the actual content of the ad, read from the post it points at. `post` carries the body text, the headline, the image URN, the landing page and each carousel card. Use it to tell someone what an ad says, or to rebuild one elsewhere. VOCABULARY: the API\'s `creative` is what Campaign Manager shows as "Ad" (campaignGroup="Campaign", campaign="Ad set", creative="Ad"). Say both names when reporting to a user, or they will look in the wrong tab and think nothing happened.'},transport:{type:`rest`,method:`POST`,path:`/v1/workspaces/{workspaceId}/linkedin/creatives/get`,auth:`user`,requestContentType:`application/json`}},{id:`linkedin.list_linkedin_creatives`,path:[`linkedin`,`creatives`,`list`],summary:'Search and list creatives for a LinkedIn Ad Account. Filter by campaign, status, or creative IDs. Uses q=criteria finder with cursor-based pagination (max 100 per page). VOCABULARY: the API\'s `creative` is what Campaign Manager shows as "Ad" (campaignGroup="Campaign", campaign="Ad set", creative="Ad"). Say both names when reporting to a user, or they will look in the wrong tab and think nothing happened.',description:``,source:`rest`,options:[{name:`workspaceId`,flag:`--workspace-id`,description:``,required:!0,valueType:`string`,location:`path`},{name:`account_id`,flag:`--account-id`,description:`LinkedIn Ad Account ID. Omit it: it defaults to the account this client is connected to, and any other account is refused.`,required:!1,valueType:`string`,location:`body`},{name:`campaign_ids`,flag:`--campaign-ids`,description:`Filter by campaign URNs or IDs`,required:!1,valueType:`json`,location:`body`},{name:`intended_statuses`,flag:`--intended-statuses`,description:`Filter by intended statuses`,required:!1,valueType:`json`,location:`body`},{name:`creative_ids`,flag:`--creative-ids`,description:`Filter by specific creative URNs`,required:!1,valueType:`json`,location:`body`},{name:`sort_order`,flag:`--sort-order`,description:`Sort order by creative ID (default: ASCENDING)`,required:!1,valueType:`string`,enum:[`ASCENDING`,`DESCENDING`],location:`body`},{name:`page_size`,flag:`--page-size`,description:`Number of results per page (max 100)`,required:!1,valueType:`number`,defaultValue:100,location:`body`},{name:`page_token`,flag:`--page-token`,description:`Cursor token for next page of results`,required:!1,valueType:`string`,location:`body`}],examples:[{description:`Example`,command:`adside linkedin creatives list --workspace-id <workspaceId>`}],output:{kind:`json`,description:'Search and list creatives for a LinkedIn Ad Account. Filter by campaign, status, or creative IDs. Uses q=criteria finder with cursor-based pagination (max 100 per page). VOCABULARY: the API\'s `creative` is what Campaign Manager shows as "Ad" (campaignGroup="Campaign", campaign="Ad set", creative="Ad"). Say both names when reporting to a user, or they will look in the wrong tab and think nothing happened.'},transport:{type:`rest`,method:`POST`,path:`/v1/workspaces/{workspaceId}/linkedin/creatives/list`,auth:`user`,requestContentType:`application/json`}},{id:`linkedin.get_demographic_insights`,path:[`linkedin`,`demographic-insights`,`get`],summary:`Get professional demographic analytics for LinkedIn ads. Break down performance by member company, industry, seniority, job title, job function, or location. Uses q=analytics with MEMBER_* pivots. Note: demographic data has 12-24h delay and 2-year retention.`,description:``,source:`rest`,options:[{name:`workspaceId`,flag:`--workspace-id`,description:``,required:!0,valueType:`string`,location:`path`},{name:`account_id`,flag:`--account-id`,description:`LinkedIn Ad Account ID. Omit it: it defaults to the account this client is connected to, and any other account is refused.`,required:!1,valueType:`string`,location:`body`},{name:`pivot`,flag:`--pivot`,description:`Professional demographic dimension to group results by`,required:!0,valueType:`string`,enum:[`MEMBER_COMPANY`,`MEMBER_COMPANY_SIZE`,`MEMBER_INDUSTRY`,`MEMBER_SENIORITY`,`MEMBER_JOB_TITLE`,`MEMBER_JOB_FUNCTION`,`MEMBER_COUNTRY_V2`,`MEMBER_REGION_V2`,`MEMBER_COUNTY`],location:`body`},{name:`time_granularity`,flag:`--time-granularity`,description:`Time granularity for results`,required:!1,valueType:`string`,defaultValue:`ALL`,enum:[`DAILY`,`MONTHLY`,`ALL`],location:`body`},{name:`date_range_start`,flag:`--date-range-start`,description:`Start date (inclusive)`,required:!0,valueType:`json`,location:`body`},{name:`date_range_end`,flag:`--date-range-end`,description:`End date (inclusive)`,required:!1,valueType:`json`,location:`body`},{name:`campaign_ids`,flag:`--campaign-ids`,description:`Filter by campaign IDs`,required:!1,valueType:`json`,location:`body`},{name:`fields`,flag:`--fields`,description:`Specific metrics to return (max 20). Note: some metrics not available with demographic pivots.`,required:!1,valueType:`json`,location:`body`}],examples:[{description:`Example`,command:`adside linkedin demographic-insights get --workspace-id <workspaceId> --pivot MEMBER_COMPANY --date-range-start '{}'`}],output:{kind:`json`,description:`Get professional demographic analytics for LinkedIn ads. Break down performance by member company, industry, seniority, job title, job function, or location. Uses q=analytics with MEMBER_* pivots. Note: demographic data has 12-24h delay and 2-year retention.`},transport:{type:`rest`,method:`POST`,path:`/v1/workspaces/{workspaceId}/linkedin/demographic-insights/get`,auth:`user`,requestContentType:`application/json`}},{id:`linkedin.get_lead_gen_form`,path:[`linkedin`,`lead-gen-forms`,`get`],summary:`Get one lead gen form with the questions it asks and the tracking parameters it appends. Use it to tell a client what a form collects before attaching it to an ad, or to check that an existing ad's form still asks for what the campaign needs.`,description:``,source:`rest`,options:[{name:`workspaceId`,flag:`--workspace-id`,description:``,required:!0,valueType:`string`,location:`path`},{name:`lead_gen_form_id`,flag:`--lead-gen-form-id`,description:`Numeric id of the form, or its full urn:li:adForm: URN — either is accepted.`,required:!0,valueType:`string`,location:`body`}],examples:[{description:`Example`,command:`adside linkedin lead-gen-forms get --workspace-id <workspaceId> --lead-gen-form-id <lead_gen_form_id>`}],output:{kind:`json`,description:`Get one lead gen form with the questions it asks and the tracking parameters it appends. Use it to tell a client what a form collects before attaching it to an ad, or to check that an existing ad's form still asks for what the campaign needs.`},transport:{type:`rest`,method:`POST`,path:`/v1/workspaces/{workspaceId}/linkedin/lead-gen-forms/get`,auth:`user`,requestContentType:`application/json`}},{id:`linkedin.list_lead_gen_forms`,path:[`linkedin`,`lead-gen-forms`,`list`],summary:"List the lead gen forms an ad account owns. A lead gen ad opens one of these inside LinkedIn, pre-filled from the member's profile, instead of sending them to a website. Each result carries the `urn` that create_creative's leadgen_form_id expects, so use this before building a LEAD_GENERATION ad — form URNs cannot be discovered any other way.",description:``,source:`rest`,options:[{name:`workspaceId`,flag:`--workspace-id`,description:``,required:!0,valueType:`string`,location:`path`},{name:`account_id`,flag:`--account-id`,description:`LinkedIn Ad Account ID (numeric). Omit it: it defaults to the account this client is connected to, and any other account is refused.`,required:!1,valueType:`string`,location:`body`},{name:`start`,flag:`--start`,description:`Index of the first form to return (offset paging).`,required:!1,valueType:`number`,defaultValue:0,location:`body`},{name:`count`,flag:`--count`,description:"How many forms to return. LinkedIn defaults to 10 if unset (measured: 10 served against a total of 30), so this tool asks for 100; check `next_start` in the response for more.",required:!1,valueType:`number`,defaultValue:100,location:`body`}],examples:[{description:`Example`,command:`adside linkedin lead-gen-forms list --workspace-id <workspaceId>`}],output:{kind:`json`,description:"List the lead gen forms an ad account owns. A lead gen ad opens one of these inside LinkedIn, pre-filled from the member's profile, instead of sending them to a website. Each result carries the `urn` that create_creative's leadgen_form_id expects, so use this before building a LEAD_GENERATION ad — form URNs cannot be discovered any other way."},transport:{type:`rest`,method:`POST`,path:`/v1/workspaces/{workspaceId}/linkedin/lead-gen-forms/list`,auth:`user`,requestContentType:`application/json`}},{id:`linkedin.get_matched_audience`,path:[`linkedin`,`matched-audiences`,`get`],summary:`Check an audience built by uploading a contact or company list: whether LinkedIn has finished matching it, how many contacts were sent, how many members it recognized, and the urn:li:adSegment: URN to target once it is ready. Use this when someone asks how an audience import turned out or how big the audience is — the size is not stored anywhere on our side and only exists here. Matching takes up to 48 hours, so a status of BUILDING shortly after an import is normal and not a failure.`,description:``,source:`rest`,options:[{name:`workspaceId`,flag:`--workspace-id`,description:``,required:!0,valueType:`string`,location:`path`},{name:`segment_id`,flag:`--segment-id`,description:`The DMP segment's numeric id — the id an audience import reports when it finishes. Not the urn:li:adSegment: URN, which is a different object; use get_ad_segment for that one.`,required:!0,valueType:`string`,location:`body`}],examples:[{description:`Example`,command:`adside linkedin matched-audiences get --workspace-id <workspaceId> --segment-id <segment_id>`}],output:{kind:`json`,description:`Check an audience built by uploading a contact or company list: whether LinkedIn has finished matching it, how many contacts were sent, how many members it recognized, and the urn:li:adSegment: URN to target once it is ready. Use this when someone asks how an audience import turned out or how big the audience is — the size is not stored anywhere on our side and only exists here. Matching takes up to 48 hours, so a status of BUILDING shortly after an import is normal and not a failure.`},transport:{type:`rest`,method:`POST`,path:`/v1/workspaces/{workspaceId}/linkedin/matched-audiences/get`,auth:`user`,requestContentType:`application/json`}},{id:`linkedin.list_matched_audiences`,path:[`linkedin`,`matched-audiences`,`list`],summary:`List the audiences an ad account has built from uploaded contact or company lists, with their matching status and sizes. Use this to find an audience by name — after an import, the numeric id needed by get_matched_audience is not something the user has, but the name they chose is.`,description:``,source:`rest`,options:[{name:`workspaceId`,flag:`--workspace-id`,description:``,required:!0,valueType:`string`,location:`path`},{name:`account_id`,flag:`--account-id`,description:`LinkedIn Ad Account ID (numeric). Omit it: it defaults to the account this client is connected to, and any other account is refused.`,required:!1,valueType:`string`,location:`body`},{name:`start`,flag:`--start`,description:`Index of the first audience to return (offset paging).`,required:!1,valueType:`number`,defaultValue:0,location:`body`},{name:`count`,flag:`--count`,description:"How many to return. LinkedIn defaults to 10 if unset, so this tool asks for 100; check `next_start` in the response for more.",required:!1,valueType:`number`,defaultValue:100,location:`body`}],examples:[{description:`Example`,command:`adside linkedin matched-audiences list --workspace-id <workspaceId>`}],output:{kind:`json`,description:`List the audiences an ad account has built from uploaded contact or company lists, with their matching status and sizes. Use this to find an audience by name — after an import, the numeric id needed by get_matched_audience is not something the user has, but the name they chose is.`},transport:{type:`rest`,method:`POST`,path:`/v1/workspaces/{workspaceId}/linkedin/matched-audiences/list`,auth:`user`,requestContentType:`application/json`}},{id:`linkedin.compare_linkedin_performance`,path:[`linkedin`,`performance`,`compare`],summary:`Compare performance across multiple campaigns side-by-side. Returns analytics grouped by campaign for easy comparison of metrics like impressions, clicks, cost, and conversions.`,description:``,source:`rest`,options:[{name:`workspaceId`,flag:`--workspace-id`,description:``,required:!0,valueType:`string`,location:`path`},{name:`account_id`,flag:`--account-id`,description:`LinkedIn Ad Account ID. Omit it: it defaults to the account this client is connected to, and any other account is refused.`,required:!1,valueType:`string`,location:`body`},{name:`campaign_ids`,flag:`--campaign-ids`,description:`Campaign IDs to compare`,required:!0,valueType:`json`,location:`body`},{name:`time_granularity`,flag:`--time-granularity`,description:`Time granularity`,required:!1,valueType:`string`,defaultValue:`ALL`,enum:[`DAILY`,`MONTHLY`,`ALL`],location:`body`},{name:`date_range_start`,flag:`--date-range-start`,description:`Start date (inclusive)`,required:!0,valueType:`json`,location:`body`},{name:`date_range_end`,flag:`--date-range-end`,description:`End date (inclusive)`,required:!1,valueType:`json`,location:`body`},{name:`fields`,flag:`--fields`,description:`Specific metrics to return (max 20)`,required:!1,valueType:`json`,location:`body`}],examples:[{description:`Example`,command:`adside linkedin performance compare --workspace-id <workspaceId> --campaign-ids '{}' --date-range-start '{}'`}],output:{kind:`json`,description:`Compare performance across multiple campaigns side-by-side. Returns analytics grouped by campaign for easy comparison of metrics like impressions, clicks, cost, and conversions.`},transport:{type:`rest`,method:`POST`,path:`/v1/workspaces/{workspaceId}/linkedin/performance/compare`,auth:`user`,requestContentType:`application/json`}},{id:`linkedin.get_saved_audience`,path:[`linkedin`,`saved-audiences`,`get`],summary:`Get one saved audience with its full targeting criteria. Read this before update_saved_audience: an update REPLACES the criteria rather than merging into them.`,description:``,source:`rest`,options:[{name:`workspaceId`,flag:`--workspace-id`,description:``,required:!0,valueType:`string`,location:`path`},{name:`saved_audience_id`,flag:`--saved-audience-id`,description:`Numeric id of the saved audience (adTargetTemplate).`,required:!0,valueType:`string`,location:`body`}],examples:[{description:`Example`,command:`adside linkedin saved-audiences get --workspace-id <workspaceId> --saved-audience-id <saved_audience_id>`}],output:{kind:`json`,description:`Get one saved audience with its full targeting criteria. Read this before update_saved_audience: an update REPLACES the criteria rather than merging into them.`},transport:{type:`rest`,method:`POST`,path:`/v1/workspaces/{workspaceId}/linkedin/saved-audiences/get`,auth:`user`,requestContentType:`application/json`}},{id:`linkedin.list_saved_audiences`,path:[`linkedin`,`saved-audiences`,`list`],summary:`List an account's saved audiences (reusable targeting templates built in Campaign Manager). Each one carries a full targeting_criteria that can be copied verbatim into create_linkedin_campaign, or into update_linkedin_campaign to give an existing campaign an audience. Prefer these over composing an audience from scratch: they are the audiences the account already trusts.`,description:``,source:`rest`,options:[{name:`workspaceId`,flag:`--workspace-id`,description:``,required:!0,valueType:`string`,location:`path`},{name:`account_id`,flag:`--account-id`,description:`LinkedIn Ad Account ID (numeric). Omit it: it defaults to the account this client is connected to, and any other account is refused.`,required:!1,valueType:`string`,location:`body`},{name:`sort_field`,flag:`--sort-field`,description:`Sort order. LinkedIn requires one; NAME is the default here.`,required:!1,valueType:`string`,defaultValue:`NAME`,enum:[`NAME`,`LAST_MODIFIED`,`ID`],location:`body`}],examples:[{description:`Example`,command:`adside linkedin saved-audiences list --workspace-id <workspaceId>`}],output:{kind:`json`,description:`List an account's saved audiences (reusable targeting templates built in Campaign Manager). Each one carries a full targeting_criteria that can be copied verbatim into create_linkedin_campaign, or into update_linkedin_campaign to give an existing campaign an audience. Prefer these over composing an audience from scratch: they are the audiences the account already trusts.`},transport:{type:`rest`,method:`POST`,path:`/v1/workspaces/{workspaceId}/linkedin/saved-audiences/list`,auth:`user`,requestContentType:`application/json`}},{id:`linkedin.get_targeting_entities`,path:[`linkedin`,`targeting-entities`,`get`],summary:`Resolve targeting URNs to human-readable names. Pass a list of URNs (e.g. urn:li:seniority:7, urn:li:industry:9) to get their display names.`,description:``,source:`rest`,options:[{name:`workspaceId`,flag:`--workspace-id`,description:``,required:!0,valueType:`string`,location:`path`},{name:`urns`,flag:`--urns`,description:`List of URNs to resolve (e.g. ['urn:li:seniority:7', 'urn:li:industry:9'])`,required:!0,valueType:`json`,location:`body`}],examples:[{description:`Example`,command:`adside linkedin targeting-entities get --workspace-id <workspaceId> --urns '{}'`}],output:{kind:`json`,description:`Resolve targeting URNs to human-readable names. Pass a list of URNs (e.g. urn:li:seniority:7, urn:li:industry:9) to get their display names.`},transport:{type:`rest`,method:`POST`,path:`/v1/workspaces/{workspaceId}/linkedin/targeting-entities/get`,auth:`user`,requestContentType:`application/json`}},{id:`linkedin.search_targeting_facets`,path:[`linkedin`,`targeting-facets`,`search`],summary:`Search for targeting entity values by facet type. Use typeahead search with a query string, or list all values for a facet. Returns URNs to use in campaign targeting criteria.`,description:``,source:`rest`,options:[{name:`workspaceId`,flag:`--workspace-id`,description:``,required:!0,valueType:`string`,location:`path`},{name:`facet`,flag:`--facet`,description:`Targeting facet to search (e.g. locations, industries, titles). These facets REQUIRE a query — they cannot be listed: employers, employersAll, employersPast, schools, skills, groups, followedCompanies, firstDegreeConnectionCompanies. Not searchable at all, but valid in campaign targeting: audienceMatchingSegments, dynamicSegments — their values are your own audience segments, not LinkedIn attributes.`,required:!0,valueType:`string`,enum:`locations.profileLocations.industries.seniorities.titles.titlesAll.titlesPast.jobFunctions.degrees.fieldsOfStudy.staffCountRanges.interests.ageRanges.genders.interfaceLocales.companyCategory.growthRate.memberBehaviors.yearsOfExperienceRanges.revenue.employers.employersAll.employersPast.schools.skills.groups.followedCompanies.firstDegreeConnectionCompanies`.split(`.`),location:`body`},{name:`query`,flag:`--query`,description:`Search text for typeahead (e.g. 'Software Engineer'). If omitted, returns all values for the facet — which only works for a listable facet.`,required:!1,valueType:`string`,location:`body`}],examples:[{description:`Example`,command:`adside linkedin targeting-facets search --workspace-id <workspaceId> --facet locations`}],output:{kind:`json`,description:`Search for targeting entity values by facet type. Use typeahead search with a query string, or list all values for a facet. Returns URNs to use in campaign targeting criteria.`},transport:{type:`rest`,method:`POST`,path:`/v1/workspaces/{workspaceId}/linkedin/targeting-facets/search`,auth:`user`,requestContentType:`application/json`}},{id:`linkedin.get_video_upload`,path:[`linkedin`,`video-upload`,`get`],summary:`Status of a video upload started with upload_video: PENDING → PREPARING → UPLOADING → PROCESSING → AVAILABLE (or FAILED). This call WAITS (up to wait_seconds, default 3 minutes) for the upload to finish before answering, so call it once rather than polling; if it still says still_running, call it again. Once AVAILABLE, the video_urn is what create_creative's SINGLE_VIDEO branch takes as video_id.`,description:``,source:`rest`,options:[{name:`workspaceId`,flag:`--workspace-id`,description:``,required:!0,valueType:`string`,location:`path`},{name:`account_id`,flag:`--account-id`,description:`LinkedIn Ad Account ID. Omit it: it defaults to the account this client is connected to, and any other account is refused.`,required:!1,valueType:`string`,location:`body`},{name:`wait_seconds`,flag:`--wait-seconds`,description:`Seconds to wait for the upload to reach AVAILABLE (or FAILED) before answering. Default 180, max 240. Leave the default: one call then usually returns the video_urn. 0 returns the current state at once.`,required:!1,valueType:`number`,defaultValue:180,location:`body`},{name:`upload_id`,flag:`--upload-id`,description:`The upload_id returned by upload_video. Omit it to get the most recent upload for this client.`,required:!1,valueType:`string`,location:`body`}],examples:[{description:`Example`,command:`adside linkedin video-upload get --workspace-id <workspaceId>`}],output:{kind:`json`,description:`Status of a video upload started with upload_video: PENDING → PREPARING → UPLOADING → PROCESSING → AVAILABLE (or FAILED). This call WAITS (up to wait_seconds, default 3 minutes) for the upload to finish before answering, so call it once rather than polling; if it still says still_running, call it again. Once AVAILABLE, the video_urn is what create_creative's SINGLE_VIDEO branch takes as video_id.`},transport:{type:`rest`,method:`POST`,path:`/v1/workspaces/{workspaceId}/linkedin/video-upload/get`,auth:`user`,requestContentType:`application/json`}},{id:`media.images.cancel`,path:[`media`,`images`,`cancel`],summary:`Cancel an image job; one a provider already accepted may still finish and is still charged`,description:``,source:`rest`,options:[{name:`workspaceId`,flag:`--workspace-id`,description:``,required:!0,valueType:`string`,location:`path`},{name:`jobId`,flag:`--job-id`,description:``,required:!0,valueType:`string`,location:`path`}],examples:[{description:`Example`,command:`adside media images cancel --workspace-id <workspaceId> --job-id <jobId>`}],output:{kind:`json`,description:`Cancel an image job; one a provider already accepted may still finish and is still charged`},transport:{type:`rest`,method:`POST`,path:`/v1/workspaces/{workspaceId}/media/images/{jobId}/cancel`,auth:`user`}},{id:`media.images.estimate`,path:[`media`,`images`,`estimate`],summary:`Price an image request without generating or charging`,description:``,source:`rest`,options:[{name:`workspaceId`,flag:`--workspace-id`,description:``,required:!0,valueType:`string`,location:`path`},{name:`model`,flag:`--model`,description:``,required:!1,valueType:`string`,location:`body`},{name:`prompt`,flag:`--prompt`,description:``,required:!0,valueType:`string`,location:`body`},{name:`maxPriceUsd`,flag:`--max-price-usd`,description:``,required:!1,valueType:`number`,location:`body`},{name:`resolution`,flag:`--resolution`,description:``,required:!1,valueType:`string`,enum:[`512`,`768`,`1K`,`1.5K`,`2K`,`4K`],location:`body`},{name:`aspectRatio`,flag:`--aspect-ratio`,description:``,required:!1,valueType:`string`,enum:[`auto`,`1:1`,`2:3`,`3:2`,`3:4`,`4:3`,`4:5`,`5:4`,`9:16`,`16:9`,`21:9`,`9:21`,`1:2`,`2:1`,`1:4`,`4:1`,`1:8`,`8:1`],location:`body`},{name:`inputReferences`,flag:`--input-references`,description:``,required:!1,valueType:`json`,location:`body`}],examples:[{description:`Example`,command:`adside media images estimate --workspace-id <workspaceId> --prompt <prompt>`}],output:{kind:`json`,description:`Price an image request without generating or charging`},transport:{type:`rest`,method:`POST`,path:`/v1/workspaces/{workspaceId}/media/images/estimate`,auth:`user`,requestContentType:`application/json`}},{id:`media.images.generate`,path:[`media`,`images`,`generate`],summary:`Generate one image, charged at its priceUsd; the same requestId returns the same job`,description:``,source:`rest`,generateRequestId:!0,options:[{name:`workspaceId`,flag:`--workspace-id`,description:``,required:!0,valueType:`string`,location:`path`},{name:`waitSeconds`,flag:`--wait-seconds`,description:``,required:!1,valueType:`number`,defaultValue:0,location:`query`},{name:`requestId`,flag:`--request-id`,description:`Submission identity (generated automatically if omitted)`,required:!1,valueType:`string`,location:`body`},{name:`model`,flag:`--model`,description:``,required:!1,valueType:`string`,location:`body`},{name:`prompt`,flag:`--prompt`,description:``,required:!0,valueType:`string`,location:`body`},{name:`maxPriceUsd`,flag:`--max-price-usd`,description:``,required:!1,valueType:`number`,location:`body`},{name:`resolution`,flag:`--resolution`,description:``,required:!1,valueType:`string`,enum:[`512`,`768`,`1K`,`1.5K`,`2K`,`4K`],location:`body`},{name:`aspectRatio`,flag:`--aspect-ratio`,description:``,required:!1,valueType:`string`,enum:[`auto`,`1:1`,`2:3`,`3:2`,`3:4`,`4:3`,`4:5`,`5:4`,`9:16`,`16:9`,`21:9`,`9:21`,`1:2`,`2:1`,`1:4`,`4:1`,`1:8`,`8:1`],location:`body`},{name:`inputReferences`,flag:`--input-references`,description:``,required:!1,valueType:`json`,location:`body`}],examples:[{description:`Example`,command:`adside media images generate --workspace-id <workspaceId> --prompt <prompt>`}],output:{kind:`json`,description:`Generate one image, charged at its priceUsd; the same requestId returns the same job`},transport:{type:`rest`,method:`POST`,path:`/v1/workspaces/{workspaceId}/media/images`,auth:`user`,requestContentType:`application/json`}},{id:`media.images.get`,path:[`media`,`images`,`get`],summary:`Read an image job, waiting up to waitSeconds for it to finish`,description:``,source:`rest`,options:[{name:`workspaceId`,flag:`--workspace-id`,description:``,required:!0,valueType:`string`,location:`path`},{name:`jobId`,flag:`--job-id`,description:``,required:!0,valueType:`string`,location:`path`},{name:`waitSeconds`,flag:`--wait-seconds`,description:``,required:!1,valueType:`number`,defaultValue:0,location:`query`}],examples:[{description:`Example`,command:`adside media images get --workspace-id <workspaceId> --job-id <jobId>`}],output:{kind:`json`,description:`Read an image job, waiting up to waitSeconds for it to finish`},transport:{type:`rest`,method:`GET`,path:`/v1/workspaces/{workspaceId}/media/images/{jobId}`,auth:`user`}},{id:`media.images.models`,path:[`media`,`images`,`models`],summary:`List the image models, what each is best for, its supported values and prices`,description:``,source:`rest`,options:[{name:`workspaceId`,flag:`--workspace-id`,description:``,required:!0,valueType:`string`,location:`path`}],examples:[{description:`Example`,command:`adside media images models --workspace-id <workspaceId>`}],output:{kind:`json`,description:`List the image models, what each is best for, its supported values and prices`},transport:{type:`rest`,method:`GET`,path:`/v1/workspaces/{workspaceId}/media/images/models`,auth:`user`}},{id:`media.jobs.list`,path:[`media`,`jobs`,`list`],summary:`List the workspace's image and video jobs, newest first`,description:``,source:`rest`,options:[{name:`workspaceId`,flag:`--workspace-id`,description:``,required:!0,valueType:`string`,location:`path`},{name:`type`,flag:`--type`,description:``,required:!1,valueType:`string`,enum:[`image`,`video`],location:`query`},{name:`status`,flag:`--status`,description:``,required:!1,valueType:`string`,enum:[`pending`,`in_progress`,`completed`,`failed`,`cancelled`,`expired`],location:`query`},{name:`cursor`,flag:`--cursor`,description:``,required:!1,valueType:`string`,location:`query`},{name:`limit`,flag:`--limit`,description:``,required:!1,valueType:`number`,defaultValue:20,location:`query`}],examples:[{description:`Example`,command:`adside media jobs list --workspace-id <workspaceId>`}],output:{kind:`json`,description:`List the workspace's image and video jobs, newest first`},transport:{type:`rest`,method:`GET`,path:`/v1/workspaces/{workspaceId}/media/jobs`,auth:`user`}},{id:`media.videos.cancel`,path:[`media`,`videos`,`cancel`],summary:`Cancel a video job; one a provider already accepted may still finish and is still charged`,description:``,source:`rest`,options:[{name:`workspaceId`,flag:`--workspace-id`,description:``,required:!0,valueType:`string`,location:`path`},{name:`jobId`,flag:`--job-id`,description:``,required:!0,valueType:`string`,location:`path`}],examples:[{description:`Example`,command:`adside media videos cancel --workspace-id <workspaceId> --job-id <jobId>`}],output:{kind:`json`,description:`Cancel a video job; one a provider already accepted may still finish and is still charged`},transport:{type:`rest`,method:`POST`,path:`/v1/workspaces/{workspaceId}/media/videos/{jobId}/cancel`,auth:`user`}},{id:`media.videos.estimate`,path:[`media`,`videos`,`estimate`],summary:`Price a video request without generating or charging`,description:``,source:`rest`,options:[{name:`workspaceId`,flag:`--workspace-id`,description:``,required:!0,valueType:`string`,location:`path`},{name:`model`,flag:`--model`,description:``,required:!1,valueType:`string`,location:`body`},{name:`prompt`,flag:`--prompt`,description:``,required:!0,valueType:`string`,location:`body`},{name:`maxPriceUsd`,flag:`--max-price-usd`,description:``,required:!1,valueType:`number`,location:`body`},{name:`duration`,flag:`--duration`,description:``,required:!1,valueType:`number`,location:`body`},{name:`resolution`,flag:`--resolution`,description:``,required:!1,valueType:`string`,enum:[`480p`,`720p`,`768p`,`1080p`,`1K`,`2K`,`4K`],location:`body`},{name:`aspectRatio`,flag:`--aspect-ratio`,description:``,required:!1,valueType:`string`,enum:[`9:16`,`16:9`,`1:1`,`4:3`,`3:4`,`3:2`,`2:3`,`21:9`,`9:21`],location:`body`},{name:`frameImages`,flag:`--frame-images`,description:``,required:!1,valueType:`json`,location:`body`},{name:`generateAudio`,flag:`--generate-audio`,description:``,required:!1,valueType:`boolean`,location:`body`}],examples:[{description:`Example`,command:`adside media videos estimate --workspace-id <workspaceId> --prompt <prompt>`}],output:{kind:`json`,description:`Price a video request without generating or charging`},transport:{type:`rest`,method:`POST`,path:`/v1/workspaces/{workspaceId}/media/videos/estimate`,auth:`user`,requestContentType:`application/json`}},{id:`media.videos.generate`,path:[`media`,`videos`,`generate`],summary:`Generate one video clip, charged at its priceUsd; the same requestId returns the same job`,description:``,source:`rest`,generateRequestId:!0,options:[{name:`workspaceId`,flag:`--workspace-id`,description:``,required:!0,valueType:`string`,location:`path`},{name:`waitSeconds`,flag:`--wait-seconds`,description:``,required:!1,valueType:`number`,defaultValue:0,location:`query`},{name:`requestId`,flag:`--request-id`,description:`Submission identity (generated automatically if omitted)`,required:!1,valueType:`string`,location:`body`},{name:`model`,flag:`--model`,description:``,required:!1,valueType:`string`,location:`body`},{name:`prompt`,flag:`--prompt`,description:``,required:!0,valueType:`string`,location:`body`},{name:`maxPriceUsd`,flag:`--max-price-usd`,description:``,required:!1,valueType:`number`,location:`body`},{name:`duration`,flag:`--duration`,description:``,required:!1,valueType:`number`,location:`body`},{name:`resolution`,flag:`--resolution`,description:``,required:!1,valueType:`string`,enum:[`480p`,`720p`,`768p`,`1080p`,`1K`,`2K`,`4K`],location:`body`},{name:`aspectRatio`,flag:`--aspect-ratio`,description:``,required:!1,valueType:`string`,enum:[`9:16`,`16:9`,`1:1`,`4:3`,`3:4`,`3:2`,`2:3`,`21:9`,`9:21`],location:`body`},{name:`frameImages`,flag:`--frame-images`,description:``,required:!1,valueType:`json`,location:`body`},{name:`generateAudio`,flag:`--generate-audio`,description:``,required:!1,valueType:`boolean`,location:`body`}],examples:[{description:`Example`,command:`adside media videos generate --workspace-id <workspaceId> --prompt <prompt>`}],output:{kind:`json`,description:`Generate one video clip, charged at its priceUsd; the same requestId returns the same job`},transport:{type:`rest`,method:`POST`,path:`/v1/workspaces/{workspaceId}/media/videos`,auth:`user`,requestContentType:`application/json`}},{id:`media.videos.get`,path:[`media`,`videos`,`get`],summary:`Read a video job, waiting up to waitSeconds for it to finish`,description:``,source:`rest`,options:[{name:`workspaceId`,flag:`--workspace-id`,description:``,required:!0,valueType:`string`,location:`path`},{name:`jobId`,flag:`--job-id`,description:``,required:!0,valueType:`string`,location:`path`},{name:`waitSeconds`,flag:`--wait-seconds`,description:``,required:!1,valueType:`number`,defaultValue:0,location:`query`}],examples:[{description:`Example`,command:`adside media videos get --workspace-id <workspaceId> --job-id <jobId>`}],output:{kind:`json`,description:`Read a video job, waiting up to waitSeconds for it to finish`},transport:{type:`rest`,method:`GET`,path:`/v1/workspaces/{workspaceId}/media/videos/{jobId}`,auth:`user`}},{id:`media.videos.models`,path:[`media`,`videos`,`models`],summary:`List the video models, what each is best for, its supported values and prices`,description:``,source:`rest`,options:[{name:`workspaceId`,flag:`--workspace-id`,description:``,required:!0,valueType:`string`,location:`path`}],examples:[{description:`Example`,command:`adside media videos models --workspace-id <workspaceId>`}],output:{kind:`json`,description:`List the video models, what each is best for, its supported values and prices`},transport:{type:`rest`,method:`GET`,path:`/v1/workspaces/{workspaceId}/media/videos/models`,auth:`user`}},{id:`meta.analyze_account_creatives`,path:[`meta`,`account-creatives`,`analyze`],summary:`Analyze all creatives in an account to identify patterns, performance insights, and optimization opportunities. Provides summary statistics and recommendations.`,description:``,source:`rest`,options:[{name:`workspaceId`,flag:`--workspace-id`,description:``,required:!0,valueType:`string`,location:`path`},{name:`account_id`,flag:`--account-id`,description:`Meta Ad Account ID to analyze (uses configured account if not provided)`,required:!1,valueType:`string`,location:`body`},{name:`limit`,flag:`--limit`,description:`Maximum number of creatives to analyze`,required:!1,valueType:`number`,defaultValue:50,location:`body`}],examples:[{description:`Example`,command:`adside meta account-creatives analyze --workspace-id <workspaceId>`}],output:{kind:`json`,description:`Analyze all creatives in an account to identify patterns, performance insights, and optimization opportunities. Provides summary statistics and recommendations.`},transport:{type:`rest`,method:`POST`,path:`/v1/workspaces/{workspaceId}/meta/account-creatives/analyze`,auth:`user`,requestContentType:`application/json`}},{id:`meta.get_account_pages`,path:[`meta`,`account-pages`,`get`],summary:`List Facebook Pages available for ad creation on the given ad account, with each Page's Instagram business account as instagram_account_id when Meta lists one for this ad account. Page IDs go in promoted_object and object_story_spec; the Instagram id goes in a creative's instagram_actor_id so the ad runs under the client's own Instagram account. An empty list does NOT mean the account has no Page (Meta gates the list on what the connecting user granted at consent), and a missing instagram_account_id does NOT mean the Page has no Instagram account (usually it is not connected to the ad account yet) — the response says what to check.`,description:``,source:`rest`,options:[{name:`workspaceId`,flag:`--workspace-id`,description:``,required:!0,valueType:`string`,location:`path`},{name:`account_id`,flag:`--account-id`,description:`Meta Ad Account ID (uses configured account if not provided)`,required:!1,valueType:`string`,location:`body`}],examples:[{description:`Example`,command:`adside meta account-pages get --workspace-id <workspaceId>`}],output:{kind:`json`,description:`List Facebook Pages available for ad creation on the given ad account, with each Page's Instagram business account as instagram_account_id when Meta lists one for this ad account. Page IDs go in promoted_object and object_story_spec; the Instagram id goes in a creative's instagram_actor_id so the ad runs under the client's own Instagram account. An empty list does NOT mean the account has no Page (Meta gates the list on what the connecting user granted at consent), and a missing instagram_account_id does NOT mean the Page has no Instagram account (usually it is not connected to the ad account yet) — the response says what to check.`},transport:{type:`rest`,method:`POST`,path:`/v1/workspaces/{workspaceId}/meta/account-pages/get`,auth:`user`,requestContentType:`application/json`}},{id:`meta.get_account_pixels`,path:[`meta`,`account-pixels`,`get`],summary:`List pixels/datasets available to this client's connected ad account, including ones with no attached ad sets. Returns IDs, names, last_fired_time and availability. Follow next_cursor for more datasets. Use get_pixel for metadata/settings and get_pixel_stats for recent event activity (standard/custom event names, counts, sources and diagnostics) before launch. An empty list does NOT mean no pixel exists: a pixel created in Events Manager is not listed until it is connected to the ad account. The empty response lists the ad account's Business datasets that are not connected to it and says how to connect one; relay that before suggesting create_dataset.`,description:``,source:`rest`,options:[{name:`workspaceId`,flag:`--workspace-id`,description:``,required:!0,valueType:`string`,location:`path`},{name:`account_id`,flag:`--account-id`,description:`Meta Ad Account ID (uses configured account if not provided)`,required:!1,valueType:`string`,location:`body`},{name:`limit`,flag:`--limit`,description:``,required:!1,valueType:`number`,defaultValue:25,location:`body`},{name:`after`,flag:`--after`,description:`Next-page cursor from get_account_pixels.`,required:!1,valueType:`string`,location:`body`}],examples:[{description:`Example`,command:`adside meta account-pixels get --workspace-id <workspaceId>`}],output:{kind:`json`,description:`List pixels/datasets available to this client's connected ad account, including ones with no attached ad sets. Returns IDs, names, last_fired_time and availability. Follow next_cursor for more datasets. Use get_pixel for metadata/settings and get_pixel_stats for recent event activity (standard/custom event names, counts, sources and diagnostics) before launch. An empty list does NOT mean no pixel exists: a pixel created in Events Manager is not listed until it is connected to the ad account. The empty response lists the ad account's Business datasets that are not connected to it and says how to connect one; relay that before suggesting create_dataset.`},transport:{type:`rest`,method:`POST`,path:`/v1/workspaces/{workspaceId}/meta/account-pixels/get`,auth:`user`,requestContentType:`application/json`}},{id:`meta.verify_account_setup`,path:[`meta`,`account-setup`,`verify`],summary:`Check Meta account access, active status, funding visibility, promotable Pages and spending capacity. Unknown prerequisites prevent ready status. Does not establish billing chargeability, business verification or launch readiness.`,description:``,source:`rest`,options:[{name:`workspaceId`,flag:`--workspace-id`,description:``,required:!0,valueType:`string`,location:`path`},{name:`account_id`,flag:`--account-id`,description:`Meta Ad Account ID to verify (uses configured account if not provided)`,required:!1,valueType:`string`,location:`body`}],examples:[{description:`Example`,command:`adside meta account-setup verify --workspace-id <workspaceId>`}],output:{kind:`json`,description:`Check Meta account access, active status, funding visibility, promotable Pages and spending capacity. Unknown prerequisites prevent ready status. Does not establish billing chargeability, business verification or launch readiness.`},transport:{type:`rest`,method:`POST`,path:`/v1/workspaces/{workspaceId}/meta/account-setup/verify`,auth:`user`,requestContentType:`application/json`}},{id:`meta.get_meta_account_spend_limit`,path:[`meta`,`account-spend-limit`,`get`],summary:`Read the Meta ad account's spending limit and how much has been spent toward it. When the limit is reached Meta stops delivery for EVERY campaign in the account at once — check this first when all ads stopped running on the same day and no campaign-level setting explains it. Amounts are in the account currency's standard units (5000 = $5,000).`,description:``,source:`rest`,options:[{name:`workspaceId`,flag:`--workspace-id`,description:``,required:!0,valueType:`string`,location:`path`},{name:`account_id`,flag:`--account-id`,description:`Meta Ad Account ID (uses configured account if not provided)`,required:!1,valueType:`string`,location:`body`}],examples:[{description:`Example`,command:`adside meta account-spend-limit get --workspace-id <workspaceId>`}],output:{kind:`json`,description:`Read the Meta ad account's spending limit and how much has been spent toward it. When the limit is reached Meta stops delivery for EVERY campaign in the account at once — check this first when all ads stopped running on the same day and no campaign-level setting explains it. Amounts are in the account currency's standard units (5000 = $5,000).`},transport:{type:`rest`,method:`POST`,path:`/v1/workspaces/{workspaceId}/meta/account-spend-limit/get`,auth:`user`,requestContentType:`application/json`}},{id:`meta.get_ad_creative`,path:[`meta`,`ad-creative`,`get`],summary:`Get a single ad creative by ID with full details including copy, media, and Advantage+ Creative (asset_feed_spec) data. Use this to retrieve the actual ad copy text (bodies, titles, descriptions) for creatives using Advantage+ or dynamic creative optimization.`,description:``,source:`rest`,options:[{name:`workspaceId`,flag:`--workspace-id`,description:``,required:!0,valueType:`string`,location:`path`},{name:`creative_id`,flag:`--creative-id`,description:`The creative ID to fetch`,required:!0,valueType:`string`,location:`body`}],examples:[{description:`Example`,command:`adside meta ad-creative get --workspace-id <workspaceId> --creative-id <creative_id>`}],output:{kind:`json`,description:`Get a single ad creative by ID with full details including copy, media, and Advantage+ Creative (asset_feed_spec) data. Use this to retrieve the actual ad copy text (bodies, titles, descriptions) for creatives using Advantage+ or dynamic creative optimization.`},transport:{type:`rest`,method:`POST`,path:`/v1/workspaces/{workspaceId}/meta/ad-creative/get`,auth:`user`,requestContentType:`application/json`}},{id:`meta.get_ad_images`,path:[`meta`,`ad-images`,`get`],summary:`Retrieve ad images from a Meta ad account. Returns image URLs, dimensions, and hashes. Use to get image URLs for displaying ad creatives or generating variations.`,description:``,source:`rest`,options:[{name:`workspaceId`,flag:`--workspace-id`,description:``,required:!0,valueType:`string`,location:`path`},{name:`account_id`,flag:`--account-id`,description:`Meta Ad Account ID (uses configured account if not provided)`,required:!1,valueType:`string`,location:`body`},{name:`hashes`,flag:`--hashes`,description:`Filter by specific image hashes`,required:!1,valueType:`json`,location:`body`},{name:`limit`,flag:`--limit`,description:`Maximum number of images to return`,required:!1,valueType:`number`,defaultValue:25,location:`body`}],examples:[{description:`Example`,command:`adside meta ad-images get --workspace-id <workspaceId>`}],output:{kind:`json`,description:`Retrieve ad images from a Meta ad account. Returns image URLs, dimensions, and hashes. Use to get image URLs for displaying ad creatives or generating variations.`},transport:{type:`rest`,method:`POST`,path:`/v1/workspaces/{workspaceId}/meta/ad-images/get`,auth:`user`,requestContentType:`application/json`}},{id:`meta.get_ad_set`,path:[`meta`,`ad-sets`,`get`],summary:`Retrieve details for a single ad set including its targeting, budget, optimization goal, and schedule. To duplicate it, pass this ad set ID as source_ad_set_id to create_ad_set_enhanced and omit targeting. If faithful duplication is refused, report the unsupported fields; never silently narrow the audience or placements.`,description:``,source:`rest`,options:[{name:`workspaceId`,flag:`--workspace-id`,description:``,required:!0,valueType:`string`,location:`path`},{name:`adset_id`,flag:`--adset-id`,description:`Ad set ID to retrieve`,required:!0,valueType:`string`,location:`body`}],examples:[{description:`Example`,command:`adside meta ad-sets get --workspace-id <workspaceId> --adset-id <adset_id>`}],output:{kind:`json`,description:`Retrieve details for a single ad set including its targeting, budget, optimization goal, and schedule. To duplicate it, pass this ad set ID as source_ad_set_id to create_ad_set_enhanced and omit targeting. If faithful duplication is refused, report the unsupported fields; never silently narrow the audience or placements.`},transport:{type:`rest`,method:`POST`,path:`/v1/workspaces/{workspaceId}/meta/ad-sets/get`,auth:`user`,requestContentType:`application/json`}},{id:`meta.list_ad_sets`,path:[`meta`,`ad-sets`,`list`],summary:`List all ad sets for a given campaign or ad account. Filter by status and paginate results. Returns ad set details including budget, targeting, and optimization settings.`,description:``,source:`rest`,options:[{name:`workspaceId`,flag:`--workspace-id`,description:``,required:!0,valueType:`string`,location:`path`},{name:`campaign_id`,flag:`--campaign-id`,description:`Filter by campaign ID`,required:!1,valueType:`string`,location:`body`},{name:`account_id`,flag:`--account-id`,description:`Filter by account ID`,required:!1,valueType:`string`,location:`body`},{name:`status`,flag:`--status`,description:`Filter by ad set status`,required:!1,valueType:`string`,enum:[`ACTIVE`,`PAUSED`,`DELETED`,`ARCHIVED`],location:`body`},{name:`limit`,flag:`--limit`,description:`Number of ad sets to return`,required:!1,valueType:`number`,defaultValue:25,location:`body`},{name:`after`,flag:`--after`,description:`Pagination cursor for next page`,required:!1,valueType:`string`,location:`body`}],examples:[{description:`Example`,command:`adside meta ad-sets list --workspace-id <workspaceId>`}],output:{kind:`json`,description:`List all ad sets for a given campaign or ad account. Filter by status and paginate results. Returns ad set details including budget, targeting, and optimization settings.`},transport:{type:`rest`,method:`POST`,path:`/v1/workspaces/{workspaceId}/meta/ad-sets/list`,auth:`user`,requestContentType:`application/json`}},{id:`meta.get_ad`,path:[`meta`,`ads`,`get`],summary:`Retrieve details for a single ad including its name, status, ad set, campaign, and creative.`,description:``,source:`rest`,options:[{name:`workspaceId`,flag:`--workspace-id`,description:``,required:!0,valueType:`string`,location:`path`},{name:`ad_id`,flag:`--ad-id`,description:`Ad ID to retrieve`,required:!0,valueType:`string`,location:`body`}],examples:[{description:`Example`,command:`adside meta ads get --workspace-id <workspaceId> --ad-id <ad_id>`}],output:{kind:`json`,description:`Retrieve details for a single ad including its name, status, ad set, campaign, and creative.`},transport:{type:`rest`,method:`POST`,path:`/v1/workspaces/{workspaceId}/meta/ads/get`,auth:`user`,requestContentType:`application/json`}},{id:`meta.list_meta_ads`,path:[`meta`,`ads`,`list`],summary:`List all ads for a given campaign, ad set, or ad account. Filter by status and paginate results. Returns ad details including creative, status, and timing.`,description:``,source:`rest`,options:[{name:`workspaceId`,flag:`--workspace-id`,description:``,required:!0,valueType:`string`,location:`path`},{name:`campaign_id`,flag:`--campaign-id`,description:`Filter by campaign ID`,required:!1,valueType:`string`,location:`body`},{name:`adset_id`,flag:`--adset-id`,description:`Filter by ad set ID`,required:!1,valueType:`string`,location:`body`},{name:`account_id`,flag:`--account-id`,description:`Filter by account ID`,required:!1,valueType:`string`,location:`body`},{name:`status`,flag:`--status`,description:`Filter by ad status`,required:!1,valueType:`string`,enum:[`ACTIVE`,`PAUSED`,`DELETED`,`ARCHIVED`],location:`body`},{name:`limit`,flag:`--limit`,description:`Number of ads to return`,required:!1,valueType:`number`,defaultValue:25,location:`body`},{name:`after`,flag:`--after`,description:`Pagination cursor for next page`,required:!1,valueType:`string`,location:`body`}],examples:[{description:`Example`,command:`adside meta ads list --workspace-id <workspaceId>`}],output:{kind:`json`,description:`List all ads for a given campaign, ad set, or ad account. Filter by status and paginate results. Returns ad details including creative, status, and timing.`},transport:{type:`rest`,method:`POST`,path:`/v1/workspaces/{workspaceId}/meta/ads/list`,auth:`user`,requestContentType:`application/json`}},{id:`meta.preview_ad`,path:[`meta`,`ads`,`preview`],summary:`Generate HTML preview of how an ad creative will appear in different placements and formats. Useful for testing creative appearance before launching campaigns.`,description:``,source:`rest`,options:[{name:`workspaceId`,flag:`--workspace-id`,description:``,required:!0,valueType:`string`,location:`path`},{name:`creative_id`,flag:`--creative-id`,description:`Creative ID to preview`,required:!0,valueType:`string`,location:`body`},{name:`ad_format`,flag:`--ad-format`,description:`Ad format for preview`,required:!0,valueType:`string`,enum:[`DESKTOP_FEED_STANDARD`,`MOBILE_FEED_STANDARD`,`MOBILE_FEED_BASIC`,`MOBILE_BANNER`,`MOBILE_MEDIUM_RECTANGLE`,`MOBILE_FULLWIDTH`,`MOBILE_INTERSTITIAL`,`INSTAGRAM_STANDARD`,`INSTAGRAM_STORY`],location:`body`},{name:`product_item_ids`,flag:`--product-item-ids`,description:`Product item IDs for dynamic ads`,required:!1,valueType:`json`,location:`body`}],examples:[{description:`Example`,command:`adside meta ads preview --workspace-id <workspaceId> --creative-id <creative_id> --ad-format DESKTOP_FEED_STANDARD`}],output:{kind:`json`,description:`Generate HTML preview of how an ad creative will appear in different placements and formats. Useful for testing creative appearance before launching campaigns.`},transport:{type:`rest`,method:`POST`,path:`/v1/workspaces/{workspaceId}/meta/ads/preview`,auth:`user`,requestContentType:`application/json`}},{id:`meta.check_api_compliance`,path:[`meta`,`api-compliance`,`check`],summary:`Check if your creative parameters are compliant with current Meta Marketing API (v25.0) requirements. Identifies deprecated features and recommends best practices.`,description:``,source:`rest`,options:[{name:`workspaceId`,flag:`--workspace-id`,description:``,required:!0,valueType:`string`,location:`path`},{name:`account_id`,flag:`--account-id`,description:`Meta Ad Account ID (uses configured account if not provided)`,required:!1,valueType:`string`,location:`body`},{name:`name`,flag:`--name`,description:`Creative name`,required:!0,valueType:`string`,location:`body`},{name:`page_id`,flag:`--page-id`,description:`Facebook Page ID (required for object_story_spec)`,required:!0,valueType:`string`,location:`body`},{name:`message`,flag:`--message`,description:"Primary ad text/message (single-variant). Mutually exclusive with `bodies`.",required:!1,valueType:`string`,location:`body`},{name:`headline`,flag:`--headline`,description:"Ad title/headline (single-variant). Mutually exclusive with `titles`.",required:!1,valueType:`string`,location:`body`},{name:`bodies`,flag:`--bodies`,description:`Multi-variant primary texts (1–5). When set, the creative is built with asset_feed_spec and must be attached to a Dynamic Creative ad set.`,required:!1,valueType:`json`,location:`body`},{name:`titles`,flag:`--titles`,description:"Multi-variant headlines (1–5). Pair with `bodies`.",required:!1,valueType:`json`,location:`body`},{name:`descriptions`,flag:`--descriptions`,description:"Multi-variant descriptions (0–5). Pair with `bodies`.",required:!1,valueType:`json`,location:`body`},{name:`picture`,flag:`--picture`,description:`External image URL - must be publicly accessible`,required:!1,valueType:`url`,location:`body`},{name:`image_hash`,flag:`--image-hash`,description:`Pre-uploaded image hash (alternative to picture URL)`,required:!1,valueType:`string`,location:`body`},{name:`video_id`,flag:`--video-id`,description:`Video ID for video creatives`,required:!1,valueType:`string`,location:`body`},{name:`placement_assets`,flag:`--placement-assets`,description:"Placement asset customization (multi-ratio ad): one image or video per placement bucket, each `placement_group` at most once. Requires `image_hash` as the fallback image for placements not listed. Upload every ratio first (upload_image_from_url / upload_video_from_url) and pass the hashes. Mutually exclusive with `bodies`/`titles` — the resulting creative must be attached to a STANDARD ad set (Meta rejects it in a Dynamic Creative ad set).",required:!1,valueType:`json`,location:`body`},{name:`call_to_action_type`,flag:`--call-to-action-type`,description:`Call to action button type (40+ supported types)`,required:!1,valueType:`string`,enum:`LEARN_MORE.SHOP_NOW.SIGN_UP.DOWNLOAD.BOOK_TRAVEL.LISTEN_MUSIC.WATCH_VIDEO.GET_QUOTE.CONTACT_US.APPLY_NOW.GET_DIRECTIONS.CALL_NOW.MESSAGE_PAGE.SUBSCRIBE.BOOK_NOW.ORDER_NOW.DONATE_NOW.SAY_THANKS.SELL_NOW.SHARE.OPEN_LINK.LIKE_PAGE.FOLLOW_PAGE.FOLLOW_USER.REQUEST_TIME.VISIT_PAGES_FEED.USE_APP.PLAY_GAME.INSTALL_APP.USE_MOBILE_APP.INSTALL_MOBILE_APP.OPEN_MOVIES.AUDIO_CALL.VIDEO_CALL.GET_OFFER.GET_OFFER_VIEW.BUY_NOW.ADD_TO_CART.SELL.GIFT_WRAP.MAKE_AN_OFFER.BUY_TICKETS.EXPLORE_MORE.GET_PROMOTIONS.GET_SHOWTIMES.LISTEN_NOW.SAVE.SEE_DETAILS.SEE_MENU.WATCH_MORE.WHATSAPP_MESSAGE`.split(`.`),location:`body`},{name:`link_url`,flag:`--link-url`,description:`Destination URL where users will be directed when clicking the ad`,required:!0,valueType:`url`,location:`body`},{name:`description`,flag:`--description`,description:`Additional description text`,required:!1,valueType:`string`,location:`body`},{name:`instagram_actor_id`,flag:`--instagram-actor-id`,description:`Optional. Instagram Business Account ID of the Page's Instagram account (typically starts with 1784) — the instagram_account_id get_account_pages reports for that Page. When omitted the tool resolves the identity itself: the Page's Instagram business account, else — for placement-customised and variation creatives only, which Meta refuses without one — its Page-backed Instagram account (created when the Page has none — a write on the client's Page the result calls out), else the Page actor override. A standard creative is left without one when the Page has no Instagram account. The result reports which one it used in instagram_identity`,required:!1,valueType:`string`,location:`body`},{name:`adlabels`,flag:`--adlabels`,description:`Ad labels for organization and tracking`,required:!1,valueType:`json`,location:`body`},{name:`enable_standard_enhancements`,flag:`--enable-standard-enhancements`,description:`Enable Standard Enhancements with individual feature control`,required:!1,valueType:`boolean`,defaultValue:!1,location:`body`},{name:`enhancement_features`,flag:`--enhancement-features`,description:`Individual enhancement feature controls`,required:!1,valueType:`json`,location:`body`},{name:`attachment_style`,flag:`--attachment-style`,description:`Attachment style for link ads`,required:!1,valueType:`string`,defaultValue:`link`,enum:[`link`,`album`],location:`body`},{name:`caption`,flag:`--caption`,description:`Caption text (typically domain name)`,required:!1,valueType:`string`,location:`body`},{name:`url_tags`,flag:`--url-tags`,description:`URL tags appended to the link URL for tracking (e.g. utm_source=...&utm_medium=...)`,required:!1,valueType:`string`,location:`body`}],examples:[{description:`Example`,command:`adside meta api-compliance check --workspace-id <workspaceId> --name <name> --page-id <page_id> --link-url https://example.com`}],output:{kind:`json`,description:`Check if your creative parameters are compliant with current Meta Marketing API (v25.0) requirements. Identifies deprecated features and recommends best practices.`},transport:{type:`rest`,method:`POST`,path:`/v1/workspaces/{workspaceId}/meta/api-compliance/check`,auth:`user`,requestContentType:`application/json`}},{id:`meta.get_meta_api_reference`,path:[`meta`,`api-reference`,`get`],summary:`Get a reference guide for valid Meta Marketing API parameters, including allowed optimization goals, billing events, and their valid combinations. Use this to troubleshoot parameter errors or to construct valid requests.`,description:``,source:`rest`,options:[{name:`workspaceId`,flag:`--workspace-id`,description:``,required:!0,valueType:`string`,location:`path`}],examples:[{description:`Example`,command:`adside meta api-reference get --workspace-id <workspaceId>`}],output:{kind:`json`,description:`Get a reference guide for valid Meta Marketing API parameters, including allowed optimization goals, billing events, and their valid combinations. Use this to troubleshoot parameter errors or to construct valid requests.`},transport:{type:`rest`,method:`POST`,path:`/v1/workspaces/{workspaceId}/meta/api-reference/get`,auth:`user`}},{id:`meta.get_attribution_data`,path:[`meta`,`attribution-data`,`get`],summary:"Retrieve attribution data with conversion tracking across multiple attribution windows (1-day click, 7-day click, 1-day view). Returns conversion metrics and cost-per-conversion analysis.\n\nRows are heavy: every row carries `actions` and `cost_per_action_type`, each entry split across three attribution windows. The response is capped in size — past that, rows are dropped and a `truncation` object says how many, and those rows are an arbitrary page rather than the top ones, because this endpoint returns no ranking. `summary` is always computed over every fetched row. Narrow the call (`limit`, a single `object_id`) rather than relying on the cap, and use the reporting-warehouse tools to rank objects over a period.",description:``,source:`rest`,options:[{name:`workspaceId`,flag:`--workspace-id`,description:``,required:!0,valueType:`string`,location:`path`},{name:`object_id`,flag:`--object-id`,description:"ID of the object to get insights for. Omit it to use the connected ad account (recommended for account-wide queries at any level). Otherwise pass a campaign ID, ad set ID, or ad ID matching `level`. Account IDs other than the connected account are rejected. Passing a page/business/user ID returns Meta error #100.",required:!1,valueType:`string`,location:`body`},{name:`level`,flag:`--level`,description:`Level of insights to retrieve`,required:!0,valueType:`string`,enum:[`account`,`campaign`,`adset`,`ad`],location:`body`},{name:`date_preset`,flag:`--date-preset`,description:`Date preset for insights`,required:!1,valueType:`string`,enum:[`today`,`yesterday`,`last_3d`,`last_7d`,`last_14d`,`last_28d`,`last_30d`,`last_90d`,`this_week_mon_today`,`this_week_sun_today`,`last_week_mon_sun`,`last_week_sun_sat`,`this_month`,`last_month`,`this_quarter`,`last_quarter`,`this_year`,`last_year`,`maximum`,`data_maximum`],location:`body`},{name:`time_range`,flag:`--time-range`,description:`Custom date range for insights`,required:!1,valueType:`json`,location:`body`},{name:`fields`,flag:`--fields`,description:`Specific fields to retrieve (e.g., impressions, clicks, spend)`,required:!1,valueType:`json`,location:`body`},{name:`breakdowns`,flag:`--breakdowns`,description:`Breakdown dimensions (e.g., age, gender, placement)`,required:!1,valueType:`json`,location:`body`},{name:`time_increment`,flag:`--time-increment`,description:`Time granularity: "monthly" for monthly rows, "all_days" for daily rows, or a number 1-90 for N-day increments`,required:!1,valueType:`json`,location:`body`},{name:`limit`,flag:`--limit`,description:`Number of insights to return`,required:!1,valueType:`number`,defaultValue:25,location:`body`},{name:`after`,flag:`--after`,description:"Cursor for the next page: pass back the `pagination.next_cursor` value from a previous response. Keep every other parameter identical, or the cursor no longer matches the query it came from.",required:!1,valueType:`string`,location:`body`}],examples:[{description:`Example`,command:`adside meta attribution-data get --workspace-id <workspaceId> --level account`}],output:{kind:`json`,description:"Retrieve attribution data with conversion tracking across multiple attribution windows (1-day click, 7-day click, 1-day view). Returns conversion metrics and cost-per-conversion analysis.\n\nRows are heavy: every row carries `actions` and `cost_per_action_type`, each entry split across three attribution windows. The response is capped in size — past that, rows are dropped and a `truncation` object says how many, and those rows are an arbitrary page rather than the top ones, because this endpoint returns no ranking. `summary` is always computed over every fetched row. Narrow the call (`limit`, a single `object_id`) rather than relying on the cap, and use the reporting-warehouse tools to rank objects over a period."},transport:{type:`rest`,method:`POST`,path:`/v1/workspaces/{workspaceId}/meta/attribution-data/get`,auth:`user`,requestContentType:`application/json`}},{id:`meta.get_audience_details`,path:[`meta`,`audience-details`,`get`],summary:`Get detailed information about a specific audience including size estimates, delivery status, operation status, data source, and targeting rules.`,description:``,source:`rest`,options:[{name:`workspaceId`,flag:`--workspace-id`,description:``,required:!0,valueType:`string`,location:`path`},{name:`audience_id`,flag:`--audience-id`,description:`The audience ID to get details for`,required:!0,valueType:`string`,location:`body`}],examples:[{description:`Example`,command:`adside meta audience-details get --workspace-id <workspaceId> --audience-id <audience_id>`}],output:{kind:`json`,description:`Get detailed information about a specific audience including size estimates, delivery status, operation status, data source, and targeting rules.`},transport:{type:`rest`,method:`POST`,path:`/v1/workspaces/{workspaceId}/meta/audience-details/get`,auth:`user`,requestContentType:`application/json`}},{id:`meta.estimate_audience_size`,path:[`meta`,`audience-size`,`estimate`],summary:`Estimate the potential reach of a targeting specification. Returns monthly and daily active user estimates with targeting recommendations.`,description:``,source:`rest`,options:[{name:`workspaceId`,flag:`--workspace-id`,description:``,required:!0,valueType:`string`,location:`path`},{name:`account_id`,flag:`--account-id`,description:`Meta Ad Account ID (uses configured account if not provided)`,required:!1,valueType:`string`,location:`body`},{name:`targeting`,flag:`--targeting`,description:`Targeting parameters for size estimation`,required:!0,valueType:`json`,location:`body`},{name:`optimization_goal`,flag:`--optimization-goal`,description:`Optimization goal for the estimate`,required:!0,valueType:`string`,location:`body`}],examples:[{description:`Example`,command:`adside meta audience-size estimate --workspace-id <workspaceId> --targeting '{}' --optimization-goal <optimization_goal>`}],output:{kind:`json`,description:`Estimate the potential reach of a targeting specification. Returns monthly and daily active user estimates with targeting recommendations.`},transport:{type:`rest`,method:`POST`,path:`/v1/workspaces/{workspaceId}/meta/audience-size/estimate`,auth:`user`,requestContentType:`application/json`}},{id:`meta.list_audiences`,path:[`meta`,`audiences`,`list`],summary:`List custom and lookalike audiences for an ad account. Supports filtering by type (custom, lookalike, saved) and pagination.`,description:``,source:`rest`,options:[{name:`workspaceId`,flag:`--workspace-id`,description:``,required:!0,valueType:`string`,location:`path`},{name:`account_id`,flag:`--account-id`,description:`Meta Ad Account ID (uses configured account if not provided)`,required:!1,valueType:`string`,location:`body`},{name:`type`,flag:`--type`,description:`Filter by audience type`,required:!1,valueType:`string`,enum:[`custom`,`lookalike`,`saved`],location:`body`},{name:`limit`,flag:`--limit`,description:`Number of audiences to return`,required:!1,valueType:`number`,defaultValue:25,location:`body`},{name:`after`,flag:`--after`,description:`Pagination cursor for next page`,required:!1,valueType:`string`,location:`body`}],examples:[{description:`Example`,command:`adside meta audiences list --workspace-id <workspaceId>`}],output:{kind:`json`,description:`List custom and lookalike audiences for an ad account. Supports filtering by type (custom, lookalike, saved) and pagination.`},transport:{type:`rest`,method:`POST`,path:`/v1/workspaces/{workspaceId}/meta/audiences/list`,auth:`user`,requestContentType:`application/json`}},{id:`meta.search_behaviors`,path:[`meta`,`behaviors`,`search`],summary:`List all available targetable behaviors from Meta's targeting categories. Returns behavior IDs, names, descriptions, and audience sizes.`,description:``,source:`rest`,options:[{name:`workspaceId`,flag:`--workspace-id`,description:``,required:!0,valueType:`string`,location:`path`},{name:`limit`,flag:`--limit`,description:`Number of results to return`,required:!1,valueType:`number`,defaultValue:100,location:`body`}],examples:[{description:`Example`,command:`adside meta behaviors search --workspace-id <workspaceId>`}],output:{kind:`json`,description:`List all available targetable behaviors from Meta's targeting categories. Returns behavior IDs, names, descriptions, and audience sizes.`},transport:{type:`rest`,method:`POST`,path:`/v1/workspaces/{workspaceId}/meta/behaviors/search`,auth:`user`,requestContentType:`application/json`}},{id:`meta.check_campaign_readiness`,path:[`meta`,`campaign-readiness`,`check`],summary:`Check if a campaign is ready for ad set creation. Identify the campaign by ID or by name. Returns a readiness report with issues, requirements, and recommendations.`,description:``,source:`rest`,options:[{name:`workspaceId`,flag:`--workspace-id`,description:``,required:!0,valueType:`string`,location:`path`},{name:`campaign_id`,flag:`--campaign-id`,description:`Campaign ID. Preferred when known. Provide this or campaign_name, not both.`,required:!1,valueType:`string`,location:`body`},{name:`campaign_name`,flag:`--campaign-name`,description:`Exact campaign name to look up (not an ID). Use campaign_id when the ID is known. Provide this or campaign_id, not both.`,required:!1,valueType:`string`,location:`body`},{name:`account_id`,flag:`--account-id`,description:`Meta Ad Account ID (required when using campaign_name, uses configured account if not provided)`,required:!1,valueType:`string`,location:`body`}],examples:[{description:`Example`,command:`adside meta campaign-readiness check --workspace-id <workspaceId>`}],output:{kind:`json`,description:`Check if a campaign is ready for ad set creation. Identify the campaign by ID or by name. Returns a readiness report with issues, requirements, and recommendations.`},transport:{type:`rest`,method:`POST`,path:`/v1/workspaces/{workspaceId}/meta/campaign-readiness/check`,auth:`user`,requestContentType:`application/json`}},{id:`meta.get_campaign`,path:[`meta`,`campaigns`,`get`],summary:`Retrieve full details for a specific campaign by ID or name. Returns all campaign fields including status, objective, budget, and timing.`,description:``,source:`rest`,options:[{name:`workspaceId`,flag:`--workspace-id`,description:``,required:!0,valueType:`string`,location:`path`},{name:`campaign_id`,flag:`--campaign-id`,description:`Campaign ID. Preferred when known. Provide this or campaign_name, not both.`,required:!1,valueType:`string`,location:`body`},{name:`campaign_name`,flag:`--campaign-name`,description:`Exact campaign name to look up (not an ID). Use campaign_id when the ID is known. Provide this or campaign_id, not both.`,required:!1,valueType:`string`,location:`body`},{name:`account_id`,flag:`--account-id`,description:`Meta Ad Account ID (required when using campaign_name, uses configured account if not provided)`,required:!1,valueType:`string`,location:`body`}],examples:[{description:`Example`,command:`adside meta campaigns get --workspace-id <workspaceId>`}],output:{kind:`json`,description:`Retrieve full details for a specific campaign by ID or name. Returns all campaign fields including status, objective, budget, and timing.`},transport:{type:`rest`,method:`POST`,path:`/v1/workspaces/{workspaceId}/meta/campaigns/get`,auth:`user`,requestContentType:`application/json`}},{id:`meta.list_meta_campaigns`,path:[`meta`,`campaigns`,`list`],summary:`Retrieve a paginated list of all campaigns for a Meta ad account. Filter by status (e.g., ACTIVE, PAUSED) and view key campaign details including budget, objective, and timing. Use this to audit or select campaigns for further actions.`,description:``,source:`rest`,options:[{name:`workspaceId`,flag:`--workspace-id`,description:``,required:!0,valueType:`string`,location:`path`},{name:`account_id`,flag:`--account-id`,description:`Meta Ad Account ID (uses configured account if not provided)`,required:!1,valueType:`string`,location:`body`},{name:`status`,flag:`--status`,description:`Filter by campaign status`,required:!1,valueType:`string`,enum:[`ACTIVE`,`PAUSED`,`DELETED`,`ARCHIVED`],location:`body`},{name:`limit`,flag:`--limit`,description:`Number of campaigns to return`,required:!1,valueType:`number`,defaultValue:25,location:`body`},{name:`after`,flag:`--after`,description:`Pagination cursor for next page`,required:!1,valueType:`string`,location:`body`}],examples:[{description:`Example`,command:`adside meta campaigns list --workspace-id <workspaceId>`}],output:{kind:`json`,description:`Retrieve a paginated list of all campaigns for a Meta ad account. Filter by status (e.g., ACTIVE, PAUSED) and view key campaign details including budget, objective, and timing. Use this to audit or select campaigns for further actions.`},transport:{type:`rest`,method:`POST`,path:`/v1/workspaces/{workspaceId}/meta/campaigns/list`,auth:`user`,requestContentType:`application/json`}},{id:`meta.get_creative_best_practices`,path:[`meta`,`creative-best-practices`,`get`],summary:`Get comprehensive best practices for creating high-performing ad creatives. Includes platform-specific guidelines, content recommendations, and optimization strategies.`,description:``,source:`rest`,options:[{name:`workspaceId`,flag:`--workspace-id`,description:``,required:!0,valueType:`string`,location:`path`}],examples:[{description:`Example`,command:`adside meta creative-best-practices get --workspace-id <workspaceId>`}],output:{kind:`json`,description:`Get comprehensive best practices for creating high-performing ad creatives. Includes platform-specific guidelines, content recommendations, and optimization strategies.`},transport:{type:`rest`,method:`POST`,path:`/v1/workspaces/{workspaceId}/meta/creative-best-practices/get`,auth:`user`}},{id:`meta.validate_creative_enhanced`,path:[`meta`,`creative-enhanced`,`validate`],summary:`Enhanced creative validation with comprehensive checks including page permissions, image accessibility, and Meta API compliance. Provides detailed feedback and fix suggestions.`,description:``,source:`rest`,options:[{name:`workspaceId`,flag:`--workspace-id`,description:``,required:!0,valueType:`string`,location:`path`},{name:`account_id`,flag:`--account-id`,description:`Meta Ad Account ID (uses configured account if not provided)`,required:!1,valueType:`string`,location:`body`},{name:`name`,flag:`--name`,description:`Creative name`,required:!0,valueType:`string`,location:`body`},{name:`page_id`,flag:`--page-id`,description:`Facebook Page ID (required for object_story_spec)`,required:!0,valueType:`string`,location:`body`},{name:`message`,flag:`--message`,description:`Primary ad text/message`,required:!0,valueType:`string`,location:`body`},{name:`headline`,flag:`--headline`,description:`Ad title/headline`,required:!1,valueType:`string`,location:`body`},{name:`picture`,flag:`--picture`,description:`External image URL - must be publicly accessible`,required:!1,valueType:`url`,location:`body`},{name:`image_hash`,flag:`--image-hash`,description:`Pre-uploaded image hash (alternative to picture URL)`,required:!1,valueType:`string`,location:`body`},{name:`video_id`,flag:`--video-id`,description:`Video ID for video creatives`,required:!1,valueType:`string`,location:`body`},{name:`call_to_action_type`,flag:`--call-to-action-type`,description:`Call to action button type (40+ supported types)`,required:!1,valueType:`string`,enum:`LEARN_MORE.SHOP_NOW.SIGN_UP.DOWNLOAD.BOOK_TRAVEL.LISTEN_MUSIC.WATCH_VIDEO.GET_QUOTE.CONTACT_US.APPLY_NOW.GET_DIRECTIONS.CALL_NOW.MESSAGE_PAGE.SUBSCRIBE.BOOK_NOW.ORDER_NOW.DONATE_NOW.SAY_THANKS.SELL_NOW.SHARE.OPEN_LINK.LIKE_PAGE.FOLLOW_PAGE.FOLLOW_USER.REQUEST_TIME.VISIT_PAGES_FEED.USE_APP.PLAY_GAME.INSTALL_APP.USE_MOBILE_APP.INSTALL_MOBILE_APP.OPEN_MOVIES.AUDIO_CALL.VIDEO_CALL.GET_OFFER.GET_OFFER_VIEW.BUY_NOW.ADD_TO_CART.SELL.GIFT_WRAP.MAKE_AN_OFFER.BUY_TICKETS.EXPLORE_MORE.GET_PROMOTIONS.GET_SHOWTIMES.LISTEN_NOW.SAVE.SEE_DETAILS.SEE_MENU.WATCH_MORE.WHATSAPP_MESSAGE`.split(`.`),location:`body`},{name:`link_url`,flag:`--link-url`,description:`Destination URL where users will be directed when clicking the ad`,required:!1,valueType:`url`,location:`body`},{name:`description`,flag:`--description`,description:`Additional description text`,required:!1,valueType:`string`,location:`body`},{name:`instagram_actor_id`,flag:`--instagram-actor-id`,description:`Optional. Instagram Business Account ID of the Page's Instagram account (typically starts with 1784) — the instagram_account_id get_account_pages reports for that Page. When omitted the tool resolves the identity itself: the Page's Instagram business account, else — for placement-customised and variation creatives only, which Meta refuses without one — its Page-backed Instagram account (created when the Page has none — a write on the client's Page the result calls out), else the Page actor override. A standard creative is left without one when the Page has no Instagram account. The result reports which one it used in instagram_identity`,required:!1,valueType:`string`,location:`body`},{name:`adlabels`,flag:`--adlabels`,description:`Ad labels for organization and tracking`,required:!1,valueType:`json`,location:`body`},{name:`enable_standard_enhancements`,flag:`--enable-standard-enhancements`,description:`Enable Standard Enhancements with individual feature control`,required:!1,valueType:`boolean`,defaultValue:!1,location:`body`},{name:`enhancement_features`,flag:`--enhancement-features`,description:`Individual enhancement feature controls`,required:!1,valueType:`json`,location:`body`},{name:`attachment_style`,flag:`--attachment-style`,description:`Attachment style for link ads`,required:!1,valueType:`string`,defaultValue:`link`,enum:[`link`,`album`],location:`body`},{name:`caption`,flag:`--caption`,description:`Caption text (typically domain name)`,required:!1,valueType:`string`,location:`body`}],examples:[{description:`Example`,command:`adside meta creative-enhanced validate --workspace-id <workspaceId> --name <name> --page-id <page_id> --message <message>`}],output:{kind:`json`,description:`Enhanced creative validation with comprehensive checks including page permissions, image accessibility, and Meta API compliance. Provides detailed feedback and fix suggestions.`},transport:{type:`rest`,method:`POST`,path:`/v1/workspaces/{workspaceId}/meta/creative-enhanced/validate`,auth:`user`,requestContentType:`application/json`}},{id:`meta.troubleshoot_creative_issues`,path:[`meta`,`creative-issues`,`troubleshoot`],summary:`Diagnose and fix common creative creation and performance issues. Provide an error message or describe your issue to get specific solutions and recommendations.`,description:``,source:`rest`,options:[{name:`workspaceId`,flag:`--workspace-id`,description:``,required:!0,valueType:`string`,location:`path`},{name:`issue_description`,flag:`--issue-description`,description:`Describe the creative issue you're experiencing or paste the error message`,required:!0,valueType:`string`,location:`body`},{name:`creative_type`,flag:`--creative-type`,description:`Type of creative experiencing issues`,required:!1,valueType:`string`,enum:[`image`,`video`,`carousel`,`collection`],location:`body`}],examples:[{description:`Example`,command:`adside meta creative-issues troubleshoot --workspace-id <workspaceId> --issue-description <issue_description>`}],output:{kind:`json`,description:`Diagnose and fix common creative creation and performance issues. Provide an error message or describe your issue to get specific solutions and recommendations.`},transport:{type:`rest`,method:`POST`,path:`/v1/workspaces/{workspaceId}/meta/creative-issues/troubleshoot`,auth:`user`,requestContentType:`application/json`}},{id:`meta.get_creative_performance`,path:[`meta`,`creative-performance`,`get`],summary:`Get guidance on analyzing creative performance metrics. Provides recommended approaches for tracking creative effectiveness and optimization strategies.`,description:``,source:`rest`,options:[{name:`workspaceId`,flag:`--workspace-id`,description:``,required:!0,valueType:`string`,location:`path`},{name:`creative_id`,flag:`--creative-id`,description:`Creative ID to preview`,required:!0,valueType:`string`,location:`body`},{name:`ad_format`,flag:`--ad-format`,description:`Ad format for preview`,required:!0,valueType:`string`,enum:[`DESKTOP_FEED_STANDARD`,`MOBILE_FEED_STANDARD`,`MOBILE_FEED_BASIC`,`MOBILE_BANNER`,`MOBILE_MEDIUM_RECTANGLE`,`MOBILE_FULLWIDTH`,`MOBILE_INTERSTITIAL`,`INSTAGRAM_STANDARD`,`INSTAGRAM_STORY`],location:`body`},{name:`product_item_ids`,flag:`--product-item-ids`,description:`Product item IDs for dynamic ads`,required:!1,valueType:`json`,location:`body`}],examples:[{description:`Example`,command:`adside meta creative-performance get --workspace-id <workspaceId> --creative-id <creative_id> --ad-format DESKTOP_FEED_STANDARD`}],output:{kind:`json`,description:`Get guidance on analyzing creative performance metrics. Provides recommended approaches for tracking creative effectiveness and optimization strategies.`},transport:{type:`rest`,method:`POST`,path:`/v1/workspaces/{workspaceId}/meta/creative-performance/get`,auth:`user`,requestContentType:`application/json`}},{id:`meta.validate_creative_setup`,path:[`meta`,`creative-setup`,`validate`],summary:`Validate ad creative parameters before creation to catch errors early. Checks required fields, URL validity, and provides object_story_spec preview. Use this before create_ad_creative to avoid API errors.`,description:``,source:`rest`,options:[{name:`workspaceId`,flag:`--workspace-id`,description:``,required:!0,valueType:`string`,location:`path`},{name:`account_id`,flag:`--account-id`,description:`Meta Ad Account ID (uses configured account if not provided)`,required:!1,valueType:`string`,location:`body`},{name:`name`,flag:`--name`,description:`Creative name`,required:!0,valueType:`string`,location:`body`},{name:`page_id`,flag:`--page-id`,description:`Facebook Page ID (required for object_story_spec)`,required:!0,valueType:`string`,location:`body`},{name:`message`,flag:`--message`,description:"Primary ad text/message (single-variant). Mutually exclusive with `bodies`.",required:!1,valueType:`string`,location:`body`},{name:`headline`,flag:`--headline`,description:"Ad title/headline (single-variant). Mutually exclusive with `titles`.",required:!1,valueType:`string`,location:`body`},{name:`bodies`,flag:`--bodies`,description:`Multi-variant primary texts (1–5). When set, the creative is built with asset_feed_spec and must be attached to a Dynamic Creative ad set.`,required:!1,valueType:`json`,location:`body`},{name:`titles`,flag:`--titles`,description:"Multi-variant headlines (1–5). Pair with `bodies`.",required:!1,valueType:`json`,location:`body`},{name:`descriptions`,flag:`--descriptions`,description:"Multi-variant descriptions (0–5). Pair with `bodies`.",required:!1,valueType:`json`,location:`body`},{name:`picture`,flag:`--picture`,description:`External image URL - must be publicly accessible`,required:!1,valueType:`url`,location:`body`},{name:`image_hash`,flag:`--image-hash`,description:`Pre-uploaded image hash (alternative to picture URL)`,required:!1,valueType:`string`,location:`body`},{name:`video_id`,flag:`--video-id`,description:`Video ID for video creatives`,required:!1,valueType:`string`,location:`body`},{name:`placement_assets`,flag:`--placement-assets`,description:"Placement asset customization (multi-ratio ad): one image or video per placement bucket, each `placement_group` at most once. Requires `image_hash` as the fallback image for placements not listed. Upload every ratio first (upload_image_from_url / upload_video_from_url) and pass the hashes. Mutually exclusive with `bodies`/`titles` — the resulting creative must be attached to a STANDARD ad set (Meta rejects it in a Dynamic Creative ad set).",required:!1,valueType:`json`,location:`body`},{name:`call_to_action_type`,flag:`--call-to-action-type`,description:`Call to action button type (40+ supported types)`,required:!1,valueType:`string`,enum:`LEARN_MORE.SHOP_NOW.SIGN_UP.DOWNLOAD.BOOK_TRAVEL.LISTEN_MUSIC.WATCH_VIDEO.GET_QUOTE.CONTACT_US.APPLY_NOW.GET_DIRECTIONS.CALL_NOW.MESSAGE_PAGE.SUBSCRIBE.BOOK_NOW.ORDER_NOW.DONATE_NOW.SAY_THANKS.SELL_NOW.SHARE.OPEN_LINK.LIKE_PAGE.FOLLOW_PAGE.FOLLOW_USER.REQUEST_TIME.VISIT_PAGES_FEED.USE_APP.PLAY_GAME.INSTALL_APP.USE_MOBILE_APP.INSTALL_MOBILE_APP.OPEN_MOVIES.AUDIO_CALL.VIDEO_CALL.GET_OFFER.GET_OFFER_VIEW.BUY_NOW.ADD_TO_CART.SELL.GIFT_WRAP.MAKE_AN_OFFER.BUY_TICKETS.EXPLORE_MORE.GET_PROMOTIONS.GET_SHOWTIMES.LISTEN_NOW.SAVE.SEE_DETAILS.SEE_MENU.WATCH_MORE.WHATSAPP_MESSAGE`.split(`.`),location:`body`},{name:`link_url`,flag:`--link-url`,description:`Destination URL where users will be directed when clicking the ad`,required:!0,valueType:`url`,location:`body`},{name:`description`,flag:`--description`,description:`Additional description text`,required:!1,valueType:`string`,location:`body`},{name:`instagram_actor_id`,flag:`--instagram-actor-id`,description:`Optional. Instagram Business Account ID of the Page's Instagram account (typically starts with 1784) — the instagram_account_id get_account_pages reports for that Page. When omitted the tool resolves the identity itself: the Page's Instagram business account, else — for placement-customised and variation creatives only, which Meta refuses without one — its Page-backed Instagram account (created when the Page has none — a write on the client's Page the result calls out), else the Page actor override. A standard creative is left without one when the Page has no Instagram account. The result reports which one it used in instagram_identity`,required:!1,valueType:`string`,location:`body`},{name:`adlabels`,flag:`--adlabels`,description:`Ad labels for organization and tracking`,required:!1,valueType:`json`,location:`body`},{name:`enable_standard_enhancements`,flag:`--enable-standard-enhancements`,description:`Enable Standard Enhancements with individual feature control`,required:!1,valueType:`boolean`,defaultValue:!1,location:`body`},{name:`enhancement_features`,flag:`--enhancement-features`,description:`Individual enhancement feature controls`,required:!1,valueType:`json`,location:`body`},{name:`attachment_style`,flag:`--attachment-style`,description:`Attachment style for link ads`,required:!1,valueType:`string`,defaultValue:`link`,enum:[`link`,`album`],location:`body`},{name:`caption`,flag:`--caption`,description:`Caption text (typically domain name)`,required:!1,valueType:`string`,location:`body`},{name:`url_tags`,flag:`--url-tags`,description:`URL tags appended to the link URL for tracking (e.g. utm_source=...&utm_medium=...)`,required:!1,valueType:`string`,location:`body`}],examples:[{description:`Example`,command:`adside meta creative-setup validate --workspace-id <workspaceId> --name <name> --page-id <page_id> --link-url https://example.com`}],output:{kind:`json`,description:`Validate ad creative parameters before creation to catch errors early. Checks required fields, URL validity, and provides object_story_spec preview. Use this before create_ad_creative to avoid API errors.`},transport:{type:`rest`,method:`POST`,path:`/v1/workspaces/{workspaceId}/meta/creative-setup/validate`,auth:`user`,requestContentType:`application/json`}},{id:`meta.list_meta_creatives`,path:[`meta`,`creatives`,`list`],summary:`Browse an ad account's creatives, one page at a time. Each row is a SUMMARY — id, name, headline, primary text, call to action, destination, whether it is an image or a video, and how many variants a dynamic creative rotates. For the full row — the complete object_story_spec, asset_feed_spec and the Advantage+ enhancement settings, plus the image URL — call get_ad_creative on the id you want; use preview_ad to see the ad rendered. Ask for the smallest page that answers the question and follow next_cursor for the rest: a full page is a large answer whatever we strip from it, because the ad copy itself is the bulk of it.`,description:``,source:`rest`,options:[{name:`workspaceId`,flag:`--workspace-id`,description:``,required:!0,valueType:`string`,location:`path`},{name:`account_id`,flag:`--account-id`,description:`Meta Ad Account ID (uses configured account if not provided)`,required:!1,valueType:`string`,location:`body`},{name:`limit`,flag:`--limit`,description:`How many creatives to return, 1-50 (default 25). Follow next_cursor for more rather than asking for a bigger page.`,required:!1,valueType:`number`,defaultValue:25,location:`body`},{name:`after`,flag:`--after`,description:`Pagination cursor for next page`,required:!1,valueType:`string`,location:`body`}],examples:[{description:`Example`,command:`adside meta creatives list --workspace-id <workspaceId>`}],output:{kind:`json`,description:`Browse an ad account's creatives, one page at a time. Each row is a SUMMARY — id, name, headline, primary text, call to action, destination, whether it is an image or a video, and how many variants a dynamic creative rotates. For the full row — the complete object_story_spec, asset_feed_spec and the Advantage+ enhancement settings, plus the image URL — call get_ad_creative on the id you want; use preview_ad to see the ad rendered. Ask for the smallest page that answers the question and follow next_cursor for the rest: a full page is a large answer whatever we strip from it, because the ad copy itself is the bulk of it.`},transport:{type:`rest`,method:`POST`,path:`/v1/workspaces/{workspaceId}/meta/creatives/list`,auth:`user`,requestContentType:`application/json`}},{id:`meta.list_custom_conversions`,path:[`meta`,`custom-conversions`,`list`],summary:`List the account's custom conversions — the named conversions built on a dataset's traffic, as opposed to Meta's standard pixel events or named custom pixel events. To verify raw event activity on a dataset, use get_pixel_stats; an empty custom-conversion list does not mean the pixel has no events.
14
+
15
+ Use this to find the ID to optimise an ad set towards: pass it as \`promoted_object.custom_conversion_id\` on create_ad_set_enhanced or update_ad_set. Many accounts never adopted Meta's standard event taxonomy and put all their real volume here, so a standard event that looks right can have fired zero times.
16
+
17
+ In reporting and insights breakdowns the same conversion appears as \`offsite_conversion.custom.<id>\`.`,description:``,source:`rest`,options:[{name:`workspaceId`,flag:`--workspace-id`,description:``,required:!0,valueType:`string`,location:`path`},{name:`account_id`,flag:`--account-id`,description:`Meta Ad Account ID (uses configured account if not provided)`,required:!1,valueType:`string`,location:`body`},{name:`limit`,flag:`--limit`,description:`Maximum to return. An account may hold up to 100.`,required:!1,valueType:`number`,location:`body`}],examples:[{description:`Example`,command:`adside meta custom-conversions list --workspace-id <workspaceId>`}],output:{kind:`json`,description:`List the account's custom conversions — the named conversions built on a dataset's traffic, as opposed to Meta's standard pixel events or named custom pixel events. To verify raw event activity on a dataset, use get_pixel_stats; an empty custom-conversion list does not mean the pixel has no events.
18
+
19
+ Use this to find the ID to optimise an ad set towards: pass it as \`promoted_object.custom_conversion_id\` on create_ad_set_enhanced or update_ad_set. Many accounts never adopted Meta's standard event taxonomy and put all their real volume here, so a standard event that looks right can have fired zero times.
20
+
21
+ In reporting and insights breakdowns the same conversion appears as \`offsite_conversion.custom.<id>\`.`},transport:{type:`rest`,method:`POST`,path:`/v1/workspaces/{workspaceId}/meta/custom-conversions/list`,auth:`user`,requestContentType:`application/json`}},{id:`meta.search_demographics`,path:[`meta`,`demographics`,`search`],summary:`List all available targetable demographics from Meta's targeting categories. Returns demographic IDs, names, descriptions, and audience sizes.`,description:``,source:`rest`,options:[{name:`workspaceId`,flag:`--workspace-id`,description:``,required:!0,valueType:`string`,location:`path`},{name:`limit`,flag:`--limit`,description:`Number of results to return`,required:!1,valueType:`number`,defaultValue:100,location:`body`}],examples:[{description:`Example`,command:`adside meta demographics search --workspace-id <workspaceId>`}],output:{kind:`json`,description:`List all available targetable demographics from Meta's targeting categories. Returns demographic IDs, names, descriptions, and audience sizes.`},transport:{type:`rest`,method:`POST`,path:`/v1/workspaces/{workspaceId}/meta/demographics/search`,auth:`user`,requestContentType:`application/json`}},{id:`meta.get_meta_error_codes`,path:[`meta`,`error-codes`,`get`],summary:`Get detailed reference for Meta Marketing API error codes, subcodes, and specific solutions. Essential for troubleshooting Marketing API integration issues.`,description:``,source:`rest`,options:[{name:`workspaceId`,flag:`--workspace-id`,description:``,required:!0,valueType:`string`,location:`path`},{name:`error_code`,flag:`--error-code`,description:`Specific error code to look up (optional - returns all if not provided)`,required:!1,valueType:`string`,location:`body`},{name:`error_subcode`,flag:`--error-subcode`,description:`Specific error subcode for detailed guidance (optional)`,required:!1,valueType:`string`,location:`body`}],examples:[{description:`Example`,command:`adside meta error-codes get --workspace-id <workspaceId>`}],output:{kind:`json`,description:`Get detailed reference for Meta Marketing API error codes, subcodes, and specific solutions. Essential for troubleshooting Marketing API integration issues.`},transport:{type:`rest`,method:`POST`,path:`/v1/workspaces/{workspaceId}/meta/error-codes/get`,auth:`user`,requestContentType:`application/json`}},{id:`meta.search_geo_locations`,path:[`meta`,`geo-locations`,`search`],summary:`Search for targetable geographic locations (countries, regions, cities, zip codes) by keyword. Returns location keys for use in ad set geo targeting.`,description:``,source:`rest`,options:[{name:`workspaceId`,flag:`--workspace-id`,description:``,required:!0,valueType:`string`,location:`path`},{name:`query`,flag:`--query`,description:`Search query for locations`,required:!0,valueType:`string`,location:`body`},{name:`location_type`,flag:`--location-type`,description:`Filter by location type`,required:!1,valueType:`string`,enum:[`country`,`region`,`city`,`zip`,`geo_market`,`electoral_district`],location:`body`},{name:`limit`,flag:`--limit`,description:`Number of results to return`,required:!1,valueType:`number`,defaultValue:25,location:`body`}],examples:[{description:`Example`,command:`adside meta geo-locations search --workspace-id <workspaceId> --query <query>`}],output:{kind:`json`,description:`Search for targetable geographic locations (countries, regions, cities, zip codes) by keyword. Returns location keys for use in ad set geo targeting.`},transport:{type:`rest`,method:`POST`,path:`/v1/workspaces/{workspaceId}/meta/geo-locations/search`,auth:`user`,requestContentType:`application/json`}},{id:`meta.export_insights`,path:[`meta`,`insights`,`export`],summary:`Export performance insights data in CSV or JSON format. Fetches up to 1000 records for comprehensive data export with optional breakdowns.`,description:``,source:`rest`,options:[{name:`workspaceId`,flag:`--workspace-id`,description:``,required:!0,valueType:`string`,location:`path`},{name:`object_id`,flag:`--object-id`,description:`ID of campaign, ad set, or ad to export insights for`,required:!0,valueType:`string`,location:`body`},{name:`level`,flag:`--level`,description:`Level of insights to export`,required:!0,valueType:`string`,enum:[`account`,`campaign`,`adset`,`ad`],location:`body`},{name:`format`,flag:`--format`,description:`Export format`,required:!1,valueType:`string`,defaultValue:`csv`,enum:[`csv`,`json`],location:`body`},{name:`date_preset`,flag:`--date-preset`,description:`Date preset for export`,required:!1,valueType:`string`,enum:[`today`,`yesterday`,`last_3d`,`last_7d`,`last_14d`,`last_28d`,`last_30d`,`last_90d`,`this_week_mon_today`,`this_week_sun_today`,`last_week_mon_sun`,`last_week_sun_sat`,`this_month`,`last_month`,`this_quarter`,`last_quarter`,`this_year`,`last_year`,`maximum`,`data_maximum`],location:`body`},{name:`time_range`,flag:`--time-range`,description:`Custom date range for export`,required:!1,valueType:`json`,location:`body`},{name:`fields`,flag:`--fields`,description:`Specific fields to export`,required:!1,valueType:`json`,location:`body`},{name:`breakdowns`,flag:`--breakdowns`,description:`Breakdown dimensions to include`,required:!1,valueType:`json`,location:`body`}],examples:[{description:`Example`,command:`adside meta insights export --workspace-id <workspaceId> --object-id <object_id> --level account`}],output:{kind:`json`,description:`Export performance insights data in CSV or JSON format. Fetches up to 1000 records for comprehensive data export with optional breakdowns.`},transport:{type:`rest`,method:`POST`,path:`/v1/workspaces/{workspaceId}/meta/insights/export`,auth:`user`,requestContentType:`application/json`}},{id:`meta.get_insights`,path:[`meta`,`insights`,`get`],summary:"LIVE performance insights straight from the Meta Graph API (impressions, clicks, spend, CTR, CPC, actions) for a campaign, ad set, ad, or account. Supports date presets, custom date ranges, breakdowns, and custom field selection. For pixel/dataset event activity independent of ad attribution or ad-set attachment, use get_pixel_stats; these insights cannot establish whether a pixel receives events.\n\nIf reporting-warehouse tools are available to you in this session (`get_top_creatives_data`, `get_campaign_spend`, `get_account_summary`, `query_reporting`), this tool is the fallback, not the default. Use it only for what the warehouse cannot answer: today and the last 24h, or a breakdown it does not carry. Ranking ads or campaigns over a past period ('which ads should I kill/scale', 'top creatives'), multi-day totals, and week- or month-over-month trends all belong to the warehouse — it aggregates in SQL, answers for every object in one call, and returns a ranked handful of rows instead of one row per object.\n\nThis tool returns one raw JSON row per object per time bucket, each carrying full `actions` and `cost_per_action_type` arrays. At `level: 'ad'` over a multi-day range that is tens of thousands of tokens — enough to fill your context and truncate your own answer. If you call it anyway, narrow it: the smallest `limit` that answers the question, an explicit `fields` list, and one call with `time_increment` rather than one call per period.\n\nThe response is capped in size. Past that, rows are dropped and a `truncation` object says how many — the rows you get back are an arbitrary page, NOT the top performers, because this endpoint returns no ranking. `summary` is always computed over every fetched row, so totals and averages stay correct even when rows are dropped. If you see `truncation`, do not rank from what remains: ask the warehouse.",description:``,source:`rest`,options:[{name:`workspaceId`,flag:`--workspace-id`,description:``,required:!0,valueType:`string`,location:`path`},{name:`object_id`,flag:`--object-id`,description:"ID of the object to get insights for. Omit it to use the connected ad account (recommended for account-wide queries at any level). Otherwise pass a campaign ID, ad set ID, or ad ID matching `level`. Account IDs other than the connected account are rejected. Passing a page/business/user ID returns Meta error #100.",required:!1,valueType:`string`,location:`body`},{name:`level`,flag:`--level`,description:`Level of insights to retrieve`,required:!0,valueType:`string`,enum:[`account`,`campaign`,`adset`,`ad`],location:`body`},{name:`date_preset`,flag:`--date-preset`,description:`Date preset for insights`,required:!1,valueType:`string`,enum:[`today`,`yesterday`,`last_3d`,`last_7d`,`last_14d`,`last_28d`,`last_30d`,`last_90d`,`this_week_mon_today`,`this_week_sun_today`,`last_week_mon_sun`,`last_week_sun_sat`,`this_month`,`last_month`,`this_quarter`,`last_quarter`,`this_year`,`last_year`,`maximum`,`data_maximum`],location:`body`},{name:`time_range`,flag:`--time-range`,description:`Custom date range for insights`,required:!1,valueType:`json`,location:`body`},{name:`fields`,flag:`--fields`,description:`Specific fields to retrieve (e.g., impressions, clicks, spend)`,required:!1,valueType:`json`,location:`body`},{name:`breakdowns`,flag:`--breakdowns`,description:`Breakdown dimensions (e.g., age, gender, placement)`,required:!1,valueType:`json`,location:`body`},{name:`time_increment`,flag:`--time-increment`,description:`Time granularity: "monthly" for monthly rows, "all_days" for daily rows, or a number 1-90 for N-day increments`,required:!1,valueType:`json`,location:`body`},{name:`limit`,flag:`--limit`,description:`Number of insights to return`,required:!1,valueType:`number`,defaultValue:25,location:`body`},{name:`after`,flag:`--after`,description:"Cursor for the next page: pass back the `pagination.next_cursor` value from a previous response. Keep every other parameter identical, or the cursor no longer matches the query it came from.",required:!1,valueType:`string`,location:`body`}],examples:[{description:`Example`,command:`adside meta insights get --workspace-id <workspaceId> --level account`}],output:{kind:`json`,description:"LIVE performance insights straight from the Meta Graph API (impressions, clicks, spend, CTR, CPC, actions) for a campaign, ad set, ad, or account. Supports date presets, custom date ranges, breakdowns, and custom field selection. For pixel/dataset event activity independent of ad attribution or ad-set attachment, use get_pixel_stats; these insights cannot establish whether a pixel receives events.\n\nIf reporting-warehouse tools are available to you in this session (`get_top_creatives_data`, `get_campaign_spend`, `get_account_summary`, `query_reporting`), this tool is the fallback, not the default. Use it only for what the warehouse cannot answer: today and the last 24h, or a breakdown it does not carry. Ranking ads or campaigns over a past period ('which ads should I kill/scale', 'top creatives'), multi-day totals, and week- or month-over-month trends all belong to the warehouse — it aggregates in SQL, answers for every object in one call, and returns a ranked handful of rows instead of one row per object.\n\nThis tool returns one raw JSON row per object per time bucket, each carrying full `actions` and `cost_per_action_type` arrays. At `level: 'ad'` over a multi-day range that is tens of thousands of tokens — enough to fill your context and truncate your own answer. If you call it anyway, narrow it: the smallest `limit` that answers the question, an explicit `fields` list, and one call with `time_increment` rather than one call per period.\n\nThe response is capped in size. Past that, rows are dropped and a `truncation` object says how many — the rows you get back are an arbitrary page, NOT the top performers, because this endpoint returns no ranking. `summary` is always computed over every fetched row, so totals and averages stay correct even when rows are dropped. If you see `truncation`, do not rank from what remains: ask the warehouse."},transport:{type:`rest`,method:`POST`,path:`/v1/workspaces/{workspaceId}/meta/insights/get`,auth:`user`,requestContentType:`application/json`}},{id:`meta.get_interest_suggestions`,path:[`meta`,`interest-suggestions`,`get`],summary:`Get suggested interests similar to a list of seed interests. Useful for expanding targeting reach based on existing high-performing interests.`,description:``,source:`rest`,options:[{name:`workspaceId`,flag:`--workspace-id`,description:``,required:!0,valueType:`string`,location:`path`},{name:`interest_list`,flag:`--interest-list`,description:`List of interest names to get suggestions for`,required:!0,valueType:`json`,location:`body`},{name:`limit`,flag:`--limit`,description:`Number of suggestions to return`,required:!1,valueType:`number`,defaultValue:25,location:`body`}],examples:[{description:`Example`,command:`adside meta interest-suggestions get --workspace-id <workspaceId> --interest-list '{}'`}],output:{kind:`json`,description:`Get suggested interests similar to a list of seed interests. Useful for expanding targeting reach based on existing high-performing interests.`},transport:{type:`rest`,method:`POST`,path:`/v1/workspaces/{workspaceId}/meta/interest-suggestions/get`,auth:`user`,requestContentType:`application/json`}},{id:`meta.search_interests`,path:[`meta`,`interests`,`search`],summary:`Search for targetable interests by keyword. Returns interest IDs, names, audience sizes, and topic paths for use in ad set targeting.`,description:``,source:`rest`,options:[{name:`workspaceId`,flag:`--workspace-id`,description:``,required:!0,valueType:`string`,location:`path`},{name:`query`,flag:`--query`,description:`Search query for interests`,required:!0,valueType:`string`,location:`body`},{name:`limit`,flag:`--limit`,description:`Number of results to return`,required:!1,valueType:`number`,defaultValue:25,location:`body`}],examples:[{description:`Example`,command:`adside meta interests search --workspace-id <workspaceId> --query <query>`}],output:{kind:`json`,description:`Search for targetable interests by keyword. Returns interest IDs, names, audience sizes, and topic paths for use in ad set targeting.`},transport:{type:`rest`,method:`POST`,path:`/v1/workspaces/{workspaceId}/meta/interests/search`,auth:`user`,requestContentType:`application/json`}},{id:`meta.compare_meta_performance`,path:[`meta`,`performance`,`compare`],summary:`Compare performance metrics across multiple campaigns, ad sets, or ads side by side. Returns ranked comparisons with summary statistics for each object.`,description:``,source:`rest`,options:[{name:`workspaceId`,flag:`--workspace-id`,description:``,required:!0,valueType:`string`,location:`path`},{name:`object_ids`,flag:`--object-ids`,description:`IDs of campaigns/ad sets/ads to compare`,required:!0,valueType:`json`,location:`body`},{name:`level`,flag:`--level`,description:`Level of objects being compared`,required:!0,valueType:`string`,enum:[`campaign`,`adset`,`ad`],location:`body`},{name:`date_preset`,flag:`--date-preset`,description:`Date preset for comparison`,required:!1,valueType:`string`,enum:[`today`,`yesterday`,`last_3d`,`last_7d`,`last_14d`,`last_28d`,`last_30d`,`last_90d`,`this_week_mon_today`,`this_week_sun_today`,`last_week_mon_sun`,`last_week_sun_sat`,`this_month`,`last_month`,`this_quarter`,`last_quarter`,`this_year`,`last_year`,`maximum`,`data_maximum`],location:`body`},{name:`time_range`,flag:`--time-range`,description:`Custom date range for comparison`,required:!1,valueType:`json`,location:`body`},{name:`metrics`,flag:`--metrics`,description:`Metrics to compare`,required:!1,valueType:`json`,location:`body`}],examples:[{description:`Example`,command:`adside meta performance compare --workspace-id <workspaceId> --object-ids '{}' --level campaign`}],output:{kind:`json`,description:`Compare performance metrics across multiple campaigns, ad sets, or ads side by side. Returns ranked comparisons with summary statistics for each object.`},transport:{type:`rest`,method:`POST`,path:`/v1/workspaces/{workspaceId}/meta/performance/compare`,auth:`user`,requestContentType:`application/json`}},{id:`meta.get_pixel_stats`,path:[`meta`,`pixel-stats`,`get`],summary:`Read recent event activity directly from Meta's pixel/dataset stats edge, even when no ad sets use it. Default event_total_counts lists standard and custom event names (in value) and counts. Supports all SDK aggregations plus exact event, event_source (WEB_ONLY/SERVER_ONLY), agent and UTC Unix time filters. Use this for prelaunch 'is this dataset receiving Lead Generated?' checks; get_insights and warehouse conversions measure attributed ad results and cannot answer that question. Meta retains only seven days of stats. Results are aggregate diagnostics, not individual event payloads or Events Manager Test Events. diagnostics_hourly_last_timestamp is Meta's diagnostic timestamp, not a guaranteed exact last firing time. Empty data means no results for this query, not never fired. Counts across different aggregations/sources may overlap; do not sum them.`,description:``,source:`rest`,options:[{name:`workspaceId`,flag:`--workspace-id`,description:``,required:!0,valueType:`string`,location:`path`},{name:`pixel_id`,flag:`--pixel-id`,description:`Pixel/dataset ID from get_account_pixels; independent of ad-set attachment.`,required:!0,valueType:`string`,location:`body`},{name:`aggregation`,flag:`--aggregation`,description:`event_total_counts lists standard/custom event names and counts; event for time buckets; event_source for browser/server mix; event_processing_results for diagnostics; host/url for origins; match_keys/had_pii for matching. Returns Meta's original aggregation/value/event fields.`,required:!1,valueType:`string`,defaultValue:`event_total_counts`,enum:[`browser_type`,`custom_data_field`,`device_os`,`device_type`,`event`,`event_detection_method`,`event_processing_results`,`event_source`,`event_total_counts`,`event_value_count`,`had_pii`,`host`,`match_keys`,`pixel_fire`,`url`,`url_by_rule`],location:`body`},{name:`start_time`,flag:`--start-time`,description:`UTC Unix seconds. Defaults to the earliest retained time (seven days before request time). Meta retains only the last seven days.`,required:!1,valueType:`number`,location:`body`},{name:`end_time`,flag:`--end-time`,description:`UTC Unix seconds, after start_time. Defaults to now.`,required:!1,valueType:`number`,location:`body`},{name:`event`,flag:`--event`,description:`Exact event name, including spaces/case, e.g. Lead Generated or Schedule.`,required:!1,valueType:`string`,location:`body`},{name:`event_source`,flag:`--event-source`,description:`Meta event-source filter, e.g. WEB_ONLY or SERVER_ONLY. The SDK defines this as a string; Meta validates supported values.`,required:!1,valueType:`string`,location:`body`},{name:`agent`,flag:`--agent`,description:`Optional SDK agent filter; omit unless diagnosing a specific integration agent.`,required:!1,valueType:`string`,location:`body`},{name:`limit`,flag:`--limit`,description:`Maximum stats buckets requested per page; nested results also have a response-size cap.`,required:!1,valueType:`number`,defaultValue:25,location:`body`},{name:`after`,flag:`--after`,description:`Next-page cursor; requires the same explicit start_time/end_time and filters as the original query. The requested window is preserved, but Meta's rolling retention may remove oldest data between pages.`,required:!1,valueType:`string`,location:`body`}],examples:[{description:`Example`,command:`adside meta pixel-stats get --workspace-id <workspaceId> --pixel-id <pixel_id>`}],output:{kind:`json`,description:`Read recent event activity directly from Meta's pixel/dataset stats edge, even when no ad sets use it. Default event_total_counts lists standard and custom event names (in value) and counts. Supports all SDK aggregations plus exact event, event_source (WEB_ONLY/SERVER_ONLY), agent and UTC Unix time filters. Use this for prelaunch 'is this dataset receiving Lead Generated?' checks; get_insights and warehouse conversions measure attributed ad results and cannot answer that question. Meta retains only seven days of stats. Results are aggregate diagnostics, not individual event payloads or Events Manager Test Events. diagnostics_hourly_last_timestamp is Meta's diagnostic timestamp, not a guaranteed exact last firing time. Empty data means no results for this query, not never fired. Counts across different aggregations/sources may overlap; do not sum them.`},transport:{type:`rest`,method:`POST`,path:`/v1/workspaces/{workspaceId}/meta/pixel-stats/get`,auth:`user`,requestContentType:`application/json`}},{id:`meta.get_pixel`,path:[`meta`,`pixels`,`get`],summary:`Read a pixel/dataset's activity metadata and optional matching/settings/dataset counters. Uses a pixel_id from get_account_pixels, independent of ad-set attachment. last_fired_time is for the whole pixel, not a specific event. Missing fields are unknown. Use get_pixel_stats to inspect specific event names/counts; neither tool writes events or changes tracking.`,description:``,source:`rest`,options:[{name:`workspaceId`,flag:`--workspace-id`,description:``,required:!0,valueType:`string`,location:`path`},{name:`pixel_id`,flag:`--pixel-id`,description:`Pixel/dataset ID from get_account_pixels; no attached ad set is required.`,required:!0,valueType:`string`,location:`body`},{name:`fields`,flag:`--fields`,description:`Metadata to read. Defaults to id, name, last_fired_time, is_unavailable. Additional matching/settings and dataset counters can depend on pixel type and access. Missing fields are unknown, not zero.`,required:!1,valueType:`json`,location:`body`}],examples:[{description:`Example`,command:`adside meta pixels get --workspace-id <workspaceId> --pixel-id <pixel_id>`}],output:{kind:`json`,description:`Read a pixel/dataset's activity metadata and optional matching/settings/dataset counters. Uses a pixel_id from get_account_pixels, independent of ad-set attachment. last_fired_time is for the whole pixel, not a specific event. Missing fields are unknown. Use get_pixel_stats to inspect specific event names/counts; neither tool writes events or changes tracking.`},transport:{type:`rest`,method:`POST`,path:`/v1/workspaces/{workspaceId}/meta/pixels/get`,auth:`user`,requestContentType:`application/json`}},{id:`meta.get_quick_fixes`,path:[`meta`,`quick-fixes`,`get`],summary:`Get targeted troubleshooting tips for common Meta Ads API errors. Provide an error message to receive likely causes, suggestions, and next steps for resolution.`,description:``,source:`rest`,options:[{name:`workspaceId`,flag:`--workspace-id`,description:``,required:!0,valueType:`string`,location:`path`},{name:`error_message`,flag:`--error-message`,description:`The error message you received from the API`,required:!0,valueType:`string`,location:`body`}],examples:[{description:`Example`,command:`adside meta quick-fixes get --workspace-id <workspaceId> --error-message <error_message>`}],output:{kind:`json`,description:`Get targeted troubleshooting tips for common Meta Ads API errors. Provide an error message to receive likely causes, suggestions, and next steps for resolution.`},transport:{type:`rest`,method:`POST`,path:`/v1/workspaces/{workspaceId}/meta/quick-fixes/get`,auth:`user`,requestContentType:`application/json`}},{id:`meta.get_video_preferred_thumbnail`,path:[`meta`,`video-preferred-thumbnail`,`get`],summary:`Wait for Meta to finish processing an uploaded video and return its preferred thumbnail URL. Use after upload_video_from_url before creating a video creative through the batch endpoint.`,description:``,source:`rest`,options:[{name:`workspaceId`,flag:`--workspace-id`,description:``,required:!0,valueType:`string`,location:`path`},{name:`video_id`,flag:`--video-id`,description:`Meta video ID returned by upload_video_from_url`,required:!0,valueType:`string`,location:`body`},{name:`timeout_ms`,flag:`--timeout-ms`,description:`Max time to wait for thumbnails to appear (default 60000)`,required:!1,valueType:`number`,location:`body`},{name:`poll_ms`,flag:`--poll-ms`,description:`Poll interval in milliseconds (default 3000)`,required:!1,valueType:`number`,location:`body`}],examples:[{description:`Example`,command:`adside meta video-preferred-thumbnail get --workspace-id <workspaceId> --video-id <video_id>`}],output:{kind:`json`,description:`Wait for Meta to finish processing an uploaded video and return its preferred thumbnail URL. Use after upload_video_from_url before creating a video creative through the batch endpoint.`},transport:{type:`rest`,method:`POST`,path:`/v1/workspaces/{workspaceId}/meta/video-preferred-thumbnail/get`,auth:`user`,requestContentType:`application/json`}},{id:`reddit.get_reddit_account_history`,path:[`reddit`,`account-history`,`get`],summary:`The change log of the connected ad account: who changed what (budgets, bids, statuses, targeting, creation) and when. Member emails and full names are redacted; Reddit usernames are kept.`,description:``,source:`rest`,options:[{name:`workspaceId`,flag:`--workspace-id`,description:``,required:!0,valueType:`string`,location:`path`},{name:`ad_account_id`,flag:`--ad-account-id`,description:`Reddit ad account id (a2_…). Omit it: it defaults to the ad account this client is connected to, and any other account is refused.`,required:!1,valueType:`string`,location:`body`},{name:`preset`,flag:`--preset`,description:`Shortcut for a date range. Default last_7d when no start_date/end_date given.`,required:!1,valueType:`string`,enum:[`today`,`yesterday`,`last_7d`,`last_14d`,`last_30d`,`this_month`,`last_month`],location:`body`},{name:`start_date`,flag:`--start-date`,description:`First day, YYYY-MM-DD, in time_zone_id.`,required:!1,valueType:`string`,location:`body`},{name:`end_date`,flag:`--end-date`,description:`Last day (inclusive), YYYY-MM-DD, in time_zone_id.`,required:!1,valueType:`string`,location:`body`},{name:`time_zone_id`,flag:`--time-zone-id`,description:`IANA zone for the date boundaries, e.g. Europe/Paris. Defaults to the ad account's time zone.`,required:!1,valueType:`string`,location:`body`},{name:`change_types`,flag:`--change-types`,description:`Only these kinds of change. Default: all.`,required:!1,valueType:`json`,location:`body`},{name:`entity_id`,flag:`--entity-id`,description:`Only changes to this campaign / ad group / ad id.`,required:!1,valueType:`string`,location:`body`},{name:`limit`,flag:`--limit`,description:``,required:!1,valueType:`number`,defaultValue:100,location:`body`}],examples:[{description:`Example`,command:`adside reddit account-history get --workspace-id <workspaceId>`}],output:{kind:`json`,description:`The change log of the connected ad account: who changed what (budgets, bids, statuses, targeting, creation) and when. Member emails and full names are redacted; Reddit usernames are kept.`},transport:{type:`rest`,method:`POST`,path:`/v1/workspaces/{workspaceId}/reddit/account-history/get`,auth:`user`,requestContentType:`application/json`}},{id:`reddit.get_reddit_account_overview`,path:[`reddit`,`account-overview`,`get`],summary:`Where the account stands: campaign / ad group / ad counts by status, spend and clicks for the last 7 days versus the 7 before, and the top campaigns by spend. Costs 5 upstream requests; use it before diving into individual campaigns.`,description:``,source:`rest`,options:[{name:`workspaceId`,flag:`--workspace-id`,description:``,required:!0,valueType:`string`,location:`path`},{name:`ad_account_id`,flag:`--ad-account-id`,description:`Reddit ad account id (a2_…). Omit it: it defaults to the ad account this client is connected to, and any other account is refused.`,required:!1,valueType:`string`,location:`body`}],examples:[{description:`Example`,command:`adside reddit account-overview get --workspace-id <workspaceId>`}],output:{kind:`json`,description:`Where the account stands: campaign / ad group / ad counts by status, spend and clicks for the last 7 days versus the 7 before, and the top campaigns by spend. Costs 5 upstream requests; use it before diving into individual campaigns.`},transport:{type:`rest`,method:`POST`,path:`/v1/workspaces/{workspaceId}/reddit/account-overview/get`,auth:`user`,requestContentType:`application/json`}},{id:`reddit.get_reddit_ad_account`,path:[`reddit`,`ad-accounts`,`get`],summary:`The Reddit ad account this client is connected to: currency, time zone, attribution windows, approval state, funding instruments (and whether any can serve), pixels and the profiles ads can be authored from. There is no 'list ad accounts' tool — a client has exactly one connected Reddit ad account.`,description:``,source:`rest`,options:[{name:`workspaceId`,flag:`--workspace-id`,description:``,required:!0,valueType:`string`,location:`path`},{name:`ad_account_id`,flag:`--ad-account-id`,description:`Reddit ad account id (a2_…). Omit it: it defaults to the ad account this client is connected to, and any other account is refused.`,required:!1,valueType:`string`,location:`body`}],examples:[{description:`Example`,command:`adside reddit ad-accounts get --workspace-id <workspaceId>`}],output:{kind:`json`,description:`The Reddit ad account this client is connected to: currency, time zone, attribution windows, approval state, funding instruments (and whether any can serve), pixels and the profiles ads can be authored from. There is no 'list ad accounts' tool — a client has exactly one connected Reddit ad account.`},transport:{type:`rest`,method:`POST`,path:`/v1/workspaces/{workspaceId}/reddit/ad-accounts/get`,auth:`user`,requestContentType:`application/json`}},{id:`reddit.get_reddit_ad_group`,path:[`reddit`,`ad-groups`,`get`],summary:`One Reddit ad group by id: status, budget, bid strategy, optimization goal, pixel, schedule and full targeting.`,description:``,source:`rest`,options:[{name:`workspaceId`,flag:`--workspace-id`,description:``,required:!0,valueType:`string`,location:`path`},{name:`ad_group_id`,flag:`--ad-group-id`,description:`Ad group id (numeric string) from list_reddit_ad_groups.`,required:!0,valueType:`string`,location:`body`}],examples:[{description:`Example`,command:`adside reddit ad-groups get --workspace-id <workspaceId> --ad-group-id <ad_group_id>`}],output:{kind:`json`,description:`One Reddit ad group by id: status, budget, bid strategy, optimization goal, pixel, schedule and full targeting.`},transport:{type:`rest`,method:`POST`,path:`/v1/workspaces/{workspaceId}/reddit/ad-groups/get`,auth:`user`,requestContentType:`application/json`}},{id:`reddit.list_reddit_ad_groups`,path:[`reddit`,`ad-groups`,`list`],summary:`List ad groups on the connected account (optionally one campaign's) with status, budget, bid and a one-line targeting summary. Reddit calls this level 'ad group'; a campaign holds ad groups, an ad group holds ads.`,description:``,source:`rest`,options:[{name:`workspaceId`,flag:`--workspace-id`,description:``,required:!0,valueType:`string`,location:`path`},{name:`ad_account_id`,flag:`--ad-account-id`,description:`Reddit ad account id (a2_…). Omit it: it defaults to the ad account this client is connected to, and any other account is refused.`,required:!1,valueType:`string`,location:`body`},{name:`campaign_id`,flag:`--campaign-id`,description:`Only ad groups in this campaign (server-side filter).`,required:!1,valueType:`string`,location:`body`},{name:`status`,flag:`--status`,description:`Filter on configured_status. ARCHIVED and DELETED objects are hidden unless asked for.`,required:!1,valueType:`string`,enum:[`ACTIVE`,`PAUSED`,`ARCHIVED`,`DELETED`],location:`body`},{name:`include_archived`,flag:`--include-archived`,description:``,required:!1,valueType:`boolean`,defaultValue:!1,location:`body`},{name:`limit`,flag:`--limit`,description:`Maximum rows to return (bounds the answer, not the scan).`,required:!1,valueType:`number`,defaultValue:100,location:`body`}],examples:[{description:`Example`,command:`adside reddit ad-groups list --workspace-id <workspaceId>`}],output:{kind:`json`,description:`List ad groups on the connected account (optionally one campaign's) with status, budget, bid and a one-line targeting summary. Reddit calls this level 'ad group'; a campaign holds ad groups, an ad group holds ads.`},transport:{type:`rest`,method:`POST`,path:`/v1/workspaces/{workspaceId}/reddit/ad-groups/list`,auth:`user`,requestContentType:`application/json`}},{id:`reddit.get_reddit_ad`,path:[`reddit`,`ads`,`get`],summary:`One Reddit ad by id with its creative (the post behind it): headline, media, destination, click URL and tracking parameters, review/rejection state, preview link.`,description:``,source:`rest`,options:[{name:`workspaceId`,flag:`--workspace-id`,description:``,required:!0,valueType:`string`,location:`path`},{name:`ad_id`,flag:`--ad-id`,description:`Ad id (numeric string) from list_reddit_ads.`,required:!0,valueType:`string`,location:`body`}],examples:[{description:`Example`,command:`adside reddit ads get --workspace-id <workspaceId> --ad-id <ad_id>`}],output:{kind:`json`,description:`One Reddit ad by id with its creative (the post behind it): headline, media, destination, click URL and tracking parameters, review/rejection state, preview link.`},transport:{type:`rest`,method:`POST`,path:`/v1/workspaces/{workspaceId}/reddit/ads/get`,auth:`user`,requestContentType:`application/json`}},{id:`reddit.list_reddit_ads`,path:[`reddit`,`ads`,`list`],summary:`List ads on the connected account, optionally within one campaign or ad group, with status, creative type and headline. Filters on configured/effective status run server-side.`,description:``,source:`rest`,options:[{name:`workspaceId`,flag:`--workspace-id`,description:``,required:!0,valueType:`string`,location:`path`},{name:`ad_account_id`,flag:`--ad-account-id`,description:`Reddit ad account id (a2_…). Omit it: it defaults to the ad account this client is connected to, and any other account is refused.`,required:!1,valueType:`string`,location:`body`},{name:`campaign_id`,flag:`--campaign-id`,description:`Only ads in this campaign (server-side filter).`,required:!1,valueType:`string`,location:`body`},{name:`ad_group_id`,flag:`--ad-group-id`,description:`Only ads in this ad group (server-side filter).`,required:!1,valueType:`string`,location:`body`},{name:`status`,flag:`--status`,description:`Filter on configured_status. ARCHIVED and DELETED objects are hidden unless asked for.`,required:!1,valueType:`string`,enum:[`ACTIVE`,`PAUSED`,`ARCHIVED`,`DELETED`],location:`body`},{name:`effective_status`,flag:`--effective-status`,description:`Filter on Reddit's effective status (server-side).`,required:!1,valueType:`string`,enum:[`ACTIVE`,`PAUSED`,`PENDING_APPROVAL`,`REJECTED`,`AD_GROUP_PAUSED`,`CAMPAIGN_PAUSED`,`COMPLETED`,`ARCHIVED`,`DELETED`],location:`body`},{name:`include_archived`,flag:`--include-archived`,description:``,required:!1,valueType:`boolean`,defaultValue:!1,location:`body`},{name:`with_creative`,flag:`--with-creative`,description:`Resolve each ad's post to show creative type and headline (one extra request per distinct post, max 25).`,required:!1,valueType:`boolean`,defaultValue:!0,location:`body`},{name:`limit`,flag:`--limit`,description:`Maximum rows to return (bounds the answer, not the scan).`,required:!1,valueType:`number`,defaultValue:100,location:`body`}],examples:[{description:`Example`,command:`adside reddit ads list --workspace-id <workspaceId>`}],output:{kind:`json`,description:`List ads on the connected account, optionally within one campaign or ad group, with status, creative type and headline. Filters on configured/effective status run server-side.`},transport:{type:`rest`,method:`POST`,path:`/v1/workspaces/{workspaceId}/reddit/ads/list`,auth:`user`,requestContentType:`application/json`}},{id:`reddit.suggest_reddit_bids`,path:[`reddit`,`bids`,`suggest`],summary:`Reddit's suggested bid range (min / median / max) for a bid type, objective and targeting, in the account currency. Costs 1 request.`,description:``,source:`rest`,options:[{name:`workspaceId`,flag:`--workspace-id`,description:``,required:!0,valueType:`string`,location:`path`},{name:`ad_account_id`,flag:`--ad-account-id`,description:`Reddit ad account id (a2_…). Omit it: it defaults to the ad account this client is connected to, and any other account is refused.`,required:!1,valueType:`string`,location:`body`},{name:`bid_type`,flag:`--bid-type`,description:``,required:!1,valueType:`string`,defaultValue:`CPC`,enum:[`CPC`,`CPM`,`CPV`,`CPV6`,`CPV15`],location:`body`},{name:`objective`,flag:`--objective`,description:``,required:!1,valueType:`string`,defaultValue:`CLICKS`,enum:[`APP_INSTALLS`,`CATALOG_SALES`,`CLICKS`,`CONVERSIONS`,`IMPRESSIONS`,`LEAD_GENERATION`,`VIDEO_VIEWABLE_IMPRESSIONS`],location:`body`},{name:`bid_strategy`,flag:`--bid-strategy`,description:`Reddit refuses a suggestion without a delivery config (400 "Missing delivery config: bid_strategy", measured 2026-09-10). MANUAL_BIDDING is what a suggested bid is for.`,required:!1,valueType:`string`,defaultValue:`MANUAL_BIDDING`,enum:[`MANUAL_BIDDING`,`MAXIMIZE_VOLUME`,`TARGET_CPX`],location:`body`},{name:`optimization_goal`,flag:`--optimization-goal`,description:`e.g. CLICKS, PURCHASE, LEAD. Defaults from the objective (CLICKS → CLICKS, CONVERSIONS → PURCHASE, VIDEO_VIEWABLE_IMPRESSIONS → VIDEO_VIEW_6S, LEAD_GENERATION → LEAD, APP_INSTALLS → MOBILE_CONVERSION_INSTALL).`,required:!1,valueType:`string`,location:`body`},{name:`targeting`,flag:`--targeting`,description:`Reddit targeting object. Every key optional; omitted = no restriction.`,required:!1,valueType:`json`,location:`body`},{name:`daily_budget`,flag:`--daily-budget`,description:`Account currency.`,required:!1,valueType:`number`,location:`body`}],examples:[{description:`Example`,command:`adside reddit bids suggest --workspace-id <workspaceId>`}],output:{kind:`json`,description:`Reddit's suggested bid range (min / median / max) for a bid type, objective and targeting, in the account currency. Costs 1 request.`},transport:{type:`rest`,method:`POST`,path:`/v1/workspaces/{workspaceId}/reddit/bids/suggest`,auth:`user`,requestContentType:`application/json`}},{id:`reddit.check_reddit_campaign_readiness`,path:[`reddit`,`campaign-readiness`,`check`],summary:`Can this campaign deliver? Checks funding, pixel, ad groups, ads, approval and delivery states and returns is_ready plus the issues, the requirements Reddit enforces and what to do next — one cheap read instead of trial-and-error writes. Accepts a campaign id or a name.`,description:``,source:`rest`,options:[{name:`workspaceId`,flag:`--workspace-id`,description:``,required:!0,valueType:`string`,location:`path`},{name:`campaign_id`,flag:`--campaign-id`,description:`Campaign id. Give this or campaign_name.`,required:!1,valueType:`string`,location:`body`},{name:`campaign_name`,flag:`--campaign-name`,description:`Exact or partial campaign name, when the id is unknown.`,required:!1,valueType:`string`,location:`body`}],examples:[{description:`Example`,command:`adside reddit campaign-readiness check --workspace-id <workspaceId>`}],output:{kind:`json`,description:`Can this campaign deliver? Checks funding, pixel, ad groups, ads, approval and delivery states and returns is_ready plus the issues, the requirements Reddit enforces and what to do next — one cheap read instead of trial-and-error writes. Accepts a campaign id or a name.`},transport:{type:`rest`,method:`POST`,path:`/v1/workspaces/{workspaceId}/reddit/campaign-readiness/check`,auth:`user`,requestContentType:`application/json`}},{id:`reddit.get_reddit_campaign`,path:[`reddit`,`campaigns`,`get`],summary:`One Reddit campaign by id: status, delivery status, objective, budget, funding instrument, pixel, dates.`,description:``,source:`rest`,options:[{name:`workspaceId`,flag:`--workspace-id`,description:``,required:!0,valueType:`string`,location:`path`},{name:`campaign_id`,flag:`--campaign-id`,description:`Campaign id (numeric string) from list_reddit_campaigns.`,required:!0,valueType:`string`,location:`body`}],examples:[{description:`Example`,command:`adside reddit campaigns get --workspace-id <workspaceId> --campaign-id <campaign_id>`}],output:{kind:`json`,description:`One Reddit campaign by id: status, delivery status, objective, budget, funding instrument, pixel, dates.`},transport:{type:`rest`,method:`POST`,path:`/v1/workspaces/{workspaceId}/reddit/campaigns/get`,auth:`user`,requestContentType:`application/json`}},{id:`reddit.list_reddit_campaigns`,path:[`reddit`,`campaigns`,`list`],summary:"List campaigns on the connected Reddit ad account with status, objective and budget. Archived and deleted campaigns are hidden unless include_archived is set. Reddit has no server-side status filter, so the filter is applied while paging and `limit` bounds the matches returned.",description:``,source:`rest`,options:[{name:`workspaceId`,flag:`--workspace-id`,description:``,required:!0,valueType:`string`,location:`path`},{name:`ad_account_id`,flag:`--ad-account-id`,description:`Reddit ad account id (a2_…). Omit it: it defaults to the ad account this client is connected to, and any other account is refused.`,required:!1,valueType:`string`,location:`body`},{name:`status`,flag:`--status`,description:`Filter on configured_status. ARCHIVED and DELETED objects are hidden unless asked for.`,required:!1,valueType:`string`,enum:[`ACTIVE`,`PAUSED`,`ARCHIVED`,`DELETED`],location:`body`},{name:`name_contains`,flag:`--name-contains`,description:`Case-insensitive substring of the campaign name.`,required:!1,valueType:`string`,location:`body`},{name:`include_archived`,flag:`--include-archived`,description:`Include ARCHIVED and DELETED campaigns (hidden by default).`,required:!1,valueType:`boolean`,defaultValue:!1,location:`body`},{name:`limit`,flag:`--limit`,description:`Maximum rows to return (bounds the answer, not the scan).`,required:!1,valueType:`number`,defaultValue:100,location:`body`}],examples:[{description:`Example`,command:`adside reddit campaigns list --workspace-id <workspaceId>`}],output:{kind:`json`,description:"List campaigns on the connected Reddit ad account with status, objective and budget. Archived and deleted campaigns are hidden unless include_archived is set. Reddit has no server-side status filter, so the filter is applied while paging and `limit` bounds the matches returned."},transport:{type:`rest`,method:`POST`,path:`/v1/workspaces/{workspaceId}/reddit/campaigns/list`,auth:`user`,requestContentType:`application/json`}},{id:`reddit.get_reddit_channel_status`,path:[`reddit`,`channel-status`,`get`],summary:`Self-diagnosis of the Reddit connection: who the token belongs to, the connected ad account and business, rate-limit state observed in this request, and the API spec version this server was built against.`,description:``,source:`rest`,options:[{name:`workspaceId`,flag:`--workspace-id`,description:``,required:!0,valueType:`string`,location:`path`}],examples:[{description:`Example`,command:`adside reddit channel-status get --workspace-id <workspaceId>`}],output:{kind:`json`,description:`Self-diagnosis of the Reddit connection: who the token belongs to, the connected ad account and business, rate-limit state observed in this request, and the API spec version this server was built against.`},transport:{type:`rest`,method:`POST`,path:`/v1/workspaces/{workspaceId}/reddit/channel-status/get`,auth:`user`}},{id:`reddit.search_reddit_communities`,path:[`reddit`,`communities`,`search`],summary:`Find subreddits to target: search by name, get suggestions similar to seed communities, or suggestions for a website. Returns names (use them without r/ in targeting.communities), member counts and categories. Suggestions are better than search for topical keywords.`,description:``,source:`rest`,options:[{name:`workspaceId`,flag:`--workspace-id`,description:``,required:!0,valueType:`string`,location:`path`},{name:`query`,flag:`--query`,description:`Search term for community names (e.g. 'marketing').`,required:!1,valueType:`string`,location:`body`},{name:`seed_communities`,flag:`--seed-communities`,description:`Get suggestions similar to these subreddit names (without r/).`,required:!1,valueType:`json`,location:`body`},{name:`website_url`,flag:`--website-url`,description:`Get suggestions relevant to this website.`,required:!1,valueType:`url`,location:`body`},{name:`limit`,flag:`--limit`,description:``,required:!1,valueType:`number`,defaultValue:25,location:`body`}],examples:[{description:`Example`,command:`adside reddit communities search --workspace-id <workspaceId>`}],output:{kind:`json`,description:`Find subreddits to target: search by name, get suggestions similar to seed communities, or suggestions for a website. Returns names (use them without r/ in targeting.communities), member counts and categories. Suggestions are better than search for topical keywords.`},transport:{type:`rest`,method:`POST`,path:`/v1/workspaces/{workspaceId}/reddit/communities/search`,auth:`user`,requestContentType:`application/json`}},{id:`reddit.list_reddit_creative_assets`,path:[`reddit`,`creative-assets`,`list`],summary:`The asset library (images, videos, headlines, CTAs) of the account's profiles — the inputs Reddit Max campaigns assemble ads from.`,description:``,source:`rest`,options:[{name:`workspaceId`,flag:`--workspace-id`,description:``,required:!0,valueType:`string`,location:`path`},{name:`ad_account_id`,flag:`--ad-account-id`,description:`Reddit ad account id (a2_…). Omit it: it defaults to the ad account this client is connected to, and any other account is refused.`,required:!1,valueType:`string`,location:`body`},{name:`profile_id`,flag:`--profile-id`,description:`Profile whose asset library to list. Omit for every profile on the account.`,required:!1,valueType:`string`,location:`body`},{name:`limit`,flag:`--limit`,description:``,required:!1,valueType:`number`,defaultValue:50,location:`body`}],examples:[{description:`Example`,command:`adside reddit creative-assets list --workspace-id <workspaceId>`}],output:{kind:`json`,description:`The asset library (images, videos, headlines, CTAs) of the account's profiles — the inputs Reddit Max campaigns assemble ads from.`},transport:{type:`rest`,method:`POST`,path:`/v1/workspaces/{workspaceId}/reddit/creative-assets/list`,auth:`user`,requestContentType:`application/json`}},{id:`reddit.analyze_reddit_creatives`,path:[`reddit`,`creatives`,`analyze`],summary:`Creative performance: every ad's spend, impressions, clicks, CTR and conversions joined with its creative type and headline, plus a by-format summary and winners / losers. Costs up to 10 requests (report, ads, posts).`,description:``,source:`rest`,options:[{name:`workspaceId`,flag:`--workspace-id`,description:``,required:!0,valueType:`string`,location:`path`},{name:`ad_account_id`,flag:`--ad-account-id`,description:`Reddit ad account id (a2_…). Omit it: it defaults to the ad account this client is connected to, and any other account is refused.`,required:!1,valueType:`string`,location:`body`},{name:`campaign_id`,flag:`--campaign-id`,description:``,required:!1,valueType:`string`,location:`body`},{name:`preset`,flag:`--preset`,description:`Shortcut for a date range. Default last_7d when no start_date/end_date given.`,required:!1,valueType:`string`,enum:[`today`,`yesterday`,`last_7d`,`last_14d`,`last_30d`,`this_month`,`last_month`],location:`body`},{name:`start_date`,flag:`--start-date`,description:`First day, YYYY-MM-DD, in time_zone_id.`,required:!1,valueType:`string`,location:`body`},{name:`end_date`,flag:`--end-date`,description:`Last day (inclusive), YYYY-MM-DD, in time_zone_id.`,required:!1,valueType:`string`,location:`body`},{name:`time_zone_id`,flag:`--time-zone-id`,description:`IANA zone for the date boundaries, e.g. Europe/Paris. Defaults to the ad account's time zone.`,required:!1,valueType:`string`,location:`body`},{name:`min_impressions`,flag:`--min-impressions`,description:``,required:!1,valueType:`number`,defaultValue:100,location:`body`}],examples:[{description:`Example`,command:`adside reddit creatives analyze --workspace-id <workspaceId>`}],output:{kind:`json`,description:`Creative performance: every ad's spend, impressions, clicks, CTR and conversions joined with its creative type and headline, plus a by-format summary and winners / losers. Costs up to 10 requests (report, ads, posts).`},transport:{type:`rest`,method:`POST`,path:`/v1/workspaces/{workspaceId}/reddit/creatives/analyze`,auth:`user`,requestContentType:`application/json`}},{id:`reddit.get_reddit_custom_audience`,path:[`reddit`,`custom-audiences`,`get`],summary:`One custom audience by id, with the ad groups on this account that target or exclude it.`,description:``,source:`rest`,options:[{name:`workspaceId`,flag:`--workspace-id`,description:``,required:!0,valueType:`string`,location:`path`},{name:`audience_id`,flag:`--audience-id`,description:`Custom audience id from list_reddit_custom_audiences.`,required:!0,valueType:`string`,location:`body`}],examples:[{description:`Example`,command:`adside reddit custom-audiences get --workspace-id <workspaceId> --audience-id <audience_id>`}],output:{kind:`json`,description:`One custom audience by id, with the ad groups on this account that target or exclude it.`},transport:{type:`rest`,method:`POST`,path:`/v1/workspaces/{workspaceId}/reddit/custom-audiences/get`,auth:`user`,requestContentType:`application/json`}},{id:`reddit.list_reddit_custom_audiences`,path:[`reddit`,`custom-audiences`,`list`],summary:`Custom audiences on the connected account (customer lists, pixel and engagement retargeting) with type, status and size range.`,description:``,source:`rest`,options:[{name:`workspaceId`,flag:`--workspace-id`,description:``,required:!0,valueType:`string`,location:`path`},{name:`ad_account_id`,flag:`--ad-account-id`,description:`Reddit ad account id (a2_…). Omit it: it defaults to the ad account this client is connected to, and any other account is refused.`,required:!1,valueType:`string`,location:`body`},{name:`name_contains`,flag:`--name-contains`,description:``,required:!1,valueType:`string`,location:`body`}],examples:[{description:`Example`,command:`adside reddit custom-audiences list --workspace-id <workspaceId>`}],output:{kind:`json`,description:`Custom audiences on the connected account (customer lists, pixel and engagement retargeting) with type, status and size range.`},transport:{type:`rest`,method:`POST`,path:`/v1/workspaces/{workspaceId}/reddit/custom-audiences/list`,auth:`user`,requestContentType:`application/json`}},{id:`reddit.get_reddit_daily_performance`,path:[`reddit`,`daily-performance`,`get`],summary:`Core metrics by day for the account, a campaign, an ad group or an ad, with day-over-day change in spend. Costs 1 request.`,description:``,source:`rest`,options:[{name:`workspaceId`,flag:`--workspace-id`,description:``,required:!0,valueType:`string`,location:`path`},{name:`ad_account_id`,flag:`--ad-account-id`,description:`Reddit ad account id (a2_…). Omit it: it defaults to the ad account this client is connected to, and any other account is refused.`,required:!1,valueType:`string`,location:`body`},{name:`level`,flag:`--level`,description:`One row per object at this level (plus any breakdowns).`,required:!1,valueType:`string`,defaultValue:`campaign`,enum:[`account`,`campaign`,`ad_group`,`ad`],location:`body`},{name:`object_id`,flag:`--object-id`,description:``,required:!1,valueType:`string`,location:`body`},{name:`metrics`,flag:`--metrics`,description:`Friendly metric names, e.g. impressions, clicks, spend, ctr, cpc, ecpm, reach, video_watched_100_percent, conversion_purchase_clicks. Default: the core group. See list_reddit_report_fields.`,required:!1,valueType:`json`,location:`body`},{name:`preset`,flag:`--preset`,description:`Shortcut for a date range. Default last_7d when no start_date/end_date given.`,required:!1,valueType:`string`,enum:[`today`,`yesterday`,`last_7d`,`last_14d`,`last_30d`,`this_month`,`last_month`],location:`body`},{name:`start_date`,flag:`--start-date`,description:`First day, YYYY-MM-DD, in time_zone_id.`,required:!1,valueType:`string`,location:`body`},{name:`end_date`,flag:`--end-date`,description:`Last day (inclusive), YYYY-MM-DD, in time_zone_id.`,required:!1,valueType:`string`,location:`body`},{name:`time_zone_id`,flag:`--time-zone-id`,description:`IANA zone for the date boundaries, e.g. Europe/Paris. Defaults to the ad account's time zone.`,required:!1,valueType:`string`,location:`body`}],examples:[{description:`Example`,command:`adside reddit daily-performance get --workspace-id <workspaceId>`}],output:{kind:`json`,description:`Core metrics by day for the account, a campaign, an ad group or an ad, with day-over-day change in spend. Costs 1 request.`},transport:{type:`rest`,method:`POST`,path:`/v1/workspaces/{workspaceId}/reddit/daily-performance/get`,auth:`user`,requestContentType:`application/json`}},{id:`reddit.diagnose_reddit_delivery`,path:[`reddit`,`delivery`,`diagnose`],summary:`Why isn't it delivering? For each campaign: effective and delivery status translated to a cause and next action, ad groups without ads, rejected ads with reasons, missing pixel or funding, and spend over the lookback as evidence. Costs up to 5 requests.`,description:``,source:`rest`,options:[{name:`workspaceId`,flag:`--workspace-id`,description:``,required:!0,valueType:`string`,location:`path`},{name:`ad_account_id`,flag:`--ad-account-id`,description:`Reddit ad account id (a2_…). Omit it: it defaults to the ad account this client is connected to, and any other account is refused.`,required:!1,valueType:`string`,location:`body`},{name:`campaign_id`,flag:`--campaign-id`,description:`Only this campaign. Default: every non-archived campaign.`,required:!1,valueType:`string`,location:`body`},{name:`lookback_days`,flag:`--lookback-days`,description:``,required:!1,valueType:`number`,defaultValue:3,location:`body`}],examples:[{description:`Example`,command:`adside reddit delivery diagnose --workspace-id <workspaceId>`}],output:{kind:`json`,description:`Why isn't it delivering? For each campaign: effective and delivery status translated to a cause and next action, ad groups without ads, rejected ads with reasons, missing pixel or funding, and spend over the lookback as evidence. Costs up to 5 requests.`},transport:{type:`rest`,method:`POST`,path:`/v1/workspaces/{workspaceId}/reddit/delivery/diagnose`,auth:`user`,requestContentType:`application/json`}},{id:`reddit.find_reddit_entity`,path:[`reddit`,`entity`,`find`],summary:`Find campaigns, ad groups or ads by name on the connected account (case-insensitive substring). Use it to turn a name from the user into an id for the other tools. Costs up to 3 list requests.`,description:``,source:`rest`,options:[{name:`workspaceId`,flag:`--workspace-id`,description:``,required:!0,valueType:`string`,location:`path`},{name:`ad_account_id`,flag:`--ad-account-id`,description:`Reddit ad account id (a2_…). Omit it: it defaults to the ad account this client is connected to, and any other account is refused.`,required:!1,valueType:`string`,location:`body`},{name:`query`,flag:`--query`,description:`Case-insensitive substring of the name.`,required:!0,valueType:`string`,location:`body`},{name:`entity_type`,flag:`--entity-type`,description:``,required:!1,valueType:`string`,defaultValue:`any`,enum:[`campaign`,`ad_group`,`ad`,`any`],location:`body`},{name:`limit`,flag:`--limit`,description:``,required:!1,valueType:`number`,defaultValue:20,location:`body`}],examples:[{description:`Example`,command:`adside reddit entity find --workspace-id <workspaceId> --query <query>`}],output:{kind:`json`,description:`Find campaigns, ad groups or ads by name on the connected account (case-insensitive substring). Use it to turn a name from the user into an id for the other tools. Costs up to 3 list requests.`},transport:{type:`rest`,method:`POST`,path:`/v1/workspaces/{workspaceId}/reddit/entity/find`,auth:`user`,requestContentType:`application/json`}},{id:`reddit.list_reddit_funding_instruments`,path:[`reddit`,`funding-instruments`,`list`],summary:`Funding instruments (payment methods / credit lines) on the connected ad account, with whether each can serve and why not. A campaign needs a servable instrument to deliver; creation succeeds without one but delivery_status stays CAMPAIGN_NOT_FUNDED.`,description:``,source:`rest`,options:[{name:`workspaceId`,flag:`--workspace-id`,description:``,required:!0,valueType:`string`,location:`path`},{name:`ad_account_id`,flag:`--ad-account-id`,description:`Reddit ad account id (a2_…). Omit it: it defaults to the ad account this client is connected to, and any other account is refused.`,required:!1,valueType:`string`,location:`body`}],examples:[{description:`Example`,command:`adside reddit funding-instruments list --workspace-id <workspaceId>`}],output:{kind:`json`,description:`Funding instruments (payment methods / credit lines) on the connected ad account, with whether each can serve and why not. A campaign needs a servable instrument to deliver; creation succeeds without one but delivery_status stays CAMPAIGN_NOT_FUNDED.`},transport:{type:`rest`,method:`POST`,path:`/v1/workspaces/{workspaceId}/reddit/funding-instruments/list`,auth:`user`,requestContentType:`application/json`}},{id:`reddit.search_reddit_geolocations`,path:[`reddit`,`geolocations`,`search`],summary:`Resolve geolocation ids for targeting: countries, regions, cities, DMAs and postal codes. Give a country to list its regions, add city_search or postal_code to narrow. validate_ids checks ids you already have.`,description:``,source:`rest`,options:[{name:`workspaceId`,flag:`--workspace-id`,description:``,required:!0,valueType:`string`,location:`path`},{name:`country`,flag:`--country`,description:`ISO country code to list regions / cities of (e.g. US).`,required:!1,valueType:`string`,location:`body`},{name:`city_search`,flag:`--city-search`,description:`City name to search (needs country).`,required:!1,valueType:`string`,location:`body`},{name:`postal_code`,flag:`--postal-code`,description:`Postal code to resolve (needs country).`,required:!1,valueType:`string`,location:`body`},{name:`validate_ids`,flag:`--validate-ids`,description:`Check that these geolocation ids are valid for targeting.`,required:!1,valueType:`json`,location:`body`}],examples:[{description:`Example`,command:`adside reddit geolocations search --workspace-id <workspaceId>`}],output:{kind:`json`,description:`Resolve geolocation ids for targeting: countries, regions, cities, DMAs and postal codes. Give a country to list its regions, add city_search or postal_code to narrow. validate_ids checks ids you already have.`},transport:{type:`rest`,method:`POST`,path:`/v1/workspaces/{workspaceId}/reddit/geolocations/search`,auth:`user`,requestContentType:`application/json`}},{id:`reddit.list_reddit_interests`,path:[`reddit`,`interests`,`list`],summary:`Every interest category Reddit offers for targeting, grouped, with the ids to put in targeting.interests.`,description:``,source:`rest`,options:[{name:`workspaceId`,flag:`--workspace-id`,description:``,required:!0,valueType:`string`,location:`path`},{name:`filter`,flag:`--filter`,description:`Substring filter on name or category.`,required:!1,valueType:`string`,location:`body`}],examples:[{description:`Example`,command:`adside reddit interests list --workspace-id <workspaceId>`}],output:{kind:`json`,description:`Every interest category Reddit offers for targeting, grouped, with the ids to put in targeting.interests.`},transport:{type:`rest`,method:`POST`,path:`/v1/workspaces/{workspaceId}/reddit/interests/list`,auth:`user`,requestContentType:`application/json`}},{id:`reddit.suggest_reddit_keywords`,path:[`reddit`,`keywords`,`suggest`],summary:`Keyword suggestions (with monthly views on Reddit) from seed terms, or validation of the seeds themselves.`,description:``,source:`rest`,options:[{name:`workspaceId`,flag:`--workspace-id`,description:``,required:!0,valueType:`string`,location:`path`},{name:`seed_keywords`,flag:`--seed-keywords`,description:`Terms to expand.`,required:!0,valueType:`json`,location:`body`},{name:`validate_only`,flag:`--validate-only`,description:`Only validate the seeds instead of suggesting more.`,required:!1,valueType:`boolean`,defaultValue:!1,location:`body`}],examples:[{description:`Example`,command:`adside reddit keywords suggest --workspace-id <workspaceId> --seed-keywords '{}'`}],output:{kind:`json`,description:`Keyword suggestions (with monthly views on Reddit) from seed terms, or validation of the seeds themselves.`},transport:{type:`rest`,method:`POST`,path:`/v1/workspaces/{workspaceId}/reddit/keywords/suggest`,auth:`user`,requestContentType:`application/json`}},{id:`reddit.analyze_reddit_pacing`,path:[`reddit`,`pacing`,`analyze`],summary:`Is spend on track? For each active ad group (and CBO campaign): budget type and amount, spend in the window, daily average, pace index (1.0 = spending the daily budget), and days remaining. Costs 3 requests.`,description:``,source:`rest`,options:[{name:`workspaceId`,flag:`--workspace-id`,description:``,required:!0,valueType:`string`,location:`path`},{name:`ad_account_id`,flag:`--ad-account-id`,description:`Reddit ad account id (a2_…). Omit it: it defaults to the ad account this client is connected to, and any other account is refused.`,required:!1,valueType:`string`,location:`body`},{name:`campaign_id`,flag:`--campaign-id`,description:`Only this campaign's ad groups.`,required:!1,valueType:`string`,location:`body`},{name:`preset`,flag:`--preset`,description:`Shortcut for a date range. Default last_7d when no start_date/end_date given.`,required:!1,valueType:`string`,enum:[`today`,`yesterday`,`last_7d`,`last_14d`,`last_30d`,`this_month`,`last_month`],location:`body`},{name:`start_date`,flag:`--start-date`,description:`First day, YYYY-MM-DD, in time_zone_id.`,required:!1,valueType:`string`,location:`body`},{name:`end_date`,flag:`--end-date`,description:`Last day (inclusive), YYYY-MM-DD, in time_zone_id.`,required:!1,valueType:`string`,location:`body`},{name:`time_zone_id`,flag:`--time-zone-id`,description:`IANA zone for the date boundaries, e.g. Europe/Paris. Defaults to the ad account's time zone.`,required:!1,valueType:`string`,location:`body`}],examples:[{description:`Example`,command:`adside reddit pacing analyze --workspace-id <workspaceId>`}],output:{kind:`json`,description:`Is spend on track? For each active ad group (and CBO campaign): budget type and amount, spend in the window, daily average, pace index (1.0 = spending the daily budget), and days remaining. Costs 3 requests.`},transport:{type:`rest`,method:`POST`,path:`/v1/workspaces/{workspaceId}/reddit/pacing/analyze`,auth:`user`,requestContentType:`application/json`}},{id:`reddit.compare_reddit_performance`,path:[`reddit`,`performance`,`compare`],summary:`Side-by-side comparison: either this window versus the previous period at a level, or several objects (campaigns, ad groups or ads) in one window. Deltas are absolute and percent; rates are recomputed from sums, never summed. Costs 2–3 requests.`,description:``,source:`rest`,options:[{name:`workspaceId`,flag:`--workspace-id`,description:``,required:!0,valueType:`string`,location:`path`},{name:`ad_account_id`,flag:`--ad-account-id`,description:`Reddit ad account id (a2_…). Omit it: it defaults to the ad account this client is connected to, and any other account is refused.`,required:!1,valueType:`string`,location:`body`},{name:`level`,flag:`--level`,description:`One row per object at this level (plus any breakdowns).`,required:!1,valueType:`string`,defaultValue:`campaign`,enum:[`account`,`campaign`,`ad_group`,`ad`],location:`body`},{name:`object_ids`,flag:`--object-ids`,description:`Compare these objects side by side in one window.`,required:!1,valueType:`json`,location:`body`},{name:`metrics`,flag:`--metrics`,description:`Friendly metric names, e.g. impressions, clicks, spend, ctr, cpc, ecpm, reach, video_watched_100_percent, conversion_purchase_clicks. Default: the core group. See list_reddit_report_fields.`,required:!1,valueType:`json`,location:`body`},{name:`preset`,flag:`--preset`,description:`Shortcut for a date range. Default last_7d when no start_date/end_date given.`,required:!1,valueType:`string`,enum:[`today`,`yesterday`,`last_7d`,`last_14d`,`last_30d`,`this_month`,`last_month`],location:`body`},{name:`start_date`,flag:`--start-date`,description:`First day, YYYY-MM-DD, in time_zone_id.`,required:!1,valueType:`string`,location:`body`},{name:`end_date`,flag:`--end-date`,description:`Last day (inclusive), YYYY-MM-DD, in time_zone_id.`,required:!1,valueType:`string`,location:`body`},{name:`time_zone_id`,flag:`--time-zone-id`,description:`IANA zone for the date boundaries, e.g. Europe/Paris. Defaults to the ad account's time zone.`,required:!1,valueType:`string`,location:`body`},{name:`compare_to`,flag:`--compare-to`,description:`previous_period = the same number of days immediately before the window.`,required:!1,valueType:`string`,defaultValue:`previous_period`,enum:[`previous_period`,`none`],location:`body`}],examples:[{description:`Example`,command:`adside reddit performance compare --workspace-id <workspaceId>`}],output:{kind:`json`,description:`Side-by-side comparison: either this window versus the previous period at a level, or several objects (campaigns, ad groups or ads) in one window. Deltas are absolute and percent; rates are recomputed from sums, never summed. Costs 2–3 requests.`},transport:{type:`rest`,method:`POST`,path:`/v1/workspaces/{workspaceId}/reddit/performance/compare`,auth:`user`,requestContentType:`application/json`}},{id:`reddit.rank_reddit_performance`,path:[`reddit`,`performance`,`rank`],summary:`Rank a dimension (campaigns, ad groups, ads, communities, keywords, interests, placements, countries, …) by one metric over a window, with a minimum-spend floor. Cost metrics rank ascending (cheapest first) and rows with zero of the metric are skipped for them. The right tool for 'which ads should I scale or kill'. Costs 1–2 requests.`,description:``,source:`rest`,options:[{name:`workspaceId`,flag:`--workspace-id`,description:``,required:!0,valueType:`string`,location:`path`},{name:`ad_account_id`,flag:`--ad-account-id`,description:`Reddit ad account id (a2_…). Omit it: it defaults to the ad account this client is connected to, and any other account is refused.`,required:!1,valueType:`string`,location:`body`},{name:`dimension`,flag:`--dimension`,description:`What to rank: campaign, ad_group, ad, community, keyword, interest, placement, country, region, os_type, gender, language.`,required:!1,valueType:`string`,defaultValue:`ad`,location:`body`},{name:`metric`,flag:`--metric`,description:`Metric to rank by. Cost metrics (cpc, ecpm, *_ecpa) rank ascending.`,required:!1,valueType:`string`,defaultValue:`spend`,location:`body`},{name:`min_spend`,flag:`--min-spend`,description:`Ignore rows under this spend (account currency).`,required:!1,valueType:`number`,defaultValue:0,location:`body`},{name:`top_n`,flag:`--top-n`,description:``,required:!1,valueType:`number`,defaultValue:10,location:`body`},{name:`preset`,flag:`--preset`,description:`Shortcut for a date range. Default last_7d when no start_date/end_date given.`,required:!1,valueType:`string`,enum:[`today`,`yesterday`,`last_7d`,`last_14d`,`last_30d`,`this_month`,`last_month`],location:`body`},{name:`start_date`,flag:`--start-date`,description:`First day, YYYY-MM-DD, in time_zone_id.`,required:!1,valueType:`string`,location:`body`},{name:`end_date`,flag:`--end-date`,description:`Last day (inclusive), YYYY-MM-DD, in time_zone_id.`,required:!1,valueType:`string`,location:`body`},{name:`time_zone_id`,flag:`--time-zone-id`,description:`IANA zone for the date boundaries, e.g. Europe/Paris. Defaults to the ad account's time zone.`,required:!1,valueType:`string`,location:`body`}],examples:[{description:`Example`,command:`adside reddit performance rank --workspace-id <workspaceId>`}],output:{kind:`json`,description:`Rank a dimension (campaigns, ad groups, ads, communities, keywords, interests, placements, countries, …) by one metric over a window, with a minimum-spend floor. Cost metrics rank ascending (cheapest first) and rows with zero of the metric are skipped for them. The right tool for 'which ads should I scale or kill'. Costs 1–2 requests.`},transport:{type:`rest`,method:`POST`,path:`/v1/workspaces/{workspaceId}/reddit/performance/rank`,auth:`user`,requestContentType:`application/json`}},{id:`reddit.list_reddit_pixel_events`,path:[`reddit`,`pixel-events`,`list`],summary:`When each standard and custom event last fired on the connected account's pixel(s), with age. Use it to confirm a pixel install or a Conversions API upload landed (test_id events do not fire here).`,description:``,source:`rest`,options:[{name:`workspaceId`,flag:`--workspace-id`,description:``,required:!0,valueType:`string`,location:`path`},{name:`ad_account_id`,flag:`--ad-account-id`,description:`Reddit ad account id (a2_…). Omit it: it defaults to the ad account this client is connected to, and any other account is refused.`,required:!1,valueType:`string`,location:`body`},{name:`pixel_id`,flag:`--pixel-id`,description:`One pixel of the connected account; omit for all of them.`,required:!1,valueType:`string`,location:`body`}],examples:[{description:`Example`,command:`adside reddit pixel-events list --workspace-id <workspaceId>`}],output:{kind:`json`,description:`When each standard and custom event last fired on the connected account's pixel(s), with age. Use it to confirm a pixel install or a Conversions API upload landed (test_id events do not fire here).`},transport:{type:`rest`,method:`POST`,path:`/v1/workspaces/{workspaceId}/reddit/pixel-events/list`,auth:`user`,requestContentType:`application/json`}},{id:`reddit.list_reddit_pixels`,path:[`reddit`,`pixels`,`list`],summary:`Reddit pixels on the connected ad account with when each standard and custom event last fired. Every ad account gets a default pixel whose id equals the ad account id; that id is what ad groups need as conversion_pixel_id.`,description:``,source:`rest`,options:[{name:`workspaceId`,flag:`--workspace-id`,description:``,required:!0,valueType:`string`,location:`path`},{name:`ad_account_id`,flag:`--ad-account-id`,description:`Reddit ad account id (a2_…). Omit it: it defaults to the ad account this client is connected to, and any other account is refused.`,required:!1,valueType:`string`,location:`body`}],examples:[{description:`Example`,command:`adside reddit pixels list --workspace-id <workspaceId>`}],output:{kind:`json`,description:`Reddit pixels on the connected ad account with when each standard and custom event last fired. Every ad account gets a default pixel whose id equals the ad account id; that id is what ad groups need as conversion_pixel_id.`},transport:{type:`rest`,method:`POST`,path:`/v1/workspaces/{workspaceId}/reddit/pixels/list`,auth:`user`,requestContentType:`application/json`}},{id:`reddit.get_reddit_post_job`,path:[`reddit`,`post-job`,`get`],summary:`Status of a structured-post creation job (QUEUED → PROCESSING → SUCCESS | CLIENT_ERROR | SERVER_ERROR) and the post id once it exists.`,description:``,source:`rest`,options:[{name:`workspaceId`,flag:`--workspace-id`,description:``,required:!0,valueType:`string`,location:`path`},{name:`job_id`,flag:`--job-id`,description:`Structured-post creation job id returned by create_reddit_post.`,required:!0,valueType:`string`,location:`body`}],examples:[{description:`Example`,command:`adside reddit post-job get --workspace-id <workspaceId> --job-id <job_id>`}],output:{kind:`json`,description:`Status of a structured-post creation job (QUEUED → PROCESSING → SUCCESS | CLIENT_ERROR | SERVER_ERROR) and the post id once it exists.`},transport:{type:`rest`,method:`POST`,path:`/v1/workspaces/{workspaceId}/reddit/post-job/get`,auth:`user`,requestContentType:`application/json`}},{id:`reddit.get_reddit_post`,path:[`reddit`,`posts`,`get`],summary:`One post (ad creative) by id: headline, type, media URLs, destination and call-to-action, comment setting, public URL. Falls back to the legacy Posts API for posts created outside Structured Posts.`,description:``,source:`rest`,options:[{name:`workspaceId`,flag:`--workspace-id`,description:``,required:!0,valueType:`string`,location:`path`},{name:`post_id`,flag:`--post-id`,description:`Post id (t3_…) from an ad or from list_reddit_posts.`,required:!0,valueType:`string`,location:`body`}],examples:[{description:`Example`,command:`adside reddit posts get --workspace-id <workspaceId> --post-id <post_id>`}],output:{kind:`json`,description:`One post (ad creative) by id: headline, type, media URLs, destination and call-to-action, comment setting, public URL. Falls back to the legacy Posts API for posts created outside Structured Posts.`},transport:{type:`rest`,method:`POST`,path:`/v1/workspaces/{workspaceId}/reddit/posts/get`,auth:`user`,requestContentType:`application/json`}},{id:`reddit.list_reddit_posts`,path:[`reddit`,`posts`,`list`],summary:`Posts (ad creatives) on the connected account's profiles — headline, type, destination, media — or the posts behind specific ads. A Reddit ad is a promoted post; copy and media live on the post and are immutable once created.`,description:``,source:`rest`,options:[{name:`workspaceId`,flag:`--workspace-id`,description:``,required:!0,valueType:`string`,location:`path`},{name:`ad_account_id`,flag:`--ad-account-id`,description:`Reddit ad account id (a2_…). Omit it: it defaults to the ad account this client is connected to, and any other account is refused.`,required:!1,valueType:`string`,location:`body`},{name:`profile_id`,flag:`--profile-id`,description:`Profile whose posts to list. Omit to use every profile shared with the ad account.`,required:!1,valueType:`string`,location:`body`},{name:`ad_ids`,flag:`--ad-ids`,description:`Alternatively, the posts behind these ads.`,required:!1,valueType:`json`,location:`body`},{name:`limit`,flag:`--limit`,description:``,required:!1,valueType:`number`,defaultValue:50,location:`body`}],examples:[{description:`Example`,command:`adside reddit posts list --workspace-id <workspaceId>`}],output:{kind:`json`,description:`Posts (ad creatives) on the connected account's profiles — headline, type, destination, media — or the posts behind specific ads. A Reddit ad is a promoted post; copy and media live on the post and are immutable once created.`},transport:{type:`rest`,method:`POST`,path:`/v1/workspaces/{workspaceId}/reddit/posts/list`,auth:`user`,requestContentType:`application/json`}},{id:`reddit.list_reddit_profiles`,path:[`reddit`,`profiles`,`list`],summary:`Reddit profiles shared with the connected ad account. Posts (ad creatives) are authored from a profile, so create_reddit_post and create_reddit_ad need one of these ids. Sharing a profile with an ad account is a Business Manager step, not an API call.`,description:``,source:`rest`,options:[{name:`workspaceId`,flag:`--workspace-id`,description:``,required:!0,valueType:`string`,location:`path`},{name:`ad_account_id`,flag:`--ad-account-id`,description:`Reddit ad account id (a2_…). Omit it: it defaults to the ad account this client is connected to, and any other account is refused.`,required:!1,valueType:`string`,location:`body`}],examples:[{description:`Example`,command:`adside reddit profiles list --workspace-id <workspaceId>`}],output:{kind:`json`,description:`Reddit profiles shared with the connected ad account. Posts (ad creatives) are authored from a profile, so create_reddit_post and create_reddit_ad need one of these ids. Sharing a profile with an ad account is a Business Manager step, not an API call.`},transport:{type:`rest`,method:`POST`,path:`/v1/workspaces/{workspaceId}/reddit/profiles/list`,auth:`user`,requestContentType:`application/json`}},{id:`reddit.estimate_reddit_reach`,path:[`reddit`,`reach`,`estimate`],summary:`How many people a targeting can reach: Reddit's channel-planning reach curve for a geolocation (7 or 28 days) and, when a targeting object is given, the audience size and delivery estimates (impressions, clicks, reach) for a hypothetical ad group. Use before committing a budget. Costs 1–2 requests.`,description:``,source:`rest`,options:[{name:`workspaceId`,flag:`--workspace-id`,description:``,required:!0,valueType:`string`,location:`path`},{name:`ad_account_id`,flag:`--ad-account-id`,description:`Reddit ad account id (a2_…). Omit it: it defaults to the ad account this client is connected to, and any other account is refused.`,required:!1,valueType:`string`,location:`body`},{name:`geolocation`,flag:`--geolocation`,description:`Country or region id, e.g. US.`,required:!0,valueType:`string`,location:`body`},{name:`duration_days`,flag:`--duration-days`,description:``,required:!1,valueType:`number`,defaultValue:7,location:`body`},{name:`gender`,flag:`--gender`,description:``,required:!1,valueType:`string`,enum:[`MALE`,`FEMALE`],location:`body`},{name:`min_age`,flag:`--min-age`,description:``,required:!1,valueType:`number`,location:`body`},{name:`max_age`,flag:`--max-age`,description:``,required:!1,valueType:`number`,location:`body`},{name:`targeting`,flag:`--targeting`,description:`When given, also returns audience size and delivery estimates for this targeting.`,required:!1,valueType:`json`,location:`body`},{name:`objective`,flag:`--objective`,description:``,required:!1,valueType:`string`,defaultValue:`CLICKS`,enum:[`APP_INSTALLS`,`CATALOG_SALES`,`CLICKS`,`CONVERSIONS`,`IMPRESSIONS`,`LEAD_GENERATION`,`VIDEO_VIEWABLE_IMPRESSIONS`],location:`body`},{name:`daily_budget`,flag:`--daily-budget`,description:`For the delivery estimate, in the account currency. Default 50.`,required:!1,valueType:`number`,location:`body`},{name:`bid_type`,flag:`--bid-type`,description:``,required:!1,valueType:`string`,defaultValue:`CPC`,enum:[`CPC`,`CPM`,`CPV`,`CPV6`,`CPV15`],location:`body`},{name:`bid`,flag:`--bid`,description:`Bid in the account currency. Default 0.50.`,required:!1,valueType:`number`,location:`body`}],examples:[{description:`Example`,command:`adside reddit reach estimate --workspace-id <workspaceId> --geolocation <geolocation>`}],output:{kind:`json`,description:`How many people a targeting can reach: Reddit's channel-planning reach curve for a geolocation (7 or 28 days) and, when a targeting object is given, the audience size and delivery estimates (impressions, clicks, reach) for a hypothetical ad group. Use before committing a budget. Costs 1–2 requests.`},transport:{type:`rest`,method:`POST`,path:`/v1/workspaces/{workspaceId}/reddit/reach/estimate`,auth:`user`,requestContentType:`application/json`}},{id:`reddit.get_reddit_report`,path:[`reddit`,`report`,`get`],summary:`Performance report for the connected Reddit ad account: any level (account, campaign, ad group, ad), friendly metric names or metric groups, optional breakdowns (date, country, community, keyword, placement, …), a date preset or range in the account's time zone. Money is converted from Reddit's micro-units; rates in the summary are recomputed from sums. Rows beyond the byte budget are dropped with a notice — narrow the window, level or metrics rather than paging.`,description:``,source:`rest`,options:[{name:`workspaceId`,flag:`--workspace-id`,description:``,required:!0,valueType:`string`,location:`path`},{name:`ad_account_id`,flag:`--ad-account-id`,description:`Reddit ad account id (a2_…). Omit it: it defaults to the ad account this client is connected to, and any other account is refused.`,required:!1,valueType:`string`,location:`body`},{name:`level`,flag:`--level`,description:`One row per object at this level (plus any breakdowns).`,required:!1,valueType:`string`,defaultValue:`campaign`,enum:[`account`,`campaign`,`ad_group`,`ad`],location:`body`},{name:`object_id`,flag:`--object-id`,description:"Restrict to one campaign / ad group / ad id (matched to `level`).",required:!1,valueType:`string`,location:`body`},{name:`metrics`,flag:`--metrics`,description:`Friendly metric names, e.g. impressions, clicks, spend, ctr, cpc, ecpm, reach, video_watched_100_percent, conversion_purchase_clicks. Default: the core group. See list_reddit_report_fields.`,required:!1,valueType:`json`,location:`body`},{name:`metric_groups`,flag:`--metric-groups`,description:`Bundles: core, video, conversions, value, app.`,required:!1,valueType:`json`,location:`body`},{name:`breakdowns`,flag:`--breakdowns`,description:`Extra dimensions: date, hour, country, region, dma, community, interest, keyword, placement, os_type, gender, language, asset_id, carousel_card. Max 3 in total (the level counts as one). Reddit has no age breakdown.`,required:!1,valueType:`json`,location:`body`},{name:`preset`,flag:`--preset`,description:`Shortcut for a date range. Default last_7d when no start_date/end_date given.`,required:!1,valueType:`string`,enum:[`today`,`yesterday`,`last_7d`,`last_14d`,`last_30d`,`this_month`,`last_month`],location:`body`},{name:`start_date`,flag:`--start-date`,description:`First day, YYYY-MM-DD, in time_zone_id.`,required:!1,valueType:`string`,location:`body`},{name:`end_date`,flag:`--end-date`,description:`Last day (inclusive), YYYY-MM-DD, in time_zone_id.`,required:!1,valueType:`string`,location:`body`},{name:`time_zone_id`,flag:`--time-zone-id`,description:`IANA zone for the date boundaries, e.g. Europe/Paris. Defaults to the ad account's time zone.`,required:!1,valueType:`string`,location:`body`},{name:`filter`,flag:`--filter`,description:"Reddit filter syntax, e.g. `campaign:effective_status==ACTIVE,ad:name=@promo` (== exact, =@ contains, comma = OR).",required:!1,valueType:`string`,location:`body`},{name:`conversion_events`,flag:`--conversion-events`,description:`Named custom pixel events to include (clicks, views, value).`,required:!1,valueType:`json`,location:`body`},{name:`sort_by`,flag:`--sort-by`,description:`Metric to sort rows by (descending). Default spend.`,required:!1,valueType:`string`,location:`body`},{name:`format`,flag:`--format`,description:`json only when fields must be reused programmatically.`,required:!1,valueType:`string`,defaultValue:`markdown`,enum:[`markdown`,`json`],location:`body`},{name:`limit`,flag:`--limit`,description:``,required:!1,valueType:`number`,defaultValue:200,location:`body`}],examples:[{description:`Example`,command:`adside reddit report get --workspace-id <workspaceId>`}],output:{kind:`json`,description:`Performance report for the connected Reddit ad account: any level (account, campaign, ad group, ad), friendly metric names or metric groups, optional breakdowns (date, country, community, keyword, placement, …), a date preset or range in the account's time zone. Money is converted from Reddit's micro-units; rates in the summary are recomputed from sums. Rows beyond the byte budget are dropped with a notice — narrow the window, level or metrics rather than paging.`},transport:{type:`rest`,method:`POST`,path:`/v1/workspaces/{workspaceId}/reddit/report/get`,auth:`user`,requestContentType:`application/json`}},{id:`reddit.list_reddit_report_fields`,path:[`reddit`,`report-fields`,`list`],summary:`The report vocabulary get_reddit_report accepts: metric groups, every metric with its unit (money, count, rate) and every breakdown. Generated from the pinned API spec. Use it when a metric name is refused.`,description:``,source:`rest`,options:[{name:`workspaceId`,flag:`--workspace-id`,description:``,required:!0,valueType:`string`,location:`path`},{name:`filter`,flag:`--filter`,description:`Substring filter, e.g. 'conversion', 'video', 'app_install'.`,required:!1,valueType:`string`,location:`body`},{name:`group`,flag:`--group`,description:`Only the members of one metric group.`,required:!1,valueType:`string`,enum:[`core`,`video`,`conversions`,`value`,`app`],location:`body`}],examples:[{description:`Example`,command:`adside reddit report-fields list --workspace-id <workspaceId>`}],output:{kind:`json`,description:`The report vocabulary get_reddit_report accepts: metric groups, every metric with its unit (money, count, rate) and every breakdown. Generated from the pinned API spec. Use it when a metric name is refused.`},transport:{type:`rest`,method:`POST`,path:`/v1/workspaces/{workspaceId}/reddit/report-fields/list`,auth:`user`,requestContentType:`application/json`}},{id:`reddit.get_reddit_saved_audience`,path:[`reddit`,`saved-audiences`,`get`],summary:`One saved audience by id with its full targeting.`,description:``,source:`rest`,options:[{name:`workspaceId`,flag:`--workspace-id`,description:``,required:!0,valueType:`string`,location:`path`},{name:`saved_audience_id`,flag:`--saved-audience-id`,description:`Saved audience id from list_reddit_saved_audiences.`,required:!0,valueType:`string`,location:`body`}],examples:[{description:`Example`,command:`adside reddit saved-audiences get --workspace-id <workspaceId> --saved-audience-id <saved_audience_id>`}],output:{kind:`json`,description:`One saved audience by id with its full targeting.`},transport:{type:`rest`,method:`POST`,path:`/v1/workspaces/{workspaceId}/reddit/saved-audiences/get`,auth:`user`,requestContentType:`application/json`}},{id:`reddit.list_reddit_saved_audiences`,path:[`reddit`,`saved-audiences`,`list`],summary:`Reusable targeting definitions (saved audiences) on the connected account.`,description:``,source:`rest`,options:[{name:`workspaceId`,flag:`--workspace-id`,description:``,required:!0,valueType:`string`,location:`path`},{name:`ad_account_id`,flag:`--ad-account-id`,description:`Reddit ad account id (a2_…). Omit it: it defaults to the ad account this client is connected to, and any other account is refused.`,required:!1,valueType:`string`,location:`body`}],examples:[{description:`Example`,command:`adside reddit saved-audiences list --workspace-id <workspaceId>`}],output:{kind:`json`,description:`Reusable targeting definitions (saved audiences) on the connected account.`},transport:{type:`rest`,method:`POST`,path:`/v1/workspaces/{workspaceId}/reddit/saved-audiences/list`,auth:`user`,requestContentType:`application/json`}},{id:`reddit.list_reddit_targeting_options`,path:[`reddit`,`targeting-options`,`list`],summary:`Static targeting vocabularies: devices, carriers, languages, time zones, industries.`,description:``,source:`rest`,options:[{name:`workspaceId`,flag:`--workspace-id`,description:``,required:!0,valueType:`string`,location:`path`},{name:`kind`,flag:`--kind`,description:``,required:!0,valueType:`string`,enum:[`devices`,`carriers`,`languages`,`time_zones`,`industries`],location:`body`}],examples:[{description:`Example`,command:`adside reddit targeting-options list --workspace-id <workspaceId> --kind devices`}],output:{kind:`json`,description:`Static targeting vocabularies: devices, carriers, languages, time zones, industries.`},transport:{type:`rest`,method:`POST`,path:`/v1/workspaces/{workspaceId}/reddit/targeting-options/list`,auth:`user`,requestContentType:`application/json`}},{id:`reddit.list_reddit_third_party_audiences`,path:[`reddit`,`third-party-audiences`,`list`],summary:`Third-party (data partner) audiences available for targeting on Reddit, with provider and size where given. Reference them from targeting.custom_audience_ids.`,description:``,source:`rest`,options:[{name:`workspaceId`,flag:`--workspace-id`,description:``,required:!0,valueType:`string`,location:`path`},{name:`limit`,flag:`--limit`,description:``,required:!1,valueType:`number`,defaultValue:50,location:`body`}],examples:[{description:`Example`,command:`adside reddit third-party-audiences list --workspace-id <workspaceId>`}],output:{kind:`json`,description:`Third-party (data partner) audiences available for targeting on Reddit, with provider and size where given. Reference them from targeting.custom_audience_ids.`},transport:{type:`rest`,method:`POST`,path:`/v1/workspaces/{workspaceId}/reddit/third-party-audiences/list`,auth:`user`,requestContentType:`application/json`}},{id:`reddit.list_reddit_third_party_trackers`,path:[`reddit`,`third-party-trackers`,`list`],summary:`The click and impression tracker domains Reddit accepts on an ad's event_trackers (DoubleVerify, IAS, MOAT, …). Check before attaching a tracker URL.`,description:``,source:`rest`,options:[{name:`workspaceId`,flag:`--workspace-id`,description:``,required:!0,valueType:`string`,location:`path`}],examples:[{description:`Example`,command:`adside reddit third-party-trackers list --workspace-id <workspaceId>`}],output:{kind:`json`,description:`The click and impression tracker domains Reddit accepts on an ad's event_trackers (DoubleVerify, IAS, MOAT, …). Check before attaching a tracker URL.`},transport:{type:`rest`,method:`POST`,path:`/v1/workspaces/{workspaceId}/reddit/third-party-trackers/list`,auth:`user`}},{id:`reddit.check_reddit_tracking_health`,path:[`reddit`,`tracking-health`,`check`],summary:`Are conversions being tracked? Every pixel on the account with the age of its last fire per standard and custom event (healthy < 24 h, stale < 7 d, never), and which active ad groups depend on a pixel that never fired. Costs 2–4 requests.`,description:``,source:`rest`,options:[{name:`workspaceId`,flag:`--workspace-id`,description:``,required:!0,valueType:`string`,location:`path`},{name:`ad_account_id`,flag:`--ad-account-id`,description:`Reddit ad account id (a2_…). Omit it: it defaults to the ad account this client is connected to, and any other account is refused.`,required:!1,valueType:`string`,location:`body`}],examples:[{description:`Example`,command:`adside reddit tracking-health check --workspace-id <workspaceId>`}],output:{kind:`json`,description:`Are conversions being tracked? Every pixel on the account with the age of its last fire per standard and custom event (healthy < 24 h, stale < 7 d, never), and which active ad groups depend on a pixel that never fired. Costs 2–4 requests.`},transport:{type:`rest`,method:`POST`,path:`/v1/workspaces/{workspaceId}/reddit/tracking-health/check`,auth:`user`,requestContentType:`application/json`}},{id:`reporting.budgets`,path:[`reporting`,`budgets`],summary:`Refresh and read current campaign budgets`,description:``,source:`rest`,options:[{name:`workspaceId`,flag:`--workspace-id`,description:``,required:!0,valueType:`string`,location:`path`}],examples:[{description:`Example`,command:`adside reporting budgets --workspace-id <workspaceId>`}],output:{kind:`json`,description:`Refresh and read current campaign budgets`},transport:{type:`rest`,method:`GET`,path:`/v1/workspaces/{workspaceId}/reporting/budgets`,auth:`user`}},{id:`reporting.conversion-mapping.get`,path:[`reporting`,`conversion-mapping`,`get`],summary:`Read the primary conversion mapping and optional suggested events`,description:``,source:`rest`,options:[{name:`workspaceId`,flag:`--workspace-id`,description:``,required:!0,valueType:`string`,location:`path`},{name:`suggestions`,flag:`--suggestions`,description:``,required:!1,valueType:`string`,defaultValue:`1`,enum:[`0`,`1`],location:`query`}],examples:[{description:`Example`,command:`adside reporting conversion-mapping get --workspace-id <workspaceId>`}],output:{kind:`json`,description:`Read the primary conversion mapping and optional suggested events`},transport:{type:`rest`,method:`GET`,path:`/v1/workspaces/{workspaceId}/reporting/conversion-mapping`,auth:`user`}},{id:`reporting.conversion-options`,path:[`reporting`,`conversion-options`],summary:`List native conversion events and custom actions with workspace activity`,description:``,source:`rest`,options:[{name:`workspaceId`,flag:`--workspace-id`,description:``,required:!0,valueType:`string`,location:`path`},{name:`source`,flag:`--source`,description:``,required:!0,valueType:`string`,enum:[`META`,`TIKTOK`,`GOOGLE`,`LINKEDIN`,`SNAPCHAT`,`REDDIT`],location:`path`}],examples:[{description:`Example`,command:`adside reporting conversion-options --workspace-id <workspaceId> --source META`}],output:{kind:`json`,description:`List native conversion events and custom actions with workspace activity`},transport:{type:`rest`,method:`GET`,path:`/v1/workspaces/{workspaceId}/reporting/conversion-options/{source}`,auth:`user`}},{id:`reporting.conversions`,path:[`reporting`,`conversions`],summary:`Query mapped conversion performance across channels`,description:``,source:`rest`,options:[{name:`workspaceId`,flag:`--workspace-id`,description:``,required:!0,valueType:`string`,location:`path`},{name:`from`,flag:`--from`,description:``,required:!0,valueType:`string`,location:`query`},{name:`to`,flag:`--to`,description:``,required:!0,valueType:`string`,location:`query`},{name:`granularity`,flag:`--granularity`,description:``,required:!1,valueType:`string`,defaultValue:`day`,enum:[`day`,`week`,`month`],location:`query`},{name:`channels`,flag:`--channels`,description:``,required:!1,valueType:`json`,location:`query`},{name:`eventId`,flag:`--event-id`,description:``,required:!1,valueType:`string`,location:`query`}],examples:[{description:`Example`,command:`adside reporting conversions --workspace-id <workspaceId> --from <from> --to <to>`}],output:{kind:`json`,description:`Query mapped conversion performance across channels`},transport:{type:`rest`,method:`GET`,path:`/v1/workspaces/{workspaceId}/reporting/conversions`,auth:`user`}},{id:`reporting.creative-filters`,path:[`reporting`,`creative-filters`],summary:`List creative intelligence filters for a reporting source`,description:``,source:`rest`,options:[{name:`workspaceId`,flag:`--workspace-id`,description:``,required:!0,valueType:`string`,location:`path`},{name:`source`,flag:`--source`,description:``,required:!1,valueType:`string`,defaultValue:`META`,enum:[`META`,`TIKTOK`,`GOOGLE`,`SNAPCHAT`,`REDDIT`],location:`query`}],examples:[{description:`Example`,command:`adside reporting creative-filters --workspace-id <workspaceId>`}],output:{kind:`json`,description:`List creative intelligence filters for a reporting source`},transport:{type:`rest`,method:`GET`,path:`/v1/workspaces/{workspaceId}/reporting/creative-filters`,auth:`user`}},{id:`reporting.creatives.analysis`,path:[`reporting`,`creatives`,`analysis`],summary:`Read the existing creative AI analysis without requesting a new one`,description:``,source:`rest`,options:[{name:`workspaceId`,flag:`--workspace-id`,description:``,required:!0,valueType:`string`,location:`path`},{name:`sourceCreativeId`,flag:`--source-creative-id`,description:``,required:!0,valueType:`string`,location:`path`},{name:`source`,flag:`--source`,description:``,required:!1,valueType:`string`,defaultValue:`META`,enum:[`META`,`TIKTOK`,`GOOGLE`,`SNAPCHAT`,`REDDIT`],location:`query`}],examples:[{description:`Example`,command:`adside reporting creatives analysis --workspace-id <workspaceId> --source-creative-id <sourceCreativeId>`}],output:{kind:`json`,description:`Read the existing creative AI analysis without requesting a new one`},transport:{type:`rest`,method:`GET`,path:`/v1/workspaces/{workspaceId}/reporting/creative-analysis/{sourceCreativeId}`,auth:`user`}},{id:`reporting.creatives.comments`,path:[`reporting`,`creatives`,`comments`],summary:`Read comments on a creative across its ad variants`,description:``,source:`rest`,options:[{name:`workspaceId`,flag:`--workspace-id`,description:``,required:!0,valueType:`string`,location:`path`},{name:`adId`,flag:`--ad-id`,description:``,required:!0,valueType:`string`,location:`path`},{name:`source`,flag:`--source`,description:``,required:!1,valueType:`string`,defaultValue:`META`,enum:[`META`,`TIKTOK`,`GOOGLE`,`LINKEDIN`,`SNAPCHAT`,`REDDIT`],location:`query`}],examples:[{description:`Example`,command:`adside reporting creatives comments --workspace-id <workspaceId> --ad-id <adId>`}],output:{kind:`json`,description:`Read comments on a creative across its ad variants`},transport:{type:`rest`,method:`GET`,path:`/v1/workspaces/{workspaceId}/reporting/creatives/{adId}/comments`,auth:`user`}},{id:`reporting.creatives.download`,path:[`reporting`,`creatives`,`download`],summary:`Download a creative video (up to 256 MiB)`,description:``,source:`rest`,options:[{name:`workspaceId`,flag:`--workspace-id`,description:``,required:!0,valueType:`string`,location:`path`},{name:`adId`,flag:`--ad-id`,description:``,required:!0,valueType:`string`,location:`path`},{name:`source`,flag:`--source`,description:``,required:!1,valueType:`string`,defaultValue:`META`,enum:[`META`,`TIKTOK`,`GOOGLE`,`LINKEDIN`,`SNAPCHAT`,`REDDIT`],location:`query`}],examples:[{description:`Example`,command:`adside reporting creatives download --workspace-id <workspaceId> --ad-id <adId>`}],output:{kind:`binary`,description:`Download a creative video (up to 256 MiB)`},transport:{type:`rest`,method:`GET`,path:`/v1/workspaces/{workspaceId}/reporting/creatives/{adId}/download`,auth:`user`}},{id:`reporting.creatives.get`,path:[`reporting`,`creatives`,`get`],summary:`Read performance and breakdowns for a creative`,description:``,source:`rest`,options:[{name:`workspaceId`,flag:`--workspace-id`,description:``,required:!0,valueType:`string`,location:`path`},{name:`adId`,flag:`--ad-id`,description:``,required:!0,valueType:`string`,location:`path`},{name:`source`,flag:`--source`,description:``,required:!1,valueType:`string`,defaultValue:`META`,enum:[`META`,`TIKTOK`,`GOOGLE`,`LINKEDIN`,`SNAPCHAT`,`REDDIT`],location:`query`},{name:`from`,flag:`--from`,description:``,required:!0,valueType:`string`,location:`query`},{name:`to`,flag:`--to`,description:``,required:!0,valueType:`string`,location:`query`},{name:`groupBy`,flag:`--group-by`,description:``,required:!1,valueType:`string`,defaultValue:`ad`,enum:[`ad`,`media`],location:`query`}],examples:[{description:`Example`,command:`adside reporting creatives get --workspace-id <workspaceId> --ad-id <adId> --from <from> --to <to>`}],output:{kind:`json`,description:`Read performance and breakdowns for a creative`},transport:{type:`rest`,method:`GET`,path:`/v1/workspaces/{workspaceId}/reporting/creatives/{adId}`,auth:`user`}},{id:`reporting.creatives.rank`,path:[`reporting`,`creatives`,`rank`],summary:`Get top creatives`,description:``,source:`rest`,options:[{name:`workspaceId`,flag:`--workspace-id`,description:``,required:!0,valueType:`string`,location:`path`},{name:`source`,flag:`--source`,description:`Ad platform to read: META, TIKTOK, GOOGLE (YouTube video ads), LINKEDIN, SNAPCHAT or REDDIT. Defaults to META.`,required:!1,valueType:`string`,defaultValue:`META`,enum:[`META`,`TIKTOK`,`GOOGLE`,`LINKEDIN`,`SNAPCHAT`,`REDDIT`],location:`body`},{name:`from`,flag:`--from`,description:"Inclusive start date, yyyy-MM-dd. Use together with `to`; takes precedence over `period`.",required:!1,valueType:`string`,location:`body`},{name:`to`,flag:`--to`,description:`Inclusive end date, yyyy-MM-dd.`,required:!1,valueType:`string`,location:`body`},{name:`period`,flag:`--period`,description:"Preset window used when `from`/`to` are omitted.",required:!1,valueType:`string`,defaultValue:`last_7_days`,enum:[`today`,`yesterday`,`last_7_days`,`last_4_weeks`,`last_3_months`,`last_12_months`,`week_to_date`,`month_to_date`,`quarter_to_date`,`year_to_date`,`all_time`,`last_30_days`],location:`body`},{name:`limit`,flag:`--limit`,description:`How many creatives to return (1-20). Defaults to 10.`,required:!1,valueType:`number`,defaultValue:10,location:`body`},{name:`format`,flag:`--format`,description:`Keep only video or static creatives. Defaults to all.`,required:!1,valueType:`string`,defaultValue:`all`,enum:[`all`,`video`,`static`],location:`body`},{name:`sortBy`,flag:`--sort-by`,description:"Ranking column. `conversion` ranks by the conversion event (see `conversionEvent` / `sortSubMetric`). A column the platform cannot sort by falls back to spend.",required:!1,valueType:`string`,defaultValue:`spend`,enum:[`spend`,`impressions`,`reach`,`clicks`,`frequency`,`ctr`,`cpm`,`cpc`,`thumbstop`,`conversion`,`comments`],location:`body`},{name:`sortOrder`,flag:`--sort-order`,description:`desc = highest first (use asc with cost metrics for cheapest).`,required:!1,valueType:`string`,defaultValue:`desc`,enum:[`asc`,`desc`],location:`body`},{name:`sortSubMetric`,flag:`--sort-sub-metric`,description:"With sortBy `conversion`: which conversion figure to rank by — count, costPer, rate, value or roas. Defaults to count.",required:!1,valueType:`string`,enum:[`costPer`,`count`,`rate`,`value`,`roas`],location:`body`},{name:`conversionEvent`,flag:`--conversion-event`,description:`Platform conversion event to report (e.g. a Meta action_type). Defaults to the client's primary mapped conversion for the platform.`,required:!1,valueType:`string`,location:`body`}],examples:[{description:`Example`,command:`adside reporting creatives rank --workspace-id <workspaceId>`}],output:{kind:`json`,description:`Get top creatives`},transport:{type:`rest`,method:`POST`,path:`/v1/workspaces/{workspaceId}/reporting/creatives/rank`,auth:`user`,requestContentType:`application/json`}},{id:`reporting.creatives.transcript`,path:[`reporting`,`creatives`,`transcript`],summary:`Request a video's timestamped transcript or return its existing result`,description:``,source:`rest`,options:[{name:`workspaceId`,flag:`--workspace-id`,description:``,required:!0,valueType:`string`,location:`path`},{name:`adId`,flag:`--ad-id`,description:``,required:!0,valueType:`string`,location:`path`},{name:`source`,flag:`--source`,description:``,required:!1,valueType:`string`,defaultValue:`META`,enum:[`META`,`TIKTOK`,`GOOGLE`,`LINKEDIN`,`SNAPCHAT`,`REDDIT`],location:`query`}],examples:[{description:`Example`,command:`adside reporting creatives transcript --workspace-id <workspaceId> --ad-id <adId>`}],output:{kind:`json`,description:`Request a video's timestamped transcript or return its existing result`},transport:{type:`rest`,method:`POST`,path:`/v1/workspaces/{workspaceId}/reporting/creatives/{adId}/transcript`,auth:`user`}},{id:`reporting.creatives.transcript-status`,path:[`reporting`,`creatives`,`transcript-status`],summary:`Read a video's transcript status and result without starting transcription`,description:``,source:`rest`,options:[{name:`workspaceId`,flag:`--workspace-id`,description:``,required:!0,valueType:`string`,location:`path`},{name:`adId`,flag:`--ad-id`,description:``,required:!0,valueType:`string`,location:`path`},{name:`source`,flag:`--source`,description:``,required:!1,valueType:`string`,defaultValue:`META`,enum:[`META`,`TIKTOK`,`GOOGLE`,`LINKEDIN`,`SNAPCHAT`,`REDDIT`],location:`query`}],examples:[{description:`Example`,command:`adside reporting creatives transcript-status --workspace-id <workspaceId> --ad-id <adId>`}],output:{kind:`json`,description:`Read a video's transcript status and result without starting transcription`},transport:{type:`rest`,method:`GET`,path:`/v1/workspaces/{workspaceId}/reporting/creatives/{adId}/transcript`,auth:`user`}},{id:`reporting.performance.query`,path:[`reporting`,`performance`,`query`],summary:`Query ad performance`,description:``,source:`rest`,options:[{name:`workspaceId`,flag:`--workspace-id`,description:``,required:!0,valueType:`string`,location:`path`},{name:`level`,flag:`--level`,description:`What each result row represents. Defaults to campaign.`,required:!1,valueType:`string`,defaultValue:`campaign`,enum:[`channel`,`campaign`,`ad`],location:`body`},{name:`from`,flag:`--from`,description:`Inclusive start date, yyyy-MM-dd.`,required:!0,valueType:`string`,location:`body`},{name:`to`,flag:`--to`,description:`Inclusive end date, yyyy-MM-dd.`,required:!0,valueType:`string`,location:`body`},{name:`metrics`,flag:`--metrics`,description:"Metrics to show per row. Defaults to spend, impressions, clicks, ctr, cpc, cpm. reach, conversions and costPerConversion need level `ad`.",required:!1,valueType:`json`,location:`body`},{name:`orderBy`,flag:`--order-by`,description:`Metric to rank rows by. Defaults to spend.`,required:!1,valueType:`string`,defaultValue:`spend`,enum:[`spend`,`impressions`,`clicks`,`ctr`,`cpc`,`cpm`,`reach`,`conversions`,`costPerConversion`],location:`body`},{name:`orderDirection`,flag:`--order-direction`,description:`Sort direction. Defaults to desc (highest first).`,required:!1,valueType:`string`,defaultValue:`desc`,enum:[`asc`,`desc`],location:`body`},{name:`limit`,flag:`--limit`,description:`Maximum rows to return (1-50). Defaults to 10.`,required:!1,valueType:`number`,defaultValue:10,location:`body`},{name:`channels`,flag:`--channels`,description:'Channel filter for level `channel` or `campaign`, e.g. ["META", "GOOGLE_SEARCH"]. Omit for every channel.',required:!1,valueType:`json`,location:`body`},{name:`source`,flag:`--source`,description:"Level `ad` only: the ad platform to read ads from. Defaults to META.",required:!1,valueType:`string`,defaultValue:`META`,enum:[`META`,`TIKTOK`,`GOOGLE`,`LINKEDIN`,`SNAPCHAT`,`REDDIT`],location:`body`},{name:`campaignName`,flag:`--campaign-name`,description:"Level `ad` only: keep ads whose campaign name contains this.",required:!1,valueType:`string`,location:`body`},{name:`adSetName`,flag:`--ad-set-name`,description:"Level `ad` only: keep ads whose ad set name contains this (Meta).",required:!1,valueType:`string`,location:`body`},{name:`conversionEvent`,flag:`--conversion-event`,description:"Level `ad` only: the platform conversion event to count (e.g. a Meta action_type). Defaults to the client's primary mapped conversion for that platform.",required:!1,valueType:`string`,location:`body`},{name:`timeSeries`,flag:`--time-series`,description:"Level `channel` or `campaign`: also return totals per time bucket.",required:!1,valueType:`boolean`,defaultValue:!1,location:`body`},{name:`granularity`,flag:`--granularity`,description:`Bucket width for the time series: day, week or month.`,required:!1,valueType:`string`,defaultValue:`day`,enum:[`day`,`week`,`month`],location:`body`},{name:`compareWithPreviousPeriod`,flag:`--compare-with-previous-period`,description:"Level `channel` or `campaign`: compare with the equally long period just before `from`.",required:!1,valueType:`boolean`,defaultValue:!1,location:`body`}],examples:[{description:`Example`,command:`adside reporting performance query --workspace-id <workspaceId> --from <from> --to <to>`}],output:{kind:`json`,description:`Query ad performance`},transport:{type:`rest`,method:`POST`,path:`/v1/workspaces/{workspaceId}/reporting/performance/query`,auth:`user`,requestContentType:`application/json`}},{id:`reporting.reports.create`,path:[`reporting`,`reports`,`create`],summary:`Save a dashboard report`,description:``,source:`rest`,options:[{name:`workspaceId`,flag:`--workspace-id`,description:``,required:!0,valueType:`string`,location:`path`},{name:`dashboardKey`,flag:`--dashboard-key`,description:``,required:!0,valueType:`string`,enum:[`top-creatives`,`spend`,`conversions`],location:`body`},{name:`name`,flag:`--name`,description:``,required:!0,valueType:`string`,location:`body`},{name:`description`,flag:`--description`,description:``,required:!1,valueType:`string`,location:`body`},{name:`icon`,flag:`--icon`,description:``,required:!0,valueType:`string`,location:`body`},{name:`definition`,flag:`--definition`,description:``,required:!0,valueType:`string`,location:`body`}],examples:[{description:`Example`,command:`adside reporting reports create --workspace-id <workspaceId> --dashboard-key top-creatives --name <name> --icon <icon> --definition <definition>`}],output:{kind:`json`,description:`Save a dashboard report`},transport:{type:`rest`,method:`POST`,path:`/v1/workspaces/{workspaceId}/reports`,auth:`user`,requestContentType:`application/json`}},{id:`reporting.reports.delete`,path:[`reporting`,`reports`,`delete`],summary:`Delete a saved report`,description:``,source:`rest`,options:[{name:`workspaceId`,flag:`--workspace-id`,description:``,required:!0,valueType:`string`,location:`path`},{name:`reportId`,flag:`--report-id`,description:``,required:!0,valueType:`string`,location:`path`},{name:`confirmationToken`,flag:`--confirmation-token`,description:``,required:!1,valueType:`string`,location:`body`}],examples:[{description:`Example`,command:`adside reporting reports delete --workspace-id <workspaceId> --report-id <reportId>`}],output:{kind:`json`,description:`Delete a saved report`},transport:{type:`rest`,method:`DELETE`,path:`/v1/workspaces/{workspaceId}/reports/{reportId}`,auth:`user`,requestContentType:`application/json`}},{id:`reporting.reports.get`,path:[`reporting`,`reports`,`get`],summary:`Read a saved report definition`,description:``,source:`rest`,options:[{name:`workspaceId`,flag:`--workspace-id`,description:``,required:!0,valueType:`string`,location:`path`},{name:`reportId`,flag:`--report-id`,description:``,required:!0,valueType:`string`,location:`path`}],examples:[{description:`Example`,command:`adside reporting reports get --workspace-id <workspaceId> --report-id <reportId>`}],output:{kind:`json`,description:`Read a saved report definition`},transport:{type:`rest`,method:`GET`,path:`/v1/workspaces/{workspaceId}/reports/{reportId}`,auth:`user`}},{id:`reporting.reports.list`,path:[`reporting`,`reports`,`list`],summary:`List saved reports`,description:``,source:`rest`,options:[{name:`workspaceId`,flag:`--workspace-id`,description:``,required:!0,valueType:`string`,location:`path`},{name:`dashboardKey`,flag:`--dashboard-key`,description:``,required:!1,valueType:`string`,enum:[`top-creatives`,`spend`,`conversions`],location:`query`}],examples:[{description:`Example`,command:`adside reporting reports list --workspace-id <workspaceId>`}],output:{kind:`json`,description:`List saved reports`},transport:{type:`rest`,method:`GET`,path:`/v1/workspaces/{workspaceId}/reports`,auth:`user`}},{id:`reporting.reports.update`,path:[`reporting`,`reports`,`update`],summary:`Update report metadata or its view definition`,description:``,source:`rest`,options:[{name:`workspaceId`,flag:`--workspace-id`,description:``,required:!0,valueType:`string`,location:`path`},{name:`reportId`,flag:`--report-id`,description:``,required:!0,valueType:`string`,location:`path`},{name:`name`,flag:`--name`,description:``,required:!1,valueType:`string`,location:`body`},{name:`description`,flag:`--description`,description:``,required:!1,valueType:`string`,location:`body`},{name:`icon`,flag:`--icon`,description:``,required:!1,valueType:`string`,location:`body`},{name:`definition`,flag:`--definition`,description:``,required:!1,valueType:`string`,location:`body`}],examples:[{description:`Example`,command:`adside reporting reports update --workspace-id <workspaceId> --report-id <reportId>`}],output:{kind:`json`,description:`Update report metadata or its view definition`},transport:{type:`rest`,method:`PATCH`,path:`/v1/workspaces/{workspaceId}/reports/{reportId}`,auth:`user`,requestContentType:`application/json`}},{id:`reporting.spend`,path:[`reporting`,`spend`],summary:`Query cross-channel spend and mapped conversions`,description:``,source:`rest`,options:[{name:`workspaceId`,flag:`--workspace-id`,description:``,required:!0,valueType:`string`,location:`path`},{name:`from`,flag:`--from`,description:``,required:!0,valueType:`string`,location:`query`},{name:`to`,flag:`--to`,description:``,required:!0,valueType:`string`,location:`query`},{name:`granularity`,flag:`--granularity`,description:``,required:!1,valueType:`string`,defaultValue:`day`,enum:[`day`,`week`,`month`],location:`query`},{name:`channels`,flag:`--channels`,description:``,required:!1,valueType:`json`,location:`query`}],examples:[{description:`Example`,command:`adside reporting spend --workspace-id <workspaceId> --from <from> --to <to>`}],output:{kind:`json`,description:`Query cross-channel spend and mapped conversions`},transport:{type:`rest`,method:`GET`,path:`/v1/workspaces/{workspaceId}/reporting/spend`,auth:`user`}},{id:`reporting.sync.start`,path:[`reporting`,`sync`,`start`],summary:`Request a manual reporting sync subject to cooldown and current connection state`,description:``,source:`rest`,options:[{name:`workspaceId`,flag:`--workspace-id`,description:``,required:!0,valueType:`string`,location:`path`},{name:`source`,flag:`--source`,description:``,required:!0,valueType:`string`,enum:[`META`,`TIKTOK`,`GOOGLE`,`LINKEDIN`,`SNAPCHAT`,`REDDIT`],location:`path`},{name:`confirmationToken`,flag:`--confirmation-token`,description:``,required:!1,valueType:`string`,location:`body`}],examples:[{description:`Example`,command:`adside reporting sync start --workspace-id <workspaceId> --source META`}],output:{kind:`json`,description:`Request a manual reporting sync subject to cooldown and current connection state`},transport:{type:`rest`,method:`POST`,path:`/v1/workspaces/{workspaceId}/reporting/sync/{source}`,auth:`user`,requestContentType:`application/json`}},{id:`reporting.sync.status`,path:[`reporting`,`sync`,`status`],summary:`Read reporting sync progress, freshness and caller-specific availability`,description:``,source:`rest`,options:[{name:`workspaceId`,flag:`--workspace-id`,description:``,required:!0,valueType:`string`,location:`path`},{name:`source`,flag:`--source`,description:``,required:!0,valueType:`string`,enum:[`META`,`TIKTOK`,`GOOGLE`,`LINKEDIN`,`SNAPCHAT`,`REDDIT`],location:`path`}],examples:[{description:`Example`,command:`adside reporting sync status --workspace-id <workspaceId> --source META`}],output:{kind:`json`,description:`Read reporting sync progress, freshness and caller-specific availability`},transport:{type:`rest`,method:`GET`,path:`/v1/workspaces/{workspaceId}/reporting/sync/{source}`,auth:`user`}},{id:`reporting.themes.get`,path:[`reporting`,`themes`,`get`],summary:`Read a messaging theme and its paginated creatives`,description:``,source:`rest`,options:[{name:`workspaceId`,flag:`--workspace-id`,description:``,required:!0,valueType:`string`,location:`path`},{name:`themeId`,flag:`--theme-id`,description:``,required:!0,valueType:`string`,location:`path`},{name:`from`,flag:`--from`,description:``,required:!0,valueType:`string`,location:`query`},{name:`to`,flag:`--to`,description:``,required:!0,valueType:`string`,location:`query`},{name:`source`,flag:`--source`,description:``,required:!1,valueType:`string`,defaultValue:`META`,enum:[`META`,`TIKTOK`,`GOOGLE`,`SNAPCHAT`,`REDDIT`],location:`query`},{name:`sortBy`,flag:`--sort-by`,description:``,required:!1,valueType:`string`,defaultValue:`spend`,enum:[`spend`,`impressions`,`reach`,`clicks`,`frequency`,`ctr`,`cpm`,`cpc`,`thumbstop`,`conversion`,`comments`,`winnerCreativeCount`,`creativeCount`,`totalAdCount`,`activeCreativeCount`],location:`query`},{name:`sortOrder`,flag:`--sort-order`,description:``,required:!1,valueType:`string`,defaultValue:`desc`,enum:[`asc`,`desc`],location:`query`},{name:`sortEvent`,flag:`--sort-event`,description:``,required:!1,valueType:`string`,location:`query`},{name:`sortSubMetric`,flag:`--sort-sub-metric`,description:``,required:!1,valueType:`string`,enum:[`costPer`,`count`,`rate`,`value`,`roas`],location:`query`},{name:`page`,flag:`--page`,description:``,required:!1,valueType:`number`,defaultValue:1,location:`query`},{name:`pageSize`,flag:`--page-size`,description:``,required:!1,valueType:`number`,defaultValue:48,location:`query`}],examples:[{description:`Example`,command:`adside reporting themes get --workspace-id <workspaceId> --theme-id <themeId> --from <from> --to <to>`}],output:{kind:`json`,description:`Read a messaging theme and its paginated creatives`},transport:{type:`rest`,method:`GET`,path:`/v1/workspaces/{workspaceId}/reporting/themes/{themeId}`,auth:`user`}},{id:`reporting.themes.list`,path:[`reporting`,`themes`,`list`],summary:`Compare performance by messaging theme`,description:``,source:`rest`,options:[{name:`workspaceId`,flag:`--workspace-id`,description:``,required:!0,valueType:`string`,location:`path`},{name:`from`,flag:`--from`,description:``,required:!0,valueType:`string`,location:`query`},{name:`to`,flag:`--to`,description:``,required:!0,valueType:`string`,location:`query`},{name:`source`,flag:`--source`,description:``,required:!1,valueType:`string`,defaultValue:`META`,enum:[`META`,`TIKTOK`,`GOOGLE`,`SNAPCHAT`,`REDDIT`],location:`query`},{name:`sortBy`,flag:`--sort-by`,description:``,required:!1,valueType:`string`,defaultValue:`spend`,enum:[`spend`,`impressions`,`reach`,`clicks`,`frequency`,`ctr`,`cpm`,`cpc`,`thumbstop`,`conversion`,`comments`,`winnerCreativeCount`,`creativeCount`,`totalAdCount`,`activeCreativeCount`],location:`query`},{name:`sortOrder`,flag:`--sort-order`,description:``,required:!1,valueType:`string`,defaultValue:`desc`,enum:[`asc`,`desc`],location:`query`},{name:`sortEvent`,flag:`--sort-event`,description:``,required:!1,valueType:`string`,location:`query`},{name:`sortSubMetric`,flag:`--sort-sub-metric`,description:``,required:!1,valueType:`string`,enum:[`costPer`,`count`,`rate`,`value`,`roas`],location:`query`}],examples:[{description:`Example`,command:`adside reporting themes list --workspace-id <workspaceId> --from <from> --to <to>`}],output:{kind:`json`,description:`Compare performance by messaging theme`},transport:{type:`rest`,method:`GET`,path:`/v1/workspaces/{workspaceId}/reporting/themes`,auth:`user`}},{id:`research.ad-library.search`,path:[`research`,`ad-library`,`search`],summary:`Search cached brand ads or explicitly request a paid scrape`,description:``,source:`rest`,options:[{name:`workspaceId`,flag:`--workspace-id`,description:``,required:!0,valueType:`string`,location:`path`},{name:`runId`,flag:`--run-id`,description:`Check on a scrape this tool started earlier. When set, every other field is ignored.`,required:!1,valueType:`string`,location:`body`},{name:`brandName`,flag:`--brand-name`,description:"The brand or company name. Required unless `runId` is set.",required:!1,valueType:`string`,location:`body`},{name:`channel`,flag:`--channel`,description:"Which ad library to search. Required unless `runId` is set.",required:!1,valueType:`string`,enum:[`META`,`GOOGLE`,`LINKEDIN`],location:`body`},{name:`domain`,flag:`--domain`,description:"The brand's website domain, for example `nike.com`. Required for GOOGLE.",required:!1,valueType:`string`,location:`body`},{name:`metaPageId`,flag:`--meta-page-id`,description:`The brand's numeric Facebook page id. Required for META.`,required:!1,valueType:`string`,location:`body`},{name:`startScrape`,flag:`--start-scrape`,description:`Set to true to start a paid scrape when the brand's ads are not already collected. Leave false to only read what is cached.`,required:!1,valueType:`boolean`,defaultValue:!1,location:`body`},{name:`limit`,flag:`--limit`,description:`How many ads to return (max 25).`,required:!1,valueType:`number`,defaultValue:10,location:`body`},{name:`confirmationToken`,flag:`--confirmation-token`,description:``,required:!1,valueType:`string`,location:`body`}],examples:[{description:`Example`,command:`adside research ad-library search --workspace-id <workspaceId>`}],output:{kind:`json`,description:`Search cached brand ads or explicitly request a paid scrape`},transport:{type:`rest`,method:`POST`,path:`/v1/workspaces/{workspaceId}/research/ad-library/search`,auth:`user`,requestContentType:`application/json`}},{id:`research.ads.analysis`,path:[`research`,`ads`,`analysis`],summary:`Read an existing creative analysis for a tracked company's ad`,description:``,source:`rest`,options:[{name:`workspaceId`,flag:`--workspace-id`,description:``,required:!0,valueType:`string`,location:`path`},{name:`trackedCompanyId`,flag:`--tracked-company-id`,description:``,required:!0,valueType:`string`,location:`path`},{name:`source`,flag:`--source`,description:``,required:!0,valueType:`string`,enum:[`META`,`GOOGLE`,`LINKEDIN`],location:`query`},{name:`adArchiveId`,flag:`--ad-archive-id`,description:``,required:!0,valueType:`string`,location:`query`}],examples:[{description:`Example`,command:`adside research ads analysis --workspace-id <workspaceId> --tracked-company-id <trackedCompanyId> --source META --ad-archive-id <adArchiveId>`}],output:{kind:`json`,description:`Read an existing creative analysis for a tracked company's ad`},transport:{type:`rest`,method:`GET`,path:`/v1/workspaces/{workspaceId}/research/ads/companies/{trackedCompanyId}/analysis`,auth:`user`}},{id:`research.ads.brands`,path:[`research`,`ads`,`brands`],summary:`Search public brands by name`,description:``,source:`rest`,options:[{name:`workspaceId`,flag:`--workspace-id`,description:``,required:!0,valueType:`string`,location:`path`},{name:`q`,flag:`--q`,description:``,required:!0,valueType:`string`,location:`query`}],examples:[{description:`Example`,command:`adside research ads brands --workspace-id <workspaceId> --q <q>`}],output:{kind:`json`,description:`Search public brands by name`},transport:{type:`rest`,method:`GET`,path:`/v1/workspaces/{workspaceId}/research/ads/brands`,auth:`user`}},{id:`research.ads.company`,path:[`research`,`ads`,`company`],summary:`Read all cached ad sources, insights and pending runs for a tracked company`,description:``,source:`rest`,options:[{name:`workspaceId`,flag:`--workspace-id`,description:``,required:!0,valueType:`string`,location:`path`},{name:`trackedCompanyId`,flag:`--tracked-company-id`,description:``,required:!0,valueType:`string`,location:`path`}],examples:[{description:`Example`,command:`adside research ads company --workspace-id <workspaceId> --tracked-company-id <trackedCompanyId>`}],output:{kind:`json`,description:`Read all cached ad sources, insights and pending runs for a tracked company`},transport:{type:`rest`,method:`GET`,path:`/v1/workspaces/{workspaceId}/research/ads/companies/{trackedCompanyId}`,auth:`user`}},{id:`research.ads.fetch`,path:[`research`,`ads`,`fetch`],summary:`Read cached public ads or start an asynchronous brand scrape`,description:``,source:`rest`,options:[{name:`workspaceId`,flag:`--workspace-id`,description:``,required:!0,valueType:`string`,location:`path`},{name:`limit`,flag:`--limit`,description:``,required:!1,valueType:`number`,location:`body`},{name:`forceRefresh`,flag:`--force-refresh`,description:``,required:!1,valueType:`boolean`,location:`body`},{name:`trackedCompanyId`,flag:`--tracked-company-id`,description:``,required:!1,valueType:`string`,location:`body`},{name:`channel`,flag:`--channel`,description:``,required:!0,valueType:`string`,enum:[`META`,`GOOGLE`,`LINKEDIN`],location:`body`},{name:`adlibraryUrl`,flag:`--adlibrary-url`,description:``,required:!1,valueType:`string`,location:`body`},{name:`searchTerm`,flag:`--search-term`,description:``,required:!1,valueType:`string`,location:`body`},{name:`domain`,flag:`--domain`,description:``,required:!1,valueType:`string`,location:`body`},{name:`companyName`,flag:`--company-name`,description:``,required:!1,valueType:`string`,location:`body`}],examples:[{description:`Example`,command:`adside research ads fetch --workspace-id <workspaceId> --channel META`}],output:{kind:`json`,description:`Read cached public ads or start an asynchronous brand scrape`},transport:{type:`rest`,method:`POST`,path:`/v1/workspaces/{workspaceId}/research/ads`,auth:`user`,requestContentType:`application/json`}},{id:`research.ads.run`,path:[`research`,`ads`,`run`],summary:`Read the status and results of a public ad-library scrape`,description:``,source:`rest`,options:[{name:`workspaceId`,flag:`--workspace-id`,description:``,required:!0,valueType:`string`,location:`path`},{name:`runId`,flag:`--run-id`,description:``,required:!0,valueType:`string`,location:`path`}],examples:[{description:`Example`,command:`adside research ads run --workspace-id <workspaceId> --run-id <runId>`}],output:{kind:`json`,description:`Read the status and results of a public ad-library scrape`},transport:{type:`rest`,method:`GET`,path:`/v1/workspaces/{workspaceId}/research/ads/runs/{runId}`,auth:`user`}},{id:`research.ads.suggestions`,path:[`research`,`ads`,`suggestions`],summary:`Find Meta Ad Library pages for a brand`,description:``,source:`rest`,options:[{name:`workspaceId`,flag:`--workspace-id`,description:``,required:!0,valueType:`string`,location:`path`},{name:`q`,flag:`--q`,description:``,required:!0,valueType:`string`,location:`query`},{name:`domain`,flag:`--domain`,description:``,required:!1,valueType:`string`,location:`query`}],examples:[{description:`Example`,command:`adside research ads suggestions --workspace-id <workspaceId> --q <q>`}],output:{kind:`json`,description:`Find Meta Ad Library pages for a brand`},transport:{type:`rest`,method:`GET`,path:`/v1/workspaces/{workspaceId}/research/ads/suggestions`,auth:`user`}},{id:`research.ads.transcript`,path:[`research`,`ads`,`transcript`],summary:`Read an existing transcript for a tracked company's video ad`,description:``,source:`rest`,options:[{name:`workspaceId`,flag:`--workspace-id`,description:``,required:!0,valueType:`string`,location:`path`},{name:`source`,flag:`--source`,description:``,required:!0,valueType:`string`,enum:[`META`,`GOOGLE`,`LINKEDIN`],location:`query`},{name:`adArchiveId`,flag:`--ad-archive-id`,description:``,required:!0,valueType:`string`,location:`query`}],examples:[{description:`Example`,command:`adside research ads transcript --workspace-id <workspaceId> --source META --ad-archive-id <adArchiveId>`}],output:{kind:`json`,description:`Read an existing transcript for a tracked company's video ad`},transport:{type:`rest`,method:`GET`,path:`/v1/workspaces/{workspaceId}/research/ads/transcript`,auth:`user`}},{id:`research.collections.add`,path:[`research`,`collections`,`add`],summary:`Add a tracked company to a collection`,description:``,source:`rest`,options:[{name:`workspaceId`,flag:`--workspace-id`,description:``,required:!0,valueType:`string`,location:`path`},{name:`collectionId`,flag:`--collection-id`,description:``,required:!0,valueType:`string`,location:`path`},{name:`trackedCompanyId`,flag:`--tracked-company-id`,description:``,required:!0,valueType:`string`,location:`body`}],examples:[{description:`Example`,command:`adside research collections add --workspace-id <workspaceId> --collection-id <collectionId> --tracked-company-id <trackedCompanyId>`}],output:{kind:`json`,description:`Add a tracked company to a collection`},transport:{type:`rest`,method:`POST`,path:`/v1/workspaces/{workspaceId}/research/collections/{collectionId}/members`,auth:`user`,requestContentType:`application/json`}},{id:`research.collections.create`,path:[`research`,`collections`,`create`],summary:`Create a company collection`,description:``,source:`rest`,options:[{name:`workspaceId`,flag:`--workspace-id`,description:``,required:!0,valueType:`string`,location:`path`},{name:`name`,flag:`--name`,description:``,required:!0,valueType:`string`,location:`body`},{name:`description`,flag:`--description`,description:``,required:!1,valueType:`string`,location:`body`},{name:`icon`,flag:`--icon`,description:``,required:!1,valueType:`string`,location:`body`},{name:`color`,flag:`--color`,description:``,required:!1,valueType:`string`,location:`body`}],examples:[{description:`Example`,command:`adside research collections create --workspace-id <workspaceId> --name <name>`}],output:{kind:`json`,description:`Create a company collection`},transport:{type:`rest`,method:`POST`,path:`/v1/workspaces/{workspaceId}/research/collections`,auth:`user`,requestContentType:`application/json`}},{id:`research.collections.delete`,path:[`research`,`collections`,`delete`],summary:`Delete a custom company collection`,description:``,source:`rest`,options:[{name:`workspaceId`,flag:`--workspace-id`,description:``,required:!0,valueType:`string`,location:`path`},{name:`collectionId`,flag:`--collection-id`,description:``,required:!0,valueType:`string`,location:`path`},{name:`confirmationToken`,flag:`--confirmation-token`,description:``,required:!1,valueType:`string`,location:`body`}],examples:[{description:`Example`,command:`adside research collections delete --workspace-id <workspaceId> --collection-id <collectionId>`}],output:{kind:`json`,description:`Delete a custom company collection`},transport:{type:`rest`,method:`DELETE`,path:`/v1/workspaces/{workspaceId}/research/collections/{collectionId}`,auth:`user`,requestContentType:`application/json`}},{id:`research.collections.get`,path:[`research`,`collections`,`get`],summary:`Read a company collection and its members`,description:``,source:`rest`,options:[{name:`workspaceId`,flag:`--workspace-id`,description:``,required:!0,valueType:`string`,location:`path`},{name:`collectionId`,flag:`--collection-id`,description:``,required:!0,valueType:`string`,location:`path`}],examples:[{description:`Example`,command:`adside research collections get --workspace-id <workspaceId> --collection-id <collectionId>`}],output:{kind:`json`,description:`Read a company collection and its members`},transport:{type:`rest`,method:`GET`,path:`/v1/workspaces/{workspaceId}/research/collections/{collectionId}`,auth:`user`}},{id:`research.collections.list`,path:[`research`,`collections`,`list`],summary:`List company collections`,description:``,source:`rest`,options:[{name:`workspaceId`,flag:`--workspace-id`,description:``,required:!0,valueType:`string`,location:`path`}],examples:[{description:`Example`,command:`adside research collections list --workspace-id <workspaceId>`}],output:{kind:`json`,description:`List company collections`},transport:{type:`rest`,method:`GET`,path:`/v1/workspaces/{workspaceId}/research/collections`,auth:`user`}},{id:`research.collections.remove`,path:[`research`,`collections`,`remove`],summary:`Remove a company from a collection`,description:``,source:`rest`,options:[{name:`workspaceId`,flag:`--workspace-id`,description:``,required:!0,valueType:`string`,location:`path`},{name:`collectionId`,flag:`--collection-id`,description:``,required:!0,valueType:`string`,location:`path`},{name:`trackedCompanyId`,flag:`--tracked-company-id`,description:``,required:!0,valueType:`string`,location:`body`}],examples:[{description:`Example`,command:`adside research collections remove --workspace-id <workspaceId> --collection-id <collectionId> --tracked-company-id <trackedCompanyId>`}],output:{kind:`json`,description:`Remove a company from a collection`},transport:{type:`rest`,method:`DELETE`,path:`/v1/workspaces/{workspaceId}/research/collections/{collectionId}/members`,auth:`user`,requestContentType:`application/json`}},{id:`research.collections.update`,path:[`research`,`collections`,`update`],summary:`Update a company collection`,description:``,source:`rest`,options:[{name:`workspaceId`,flag:`--workspace-id`,description:``,required:!0,valueType:`string`,location:`path`},{name:`collectionId`,flag:`--collection-id`,description:``,required:!0,valueType:`string`,location:`path`},{name:`name`,flag:`--name`,description:``,required:!1,valueType:`string`,location:`body`},{name:`description`,flag:`--description`,description:``,required:!1,valueType:`string`,location:`body`},{name:`icon`,flag:`--icon`,description:``,required:!1,valueType:`string`,location:`body`},{name:`color`,flag:`--color`,description:``,required:!1,valueType:`string`,location:`body`}],examples:[{description:`Example`,command:`adside research collections update --workspace-id <workspaceId> --collection-id <collectionId>`}],output:{kind:`json`,description:`Update a company collection`},transport:{type:`rest`,method:`PATCH`,path:`/v1/workspaces/{workspaceId}/research/collections/{collectionId}`,auth:`user`,requestContentType:`application/json`}},{id:`research.companies.ads.get`,path:[`research`,`companies`,`ads`,`get`],summary:`Read a tracked company's ad for its detail view`,description:``,source:`rest`,options:[{name:`workspaceId`,flag:`--workspace-id`,description:``,required:!0,valueType:`string`,location:`path`},{name:`companyId`,flag:`--company-id`,description:``,required:!0,valueType:`string`,location:`path`},{name:`source`,flag:`--source`,description:``,required:!0,valueType:`string`,enum:[`META`,`GOOGLE`,`LINKEDIN`],location:`path`},{name:`adArchiveId`,flag:`--ad-archive-id`,description:``,required:!0,valueType:`string`,location:`path`}],examples:[{description:`Example`,command:`adside research companies ads get --workspace-id <workspaceId> --company-id <companyId> --source META --ad-archive-id <adArchiveId>`}],output:{kind:`json`,description:`Read a tracked company's ad for its detail view`},transport:{type:`rest`,method:`GET`,path:`/v1/workspaces/{workspaceId}/research/companies/{companyId}/ads/{source}/{adArchiveId}`,auth:`user`}},{id:`research.companies.delete`,path:[`research`,`companies`,`delete`],summary:`Archive a tracked company, or permanently remove it`,description:``,source:`rest`,options:[{name:`workspaceId`,flag:`--workspace-id`,description:``,required:!0,valueType:`string`,location:`path`},{name:`companyId`,flag:`--company-id`,description:``,required:!0,valueType:`string`,location:`path`},{name:`hard`,flag:`--hard`,description:``,required:!1,valueType:`string`,defaultValue:`false`,enum:[`true`,`false`],location:`query`},{name:`confirmationToken`,flag:`--confirmation-token`,description:``,required:!1,valueType:`string`,location:`body`}],examples:[{description:`Example`,command:`adside research companies delete --workspace-id <workspaceId> --company-id <companyId>`}],output:{kind:`json`,description:`Archive a tracked company, or permanently remove it`},transport:{type:`rest`,method:`DELETE`,path:`/v1/workspaces/{workspaceId}/research/companies/{companyId}`,auth:`user`,requestContentType:`application/json`}},{id:`research.companies.get`,path:[`research`,`companies`,`get`],summary:`Read a tracked company`,description:``,source:`rest`,options:[{name:`workspaceId`,flag:`--workspace-id`,description:``,required:!0,valueType:`string`,location:`path`},{name:`companyId`,flag:`--company-id`,description:``,required:!0,valueType:`string`,location:`path`}],examples:[{description:`Example`,command:`adside research companies get --workspace-id <workspaceId> --company-id <companyId>`}],output:{kind:`json`,description:`Read a tracked company`},transport:{type:`rest`,method:`GET`,path:`/v1/workspaces/{workspaceId}/research/companies/{companyId}`,auth:`user`}},{id:`research.companies.list`,path:[`research`,`companies`,`list`],summary:`List tracked companies and their current extraction state`,description:``,source:`rest`,options:[{name:`workspaceId`,flag:`--workspace-id`,description:``,required:!0,valueType:`string`,location:`path`},{name:`status`,flag:`--status`,description:``,required:!1,valueType:`string`,enum:[`active`,`paused`,`archived`],location:`query`},{name:`collectionId`,flag:`--collection-id`,description:``,required:!1,valueType:`string`,location:`query`},{name:`classification`,flag:`--classification`,description:``,required:!1,valueType:`string`,enum:[`COMPETITOR`,`INSPIRATION`,`SELF`],location:`query`}],examples:[{description:`Example`,command:`adside research companies list --workspace-id <workspaceId>`}],output:{kind:`json`,description:`List tracked companies and their current extraction state`},transport:{type:`rest`,method:`GET`,path:`/v1/workspaces/{workspaceId}/research/companies`,auth:`user`}},{id:`research.companies.refresh-ads`,path:[`research`,`companies`,`refresh-ads`],summary:`Refresh tracked-company ads, with explicit force for an already populated library`,description:``,source:`rest`,options:[{name:`workspaceId`,flag:`--workspace-id`,description:``,required:!0,valueType:`string`,location:`path`},{name:`companyId`,flag:`--company-id`,description:``,required:!0,valueType:`string`,location:`path`},{name:`forceRefresh`,flag:`--force-refresh`,description:``,required:!1,valueType:`boolean`,defaultValue:!1,location:`body`},{name:`confirmationToken`,flag:`--confirmation-token`,description:``,required:!1,valueType:`string`,location:`body`}],examples:[{description:`Example`,command:`adside research companies refresh-ads --workspace-id <workspaceId> --company-id <companyId>`}],output:{kind:`json`,description:`Refresh tracked-company ads, with explicit force for an already populated library`},transport:{type:`rest`,method:`POST`,path:`/v1/workspaces/{workspaceId}/research/companies/{companyId}/ad-refresh`,auth:`user`,requestContentType:`application/json`}},{id:`research.companies.refresh-profile`,path:[`research`,`companies`,`refresh-profile`],summary:`Refresh a competitor profile subject to the shared cooldown`,description:``,source:`rest`,options:[{name:`workspaceId`,flag:`--workspace-id`,description:``,required:!0,valueType:`string`,location:`path`},{name:`companyId`,flag:`--company-id`,description:``,required:!0,valueType:`string`,location:`path`}],examples:[{description:`Example`,command:`adside research companies refresh-profile --workspace-id <workspaceId> --company-id <companyId>`}],output:{kind:`json`,description:`Refresh a competitor profile subject to the shared cooldown`},transport:{type:`rest`,method:`POST`,path:`/v1/workspaces/{workspaceId}/research/companies/{companyId}/profile-refresh`,auth:`user`}},{id:`research.companies.track`,path:[`research`,`companies`,`track`],summary:`Track or reactivate a company and request its research`,description:``,source:`rest`,options:[{name:`workspaceId`,flag:`--workspace-id`,description:``,required:!0,valueType:`string`,location:`path`},{name:`websiteUrl`,flag:`--website-url`,description:``,required:!0,valueType:`url`,location:`body`},{name:`collectionIds`,flag:`--collection-ids`,description:``,required:!1,valueType:`json`,location:`body`},{name:`nickname`,flag:`--nickname`,description:``,required:!1,valueType:`string`,location:`body`},{name:`notes`,flag:`--notes`,description:``,required:!1,valueType:`string`,location:`body`},{name:`priority`,flag:`--priority`,description:``,required:!1,valueType:`number`,location:`body`},{name:`classification`,flag:`--classification`,description:``,required:!1,valueType:`string`,enum:[`COMPETITOR`,`INSPIRATION`,`SELF`],location:`body`},{name:`confirmationToken`,flag:`--confirmation-token`,description:``,required:!1,valueType:`string`,location:`body`}],examples:[{description:`Example`,command:`adside research companies track --workspace-id <workspaceId> --website-url https://example.com`}],output:{kind:`json`,description:`Track or reactivate a company and request its research`},transport:{type:`rest`,method:`POST`,path:`/v1/workspaces/{workspaceId}/research/companies`,auth:`user`,requestContentType:`application/json`}},{id:`research.companies.update`,path:[`research`,`companies`,`update`],summary:`Update a tracked company's workspace metadata`,description:``,source:`rest`,options:[{name:`workspaceId`,flag:`--workspace-id`,description:``,required:!0,valueType:`string`,location:`path`},{name:`companyId`,flag:`--company-id`,description:``,required:!0,valueType:`string`,location:`path`},{name:`nickname`,flag:`--nickname`,description:``,required:!1,valueType:`string`,location:`body`},{name:`notes`,flag:`--notes`,description:``,required:!1,valueType:`string`,location:`body`},{name:`priority`,flag:`--priority`,description:``,required:!1,valueType:`number`,location:`body`},{name:`classification`,flag:`--classification`,description:``,required:!1,valueType:`string`,enum:[`COMPETITOR`,`INSPIRATION`,`SELF`],location:`body`},{name:`status`,flag:`--status`,description:``,required:!1,valueType:`string`,enum:[`active`,`paused`,`archived`],location:`body`}],examples:[{description:`Example`,command:`adside research companies update --workspace-id <workspaceId> --company-id <companyId>`}],output:{kind:`json`,description:`Update a tracked company's workspace metadata`},transport:{type:`rest`,method:`PATCH`,path:`/v1/workspaces/{workspaceId}/research/companies/{companyId}`,auth:`user`,requestContentType:`application/json`}},{id:`research.discover`,path:[`research`,`discover`],summary:`Discover competitors for the workspace's company`,description:``,source:`rest`,options:[{name:`workspaceId`,flag:`--workspace-id`,description:``,required:!0,valueType:`string`,location:`path`}],examples:[{description:`Example`,command:`adside research discover --workspace-id <workspaceId>`}],output:{kind:`json`,description:`Discover competitors for the workspace's company`},transport:{type:`rest`,method:`POST`,path:`/v1/workspaces/{workspaceId}/research/discover`,auth:`user`}},{id:`research.feed`,path:[`research`,`feed`],summary:`Query and filter the workspace's cross-competitor ad feed`,description:``,source:`rest`,options:[{name:`workspaceId`,flag:`--workspace-id`,description:``,required:!0,valueType:`string`,location:`path`},{name:`channels`,flag:`--channels`,description:``,required:!1,valueType:`json`,location:`body`},{name:`trackedCompanyIds`,flag:`--tracked-company-ids`,description:``,required:!1,valueType:`json`,location:`body`},{name:`collectionId`,flag:`--collection-id`,description:``,required:!1,valueType:`string`,location:`body`},{name:`classification`,flag:`--classification`,description:``,required:!1,valueType:`string`,enum:[`COMPETITOR`,`INSPIRATION`,`SELF`],location:`body`},{name:`classifications`,flag:`--classifications`,description:``,required:!1,valueType:`json`,location:`body`},{name:`landingPages`,flag:`--landing-pages`,description:``,required:!1,valueType:`json`,location:`body`},{name:`languages`,flag:`--languages`,description:``,required:!1,valueType:`json`,location:`body`},{name:`aiTags`,flag:`--ai-tags`,description:``,required:!1,valueType:`json`,location:`body`},{name:`formatTypes`,flag:`--format-types`,description:``,required:!1,valueType:`json`,location:`body`},{name:`daysActive`,flag:`--days-active`,description:``,required:!1,valueType:`string`,enum:[`under7`,`over7`],location:`body`},{name:`statuses`,flag:`--statuses`,description:``,required:!1,valueType:`json`,location:`body`},{name:`adLengths`,flag:`--ad-lengths`,description:``,required:!1,valueType:`json`,location:`body`},{name:`sort`,flag:`--sort`,description:``,required:!1,valueType:`string`,defaultValue:`newest`,enum:[`newest`,`longevity`,`impressions`],location:`body`},{name:`cursor`,flag:`--cursor`,description:``,required:!1,valueType:`string`,location:`body`},{name:`limit`,flag:`--limit`,description:``,required:!1,valueType:`number`,defaultValue:50,location:`body`}],examples:[{description:`Example`,command:`adside research feed --workspace-id <workspaceId>`}],output:{kind:`json`,description:`Query and filter the workspace's cross-competitor ad feed`},transport:{type:`rest`,method:`POST`,path:`/v1/workspaces/{workspaceId}/research/feed/query`,auth:`user`,requestContentType:`application/json`}},{id:`research.inspiration.get`,path:[`research`,`inspiration`,`get`],summary:`Read one inspiration item in this workspace's feed`,description:``,source:`rest`,options:[{name:`workspaceId`,flag:`--workspace-id`,description:``,required:!0,valueType:`string`,location:`path`},{name:`itemId`,flag:`--item-id`,description:``,required:!0,valueType:`string`,location:`path`}],examples:[{description:`Example`,command:`adside research inspiration get --workspace-id <workspaceId> --item-id <itemId>`}],output:{kind:`json`,description:`Read one inspiration item in this workspace's feed`},transport:{type:`rest`,method:`GET`,path:`/v1/workspaces/{workspaceId}/research/inspiration/{itemId}`,auth:`user`}},{id:`research.inspiration.list`,path:[`research`,`inspiration`,`list`],summary:`Read the workspace inspiration feed`,description:``,source:`rest`,options:[{name:`workspaceId`,flag:`--workspace-id`,description:``,required:!0,valueType:`string`,location:`path`},{name:`page`,flag:`--page`,description:``,required:!1,valueType:`number`,defaultValue:1,location:`query`},{name:`pageSize`,flag:`--page-size`,description:``,required:!1,valueType:`number`,defaultValue:24,location:`query`}],examples:[{description:`Example`,command:`adside research inspiration list --workspace-id <workspaceId>`}],output:{kind:`json`,description:`Read the workspace inspiration feed`},transport:{type:`rest`,method:`GET`,path:`/v1/workspaces/{workspaceId}/research/inspiration`,auth:`user`}},{id:`research.inspiration.refresh`,path:[`research`,`inspiration`,`refresh`],summary:`Refresh the workspace inspiration feed`,description:``,source:`rest`,options:[{name:`workspaceId`,flag:`--workspace-id`,description:``,required:!0,valueType:`string`,location:`path`}],examples:[{description:`Example`,command:`adside research inspiration refresh --workspace-id <workspaceId>`}],output:{kind:`json`,description:`Refresh the workspace inspiration feed`},transport:{type:`rest`,method:`POST`,path:`/v1/workspaces/{workspaceId}/research/inspiration/refresh`,auth:`user`}},{id:`research.inspiration.run`,path:[`research`,`inspiration`,`run`],summary:`Read inspiration refresh status`,description:``,source:`rest`,options:[{name:`workspaceId`,flag:`--workspace-id`,description:``,required:!0,valueType:`string`,location:`path`},{name:`runId`,flag:`--run-id`,description:``,required:!0,valueType:`string`,location:`path`}],examples:[{description:`Example`,command:`adside research inspiration run --workspace-id <workspaceId> --run-id <runId>`}],output:{kind:`json`,description:`Read inspiration refresh status`},transport:{type:`rest`,method:`GET`,path:`/v1/workspaces/{workspaceId}/research/inspiration/runs/{runId}`,auth:`user`}},{id:`routines.create`,path:[`routines`,`create`],summary:"Approve and create a scheduled routine; returns it with `task.url`, its page in Adside.",description:``,source:`rest`,options:[{name:`workspaceId`,flag:`--workspace-id`,description:``,required:!0,valueType:`string`,location:`path`},{name:`name`,flag:`--name`,description:``,required:!0,valueType:`string`,location:`body`},{name:`instructions`,flag:`--instructions`,description:``,required:!0,valueType:`string`,location:`body`},{name:`cronSchedule`,flag:`--cron-schedule`,description:``,required:!0,valueType:`string`,location:`body`},{name:`timezone`,flag:`--timezone`,description:``,required:!1,valueType:`string`,location:`body`},{name:`enabled`,flag:`--enabled`,description:``,required:!1,valueType:`boolean`,location:`body`},{name:`slackChannelId`,flag:`--slack-channel-id`,description:``,required:!1,valueType:`string`,location:`body`},{name:`confirmationToken`,flag:`--confirmation-token`,description:``,required:!1,valueType:`string`,location:`body`}],examples:[{description:`Example`,command:`adside routines create --workspace-id <workspaceId> --name <name> --instructions <instructions> --cron-schedule <cronSchedule>`}],output:{kind:`json`,description:"Approve and create a scheduled routine; returns it with `task.url`, its page in Adside."},transport:{type:`rest`,method:`POST`,path:`/v1/workspaces/{workspaceId}/routines`,auth:`user`,requestContentType:`application/json`}},{id:`routines.delete`,path:[`routines`,`delete`],summary:`Delete a scheduled routine`,description:``,source:`rest`,options:[{name:`workspaceId`,flag:`--workspace-id`,description:``,required:!0,valueType:`string`,location:`path`},{name:`taskId`,flag:`--task-id`,description:``,required:!0,valueType:`string`,location:`path`},{name:`confirmationToken`,flag:`--confirmation-token`,description:``,required:!1,valueType:`string`,location:`body`}],examples:[{description:`Example`,command:`adside routines delete --workspace-id <workspaceId> --task-id <taskId>`}],output:{kind:`json`,description:`Delete a scheduled routine`},transport:{type:`rest`,method:`DELETE`,path:`/v1/workspaces/{workspaceId}/routines/{taskId}`,auth:`user`,requestContentType:`application/json`}},{id:`routines.get`,path:[`routines`,`get`],summary:`Read a routine and its recent actions`,description:``,source:`rest`,options:[{name:`workspaceId`,flag:`--workspace-id`,description:``,required:!0,valueType:`string`,location:`path`},{name:`taskId`,flag:`--task-id`,description:``,required:!0,valueType:`string`,location:`path`}],examples:[{description:`Example`,command:`adside routines get --workspace-id <workspaceId> --task-id <taskId>`}],output:{kind:`json`,description:`Read a routine and its recent actions`},transport:{type:`rest`,method:`GET`,path:`/v1/workspaces/{workspaceId}/routines/{taskId}`,auth:`user`}},{id:`routines.list`,path:[`routines`,`list`],summary:`List workspace routines`,description:``,source:`rest`,options:[{name:`workspaceId`,flag:`--workspace-id`,description:``,required:!0,valueType:`string`,location:`path`}],examples:[{description:`Example`,command:`adside routines list --workspace-id <workspaceId>`}],output:{kind:`json`,description:`List workspace routines`},transport:{type:`rest`,method:`GET`,path:`/v1/workspaces/{workspaceId}/routines`,auth:`user`}},{id:`routines.run`,path:[`routines`,`run`],summary:`Trigger an immediate authorized routine run`,description:``,source:`rest`,options:[{name:`workspaceId`,flag:`--workspace-id`,description:``,required:!0,valueType:`string`,location:`path`},{name:`taskId`,flag:`--task-id`,description:``,required:!0,valueType:`string`,location:`path`},{name:`confirmationToken`,flag:`--confirmation-token`,description:``,required:!1,valueType:`string`,location:`body`}],examples:[{description:`Example`,command:`adside routines run --workspace-id <workspaceId> --task-id <taskId>`}],output:{kind:`json`,description:`Trigger an immediate authorized routine run`},transport:{type:`rest`,method:`POST`,path:`/v1/workspaces/{workspaceId}/routines/{taskId}/runs`,auth:`user`,requestContentType:`application/json`}},{id:`routines.runs`,path:[`routines`,`runs`],summary:`Read recent routine runs`,description:``,source:`rest`,options:[{name:`workspaceId`,flag:`--workspace-id`,description:``,required:!0,valueType:`string`,location:`path`},{name:`taskId`,flag:`--task-id`,description:``,required:!0,valueType:`string`,location:`path`},{name:`limit`,flag:`--limit`,description:``,required:!1,valueType:`number`,defaultValue:5,location:`query`},{name:`runId`,flag:`--run-id`,description:``,required:!1,valueType:`string`,location:`query`}],examples:[{description:`Example`,command:`adside routines runs --workspace-id <workspaceId> --task-id <taskId>`}],output:{kind:`json`,description:`Read recent routine runs`},transport:{type:`rest`,method:`GET`,path:`/v1/workspaces/{workspaceId}/routines/{taskId}/runs`,auth:`user`}},{id:`routines.runs.recent`,path:[`routines`,`runs`,`recent`],summary:`Read recent results across this workspace's routines`,description:``,source:`rest`,options:[{name:`workspaceId`,flag:`--workspace-id`,description:``,required:!0,valueType:`string`,location:`path`},{name:`since`,flag:`--since`,description:``,required:!0,valueType:`string`,location:`query`},{name:`limit`,flag:`--limit`,description:``,required:!1,valueType:`number`,defaultValue:10,location:`query`}],examples:[{description:`Example`,command:`adside routines runs recent --workspace-id <workspaceId> --since <since>`}],output:{kind:`json`,description:`Read recent results across this workspace's routines`},transport:{type:`rest`,method:`GET`,path:`/v1/workspaces/{workspaceId}/routines/runs/recent`,auth:`user`}},{id:`routines.templates`,path:[`routines`,`templates`],summary:`List active routine templates and their suggested skills`,description:``,source:`rest`,options:[{name:`organizationId`,flag:`--organization-id`,description:``,required:!0,valueType:`string`,location:`path`}],examples:[{description:`Example`,command:`adside routines templates --organization-id <organizationId>`}],output:{kind:`json`,description:`List active routine templates and their suggested skills`},transport:{type:`rest`,method:`GET`,path:`/v1/organizations/{organizationId}/routines/templates`,auth:`user`}},{id:`routines.update`,path:[`routines`,`update`],summary:`Approve routine edits and reauthorize its future runs`,description:``,source:`rest`,options:[{name:`workspaceId`,flag:`--workspace-id`,description:``,required:!0,valueType:`string`,location:`path`},{name:`taskId`,flag:`--task-id`,description:``,required:!0,valueType:`string`,location:`path`},{name:`name`,flag:`--name`,description:``,required:!1,valueType:`string`,location:`body`},{name:`instructions`,flag:`--instructions`,description:``,required:!1,valueType:`string`,location:`body`},{name:`cronSchedule`,flag:`--cron-schedule`,description:``,required:!1,valueType:`string`,location:`body`},{name:`timezone`,flag:`--timezone`,description:``,required:!1,valueType:`string`,location:`body`},{name:`enabled`,flag:`--enabled`,description:``,required:!1,valueType:`boolean`,location:`body`},{name:`slackChannelId`,flag:`--slack-channel-id`,description:``,required:!1,valueType:`string`,location:`body`},{name:`confirmationToken`,flag:`--confirmation-token`,description:``,required:!1,valueType:`string`,location:`body`}],examples:[{description:`Example`,command:`adside routines update --workspace-id <workspaceId> --task-id <taskId>`}],output:{kind:`json`,description:`Approve routine edits and reauthorize its future runs`},transport:{type:`rest`,method:`PATCH`,path:`/v1/workspaces/{workspaceId}/routines/{taskId}`,auth:`user`,requestContentType:`application/json`}},{id:`skills.create`,path:[`skills`,`create`],summary:`Create a skill in the organization library`,description:``,source:`rest`,options:[{name:`organizationId`,flag:`--organization-id`,description:``,required:!0,valueType:`string`,location:`path`},{name:`name`,flag:`--name`,description:``,required:!0,valueType:`string`,location:`body`},{name:`slug`,flag:`--slug`,description:``,required:!0,valueType:`string`,location:`body`},{name:`description`,flag:`--description`,description:``,required:!1,valueType:`string`,defaultValue:``,location:`body`},{name:`thumbnailUrl`,flag:`--thumbnail-url`,description:``,required:!1,valueType:`url`,location:`body`},{name:`content`,flag:`--content`,description:``,required:!0,valueType:`string`,location:`body`},{name:`tags`,flag:`--tags`,description:``,required:!1,valueType:`json`,location:`body`}],examples:[{description:`Example`,command:`adside skills create --organization-id <organizationId> --name <name> --slug <slug> --content <content>`}],output:{kind:`json`,description:`Create a skill in the organization library`},transport:{type:`rest`,method:`POST`,path:`/v1/organizations/{organizationId}/skills`,auth:`user`,requestContentType:`application/json`}},{id:`skills.delete`,path:[`skills`,`delete`],summary:`Delete a skill`,description:``,source:`rest`,options:[{name:`organizationId`,flag:`--organization-id`,description:``,required:!0,valueType:`string`,location:`path`},{name:`skillId`,flag:`--skill-id`,description:``,required:!0,valueType:`string`,location:`path`}],examples:[{description:`Example`,command:`adside skills delete --organization-id <organizationId> --skill-id <skillId>`}],output:{kind:`json`,description:`Delete a skill`},transport:{type:`rest`,method:`DELETE`,path:`/v1/organizations/{organizationId}/skills/{skillId}`,auth:`user`}},{id:`skills.generate`,path:[`skills`,`generate`],summary:`Draft skill instructions from a description`,description:``,source:`rest`,options:[{name:`organizationId`,flag:`--organization-id`,description:``,required:!0,valueType:`string`,location:`path`},{name:`description`,flag:`--description`,description:``,required:!0,valueType:`string`,location:`body`}],examples:[{description:`Example`,command:`adside skills generate --organization-id <organizationId> --description <description>`}],output:{kind:`json`,description:`Draft skill instructions from a description`},transport:{type:`rest`,method:`POST`,path:`/v1/organizations/{organizationId}/skills/generate`,auth:`user`,requestContentType:`application/json`}},{id:`skills.get`,path:[`skills`,`get`],summary:`Read a skill`,description:``,source:`rest`,options:[{name:`organizationId`,flag:`--organization-id`,description:``,required:!0,valueType:`string`,location:`path`},{name:`skillId`,flag:`--skill-id`,description:``,required:!0,valueType:`string`,location:`path`}],examples:[{description:`Example`,command:`adside skills get --organization-id <organizationId> --skill-id <skillId>`}],output:{kind:`json`,description:`Read a skill`},transport:{type:`rest`,method:`GET`,path:`/v1/organizations/{organizationId}/skills/{skillId}`,auth:`user`}},{id:`skills.get-by-slug`,path:[`skills`,`get-by-slug`],summary:`Read a skill by its stable slug`,description:``,source:`rest`,options:[{name:`organizationId`,flag:`--organization-id`,description:``,required:!0,valueType:`string`,location:`path`},{name:`skillSlug`,flag:`--skill-slug`,description:``,required:!0,valueType:`string`,location:`path`}],examples:[{description:`Example`,command:`adside skills get-by-slug --organization-id <organizationId> --skill-slug <skillSlug>`}],output:{kind:`json`,description:`Read a skill by its stable slug`},transport:{type:`rest`,method:`GET`,path:`/v1/organizations/{organizationId}/skills/by-slug/{skillSlug}`,auth:`user`}},{id:`skills.list`,path:[`skills`,`list`],summary:`List organization skills`,description:``,source:`rest`,options:[{name:`organizationId`,flag:`--organization-id`,description:``,required:!0,valueType:`string`,location:`path`},{name:`tag`,flag:`--tag`,description:``,required:!1,valueType:`string`,location:`query`}],examples:[{description:`Example`,command:`adside skills list --organization-id <organizationId>`}],output:{kind:`json`,description:`List organization skills`},transport:{type:`rest`,method:`GET`,path:`/v1/organizations/{organizationId}/skills`,auth:`user`}},{id:`skills.templates`,path:[`skills`,`templates`],summary:`List active skill templates available to this organization`,description:``,source:`rest`,options:[{name:`organizationId`,flag:`--organization-id`,description:``,required:!0,valueType:`string`,location:`path`}],examples:[{description:`Example`,command:`adside skills templates --organization-id <organizationId>`}],output:{kind:`json`,description:`List active skill templates available to this organization`},transport:{type:`rest`,method:`GET`,path:`/v1/organizations/{organizationId}/skills/templates`,auth:`user`}},{id:`skills.update`,path:[`skills`,`update`],summary:`Edit a skill`,description:``,source:`rest`,options:[{name:`organizationId`,flag:`--organization-id`,description:``,required:!0,valueType:`string`,location:`path`},{name:`skillId`,flag:`--skill-id`,description:``,required:!0,valueType:`string`,location:`path`},{name:`name`,flag:`--name`,description:``,required:!1,valueType:`string`,location:`body`},{name:`slug`,flag:`--slug`,description:``,required:!1,valueType:`string`,location:`body`},{name:`description`,flag:`--description`,description:``,required:!1,valueType:`string`,location:`body`},{name:`thumbnailUrl`,flag:`--thumbnail-url`,description:``,required:!1,valueType:`url`,location:`body`},{name:`content`,flag:`--content`,description:``,required:!1,valueType:`string`,location:`body`},{name:`tags`,flag:`--tags`,description:``,required:!1,valueType:`json`,location:`body`}],examples:[{description:`Example`,command:`adside skills update --organization-id <organizationId> --skill-id <skillId>`}],output:{kind:`json`,description:`Edit a skill`},transport:{type:`rest`,method:`PATCH`,path:`/v1/organizations/{organizationId}/skills/{skillId}`,auth:`user`,requestContentType:`application/json`}},{id:`snapchat.get_ad_account`,path:[`snapchat`,`ad-accounts`,`get`],summary:`Get the Snapchat ad account this client is connected to — name, status, currency, timezone, and your role on it. There is no 'list ad accounts' tool: a client has exactly one connected Snapchat ad account, and this returns it.`,description:``,source:`rest`,options:[{name:`workspaceId`,flag:`--workspace-id`,description:``,required:!0,valueType:`string`,location:`path`},{name:`ad_account_id`,flag:`--ad-account-id`,description:`Omit it: it defaults to the ad account this client is connected to, and any other account is refused.`,required:!1,valueType:`string`,location:`body`}],examples:[{description:`Example`,command:`adside snapchat ad-accounts get --workspace-id <workspaceId>`}],output:{kind:`json`,description:`Get the Snapchat ad account this client is connected to — name, status, currency, timezone, and your role on it. There is no 'list ad accounts' tool: a client has exactly one connected Snapchat ad account, and this returns it.`},transport:{type:`rest`,method:`POST`,path:`/v1/workspaces/{workspaceId}/snapchat/ad-accounts/get`,auth:`user`,requestContentType:`application/json`}},{id:`snapchat.get_ad_squad`,path:[`snapchat`,`ad-squad`,`get`],summary:`Get a single Snapchat ad squad by id.`,description:``,source:`rest`,options:[{name:`workspaceId`,flag:`--workspace-id`,description:``,required:!0,valueType:`string`,location:`path`},{name:`ad_squad_id`,flag:`--ad-squad-id`,description:`Ad squad id (UUID) to fetch`,required:!0,valueType:`string`,location:`body`}],examples:[{description:`Example`,command:`adside snapchat ad-squad get --workspace-id <workspaceId> --ad-squad-id <ad_squad_id>`}],output:{kind:`json`,description:`Get a single Snapchat ad squad by id.`},transport:{type:`rest`,method:`POST`,path:`/v1/workspaces/{workspaceId}/snapchat/ad-squad/get`,auth:`user`,requestContentType:`application/json`}},{id:`snapchat.list_ad_squads`,path:[`snapchat`,`ad-squads`,`list`],summary:`List Snapchat ad squads for this client's ad account, optionally filtered by campaign or status.`,description:``,source:`rest`,options:[{name:`workspaceId`,flag:`--workspace-id`,description:``,required:!0,valueType:`string`,location:`path`},{name:`ad_account_id`,flag:`--ad-account-id`,description:`Omit it: it defaults to the ad account this client is connected to, and any other account is refused.`,required:!1,valueType:`string`,location:`body`},{name:`campaign_id`,flag:`--campaign-id`,description:`Filter to ad squads under this campaign`,required:!1,valueType:`string`,location:`body`},{name:`status`,flag:`--status`,description:``,required:!1,valueType:`string`,enum:[`ACTIVE`,`PAUSED`],location:`body`},{name:`limit`,flag:`--limit`,description:``,required:!1,valueType:`number`,defaultValue:200,location:`body`}],examples:[{description:`Example`,command:`adside snapchat ad-squads list --workspace-id <workspaceId>`}],output:{kind:`json`,description:`List Snapchat ad squads for this client's ad account, optionally filtered by campaign or status.`},transport:{type:`rest`,method:`POST`,path:`/v1/workspaces/{workspaceId}/snapchat/ad-squads/list`,auth:`user`,requestContentType:`application/json`}},{id:`snapchat.get_ad`,path:[`snapchat`,`ads`,`get`],summary:`Get a single Snapchat ad by id.`,description:``,source:`rest`,options:[{name:`workspaceId`,flag:`--workspace-id`,description:``,required:!0,valueType:`string`,location:`path`},{name:`ad_id`,flag:`--ad-id`,description:`Ad id (UUID) to fetch`,required:!0,valueType:`string`,location:`body`}],examples:[{description:`Example`,command:`adside snapchat ads get --workspace-id <workspaceId> --ad-id <ad_id>`}],output:{kind:`json`,description:`Get a single Snapchat ad by id.`},transport:{type:`rest`,method:`POST`,path:`/v1/workspaces/{workspaceId}/snapchat/ads/get`,auth:`user`,requestContentType:`application/json`}},{id:`snapchat.list_ads`,path:[`snapchat`,`ads`,`list`],summary:`List Snapchat ads for this client's ad account, optionally filtered by ad squad or status.`,description:``,source:`rest`,options:[{name:`workspaceId`,flag:`--workspace-id`,description:``,required:!0,valueType:`string`,location:`path`},{name:`ad_account_id`,flag:`--ad-account-id`,description:`Omit it: it defaults to the ad account this client is connected to, and any other account is refused.`,required:!1,valueType:`string`,location:`body`},{name:`ad_squad_id`,flag:`--ad-squad-id`,description:`Filter to ads under this ad squad`,required:!1,valueType:`string`,location:`body`},{name:`status`,flag:`--status`,description:``,required:!1,valueType:`string`,enum:[`ACTIVE`,`PAUSED`],location:`body`},{name:`limit`,flag:`--limit`,description:``,required:!1,valueType:`number`,defaultValue:200,location:`body`}],examples:[{description:`Example`,command:`adside snapchat ads list --workspace-id <workspaceId>`}],output:{kind:`json`,description:`List Snapchat ads for this client's ad account, optionally filtered by ad squad or status.`},transport:{type:`rest`,method:`POST`,path:`/v1/workspaces/{workspaceId}/snapchat/ads/list`,auth:`user`,requestContentType:`application/json`}},{id:`snapchat.get_campaign`,path:[`snapchat`,`campaigns`,`get`],summary:`Get a single Snapchat campaign by id.`,description:``,source:`rest`,options:[{name:`workspaceId`,flag:`--workspace-id`,description:``,required:!0,valueType:`string`,location:`path`},{name:`campaign_id`,flag:`--campaign-id`,description:`Campaign id (UUID) to fetch`,required:!0,valueType:`string`,location:`body`}],examples:[{description:`Example`,command:`adside snapchat campaigns get --workspace-id <workspaceId> --campaign-id <campaign_id>`}],output:{kind:`json`,description:`Get a single Snapchat campaign by id.`},transport:{type:`rest`,method:`POST`,path:`/v1/workspaces/{workspaceId}/snapchat/campaigns/get`,auth:`user`,requestContentType:`application/json`}},{id:`snapchat.list_campaigns`,path:[`snapchat`,`campaigns`,`list`],summary:`List Snapchat ad campaigns for this client's ad account, optionally filtered by status.`,description:``,source:`rest`,options:[{name:`workspaceId`,flag:`--workspace-id`,description:``,required:!0,valueType:`string`,location:`path`},{name:`ad_account_id`,flag:`--ad-account-id`,description:`Omit it: it defaults to the ad account this client is connected to, and any other account is refused.`,required:!1,valueType:`string`,location:`body`},{name:`status`,flag:`--status`,description:`Filter to campaigns in this status`,required:!1,valueType:`string`,enum:[`ACTIVE`,`PAUSED`],location:`body`},{name:`limit`,flag:`--limit`,description:``,required:!1,valueType:`number`,defaultValue:200,location:`body`}],examples:[{description:`Example`,command:`adside snapchat campaigns list --workspace-id <workspaceId>`}],output:{kind:`json`,description:`List Snapchat ad campaigns for this client's ad account, optionally filtered by status.`},transport:{type:`rest`,method:`POST`,path:`/v1/workspaces/{workspaceId}/snapchat/campaigns/list`,auth:`user`,requestContentType:`application/json`}},{id:`snapchat.get_creative_preview`,path:[`snapchat`,`creative-preview`,`get`],summary:`Get a 90-day signed preview link for a Snapchat creative — no login required. Use this to show what the ad looks like.`,description:``,source:`rest`,options:[{name:`workspaceId`,flag:`--workspace-id`,description:``,required:!0,valueType:`string`,location:`path`},{name:`creative_id`,flag:`--creative-id`,description:`Creative id (UUID) to preview`,required:!0,valueType:`string`,location:`body`}],examples:[{description:`Example`,command:`adside snapchat creative-preview get --workspace-id <workspaceId> --creative-id <creative_id>`}],output:{kind:`json`,description:`Get a 90-day signed preview link for a Snapchat creative — no login required. Use this to show what the ad looks like.`},transport:{type:`rest`,method:`POST`,path:`/v1/workspaces/{workspaceId}/snapchat/creative-preview/get`,auth:`user`,requestContentType:`application/json`}},{id:`snapchat.get_creative`,path:[`snapchat`,`creatives`,`get`],summary:`Get a single Snapchat creative by id, including its derived destination URL (web_view_properties.url, deep_link_properties.deep_link_uri, or the app-store id, depending on creative type).`,description:``,source:`rest`,options:[{name:`workspaceId`,flag:`--workspace-id`,description:``,required:!0,valueType:`string`,location:`path`},{name:`creative_id`,flag:`--creative-id`,description:`Creative id (UUID) to fetch`,required:!0,valueType:`string`,location:`body`}],examples:[{description:`Example`,command:`adside snapchat creatives get --workspace-id <workspaceId> --creative-id <creative_id>`}],output:{kind:`json`,description:`Get a single Snapchat creative by id, including its derived destination URL (web_view_properties.url, deep_link_properties.deep_link_uri, or the app-store id, depending on creative type).`},transport:{type:`rest`,method:`POST`,path:`/v1/workspaces/{workspaceId}/snapchat/creatives/get`,auth:`user`,requestContentType:`application/json`}},{id:`snapchat.list_creatives`,path:[`snapchat`,`creatives`,`list`],summary:`List Snapchat creatives for this client's ad account, optionally filtered by type or review status. Each creative's destination URL (where the ad points) is derived from its type-specific properties and included.`,description:``,source:`rest`,options:[{name:`workspaceId`,flag:`--workspace-id`,description:``,required:!0,valueType:`string`,location:`path`},{name:`ad_account_id`,flag:`--ad-account-id`,description:`Omit it: it defaults to the ad account this client is connected to, and any other account is refused.`,required:!1,valueType:`string`,location:`body`},{name:`type`,flag:`--type`,description:`Filter by creative type, e.g. WEB_VIEW`,required:!1,valueType:`string`,location:`body`},{name:`review_status`,flag:`--review-status`,description:``,required:!1,valueType:`string`,enum:[`PENDING_REVIEW`,`APPROVED`,`DISAPPROVED`],location:`body`},{name:`limit`,flag:`--limit`,description:``,required:!1,valueType:`number`,defaultValue:200,location:`body`}],examples:[{description:`Example`,command:`adside snapchat creatives list --workspace-id <workspaceId>`}],output:{kind:`json`,description:`List Snapchat creatives for this client's ad account, optionally filtered by type or review status. Each creative's destination URL (where the ad points) is derived from its type-specific properties and included.`},transport:{type:`rest`,method:`POST`,path:`/v1/workspaces/{workspaceId}/snapchat/creatives/list`,auth:`user`,requestContentType:`application/json`}},{id:`snapchat.list_media`,path:[`snapchat`,`media`,`list`],summary:`List media (uploaded images/videos) on this client's ad account.`,description:``,source:`rest`,options:[{name:`workspaceId`,flag:`--workspace-id`,description:``,required:!0,valueType:`string`,location:`path`},{name:`ad_account_id`,flag:`--ad-account-id`,description:`Omit it: it defaults to the ad account this client is connected to, and any other account is refused.`,required:!1,valueType:`string`,location:`body`},{name:`type`,flag:`--type`,description:`Filter by media type`,required:!1,valueType:`string`,enum:[`VIDEO`,`IMAGE`,`LENS_PACKAGE`,`PLAYABLE`],location:`body`},{name:`limit`,flag:`--limit`,description:``,required:!1,valueType:`number`,defaultValue:200,location:`body`}],examples:[{description:`Example`,command:`adside snapchat media list --workspace-id <workspaceId>`}],output:{kind:`json`,description:`List media (uploaded images/videos) on this client's ad account.`},transport:{type:`rest`,method:`POST`,path:`/v1/workspaces/{workspaceId}/snapchat/media/list`,auth:`user`,requestContentType:`application/json`}},{id:`snapchat.list_pixels`,path:[`snapchat`,`pixels`,`list`],summary:"List the Snap Pixels configured on this client's ad account — use the pixel id as `pixel_id` targeting on ad squads, or to look up conversion events.",description:``,source:`rest`,options:[{name:`workspaceId`,flag:`--workspace-id`,description:``,required:!0,valueType:`string`,location:`path`},{name:`ad_account_id`,flag:`--ad-account-id`,description:`Omit it: it defaults to the ad account this client is connected to, and any other account is refused.`,required:!1,valueType:`string`,location:`body`}],examples:[{description:`Example`,command:`adside snapchat pixels list --workspace-id <workspaceId>`}],output:{kind:`json`,description:"List the Snap Pixels configured on this client's ad account — use the pixel id as `pixel_id` targeting on ad squads, or to look up conversion events."},transport:{type:`rest`,method:`POST`,path:`/v1/workspaces/{workspaceId}/snapchat/pixels/list`,auth:`user`,requestContentType:`application/json`}},{id:`snapchat.get_stats`,path:[`snapchat`,`stats`,`get`],summary:"Get Snapchat delivery/reach/conversion stats for an ad account, campaign, ad squad, or ad. `spend` and every `*_value` conversion metric are returned already converted from Snapchat's micro-currency to the ad account's normal currency units (÷ 1,000,000).",description:``,source:`rest`,options:[{name:`workspaceId`,flag:`--workspace-id`,description:``,required:!0,valueType:`string`,location:`path`},{name:`entity_level`,flag:`--entity-level`,description:`Which level of the hierarchy to pull stats for`,required:!0,valueType:`string`,enum:[`adaccount`,`campaign`,`adsquad`,`ad`],location:`body`},{name:`entity_id`,flag:`--entity-id`,description:`Required for campaign/adsquad/ad. For adaccount, omit it: it defaults to the ad account this client is connected to, and any other account is refused.`,required:!1,valueType:`string`,location:`body`},{name:`granularity`,flag:`--granularity`,description:`DAY needs start_time/end_time within 31 days; HOUR within 7 days; TOTAL/LIFETIME need no date range (LIFETIME is finalized-only data).`,required:!1,valueType:`string`,defaultValue:`DAY`,enum:[`TOTAL`,`DAY`,`HOUR`,`LIFETIME`],location:`body`},{name:`breakdown`,flag:`--breakdown`,description:`One call per parent: 'ad' at any level, 'adsquad' on a campaign, 'campaign' on an ad account.`,required:!1,valueType:`string`,enum:[`ad`,`adsquad`,`campaign`],location:`body`},{name:`fields`,flag:`--fields`,description:`Metric names, e.g. impressions, swipes, spend, video_views_5s`,required:!1,valueType:`json`,location:`body`},{name:`start_time`,flag:`--start-time`,description:`ISO 8601, required for DAY/HOUR granularity`,required:!1,valueType:`string`,location:`body`},{name:`end_time`,flag:`--end-time`,description:`ISO 8601, required for DAY/HOUR granularity`,required:!1,valueType:`string`,location:`body`},{name:`dimension`,flag:`--dimension`,description:`Insights breakdown dimension (DAY/TOTAL/LIFETIME only)`,required:!1,valueType:`string`,enum:[`GEO`,`DEMO`,`INTEREST`,`DEVICE`],location:`body`},{name:`pivot`,flag:`--pivot`,description:`Pivot fields for the chosen dimension, e.g. gender,age_bucket for DEMO`,required:!1,valueType:`json`,location:`body`},{name:`swipe_up_attribution_window`,flag:`--swipe-up-attribution-window`,description:`Default 28_DAY`,required:!1,valueType:`string`,enum:[`1_DAY`,`7_DAY`,`28_DAY`],location:`body`},{name:`view_attribution_window`,flag:`--view-attribution-window`,description:`Default 1_DAY`,required:!1,valueType:`string`,enum:[`none`,`1_HOUR`,`3_HOUR`,`6_HOUR`,`1_DAY`,`7_DAY`],location:`body`}],examples:[{description:`Example`,command:`adside snapchat stats get --workspace-id <workspaceId> --entity-level adaccount`}],output:{kind:`json`,description:"Get Snapchat delivery/reach/conversion stats for an ad account, campaign, ad squad, or ad. `spend` and every `*_value` conversion metric are returned already converted from Snapchat's micro-currency to the ad account's normal currency units (÷ 1,000,000)."},transport:{type:`rest`,method:`POST`,path:`/v1/workspaces/{workspaceId}/snapchat/stats/get`,auth:`user`,requestContentType:`application/json`}},{id:`tiktok.get_action_categories`,path:[`tiktok`,`action-categories`,`get`],summary:`List TikTok behavior/action categories for targeting (user actions on TikTok)`,description:``,source:`rest`,options:[{name:`workspaceId`,flag:`--workspace-id`,description:``,required:!0,valueType:`string`,location:`path`},{name:`advertiser_id`,flag:`--advertiser-id`,description:`Omit it: it defaults to the advertiser this client is connected to, and any other advertiser is refused.`,required:!1,valueType:`string`,location:`body`},{name:`language`,flag:`--language`,description:`Language code`,required:!1,valueType:`string`,defaultValue:`en`,location:`body`}],examples:[{description:`Example`,command:`adside tiktok action-categories get --workspace-id <workspaceId>`}],output:{kind:`json`,description:`List TikTok behavior/action categories for targeting (user actions on TikTok)`},transport:{type:`rest`,method:`POST`,path:`/v1/workspaces/{workspaceId}/tiktok/action-categories/get`,auth:`user`,requestContentType:`application/json`}},{id:`tiktok.list_ad_groups`,path:[`tiktok`,`ad-groups`,`list`],summary:`List TikTok ad groups with optional filtering`,description:``,source:`rest`,options:[{name:`workspaceId`,flag:`--workspace-id`,description:``,required:!0,valueType:`string`,location:`path`},{name:`advertiser_id`,flag:`--advertiser-id`,description:`Omit it: it defaults to the advertiser this client is connected to, and any other advertiser is refused.`,required:!1,valueType:`string`,location:`body`},{name:`adgroup_ids`,flag:`--adgroup-ids`,description:`Filter by ad group IDs`,required:!1,valueType:`json`,location:`body`},{name:`campaign_ids`,flag:`--campaign-ids`,description:`Filter by parent campaign IDs`,required:!1,valueType:`json`,location:`body`},{name:`filtering`,flag:`--filtering`,description:``,required:!1,valueType:`json`,location:`body`},{name:`page`,flag:`--page`,description:``,required:!1,valueType:`number`,defaultValue:1,location:`body`},{name:`page_size`,flag:`--page-size`,description:``,required:!1,valueType:`number`,defaultValue:100,location:`body`}],examples:[{description:`Example`,command:`adside tiktok ad-groups list --workspace-id <workspaceId>`}],output:{kind:`json`,description:`List TikTok ad groups with optional filtering`},transport:{type:`rest`,method:`POST`,path:`/v1/workspaces/{workspaceId}/tiktok/ad-groups/list`,auth:`user`,requestContentType:`application/json`}},{id:`tiktok.list_ads`,path:[`tiktok`,`ads`,`list`],summary:`List TikTok ads with optional filtering by ad group, campaign, or status`,description:``,source:`rest`,options:[{name:`workspaceId`,flag:`--workspace-id`,description:``,required:!0,valueType:`string`,location:`path`},{name:`advertiser_id`,flag:`--advertiser-id`,description:`Omit it: it defaults to the advertiser this client is connected to, and any other advertiser is refused.`,required:!1,valueType:`string`,location:`body`},{name:`ad_ids`,flag:`--ad-ids`,description:`Filter by ad IDs`,required:!1,valueType:`json`,location:`body`},{name:`adgroup_ids`,flag:`--adgroup-ids`,description:`Filter by ad group IDs`,required:!1,valueType:`json`,location:`body`},{name:`campaign_ids`,flag:`--campaign-ids`,description:`Filter by campaign IDs`,required:!1,valueType:`json`,location:`body`},{name:`filtering`,flag:`--filtering`,description:``,required:!1,valueType:`json`,location:`body`},{name:`page`,flag:`--page`,description:``,required:!1,valueType:`number`,defaultValue:1,location:`body`},{name:`page_size`,flag:`--page-size`,description:``,required:!1,valueType:`number`,defaultValue:100,location:`body`}],examples:[{description:`Example`,command:`adside tiktok ads list --workspace-id <workspaceId>`}],output:{kind:`json`,description:`List TikTok ads with optional filtering by ad group, campaign, or status`},transport:{type:`rest`,method:`POST`,path:`/v1/workspaces/{workspaceId}/tiktok/ads/list`,auth:`user`,requestContentType:`application/json`}},{id:`tiktok.get_advertiser_info`,path:[`tiktok`,`advertiser-info`,`get`],summary:`Get TikTok advertiser account details (name, status, currency, timezone, balance)`,description:``,source:`rest`,options:[{name:`workspaceId`,flag:`--workspace-id`,description:``,required:!0,valueType:`string`,location:`path`},{name:`advertiser_id`,flag:`--advertiser-id`,description:`Omit it: it defaults to the advertiser this client is connected to, and any other advertiser is refused.`,required:!1,valueType:`string`,location:`body`}],examples:[{description:`Example`,command:`adside tiktok advertiser-info get --workspace-id <workspaceId>`}],output:{kind:`json`,description:`Get TikTok advertiser account details (name, status, currency, timezone, balance)`},transport:{type:`rest`,method:`POST`,path:`/v1/workspaces/{workspaceId}/tiktok/advertiser-info/get`,auth:`user`,requestContentType:`application/json`}},{id:`tiktok.list_advertisers`,path:[`tiktok`,`advertisers`,`list`],summary:`List the TikTok advertiser account this client is connected to. Always returns that one account — other advertisers the credentials can reach belong to other clients and are not available here.`,description:``,source:`rest`,options:[{name:`workspaceId`,flag:`--workspace-id`,description:``,required:!0,valueType:`string`,location:`path`}],examples:[{description:`Example`,command:`adside tiktok advertisers list --workspace-id <workspaceId>`}],output:{kind:`json`,description:`List the TikTok advertiser account this client is connected to. Always returns that one account — other advertisers the credentials can reach belong to other clients and are not available here.`},transport:{type:`rest`,method:`POST`,path:`/v1/workspaces/{workspaceId}/tiktok/advertisers/list`,auth:`user`}},{id:`tiktok.get_audience_report`,path:[`tiktok`,`audience-report`,`get`],summary:`Get TikTok audience demographic breakdown (age, gender, country, OS, language)`,description:``,source:`rest`,options:[{name:`workspaceId`,flag:`--workspace-id`,description:``,required:!0,valueType:`string`,location:`path`},{name:`advertiser_id`,flag:`--advertiser-id`,description:`Omit it: it defaults to the advertiser this client is connected to, and any other advertiser is refused.`,required:!1,valueType:`string`,location:`body`},{name:`data_level`,flag:`--data-level`,description:``,required:!1,valueType:`string`,defaultValue:`AUCTION_CAMPAIGN`,enum:[`AUCTION_CAMPAIGN`,`AUCTION_ADGROUP`,`AUCTION_AD`],location:`body`},{name:`dimensions`,flag:`--dimensions`,description:`Audience dimensions: gender, age, country_code, ac (Android/iOS), language`,required:!1,valueType:`json`,location:`body`},{name:`metrics`,flag:`--metrics`,description:`Metrics to include`,required:!1,valueType:`json`,location:`body`},{name:`start_date`,flag:`--start-date`,description:`Start date (YYYY-MM-DD)`,required:!0,valueType:`string`,location:`body`},{name:`end_date`,flag:`--end-date`,description:`End date (YYYY-MM-DD)`,required:!0,valueType:`string`,location:`body`},{name:`filters`,flag:`--filters`,description:``,required:!1,valueType:`json`,location:`body`},{name:`page`,flag:`--page`,description:``,required:!1,valueType:`number`,defaultValue:1,location:`body`},{name:`page_size`,flag:`--page-size`,description:``,required:!1,valueType:`number`,defaultValue:100,location:`body`}],examples:[{description:`Example`,command:`adside tiktok audience-report get --workspace-id <workspaceId> --start-date <start_date> --end-date <end_date>`}],output:{kind:`json`,description:`Get TikTok audience demographic breakdown (age, gender, country, OS, language)`},transport:{type:`rest`,method:`POST`,path:`/v1/workspaces/{workspaceId}/tiktok/audience-report/get`,auth:`user`,requestContentType:`application/json`}},{id:`tiktok.list_campaigns`,path:[`tiktok`,`campaigns`,`list`],summary:`List TikTok ad campaigns with optional filtering by name, objective, status. Returns paginated results.`,description:``,source:`rest`,options:[{name:`workspaceId`,flag:`--workspace-id`,description:``,required:!0,valueType:`string`,location:`path`},{name:`advertiser_id`,flag:`--advertiser-id`,description:`Omit it: it defaults to the advertiser this client is connected to, and any other advertiser is refused.`,required:!1,valueType:`string`,location:`body`},{name:`campaign_ids`,flag:`--campaign-ids`,description:`Filter by specific campaign IDs`,required:!1,valueType:`json`,location:`body`},{name:`filtering`,flag:`--filtering`,description:``,required:!1,valueType:`json`,location:`body`},{name:`page`,flag:`--page`,description:``,required:!1,valueType:`number`,defaultValue:1,location:`body`},{name:`page_size`,flag:`--page-size`,description:``,required:!1,valueType:`number`,defaultValue:100,location:`body`}],examples:[{description:`Example`,command:`adside tiktok campaigns list --workspace-id <workspaceId>`}],output:{kind:`json`,description:`List TikTok ad campaigns with optional filtering by name, objective, status. Returns paginated results.`},transport:{type:`rest`,method:`POST`,path:`/v1/workspaces/{workspaceId}/tiktok/campaigns/list`,auth:`user`,requestContentType:`application/json`}},{id:`tiktok.get_identities`,path:[`tiktok`,`identities`,`get`],summary:`List available TikTok identities for ad creation. An identity is required as the ad author.`,description:``,source:`rest`,options:[{name:`workspaceId`,flag:`--workspace-id`,description:``,required:!0,valueType:`string`,location:`path`},{name:`advertiser_id`,flag:`--advertiser-id`,description:`Omit it: it defaults to the advertiser this client is connected to, and any other advertiser is refused.`,required:!1,valueType:`string`,location:`body`},{name:`identity_type`,flag:`--identity-type`,description:`Filter by identity type`,required:!1,valueType:`string`,enum:[`CUSTOMIZED_USER`,`AUTH_CODE`,`TT_USER`,`BC_AUTH_TT`],location:`body`}],examples:[{description:`Example`,command:`adside tiktok identities get --workspace-id <workspaceId>`}],output:{kind:`json`,description:`List available TikTok identities for ad creation. An identity is required as the ad author.`},transport:{type:`rest`,method:`POST`,path:`/v1/workspaces/{workspaceId}/tiktok/identities/get`,auth:`user`,requestContentType:`application/json`}},{id:`tiktok.get_image_info`,path:[`tiktok`,`image-info`,`get`],summary:`Get TikTok image details (dimensions, format, URL)`,description:``,source:`rest`,options:[{name:`workspaceId`,flag:`--workspace-id`,description:``,required:!0,valueType:`string`,location:`path`},{name:`advertiser_id`,flag:`--advertiser-id`,description:`Omit it: it defaults to the advertiser this client is connected to, and any other advertiser is refused.`,required:!1,valueType:`string`,location:`body`},{name:`image_ids`,flag:`--image-ids`,description:`Image IDs to get info for`,required:!0,valueType:`json`,location:`body`}],examples:[{description:`Example`,command:`adside tiktok image-info get --workspace-id <workspaceId> --image-ids '{}'`}],output:{kind:`json`,description:`Get TikTok image details (dimensions, format, URL)`},transport:{type:`rest`,method:`POST`,path:`/v1/workspaces/{workspaceId}/tiktok/image-info/get`,auth:`user`,requestContentType:`application/json`}},{id:`tiktok.get_interest_categories`,path:[`tiktok`,`interest-categories`,`get`],summary:`List all TikTok interest category tree for browsing (not keyword search). Returns hierarchical categories with IDs.`,description:``,source:`rest`,options:[{name:`workspaceId`,flag:`--workspace-id`,description:``,required:!0,valueType:`string`,location:`path`},{name:`advertiser_id`,flag:`--advertiser-id`,description:`Omit it: it defaults to the advertiser this client is connected to, and any other advertiser is refused.`,required:!1,valueType:`string`,location:`body`},{name:`language`,flag:`--language`,description:`Language code for category names`,required:!1,valueType:`string`,defaultValue:`en`,location:`body`}],examples:[{description:`Example`,command:`adside tiktok interest-categories get --workspace-id <workspaceId>`}],output:{kind:`json`,description:`List all TikTok interest category tree for browsing (not keyword search). Returns hierarchical categories with IDs.`},transport:{type:`rest`,method:`POST`,path:`/v1/workspaces/{workspaceId}/tiktok/interest-categories/get`,auth:`user`,requestContentType:`application/json`}},{id:`tiktok.search_interest_categories`,path:[`tiktok`,`interest-categories`,`search`],summary:`Search TikTok interest categories by keyword for targeting. Returns interest IDs to use in ad group targeting.`,description:``,source:`rest`,options:[{name:`workspaceId`,flag:`--workspace-id`,description:``,required:!0,valueType:`string`,location:`path`},{name:`advertiser_id`,flag:`--advertiser-id`,description:`Omit it: it defaults to the advertiser this client is connected to, and any other advertiser is refused.`,required:!1,valueType:`string`,location:`body`},{name:`keyword`,flag:`--keyword`,description:`Search keyword for interest targeting`,required:!0,valueType:`string`,location:`body`},{name:`language`,flag:`--language`,description:`Language code for results`,required:!1,valueType:`string`,defaultValue:`en`,location:`body`}],examples:[{description:`Example`,command:`adside tiktok interest-categories search --workspace-id <workspaceId> --keyword <keyword>`}],output:{kind:`json`,description:`Search TikTok interest categories by keyword for targeting. Returns interest IDs to use in ad group targeting.`},transport:{type:`rest`,method:`POST`,path:`/v1/workspaces/{workspaceId}/tiktok/interest-categories/search`,auth:`user`,requestContentType:`application/json`}},{id:`tiktok.search_locations`,path:[`tiktok`,`locations`,`search`],summary:`Search TikTok targeting locations by keyword. Returns location IDs for use in ad group targeting.`,description:``,source:`rest`,options:[{name:`workspaceId`,flag:`--workspace-id`,description:``,required:!0,valueType:`string`,location:`path`},{name:`advertiser_id`,flag:`--advertiser-id`,description:`Omit it: it defaults to the advertiser this client is connected to, and any other advertiser is refused.`,required:!1,valueType:`string`,location:`body`},{name:`keyword`,flag:`--keyword`,description:`Location name to search`,required:!0,valueType:`string`,location:`body`},{name:`level`,flag:`--level`,description:`Location level to search`,required:!1,valueType:`string`,enum:[`COUNTRY`,`PROVINCE`,`CITY`,`DMA`],location:`body`},{name:`language`,flag:`--language`,description:``,required:!1,valueType:`string`,defaultValue:`en`,location:`body`}],examples:[{description:`Example`,command:`adside tiktok locations search --workspace-id <workspaceId> --keyword <keyword>`}],output:{kind:`json`,description:`Search TikTok targeting locations by keyword. Returns location IDs for use in ad group targeting.`},transport:{type:`rest`,method:`POST`,path:`/v1/workspaces/{workspaceId}/tiktok/locations/search`,auth:`user`,requestContentType:`application/json`}},{id:`tiktok.get_report`,path:[`tiktok`,`report`,`get`],summary:`Get TikTok integrated reporting with dimensions, metrics, date range, and filters. Supports campaign/ad group/ad level.`,description:``,source:`rest`,options:[{name:`workspaceId`,flag:`--workspace-id`,description:``,required:!0,valueType:`string`,location:`path`},{name:`advertiser_id`,flag:`--advertiser-id`,description:`Omit it: it defaults to the advertiser this client is connected to, and any other advertiser is refused.`,required:!1,valueType:`string`,location:`body`},{name:`report_type`,flag:`--report-type`,description:`BASIC = standard metrics, AUDIENCE = demographic breakdown`,required:!1,valueType:`string`,defaultValue:`BASIC`,enum:[`BASIC`,`AUDIENCE`,`PLAYABLE_MATERIAL`,`CATALOG`],location:`body`},{name:`data_level`,flag:`--data-level`,description:`Reporting level`,required:!1,valueType:`string`,defaultValue:`AUCTION_CAMPAIGN`,enum:[`AUCTION_CAMPAIGN`,`AUCTION_ADGROUP`,`AUCTION_AD`],location:`body`},{name:`dimensions`,flag:`--dimensions`,description:`Grouping dimensions: campaign_id, adgroup_id, ad_id, stat_time_day, country_code, gender, age, etc.`,required:!1,valueType:`json`,location:`body`},{name:`metrics`,flag:`--metrics`,description:`Metrics: spend, impressions, clicks, conversions, ctr, cpc, cpm, reach, frequency, video_views_p25/p50/p75/p100`,required:!1,valueType:`json`,location:`body`},{name:`start_date`,flag:`--start-date`,description:`Start date (YYYY-MM-DD)`,required:!0,valueType:`string`,location:`body`},{name:`end_date`,flag:`--end-date`,description:`End date (YYYY-MM-DD)`,required:!0,valueType:`string`,location:`body`},{name:`filters`,flag:`--filters`,description:``,required:!1,valueType:`json`,location:`body`},{name:`page`,flag:`--page`,description:``,required:!1,valueType:`number`,defaultValue:1,location:`body`},{name:`page_size`,flag:`--page-size`,description:``,required:!1,valueType:`number`,defaultValue:100,location:`body`}],examples:[{description:`Example`,command:`adside tiktok report get --workspace-id <workspaceId> --start-date <start_date> --end-date <end_date>`}],output:{kind:`json`,description:`Get TikTok integrated reporting with dimensions, metrics, date range, and filters. Supports campaign/ad group/ad level.`},transport:{type:`rest`,method:`POST`,path:`/v1/workspaces/{workspaceId}/tiktok/report/get`,auth:`user`,requestContentType:`application/json`}},{id:`tiktok.get_video_info`,path:[`tiktok`,`video-info`,`get`],summary:`Get TikTok video processing status and details (duration, dimensions, format)`,description:``,source:`rest`,options:[{name:`workspaceId`,flag:`--workspace-id`,description:``,required:!0,valueType:`string`,location:`path`},{name:`advertiser_id`,flag:`--advertiser-id`,description:`Omit it: it defaults to the advertiser this client is connected to, and any other advertiser is refused.`,required:!1,valueType:`string`,location:`body`},{name:`video_ids`,flag:`--video-ids`,description:`Video IDs to get info for`,required:!0,valueType:`json`,location:`body`}],examples:[{description:`Example`,command:`adside tiktok video-info get --workspace-id <workspaceId> --video-ids '{}'`}],output:{kind:`json`,description:`Get TikTok video processing status and details (duration, dimensions, format)`},transport:{type:`rest`,method:`POST`,path:`/v1/workspaces/{workspaceId}/tiktok/video-info/get`,auth:`user`,requestContentType:`application/json`}},{id:`todos.assignees`,path:[`todos`,`assignees`],summary:`List eligible task assignees`,description:``,source:`rest`,options:[{name:`workspaceId`,flag:`--workspace-id`,description:``,required:!0,valueType:`string`,location:`path`}],examples:[{description:`Example`,command:`adside todos assignees --workspace-id <workspaceId>`}],output:{kind:`json`,description:`List eligible task assignees`},transport:{type:`rest`,method:`GET`,path:`/v1/workspaces/{workspaceId}/todos/assignees`,auth:`user`}},{id:`todos.create`,path:[`todos`,`create`],summary:`Create a task`,description:``,source:`rest`,options:[{name:`workspaceId`,flag:`--workspace-id`,description:``,required:!0,valueType:`string`,location:`path`},{name:`title`,flag:`--title`,description:``,required:!0,valueType:`string`,location:`body`},{name:`body`,flag:`--body`,description:``,required:!1,valueType:`string`,location:`body`},{name:`assigneeUserId`,flag:`--assignee-user-id`,description:``,required:!1,valueType:`string`,location:`body`},{name:`assigneeType`,flag:`--assignee-type`,description:``,required:!1,valueType:`string`,enum:[`AGENT`],location:`body`},{name:`dueDate`,flag:`--due-date`,description:``,required:!1,valueType:`string`,location:`body`}],examples:[{description:`Example`,command:`adside todos create --workspace-id <workspaceId> --title <title>`}],output:{kind:`json`,description:`Create a task`},transport:{type:`rest`,method:`POST`,path:`/v1/workspaces/{workspaceId}/todos`,auth:`user`,requestContentType:`application/json`}},{id:`todos.delete`,path:[`todos`,`delete`],summary:`Delete a task`,description:``,source:`rest`,options:[{name:`workspaceId`,flag:`--workspace-id`,description:``,required:!0,valueType:`string`,location:`path`},{name:`todoId`,flag:`--todo-id`,description:``,required:!0,valueType:`string`,location:`path`}],examples:[{description:`Example`,command:`adside todos delete --workspace-id <workspaceId> --todo-id <todoId>`}],output:{kind:`json`,description:`Delete a task`},transport:{type:`rest`,method:`DELETE`,path:`/v1/workspaces/{workspaceId}/todos/{todoId}`,auth:`user`}},{id:`todos.get`,path:[`todos`,`get`],summary:`Read a task`,description:``,source:`rest`,options:[{name:`workspaceId`,flag:`--workspace-id`,description:``,required:!0,valueType:`string`,location:`path`},{name:`todoId`,flag:`--todo-id`,description:``,required:!0,valueType:`string`,location:`path`}],examples:[{description:`Example`,command:`adside todos get --workspace-id <workspaceId> --todo-id <todoId>`}],output:{kind:`json`,description:`Read a task`},transport:{type:`rest`,method:`GET`,path:`/v1/workspaces/{workspaceId}/todos/{todoId}`,auth:`user`}},{id:`todos.list`,path:[`todos`,`list`],summary:`List tasks with assignee, status and due-date filters`,description:``,source:`rest`,options:[{name:`workspaceId`,flag:`--workspace-id`,description:``,required:!0,valueType:`string`,location:`path`},{name:`assignee`,flag:`--assignee`,description:``,required:!1,valueType:`string`,enum:[`agent`,`all`],location:`query`},{name:`status`,flag:`--status`,description:``,required:!1,valueType:`string`,enum:[`OPEN`,`DONE`,`CANCELLED`],location:`query`},{name:`assigneeUserId`,flag:`--assignee-user-id`,description:``,required:!1,valueType:`string`,location:`query`},{name:`source`,flag:`--source`,description:``,required:!1,valueType:`string`,enum:[`SLACK`,`WEB`,`CHAT`,`CALL`,`ONBOARDING`],location:`query`},{name:`unassigned`,flag:`--unassigned`,description:``,required:!1,valueType:`json`,location:`query`},{name:`dueFrom`,flag:`--due-from`,description:``,required:!1,valueType:`string`,location:`query`},{name:`dueTo`,flag:`--due-to`,description:``,required:!1,valueType:`string`,location:`query`},{name:`hasDueDate`,flag:`--has-due-date`,description:``,required:!1,valueType:`json`,location:`query`}],examples:[{description:`Example`,command:`adside todos list --workspace-id <workspaceId>`}],output:{kind:`json`,description:`List tasks with assignee, status and due-date filters`},transport:{type:`rest`,method:`GET`,path:`/v1/workspaces/{workspaceId}/todos`,auth:`user`}},{id:`todos.mine`,path:[`todos`,`mine`],summary:`List tasks assigned to the caller across their accessible workspaces`,description:``,source:`rest`,options:[{name:`organizationId`,flag:`--organization-id`,description:``,required:!0,valueType:`string`,location:`path`},{name:`status`,flag:`--status`,description:``,required:!1,valueType:`string`,enum:[`OPEN`,`DONE`,`CANCELLED`],location:`query`}],examples:[{description:`Example`,command:`adside todos mine --organization-id <organizationId>`}],output:{kind:`json`,description:`List tasks assigned to the caller across their accessible workspaces`},transport:{type:`rest`,method:`GET`,path:`/v1/organizations/{organizationId}/todos`,auth:`user`}},{id:`todos.update`,path:[`todos`,`update`],summary:`Edit a task or its status and assignee`,description:``,source:`rest`,options:[{name:`workspaceId`,flag:`--workspace-id`,description:``,required:!0,valueType:`string`,location:`path`},{name:`todoId`,flag:`--todo-id`,description:``,required:!0,valueType:`string`,location:`path`},{name:`title`,flag:`--title`,description:``,required:!1,valueType:`string`,location:`body`},{name:`body`,flag:`--body`,description:``,required:!1,valueType:`string`,location:`body`},{name:`assigneeUserId`,flag:`--assignee-user-id`,description:``,required:!1,valueType:`string`,location:`body`},{name:`dueDate`,flag:`--due-date`,description:``,required:!1,valueType:`string`,location:`body`},{name:`status`,flag:`--status`,description:``,required:!1,valueType:`string`,enum:[`OPEN`,`DONE`,`CANCELLED`],location:`body`}],examples:[{description:`Example`,command:`adside todos update --workspace-id <workspaceId> --todo-id <todoId>`}],output:{kind:`json`,description:`Edit a task or its status and assignee`},transport:{type:`rest`,method:`PATCH`,path:`/v1/workspaces/{workspaceId}/todos/{todoId}`,auth:`user`,requestContentType:`application/json`}},{id:`me.get`,path:[`whoami`],summary:`Read who is signed in, with their organizations and the workspaces they can open`,description:``,source:`rest`,options:[],examples:[{description:`Example`,command:`adside whoami`}],output:{kind:`json`,description:`Read who is signed in, with their organizations and the workspaces they can open`},transport:{type:`rest`,method:`GET`,path:`/v1/me`,auth:`user`}},{id:`workspace.connections`,path:[`workspace`,`connections`],summary:`Read client-safe connection summaries without provider credentials`,description:``,source:`rest`,options:[{name:`workspaceId`,flag:`--workspace-id`,description:``,required:!0,valueType:`string`,location:`path`},{name:`includeSync`,flag:`--include-sync`,description:``,required:!1,valueType:`string`,defaultValue:`false`,enum:[`false`,`true`],location:`query`}],examples:[{description:`Example`,command:`adside workspace connections --workspace-id <workspaceId>`}],output:{kind:`json`,description:`Read client-safe connection summaries without provider credentials`},transport:{type:`rest`,method:`GET`,path:`/v1/workspaces/{workspaceId}/connections`,auth:`user`}},{id:`x.get_x_account_history`,path:[`x`,`account-history`,`get`],summary:`The change log of one object on the connected account (X requires an entity_type and entity_id): who changed which field, old → new value, and when. Actors appear as X user ids; no handles or emails are returned.`,description:``,source:`rest`,options:[{name:`workspaceId`,flag:`--workspace-id`,description:``,required:!0,valueType:`string`,location:`path`},{name:`account_id`,flag:`--account-id`,description:`X ads account id (e.g. 18ce55xcrlv). Omit it: it defaults to the ads account this client is connected to, and any other account is refused.`,required:!1,valueType:`string`,location:`body`},{name:`entity_type`,flag:`--entity-type`,description:`Kind of object whose change log to read (X requires it).`,required:!0,valueType:`string`,enum:[`CAMPAIGN`,`LINE_ITEM`,`PROMOTED_TWEET`,`TARGETING_CRITERION`,`FUNDING_INSTRUMENT`,`PROMOTED_ACCOUNT`,`PROMOTED_TWEET_REVIEW`],location:`body`},{name:`entity_id`,flag:`--entity-id`,description:`The object's id (X requires it).`,required:!0,valueType:`string`,location:`body`},{name:`preset`,flag:`--preset`,description:`Shortcut for a date range. Default last_7d when no start_date/end_date given.`,required:!1,valueType:`string`,enum:[`today`,`yesterday`,`last_7d`,`last_14d`,`last_30d`,`this_month`,`last_month`],location:`body`},{name:`start_date`,flag:`--start-date`,description:`First day, YYYY-MM-DD, in the account's time zone.`,required:!1,valueType:`string`,location:`body`},{name:`end_date`,flag:`--end-date`,description:`Last day (inclusive), YYYY-MM-DD, in the account's time zone. The exclusive end X wants is computed for you.`,required:!1,valueType:`string`,location:`body`},{name:`user_id`,flag:`--user-id`,description:`Only changes made by this X user id.`,required:!1,valueType:`string`,location:`body`},{name:`limit`,flag:`--limit`,description:``,required:!1,valueType:`number`,defaultValue:100,location:`body`}],examples:[{description:`Example`,command:`adside x account-history get --workspace-id <workspaceId> --entity-type CAMPAIGN --entity-id <entity_id>`}],output:{kind:`json`,description:`The change log of one object on the connected account (X requires an entity_type and entity_id): who changed which field, old → new value, and when. Actors appear as X user ids; no handles or emails are returned.`},transport:{type:`rest`,method:`POST`,path:`/v1/workspaces/{workspaceId}/x/account-history/get`,auth:`user`,requestContentType:`application/json`}},{id:`x.get_x_account_overview`,path:[`x`,`account-overview`,`get`],summary:`Where the account stands: campaign / line item / promoted post counts by status and servability, spend, impressions and clicks for the last 7 days versus the 7 before, and the top 3 campaigns by spend. Costs up to 7 requests; use it before diving into individual campaigns.`,description:``,source:`rest`,options:[{name:`workspaceId`,flag:`--workspace-id`,description:``,required:!0,valueType:`string`,location:`path`},{name:`account_id`,flag:`--account-id`,description:`X ads account id (e.g. 18ce55xcrlv). Omit it: it defaults to the ads account this client is connected to, and any other account is refused.`,required:!1,valueType:`string`,location:`body`}],examples:[{description:`Example`,command:`adside x account-overview get --workspace-id <workspaceId>`}],output:{kind:`json`,description:`Where the account stands: campaign / line item / promoted post counts by status and servability, spend, impressions and clicks for the last 7 days versus the 7 before, and the top 3 campaigns by spend. Costs up to 7 requests; use it before diving into individual campaigns.`},transport:{type:`rest`,method:`POST`,path:`/v1/workspaces/{workspaceId}/x/account-overview/get`,auth:`user`,requestContentType:`application/json`}},{id:`x.list_x_account_posts`,path:[`x`,`account-posts`,`list`],summary:`Posts available to the connected account as ad creatives: nullcast (promoted-only) posts by default, or the handle's organic timeline, with text, media keys and card. A promoted post is one of these attached to a line item.`,description:``,source:`rest`,options:[{name:`workspaceId`,flag:`--workspace-id`,description:``,required:!0,valueType:`string`,location:`path`},{name:`account_id`,flag:`--account-id`,description:`X ads account id (e.g. 18ce55xcrlv). Omit it: it defaults to the ads account this client is connected to, and any other account is refused.`,required:!1,valueType:`string`,location:`body`},{name:`timeline_type`,flag:`--timeline-type`,description:`NULLCAST = promoted-only posts (the usual ad creatives); ORGANIC = the handle's public timeline.`,required:!1,valueType:`string`,defaultValue:`NULLCAST`,enum:[`NULLCAST`,`ORGANIC`,`ALL`],location:`body`},{name:`tweet_type`,flag:`--tweet-type`,description:``,required:!1,valueType:`string`,defaultValue:`PUBLISHED`,enum:[`PUBLISHED`,`SCHEDULED`,`DRAFT`],location:`body`},{name:`name_contains`,flag:`--name-contains`,description:`Substring of the post's internal name or text.`,required:!1,valueType:`string`,location:`body`},{name:`include_mentions_and_replies`,flag:`--include-mentions-and-replies`,description:``,required:!1,valueType:`boolean`,defaultValue:!1,location:`body`},{name:`limit`,flag:`--limit`,description:``,required:!1,valueType:`number`,defaultValue:50,location:`body`}],examples:[{description:`Example`,command:`adside x account-posts list --workspace-id <workspaceId>`}],output:{kind:`json`,description:`Posts available to the connected account as ad creatives: nullcast (promoted-only) posts by default, or the handle's organic timeline, with text, media keys and card. A promoted post is one of these attached to a line item.`},transport:{type:`rest`,method:`POST`,path:`/v1/workspaces/{workspaceId}/x/account-posts/list`,auth:`user`,requestContentType:`application/json`}},{id:`x.get_x_active_entities`,path:[`x`,`active-entities`,`get`],summary:`Which entities had any activity (impressions, spend) in a window of up to 90 days, with their activity window and the placements they ran on — the tool to run BEFORE a stats call so you only ask about ids that have data (X: 'you should not request analytics for IDs outside of this set').`,description:``,source:`rest`,options:[{name:`workspaceId`,flag:`--workspace-id`,description:``,required:!0,valueType:`string`,location:`path`},{name:`account_id`,flag:`--account-id`,description:`X ads account id (e.g. 18ce55xcrlv). Omit it: it defaults to the ads account this client is connected to, and any other account is refused.`,required:!1,valueType:`string`,location:`body`},{name:`entity`,flag:`--entity`,description:``,required:!1,valueType:`string`,defaultValue:`CAMPAIGN`,enum:[`CAMPAIGN`,`LINE_ITEM`,`PROMOTED_TWEET`,`FUNDING_INSTRUMENT`,`PROMOTED_ACCOUNT`,`MEDIA_CREATIVE`],location:`body`},{name:`preset`,flag:`--preset`,description:`Shortcut for a date range. Default last_7d when no start_date/end_date given.`,required:!1,valueType:`string`,enum:[`today`,`yesterday`,`last_7d`,`last_14d`,`last_30d`,`this_month`,`last_month`],location:`body`},{name:`start_date`,flag:`--start-date`,description:`First day, YYYY-MM-DD, in the account's time zone.`,required:!1,valueType:`string`,location:`body`},{name:`end_date`,flag:`--end-date`,description:`Last day (inclusive), YYYY-MM-DD, in the account's time zone. The exclusive end X wants is computed for you.`,required:!1,valueType:`string`,location:`body`},{name:`campaign_ids`,flag:`--campaign-ids`,description:`Only entities under these campaigns.`,required:!1,valueType:`json`,location:`body`},{name:`line_item_ids`,flag:`--line-item-ids`,description:`Only entities under these line items.`,required:!1,valueType:`json`,location:`body`}],examples:[{description:`Example`,command:`adside x active-entities get --workspace-id <workspaceId>`}],output:{kind:`json`,description:`Which entities had any activity (impressions, spend) in a window of up to 90 days, with their activity window and the placements they ran on — the tool to run BEFORE a stats call so you only ask about ids that have data (X: 'you should not request analytics for IDs outside of this set').`},transport:{type:`rest`,method:`POST`,path:`/v1/workspaces/{workspaceId}/x/active-entities/get`,auth:`user`,requestContentType:`application/json`}},{id:`x.get_x_ad_account`,path:[`x`,`ad-accounts`,`get`],summary:`The X ads account this client is connected to: approval state, time zone, currency, what the connected user's token may do on it (ACCOUNT_ADMIN / AD_MANAGER can write, ANALYST is read-only, TWEET_COMPOSER can author nullcast posts), enabled features, promotable users and funding instruments (and whether any can fund). There is no 'list ads accounts' tool — a client has exactly one connected X ads account. Costs 5 requests.`,description:``,source:`rest`,options:[{name:`workspaceId`,flag:`--workspace-id`,description:``,required:!0,valueType:`string`,location:`path`},{name:`account_id`,flag:`--account-id`,description:`X ads account id (e.g. 18ce55xcrlv). Omit it: it defaults to the ads account this client is connected to, and any other account is refused.`,required:!1,valueType:`string`,location:`body`}],examples:[{description:`Example`,command:`adside x ad-accounts get --workspace-id <workspaceId>`}],output:{kind:`json`,description:`The X ads account this client is connected to: approval state, time zone, currency, what the connected user's token may do on it (ACCOUNT_ADMIN / AD_MANAGER can write, ANALYST is read-only, TWEET_COMPOSER can author nullcast posts), enabled features, promotable users and funding instruments (and whether any can fund). There is no 'list ads accounts' tool — a client has exactly one connected X ads account. Costs 5 requests.`},transport:{type:`rest`,method:`POST`,path:`/v1/workspaces/{workspaceId}/x/ad-accounts/get`,auth:`user`,requestContentType:`application/json`}},{id:`x.estimate_x_audience`,path:[`x`,`audiences`,`estimate`],summary:`How many X users a set of targeting criteria reaches (min–max), for a line item you are about to build or change. Read-like: nothing is created. Costs 1 request.`,description:``,source:`rest`,options:[{name:`workspaceId`,flag:`--workspace-id`,description:``,required:!0,valueType:`string`,location:`path`},{name:`account_id`,flag:`--account-id`,description:`X ads account id (e.g. 18ce55xcrlv). Omit it: it defaults to the ads account this client is connected to, and any other account is refused.`,required:!1,valueType:`string`,location:`body`},{name:`targeting_criteria`,flag:`--targeting-criteria`,description:`A hypothetical line item's criteria.`,required:!0,valueType:`json`,location:`body`}],examples:[{description:`Example`,command:`adside x audiences estimate --workspace-id <workspaceId> --targeting-criteria '{}'`}],output:{kind:`json`,description:`How many X users a set of targeting criteria reaches (min–max), for a line item you are about to build or change. Read-like: nothing is created. Costs 1 request.`},transport:{type:`rest`,method:`POST`,path:`/v1/workspaces/{workspaceId}/x/audiences/estimate`,auth:`user`,requestContentType:`application/json`}},{id:`x.list_x_bidding_rules`,path:[`x`,`bidding-rules`,`list`],summary:`X's minimum / maximum bid per objective for a currency (from GET bidding_rules, a global read cached for an hour), plus the objective × product type × creative × pricing table. Use it to sanity-check a bid before creating or changing a line item.`,description:``,source:`rest`,options:[{name:`workspaceId`,flag:`--workspace-id`,description:``,required:!0,valueType:`string`,location:`path`},{name:`account_id`,flag:`--account-id`,description:`X ads account id (e.g. 18ce55xcrlv). Omit it: it defaults to the ads account this client is connected to, and any other account is refused.`,required:!1,valueType:`string`,location:`body`},{name:`currency`,flag:`--currency`,description:`ISO-4217; defaults to the account's funding instrument currency.`,required:!1,valueType:`string`,location:`body`}],examples:[{description:`Example`,command:`adside x bidding-rules list --workspace-id <workspaceId>`}],output:{kind:`json`,description:`X's minimum / maximum bid per objective for a currency (from GET bidding_rules, a global read cached for an hour), plus the objective × product type × creative × pricing table. Use it to sanity-check a bid before creating or changing a line item.`},transport:{type:`rest`,method:`POST`,path:`/v1/workspaces/{workspaceId}/x/bidding-rules/list`,auth:`user`,requestContentType:`application/json`}},{id:`x.get_x_campaign_reach`,path:[`x`,`campaign-reach`,`get`],summary:`Total audience reach and average frequency for up to 20 campaigns over a window. Costs 1 request.`,description:``,source:`rest`,options:[{name:`workspaceId`,flag:`--workspace-id`,description:``,required:!0,valueType:`string`,location:`path`},{name:`account_id`,flag:`--account-id`,description:`X ads account id (e.g. 18ce55xcrlv). Omit it: it defaults to the ads account this client is connected to, and any other account is refused.`,required:!1,valueType:`string`,location:`body`},{name:`campaign_ids`,flag:`--campaign-ids`,description:``,required:!0,valueType:`json`,location:`body`},{name:`preset`,flag:`--preset`,description:`Shortcut for a date range. Default last_7d when no start_date/end_date given.`,required:!1,valueType:`string`,enum:[`today`,`yesterday`,`last_7d`,`last_14d`,`last_30d`,`this_month`,`last_month`],location:`body`},{name:`start_date`,flag:`--start-date`,description:`First day, YYYY-MM-DD, in the account's time zone.`,required:!1,valueType:`string`,location:`body`},{name:`end_date`,flag:`--end-date`,description:`Last day (inclusive), YYYY-MM-DD, in the account's time zone. The exclusive end X wants is computed for you.`,required:!1,valueType:`string`,location:`body`}],examples:[{description:`Example`,command:`adside x campaign-reach get --workspace-id <workspaceId> --campaign-ids '{}'`}],output:{kind:`json`,description:`Total audience reach and average frequency for up to 20 campaigns over a window. Costs 1 request.`},transport:{type:`rest`,method:`POST`,path:`/v1/workspaces/{workspaceId}/x/campaign-reach/get`,auth:`user`,requestContentType:`application/json`}},{id:`x.check_x_campaign_readiness`,path:[`x`,`campaign-readiness`,`check`],summary:`Can this campaign deliver? Checks the funding instrument, line items (future window, non-empty targeting, bid, objective requirements such as a web event tag or app store id), promoted posts (at least one ACCEPTED) and every reasons_not_servable value, and returns is_ready plus the issues, the requirements X enforces and what to do next — one cheap read instead of trial-and-error writes. Accepts a campaign id or a name. Costs up to 6 requests.`,description:``,source:`rest`,options:[{name:`workspaceId`,flag:`--workspace-id`,description:``,required:!0,valueType:`string`,location:`path`},{name:`campaign_id`,flag:`--campaign-id`,description:`Campaign id. Give this or campaign_name.`,required:!1,valueType:`string`,location:`body`},{name:`campaign_name`,flag:`--campaign-name`,description:`Exact or partial campaign name, when the id is unknown.`,required:!1,valueType:`string`,location:`body`}],examples:[{description:`Example`,command:`adside x campaign-readiness check --workspace-id <workspaceId>`}],output:{kind:`json`,description:`Can this campaign deliver? Checks the funding instrument, line items (future window, non-empty targeting, bid, objective requirements such as a web event tag or app store id), promoted posts (at least one ACCEPTED) and every reasons_not_servable value, and returns is_ready plus the issues, the requirements X enforces and what to do next — one cheap read instead of trial-and-error writes. Accepts a campaign id or a name. Costs up to 6 requests.`},transport:{type:`rest`,method:`POST`,path:`/v1/workspaces/{workspaceId}/x/campaign-readiness/check`,auth:`user`,requestContentType:`application/json`}},{id:`x.get_x_campaign`,path:[`x`,`campaigns`,`get`],summary:`One X campaign by id: status and why it is or is not servable, funding instrument, budgets, and a summary of its line items (objective, window, statuses) and promoted posts (approval). Costs 3–4 requests.`,description:``,source:`rest`,options:[{name:`workspaceId`,flag:`--workspace-id`,description:``,required:!0,valueType:`string`,location:`path`},{name:`campaign_id`,flag:`--campaign-id`,description:`Campaign id (base-36) from list_x_campaigns.`,required:!0,valueType:`string`,location:`body`}],examples:[{description:`Example`,command:`adside x campaigns get --workspace-id <workspaceId> --campaign-id <campaign_id>`}],output:{kind:`json`,description:`One X campaign by id: status and why it is or is not servable, funding instrument, budgets, and a summary of its line items (objective, window, statuses) and promoted posts (approval). Costs 3–4 requests.`},transport:{type:`rest`,method:`POST`,path:`/v1/workspaces/{workspaceId}/x/campaigns/get`,auth:`user`,requestContentType:`application/json`}},{id:`x.list_x_campaigns`,path:[`x`,`campaigns`,`list`],summary:"List campaigns on the connected X ads account with status, servability (reasons_not_servable) and budgets. Deleted campaigns are hidden unless with_deleted is set. X has no server-side status filter, so `status` is applied while paging and `limit` bounds the matches returned.",description:``,source:`rest`,options:[{name:`workspaceId`,flag:`--workspace-id`,description:``,required:!0,valueType:`string`,location:`path`},{name:`account_id`,flag:`--account-id`,description:`X ads account id (e.g. 18ce55xcrlv). Omit it: it defaults to the ads account this client is connected to, and any other account is refused.`,required:!1,valueType:`string`,location:`body`},{name:`status`,flag:`--status`,description:`Filter on entity_status. Deleted objects are hidden unless with_deleted is set.`,required:!1,valueType:`string`,enum:[`ACTIVE`,`PAUSED`,`DRAFT`],location:`body`},{name:`name_contains`,flag:`--name-contains`,description:`Case-insensitive substring of the campaign name.`,required:!1,valueType:`string`,location:`body`},{name:`funding_instrument_id`,flag:`--funding-instrument-id`,description:`Only campaigns on this funding instrument (server-side filter).`,required:!1,valueType:`string`,location:`body`},{name:`with_deleted`,flag:`--with-deleted`,description:`Include deleted campaigns (X keeps them listable).`,required:!1,valueType:`boolean`,defaultValue:!1,location:`body`},{name:`with_draft`,flag:`--with-draft`,description:`Include DRAFT campaigns.`,required:!1,valueType:`boolean`,defaultValue:!0,location:`body`},{name:`limit`,flag:`--limit`,description:`Maximum rows to return (bounds the answer, not the scan).`,required:!1,valueType:`number`,defaultValue:100,location:`body`}],examples:[{description:`Example`,command:`adside x campaigns list --workspace-id <workspaceId>`}],output:{kind:`json`,description:"List campaigns on the connected X ads account with status, servability (reasons_not_servable) and budgets. Deleted campaigns are hidden unless with_deleted is set. X has no server-side status filter, so `status` is applied while paging and `limit` bounds the matches returned."},transport:{type:`rest`,method:`POST`,path:`/v1/workspaces/{workspaceId}/x/campaigns/list`,auth:`user`,requestContentType:`application/json`}},{id:`x.list_x_cards`,path:[`x`,`cards`,`list`],summary:`Cards on the connected account (website / app / carousel cards a post references through card_uri): card type, components (media, title and destination) and uri. Legacy per-type cards are hidden unless include_legacy_cards is set.`,description:``,source:`rest`,options:[{name:`workspaceId`,flag:`--workspace-id`,description:``,required:!0,valueType:`string`,location:`path`},{name:`account_id`,flag:`--account-id`,description:`X ads account id (e.g. 18ce55xcrlv). Omit it: it defaults to the ads account this client is connected to, and any other account is refused.`,required:!1,valueType:`string`,location:`body`},{name:`card_type`,flag:`--card-type`,description:`e.g. IMAGE_WEBSITE, VIDEO_WEBSITE, IMAGE_CAROUSEL_WEBSITE, IMAGE_APP.`,required:!1,valueType:`string`,location:`body`},{name:`q`,flag:`--q`,description:`Substring of the card name (server-side).`,required:!1,valueType:`string`,location:`body`},{name:`include_legacy_cards`,flag:`--include-legacy-cards`,description:`Also list cards created with the deprecated per-type endpoints.`,required:!1,valueType:`boolean`,defaultValue:!1,location:`body`},{name:`with_deleted`,flag:`--with-deleted`,description:``,required:!1,valueType:`boolean`,defaultValue:!1,location:`body`},{name:`limit`,flag:`--limit`,description:``,required:!1,valueType:`number`,defaultValue:50,location:`body`}],examples:[{description:`Example`,command:`adside x cards list --workspace-id <workspaceId>`}],output:{kind:`json`,description:`Cards on the connected account (website / app / carousel cards a post references through card_uri): card type, components (media, title and destination) and uri. Legacy per-type cards are hidden unless include_legacy_cards is set.`},transport:{type:`rest`,method:`POST`,path:`/v1/workspaces/{workspaceId}/x/cards/list`,auth:`user`,requestContentType:`application/json`}},{id:`x.get_x_channel_status`,path:[`x`,`channel-status`,`get`],summary:`Self-diagnosis of the X connection: the connected ads account and its approval, who the token belongs to and their permissions, production vs sandbox, the API version X reported, and rate-limit state observed in this request. Costs 2 requests.`,description:``,source:`rest`,options:[{name:`workspaceId`,flag:`--workspace-id`,description:``,required:!0,valueType:`string`,location:`path`}],examples:[{description:`Example`,command:`adside x channel-status get --workspace-id <workspaceId>`}],output:{kind:`json`,description:`Self-diagnosis of the X connection: the connected ads account and its approval, who the token belongs to and their permissions, production vs sandbox, the API version X reported, and rate-limit state observed in this request. Costs 2 requests.`},transport:{type:`rest`,method:`POST`,path:`/v1/workspaces/{workspaceId}/x/channel-status/get`,auth:`user`}},{id:`x.get_x_custom_audience`,path:[`x`,`custom-audiences`,`get`],summary:`One custom audience with its size, targetability, type, and the campaigns / line items currently targeting it. Costs 2 requests.`,description:``,source:`rest`,options:[{name:`workspaceId`,flag:`--workspace-id`,description:``,required:!0,valueType:`string`,location:`path`},{name:`audience_id`,flag:`--audience-id`,description:`Custom audience id (base-36) from list_x_custom_audiences.`,required:!0,valueType:`string`,location:`body`}],examples:[{description:`Example`,command:`adside x custom-audiences get --workspace-id <workspaceId> --audience-id <audience_id>`}],output:{kind:`json`,description:`One custom audience with its size, targetability, type, and the campaigns / line items currently targeting it. Costs 2 requests.`},transport:{type:`rest`,method:`POST`,path:`/v1/workspaces/{workspaceId}/x/custom-audiences/get`,auth:`user`,requestContentType:`application/json`}},{id:`x.list_x_custom_audiences`,path:[`x`,`custom-audiences`,`list`],summary:`Custom audiences on the connected account (CRM lists, website / app / engagement audiences): size, whether targetable and why not (X needs ≥100 matched users active in 90 days), permission level, owner. Website audiences come from the X Pixel in Events Manager, not the API.`,description:``,source:`rest`,options:[{name:`workspaceId`,flag:`--workspace-id`,description:``,required:!0,valueType:`string`,location:`path`},{name:`account_id`,flag:`--account-id`,description:`X ads account id (e.g. 18ce55xcrlv). Omit it: it defaults to the ads account this client is connected to, and any other account is refused.`,required:!1,valueType:`string`,location:`body`},{name:`name_contains`,flag:`--name-contains`,description:``,required:!1,valueType:`string`,location:`body`},{name:`permission_scope`,flag:`--permission-scope`,description:`OWNER = audiences this account owns; SHARED = audiences shared into it.`,required:!1,valueType:`string`,enum:[`OWNER`,`SHARED`],location:`body`},{name:`targetable_only`,flag:`--targetable-only`,description:``,required:!1,valueType:`boolean`,defaultValue:!1,location:`body`},{name:`with_deleted`,flag:`--with-deleted`,description:``,required:!1,valueType:`boolean`,defaultValue:!1,location:`body`},{name:`limit`,flag:`--limit`,description:``,required:!1,valueType:`number`,defaultValue:100,location:`body`}],examples:[{description:`Example`,command:`adside x custom-audiences list --workspace-id <workspaceId>`}],output:{kind:`json`,description:`Custom audiences on the connected account (CRM lists, website / app / engagement audiences): size, whether targetable and why not (X needs ≥100 matched users active in 90 days), permission level, owner. Website audiences come from the X Pixel in Events Manager, not the API.`},transport:{type:`rest`,method:`POST`,path:`/v1/workspaces/{workspaceId}/x/custom-audiences/list`,auth:`user`,requestContentType:`application/json`}},{id:`x.get_x_daily_performance`,path:[`x`,`daily-performance`,`get`],summary:`Core metrics by day for the account, one campaign, one line item or one promoted post, with day-over-day change in spend (sync, ≤7 days; longer windows through the job triple). Costs 1 request.`,description:``,source:`rest`,options:[{name:`workspaceId`,flag:`--workspace-id`,description:``,required:!0,valueType:`string`,location:`path`},{name:`account_id`,flag:`--account-id`,description:`X ads account id (e.g. 18ce55xcrlv). Omit it: it defaults to the ads account this client is connected to, and any other account is refused.`,required:!1,valueType:`string`,location:`body`},{name:`entity`,flag:`--entity`,description:``,required:!1,valueType:`string`,defaultValue:`ACCOUNT`,enum:[`ACCOUNT`,`CAMPAIGN`,`LINE_ITEM`,`PROMOTED_TWEET`],location:`body`},{name:`entity_id`,flag:`--entity-id`,description:`One object of that entity; omit for ACCOUNT.`,required:!1,valueType:`string`,location:`body`},{name:`metrics`,flag:`--metrics`,description:`Friendly metric names: spend, impressions, engagements, clicks, url_clicks, likes, follows, video_total_views, conversion_purchases, … plus derived ones (cpm, cpe, cplc, ctr, engagement_rate, cpv, cpa, roas) computed here. Default: the ENGAGEMENT + BILLING groups. See list_x_metrics.`,required:!1,valueType:`json`,location:`body`},{name:`placement`,flag:`--placement`,description:`One placement per stats request (X accepts a single value). Default ALL_ON_TWITTER; other placements are separate calls.`,required:!1,valueType:`string`,defaultValue:`ALL_ON_TWITTER`,enum:[`ALL_ON_TWITTER`,`PUBLISHER_NETWORK`,`SPOTLIGHT`,`TREND`],location:`body`},{name:`preset`,flag:`--preset`,description:`Shortcut for a date range. Default last_7d when no start_date/end_date given.`,required:!1,valueType:`string`,enum:[`today`,`yesterday`,`last_7d`,`last_14d`,`last_30d`,`this_month`,`last_month`],location:`body`},{name:`start_date`,flag:`--start-date`,description:`First day, YYYY-MM-DD, in the account's time zone.`,required:!1,valueType:`string`,location:`body`},{name:`end_date`,flag:`--end-date`,description:`Last day (inclusive), YYYY-MM-DD, in the account's time zone. The exclusive end X wants is computed for you.`,required:!1,valueType:`string`,location:`body`}],examples:[{description:`Example`,command:`adside x daily-performance get --workspace-id <workspaceId>`}],output:{kind:`json`,description:`Core metrics by day for the account, one campaign, one line item or one promoted post, with day-over-day change in spend (sync, ≤7 days; longer windows through the job triple). Costs 1 request.`},transport:{type:`rest`,method:`POST`,path:`/v1/workspaces/{workspaceId}/x/daily-performance/get`,auth:`user`,requestContentType:`application/json`}},{id:`x.diagnose_x_delivery`,path:[`x`,`delivery`,`diagnose`],summary:`Why isn't it delivering? For each campaign: every reasons_not_servable value on it and its line items translated to a cause and next action, line items without promoted posts, promoted posts not ACCEPTED, windows not started / ended, empty (worldwide) targeting, funding problems, and spend over the lookback as evidence. Costs up to 8 requests.`,description:``,source:`rest`,options:[{name:`workspaceId`,flag:`--workspace-id`,description:``,required:!0,valueType:`string`,location:`path`},{name:`account_id`,flag:`--account-id`,description:`X ads account id (e.g. 18ce55xcrlv). Omit it: it defaults to the ads account this client is connected to, and any other account is refused.`,required:!1,valueType:`string`,location:`body`},{name:`campaign_id`,flag:`--campaign-id`,description:`Only this campaign. Default: every non-deleted campaign.`,required:!1,valueType:`string`,location:`body`},{name:`lookback_days`,flag:`--lookback-days`,description:``,required:!1,valueType:`number`,defaultValue:3,location:`body`}],examples:[{description:`Example`,command:`adside x delivery diagnose --workspace-id <workspaceId>`}],output:{kind:`json`,description:`Why isn't it delivering? For each campaign: every reasons_not_servable value on it and its line items translated to a cause and next action, line items without promoted posts, promoted posts not ACCEPTED, windows not started / ended, empty (worldwide) targeting, funding problems, and spend over the lookback as evidence. Costs up to 8 requests.`},transport:{type:`rest`,method:`POST`,path:`/v1/workspaces/{workspaceId}/x/delivery/diagnose`,auth:`user`,requestContentType:`application/json`}},{id:`x.find_x_entity`,path:[`x`,`entity`,`find`],summary:`Find campaigns, line items or nullcast posts by name (or post text) on the connected account, case-insensitive substring. Use it to turn a name from the user into an id for the other tools. Costs up to 3 list requests; posts are searched in the most recent 200.`,description:``,source:`rest`,options:[{name:`workspaceId`,flag:`--workspace-id`,description:``,required:!0,valueType:`string`,location:`path`},{name:`account_id`,flag:`--account-id`,description:`X ads account id (e.g. 18ce55xcrlv). Omit it: it defaults to the ads account this client is connected to, and any other account is refused.`,required:!1,valueType:`string`,location:`body`},{name:`query`,flag:`--query`,description:`Case-insensitive substring of the name (or post text).`,required:!0,valueType:`string`,location:`body`},{name:`entity_type`,flag:`--entity-type`,description:``,required:!1,valueType:`string`,defaultValue:`any`,enum:[`campaign`,`line_item`,`post`,`any`],location:`body`},{name:`limit`,flag:`--limit`,description:``,required:!1,valueType:`number`,defaultValue:20,location:`body`}],examples:[{description:`Example`,command:`adside x entity find --workspace-id <workspaceId> --query <query>`}],output:{kind:`json`,description:`Find campaigns, line items or nullcast posts by name (or post text) on the connected account, case-insensitive substring. Use it to turn a name from the user into an id for the other tools. Costs up to 3 list requests; posts are searched in the most recent 200.`},transport:{type:`rest`,method:`POST`,path:`/v1/workspaces/{workspaceId}/x/entity/find`,auth:`user`,requestContentType:`application/json`}},{id:`x.list_x_funding_instruments`,path:[`x`,`funding-instruments`,`list`],summary:`Funding instruments (credit card, credit line, insertion order) on the connected X ads account: type, currency, credit limit / remaining, whether each is able to fund and why not. A campaign needs one that is able to fund to deliver; funding instruments cannot be created through the API.`,description:``,source:`rest`,options:[{name:`workspaceId`,flag:`--workspace-id`,description:``,required:!0,valueType:`string`,location:`path`},{name:`account_id`,flag:`--account-id`,description:`X ads account id (e.g. 18ce55xcrlv). Omit it: it defaults to the ads account this client is connected to, and any other account is refused.`,required:!1,valueType:`string`,location:`body`},{name:`with_deleted`,flag:`--with-deleted`,description:``,required:!1,valueType:`boolean`,defaultValue:!1,location:`body`}],examples:[{description:`Example`,command:`adside x funding-instruments list --workspace-id <workspaceId>`}],output:{kind:`json`,description:`Funding instruments (credit card, credit line, insertion order) on the connected X ads account: type, currency, credit limit / remaining, whether each is able to fund and why not. A campaign needs one that is able to fund to deliver; funding instruments cannot be created through the API.`},transport:{type:`rest`,method:`POST`,path:`/v1/workspaces/{workspaceId}/x/funding-instruments/list`,auth:`user`,requestContentType:`application/json`}},{id:`x.search_x_keyword_insights`,path:[`x`,`keyword-insights`,`search`],summary:`Conversation volume on X for keywords over a window (daily or hourly), to size keyword targeting before committing budget. Costs 1 request.`,description:``,source:`rest`,options:[{name:`workspaceId`,flag:`--workspace-id`,description:``,required:!0,valueType:`string`,location:`path`},{name:`keywords`,flag:`--keywords`,description:`Keywords to measure conversation volume for.`,required:!0,valueType:`json`,location:`body`},{name:`granularity`,flag:`--granularity`,description:``,required:!1,valueType:`string`,defaultValue:`DAY`,enum:[`DAY`,`HOUR`],location:`body`},{name:`preset`,flag:`--preset`,description:`Shortcut for a date range. Default last_7d when no start_date/end_date given.`,required:!1,valueType:`string`,enum:[`today`,`yesterday`,`last_7d`,`last_14d`,`last_30d`,`this_month`,`last_month`],location:`body`},{name:`start_date`,flag:`--start-date`,description:`First day, YYYY-MM-DD, in the account's time zone.`,required:!1,valueType:`string`,location:`body`},{name:`end_date`,flag:`--end-date`,description:`Last day (inclusive), YYYY-MM-DD, in the account's time zone. The exclusive end X wants is computed for you.`,required:!1,valueType:`string`,location:`body`}],examples:[{description:`Example`,command:`adside x keyword-insights search --workspace-id <workspaceId> --keywords '{}'`}],output:{kind:`json`,description:`Conversation volume on X for keywords over a window (daily or hourly), to size keyword targeting before committing budget. Costs 1 request.`},transport:{type:`rest`,method:`POST`,path:`/v1/workspaces/{workspaceId}/x/keyword-insights/search`,auth:`user`,requestContentType:`application/json`}},{id:`x.get_x_line_item`,path:[`x`,`line-items`,`get`],summary:`One X line item by id: status and servability, objective, product type, placements, goal, bid strategy and amount, budgets, window, frequency cap, app / web-event settings, and its targeting criteria grouped by type with X's AND/OR semantics spelled out. Costs 2–3 requests.`,description:``,source:`rest`,options:[{name:`workspaceId`,flag:`--workspace-id`,description:``,required:!0,valueType:`string`,location:`path`},{name:`line_item_id`,flag:`--line-item-id`,description:`Line item id (base-36) from list_x_line_items.`,required:!0,valueType:`string`,location:`body`}],examples:[{description:`Example`,command:`adside x line-items get --workspace-id <workspaceId> --line-item-id <line_item_id>`}],output:{kind:`json`,description:`One X line item by id: status and servability, objective, product type, placements, goal, bid strategy and amount, budgets, window, frequency cap, app / web-event settings, and its targeting criteria grouped by type with X's AND/OR semantics spelled out. Costs 2–3 requests.`},transport:{type:`rest`,method:`POST`,path:`/v1/workspaces/{workspaceId}/x/line-items/get`,auth:`user`,requestContentType:`application/json`}},{id:`x.list_x_line_items`,path:[`x`,`line-items`,`list`],summary:`List line items (ad groups) on the connected account, optionally one campaign's, with status, servability, objective, bid, budgets and window. X calls this level 'line item': a campaign holds line items, a line item holds promoted posts and targeting criteria, and the schedule (start_time / end_time) lives here, not on the campaign.`,description:``,source:`rest`,options:[{name:`workspaceId`,flag:`--workspace-id`,description:``,required:!0,valueType:`string`,location:`path`},{name:`account_id`,flag:`--account-id`,description:`X ads account id (e.g. 18ce55xcrlv). Omit it: it defaults to the ads account this client is connected to, and any other account is refused.`,required:!1,valueType:`string`,location:`body`},{name:`campaign_id`,flag:`--campaign-id`,description:`Only line items in this campaign (server-side filter).`,required:!1,valueType:`string`,location:`body`},{name:`status`,flag:`--status`,description:`Filter on entity_status. Deleted objects are hidden unless with_deleted is set.`,required:!1,valueType:`string`,enum:[`ACTIVE`,`PAUSED`,`DRAFT`],location:`body`},{name:`name_contains`,flag:`--name-contains`,description:``,required:!1,valueType:`string`,location:`body`},{name:`with_deleted`,flag:`--with-deleted`,description:``,required:!1,valueType:`boolean`,defaultValue:!1,location:`body`},{name:`limit`,flag:`--limit`,description:`Maximum rows to return (bounds the answer, not the scan).`,required:!1,valueType:`number`,defaultValue:100,location:`body`}],examples:[{description:`Example`,command:`adside x line-items list --workspace-id <workspaceId>`}],output:{kind:`json`,description:`List line items (ad groups) on the connected account, optionally one campaign's, with status, servability, objective, bid, budgets and window. X calls this level 'line item': a campaign holds line items, a line item holds promoted posts and targeting criteria, and the schedule (start_time / end_time) lives here, not on the campaign.`},transport:{type:`rest`,method:`POST`,path:`/v1/workspaces/{workspaceId}/x/line-items/list`,auth:`user`,requestContentType:`application/json`}},{id:`x.list_x_media_library`,path:[`x`,`media-library`,`list`],summary:`Images, GIFs and videos in the connected account's Media Library with media keys (what a post or card references), type, processing status, aspect ratio and URL. Pages of 50 (X's cap for this endpoint).`,description:``,source:`rest`,options:[{name:`workspaceId`,flag:`--workspace-id`,description:``,required:!0,valueType:`string`,location:`path`},{name:`account_id`,flag:`--account-id`,description:`X ads account id (e.g. 18ce55xcrlv). Omit it: it defaults to the ads account this client is connected to, and any other account is refused.`,required:!1,valueType:`string`,location:`body`},{name:`media_type`,flag:`--media-type`,description:``,required:!1,valueType:`string`,enum:[`GIF`,`IMAGE`,`VIDEO`],location:`body`},{name:`q`,flag:`--q`,description:`Substring of the media name / title / file name (server-side).`,required:!1,valueType:`string`,location:`body`},{name:`limit`,flag:`--limit`,description:``,required:!1,valueType:`number`,defaultValue:50,location:`body`}],examples:[{description:`Example`,command:`adside x media-library list --workspace-id <workspaceId>`}],output:{kind:`json`,description:`Images, GIFs and videos in the connected account's Media Library with media keys (what a post or card references), type, processing status, aspect ratio and URL. Pages of 50 (X's cap for this endpoint).`},transport:{type:`rest`,method:`POST`,path:`/v1/workspaces/{workspaceId}/x/media-library/list`,auth:`user`,requestContentType:`application/json`}},{id:`x.get_x_media_status`,path:[`x`,`media-status`,`get`],summary:`Processing state of one media item: the Media Library record (media_status, e.g. TRANSCODE_COMPLETED) and, for a video still processing, the upload's v2 STATUS (pending / in_progress / succeeded / failed, with progress). Use it after an upload before referencing the media key in a post or card.`,description:``,source:`rest`,options:[{name:`workspaceId`,flag:`--workspace-id`,description:``,required:!0,valueType:`string`,location:`path`},{name:`account_id`,flag:`--account-id`,description:`X ads account id (e.g. 18ce55xcrlv). Omit it: it defaults to the ads account this client is connected to, and any other account is refused.`,required:!1,valueType:`string`,location:`body`},{name:`media_key`,flag:`--media-key`,description:`Media key from list_x_media_library.`,required:!0,valueType:`string`,location:`body`}],examples:[{description:`Example`,command:`adside x media-status get --workspace-id <workspaceId> --media-key <media_key>`}],output:{kind:`json`,description:`Processing state of one media item: the Media Library record (media_status, e.g. TRANSCODE_COMPLETED) and, for a video still processing, the upload's v2 STATUS (pending / in_progress / succeeded / failed, with progress). Use it after an upload before referencing the media key in a post or card.`},transport:{type:`rest`,method:`POST`,path:`/v1/workspaces/{workspaceId}/x/media-status/get`,auth:`user`,requestContentType:`application/json`}},{id:`x.list_x_metrics`,path:[`x`,`metrics`,`list`],summary:`The analytics vocabulary get_x_stats accepts: metric groups and their exact metric names, friendly aliases (spend = billed_charge_local_micro), the derived metrics computed here with their formulas, the segmentation types X still supports, and the objective → required-metrics table. Use it when a metric name is refused.`,description:``,source:`rest`,options:[{name:`workspaceId`,flag:`--workspace-id`,description:``,required:!0,valueType:`string`,location:`path`},{name:`filter`,flag:`--filter`,description:`Substring filter, e.g. 'conversion', 'video'.`,required:!1,valueType:`string`,location:`body`},{name:`group`,flag:`--group`,description:`Only the members of one metric group.`,required:!1,valueType:`string`,enum:[`ENGAGEMENT`,`BILLING`,`VIDEO`,`WEB_CONVERSION`,`MOBILE_CONVERSION`,`LIFE_TIME_VALUE_MOBILE_CONVERSION`],location:`body`}],examples:[{description:`Example`,command:`adside x metrics list --workspace-id <workspaceId>`}],output:{kind:`json`,description:`The analytics vocabulary get_x_stats accepts: metric groups and their exact metric names, friendly aliases (spend = billed_charge_local_micro), the derived metrics computed here with their formulas, the segmentation types X still supports, and the objective → required-metrics table. Use it when a metric name is refused.`},transport:{type:`rest`,method:`POST`,path:`/v1/workspaces/{workspaceId}/x/metrics/list`,auth:`user`,requestContentType:`application/json`}},{id:`x.analyze_x_pacing`,path:[`x`,`pacing`,`analyze`],summary:`Is spend on track? For each active line item (and its campaign): daily / total budget, spend in the window, daily average, pace index (1.0 = spending the daily budget), days remaining in the line item's window. Costs up to 4 requests (line items, campaigns, active entities, stats).`,description:``,source:`rest`,options:[{name:`workspaceId`,flag:`--workspace-id`,description:``,required:!0,valueType:`string`,location:`path`},{name:`account_id`,flag:`--account-id`,description:`X ads account id (e.g. 18ce55xcrlv). Omit it: it defaults to the ads account this client is connected to, and any other account is refused.`,required:!1,valueType:`string`,location:`body`},{name:`campaign_id`,flag:`--campaign-id`,description:`Only this campaign's line items.`,required:!1,valueType:`string`,location:`body`},{name:`preset`,flag:`--preset`,description:`Shortcut for a date range. Default last_7d when no start_date/end_date given.`,required:!1,valueType:`string`,enum:[`today`,`yesterday`,`last_7d`,`last_14d`,`last_30d`,`this_month`,`last_month`],location:`body`},{name:`start_date`,flag:`--start-date`,description:`First day, YYYY-MM-DD, in the account's time zone.`,required:!1,valueType:`string`,location:`body`},{name:`end_date`,flag:`--end-date`,description:`Last day (inclusive), YYYY-MM-DD, in the account's time zone. The exclusive end X wants is computed for you.`,required:!1,valueType:`string`,location:`body`}],examples:[{description:`Example`,command:`adside x pacing analyze --workspace-id <workspaceId>`}],output:{kind:`json`,description:`Is spend on track? For each active line item (and its campaign): daily / total budget, spend in the window, daily average, pace index (1.0 = spending the daily budget), days remaining in the line item's window. Costs up to 4 requests (line items, campaigns, active entities, stats).`},transport:{type:`rest`,method:`POST`,path:`/v1/workspaces/{workspaceId}/x/pacing/analyze`,auth:`user`,requestContentType:`application/json`}},{id:`x.compare_x_performance`,path:[`x`,`performance`,`compare`],summary:`Side-by-side comparison: this window versus the previous period for the account (or one level's active entities), or several objects (≤20) in one window. Deltas are absolute and percent; rates are recomputed from sums, never summed. Costs 2–4 sync stats calls (each ≤7 days).`,description:``,source:`rest`,options:[{name:`workspaceId`,flag:`--workspace-id`,description:``,required:!0,valueType:`string`,location:`path`},{name:`account_id`,flag:`--account-id`,description:`X ads account id (e.g. 18ce55xcrlv). Omit it: it defaults to the ads account this client is connected to, and any other account is refused.`,required:!1,valueType:`string`,location:`body`},{name:`entity`,flag:`--entity`,description:``,required:!1,valueType:`string`,defaultValue:`ACCOUNT`,enum:[`ACCOUNT`,`CAMPAIGN`,`LINE_ITEM`,`PROMOTED_TWEET`],location:`body`},{name:`entity_ids`,flag:`--entity-ids`,description:`Compare these objects side by side in one window (≤20). Without ids: this window vs the previous period.`,required:!1,valueType:`json`,location:`body`},{name:`metrics`,flag:`--metrics`,description:`Friendly metric names: spend, impressions, engagements, clicks, url_clicks, likes, follows, video_total_views, conversion_purchases, … plus derived ones (cpm, cpe, cplc, ctr, engagement_rate, cpv, cpa, roas) computed here. Default: the ENGAGEMENT + BILLING groups. See list_x_metrics.`,required:!1,valueType:`json`,location:`body`},{name:`placement`,flag:`--placement`,description:`One placement per stats request (X accepts a single value). Default ALL_ON_TWITTER; other placements are separate calls.`,required:!1,valueType:`string`,defaultValue:`ALL_ON_TWITTER`,enum:[`ALL_ON_TWITTER`,`PUBLISHER_NETWORK`,`SPOTLIGHT`,`TREND`],location:`body`},{name:`preset`,flag:`--preset`,description:`Shortcut for a date range. Default last_7d when no start_date/end_date given.`,required:!1,valueType:`string`,enum:[`today`,`yesterday`,`last_7d`,`last_14d`,`last_30d`,`this_month`,`last_month`],location:`body`},{name:`start_date`,flag:`--start-date`,description:`First day, YYYY-MM-DD, in the account's time zone.`,required:!1,valueType:`string`,location:`body`},{name:`end_date`,flag:`--end-date`,description:`Last day (inclusive), YYYY-MM-DD, in the account's time zone. The exclusive end X wants is computed for you.`,required:!1,valueType:`string`,location:`body`},{name:`compare_to`,flag:`--compare-to`,description:``,required:!1,valueType:`string`,defaultValue:`previous_period`,enum:[`previous_period`,`none`],location:`body`}],examples:[{description:`Example`,command:`adside x performance compare --workspace-id <workspaceId>`}],output:{kind:`json`,description:`Side-by-side comparison: this window versus the previous period for the account (or one level's active entities), or several objects (≤20) in one window. Deltas are absolute and percent; rates are recomputed from sums, never summed. Costs 2–4 sync stats calls (each ≤7 days).`},transport:{type:`rest`,method:`POST`,path:`/v1/workspaces/{workspaceId}/x/performance/compare`,auth:`user`,requestContentType:`application/json`}},{id:`x.get_x_post`,path:[`x`,`posts`,`get`],summary:`One post by tweet id as the ads account sees it: text, nullcast flag, media keys and types, card, landing URL, conversation settings.`,description:``,source:`rest`,options:[{name:`workspaceId`,flag:`--workspace-id`,description:``,required:!0,valueType:`string`,location:`path`},{name:`account_id`,flag:`--account-id`,description:`X ads account id (e.g. 18ce55xcrlv). Omit it: it defaults to the ads account this client is connected to, and any other account is refused.`,required:!1,valueType:`string`,location:`body`},{name:`tweet_id`,flag:`--tweet-id`,description:`Tweet id (numeric string) from a promoted post or list_x_account_posts.`,required:!0,valueType:`string`,location:`body`},{name:`tweet_type`,flag:`--tweet-type`,description:``,required:!1,valueType:`string`,defaultValue:`PUBLISHED`,enum:[`PUBLISHED`,`SCHEDULED`,`DRAFT`],location:`body`}],examples:[{description:`Example`,command:`adside x posts get --workspace-id <workspaceId> --tweet-id <tweet_id>`}],output:{kind:`json`,description:`One post by tweet id as the ads account sees it: text, nullcast flag, media keys and types, card, landing URL, conversation settings.`},transport:{type:`rest`,method:`POST`,path:`/v1/workspaces/{workspaceId}/x/posts/get`,auth:`user`,requestContentType:`application/json`}},{id:`x.preview_x_post`,path:[`x`,`posts`,`preview`],summary:`Accurate, up-to-date renderings of posts (published, scheduled or draft) as X shows them, as preview URLs (iframe sources on ton.twimg.com). Up to 200 tweet ids per call; no spend involved.`,description:``,source:`rest`,options:[{name:`workspaceId`,flag:`--workspace-id`,description:``,required:!0,valueType:`string`,location:`path`},{name:`account_id`,flag:`--account-id`,description:`X ads account id (e.g. 18ce55xcrlv). Omit it: it defaults to the ads account this client is connected to, and any other account is refused.`,required:!1,valueType:`string`,location:`body`},{name:`tweet_ids`,flag:`--tweet-ids`,description:`Tweet ids (numeric strings) to render, ≤200.`,required:!0,valueType:`json`,location:`body`},{name:`tweet_type`,flag:`--tweet-type`,description:``,required:!1,valueType:`string`,defaultValue:`PUBLISHED`,enum:[`PUBLISHED`,`SCHEDULED`,`DRAFT`],location:`body`}],examples:[{description:`Example`,command:`adside x posts preview --workspace-id <workspaceId> --tweet-ids '{}'`}],output:{kind:`json`,description:`Accurate, up-to-date renderings of posts (published, scheduled or draft) as X shows them, as preview URLs (iframe sources on ton.twimg.com). Up to 200 tweet ids per call; no spend involved.`},transport:{type:`rest`,method:`POST`,path:`/v1/workspaces/{workspaceId}/x/posts/preview`,auth:`user`,requestContentType:`application/json`}},{id:`x.list_x_promotable_users`,path:[`x`,`promotable-users`,`list`],summary:`Users whose posts this ads account may promote: the FULL user (nullcast posts are authored as this user — its user_id is the as_user_id for create tools) and any RETWEETS_ONLY users.`,description:``,source:`rest`,options:[{name:`workspaceId`,flag:`--workspace-id`,description:``,required:!0,valueType:`string`,location:`path`},{name:`account_id`,flag:`--account-id`,description:`X ads account id (e.g. 18ce55xcrlv). Omit it: it defaults to the ads account this client is connected to, and any other account is refused.`,required:!1,valueType:`string`,location:`body`}],examples:[{description:`Example`,command:`adside x promotable-users list --workspace-id <workspaceId>`}],output:{kind:`json`,description:`Users whose posts this ads account may promote: the FULL user (nullcast posts are authored as this user — its user_id is the as_user_id for create tools) and any RETWEETS_ONLY users.`},transport:{type:`rest`,method:`POST`,path:`/v1/workspaces/{workspaceId}/x/promotable-users/list`,auth:`user`,requestContentType:`application/json`}},{id:`x.get_x_promoted_post`,path:[`x`,`promoted-posts`,`get`],summary:`One promoted post by id with its tweet (text, media, card, landing URL), approval status and a rendered preview URL. Costs 3 requests.`,description:``,source:`rest`,options:[{name:`workspaceId`,flag:`--workspace-id`,description:``,required:!0,valueType:`string`,location:`path`},{name:`promoted_tweet_id`,flag:`--promoted-tweet-id`,description:`Promoted post id (base-36) from list_x_promoted_posts.`,required:!0,valueType:`string`,location:`body`}],examples:[{description:`Example`,command:`adside x promoted-posts get --workspace-id <workspaceId> --promoted-tweet-id <promoted_tweet_id>`}],output:{kind:`json`,description:`One promoted post by id with its tweet (text, media, card, landing URL), approval status and a rendered preview URL. Costs 3 requests.`},transport:{type:`rest`,method:`POST`,path:`/v1/workspaces/{workspaceId}/x/promoted-posts/get`,auth:`user`,requestContentType:`application/json`}},{id:`x.list_x_promoted_posts`,path:[`x`,`promoted-posts`,`list`],summary:`Promoted posts (promoted tweets) on the connected account, optionally for one line item or campaign, each with entity status, X's approval status and — by default — the post's text, media type and card from one batched tweet lookup. A promoted post is immutable: to change the creative, delete it and promote a new post.`,description:``,source:`rest`,options:[{name:`workspaceId`,flag:`--workspace-id`,description:``,required:!0,valueType:`string`,location:`path`},{name:`account_id`,flag:`--account-id`,description:`X ads account id (e.g. 18ce55xcrlv). Omit it: it defaults to the ads account this client is connected to, and any other account is refused.`,required:!1,valueType:`string`,location:`body`},{name:`line_item_id`,flag:`--line-item-id`,description:`Only promoted posts on this line item.`,required:!1,valueType:`string`,location:`body`},{name:`campaign_id`,flag:`--campaign-id`,description:`Only promoted posts in this campaign (its line items are looked up first).`,required:!1,valueType:`string`,location:`body`},{name:`approval_status`,flag:`--approval-status`,description:`Filter on X's review outcome.`,required:!1,valueType:`string`,enum:[`ACCEPTED`,`UNDER_REVIEW`,`REJECTED`],location:`body`},{name:`with_deleted`,flag:`--with-deleted`,description:``,required:!1,valueType:`boolean`,defaultValue:!1,location:`body`},{name:`with_text`,flag:`--with-text`,description:`Look up each promoted post's tweet for text, media and card (one batched request per 200).`,required:!1,valueType:`boolean`,defaultValue:!0,location:`body`},{name:`limit`,flag:`--limit`,description:`Maximum rows to return (bounds the answer, not the scan).`,required:!1,valueType:`number`,defaultValue:100,location:`body`}],examples:[{description:`Example`,command:`adside x promoted-posts list --workspace-id <workspaceId>`}],output:{kind:`json`,description:`Promoted posts (promoted tweets) on the connected account, optionally for one line item or campaign, each with entity status, X's approval status and — by default — the post's text, media type and card from one batched tweet lookup. A promoted post is immutable: to change the creative, delete it and promote a new post.`},transport:{type:`rest`,method:`POST`,path:`/v1/workspaces/{workspaceId}/x/promoted-posts/list`,auth:`user`,requestContentType:`application/json`}},{id:`x.get_x_stats`,path:[`x`,`stats`,`get`],summary:`Synchronous performance stats for up to 20 entities over at most 7 days (X's caps): any entity level, friendly metric names or X metric groups, DAY / HOUR / TOTAL granularity, one placement. Money is converted from X's micros; derived metrics (CPM, CPE, CTR, …) are computed here from X's formulas. Longer windows go through create_x_stats_job. Run get_x_active_entities first so you only ask about ids that had activity. Costs 1–3 requests.`,description:``,source:`rest`,options:[{name:`workspaceId`,flag:`--workspace-id`,description:``,required:!0,valueType:`string`,location:`path`},{name:`account_id`,flag:`--account-id`,description:`X ads account id (e.g. 18ce55xcrlv). Omit it: it defaults to the ads account this client is connected to, and any other account is refused.`,required:!1,valueType:`string`,location:`body`},{name:`entity`,flag:`--entity`,description:``,required:!1,valueType:`string`,defaultValue:`CAMPAIGN`,enum:[`ACCOUNT`,`FUNDING_INSTRUMENT`,`CAMPAIGN`,`LINE_ITEM`,`PROMOTED_TWEET`,`PROMOTED_ACCOUNT`,`MEDIA_CREATIVE`],location:`body`},{name:`entity_ids`,flag:`--entity-ids`,description:`Up to 20 ids of that entity (X's cap). For ACCOUNT omit it. Omit for CAMPAIGN / LINE_ITEM / PROMOTED_TWEET to use the entities active in the window (from get_x_active_entities, first 20).`,required:!1,valueType:`json`,location:`body`},{name:`preset`,flag:`--preset`,description:`Shortcut for a date range. Default last_7d when no start_date/end_date given.`,required:!1,valueType:`string`,enum:[`today`,`yesterday`,`last_7d`,`last_14d`,`last_30d`,`this_month`,`last_month`],location:`body`},{name:`start_date`,flag:`--start-date`,description:`First day, YYYY-MM-DD, in the account's time zone.`,required:!1,valueType:`string`,location:`body`},{name:`end_date`,flag:`--end-date`,description:`Last day (inclusive), YYYY-MM-DD, in the account's time zone. The exclusive end X wants is computed for you.`,required:!1,valueType:`string`,location:`body`},{name:`granularity`,flag:`--granularity`,description:`DAY buckets are midnight-to-midnight in the account's time zone; HOUR is hourly; TOTAL is one bucket.`,required:!1,valueType:`string`,defaultValue:`DAY`,enum:[`DAY`,`HOUR`,`TOTAL`],location:`body`},{name:`placement`,flag:`--placement`,description:`One placement per stats request (X accepts a single value). Default ALL_ON_TWITTER; other placements are separate calls.`,required:!1,valueType:`string`,defaultValue:`ALL_ON_TWITTER`,enum:[`ALL_ON_TWITTER`,`PUBLISHER_NETWORK`,`SPOTLIGHT`,`TREND`],location:`body`},{name:`metrics`,flag:`--metrics`,description:`Friendly metric names: spend, impressions, engagements, clicks, url_clicks, likes, follows, video_total_views, conversion_purchases, … plus derived ones (cpm, cpe, cplc, ctr, engagement_rate, cpv, cpa, roas) computed here. Default: the ENGAGEMENT + BILLING groups. See list_x_metrics.`,required:!1,valueType:`json`,location:`body`},{name:`metric_groups`,flag:`--metric-groups`,description:`X metric groups to request. MOBILE_CONVERSION must be requested alone.`,required:!1,valueType:`json`,location:`body`},{name:`format`,flag:`--format`,description:`json only when fields must be reused programmatically.`,required:!1,valueType:`string`,defaultValue:`markdown`,enum:[`markdown`,`json`],location:`body`}],examples:[{description:`Example`,command:`adside x stats get --workspace-id <workspaceId>`}],output:{kind:`json`,description:`Synchronous performance stats for up to 20 entities over at most 7 days (X's caps): any entity level, friendly metric names or X metric groups, DAY / HOUR / TOTAL granularity, one placement. Money is converted from X's micros; derived metrics (CPM, CPE, CTR, …) are computed here from X's formulas. Longer windows go through create_x_stats_job. Run get_x_active_entities first so you only ask about ids that had activity. Costs 1–3 requests.`},transport:{type:`rest`,method:`POST`,path:`/v1/workspaces/{workspaceId}/x/stats/get`,auth:`user`,requestContentType:`application/json`}},{id:`x.create_x_stats_job`,path:[`x`,`stats-job`,`create`],summary:`Start an asynchronous stats job for up to 20 entities over up to 90 days (45 if segmented), one placement, optional segmentation. Returns the job id; poll it with get_x_stats_job and download with fetch_x_stats_job_result. Read-like (no spend). Costs 1 request; X allows 100 concurrent jobs per account.`,description:``,source:`rest`,options:[{name:`workspaceId`,flag:`--workspace-id`,description:``,required:!0,valueType:`string`,location:`path`},{name:`account_id`,flag:`--account-id`,description:`X ads account id (e.g. 18ce55xcrlv). Omit it: it defaults to the ads account this client is connected to, and any other account is refused.`,required:!1,valueType:`string`,location:`body`},{name:`entity`,flag:`--entity`,description:``,required:!1,valueType:`string`,defaultValue:`CAMPAIGN`,enum:[`ACCOUNT`,`FUNDING_INSTRUMENT`,`CAMPAIGN`,`LINE_ITEM`,`PROMOTED_TWEET`,`PROMOTED_ACCOUNT`,`MEDIA_CREATIVE`],location:`body`},{name:`entity_ids`,flag:`--entity-ids`,description:`Up to 20 ids of that entity.`,required:!0,valueType:`json`,location:`body`},{name:`preset`,flag:`--preset`,description:`Shortcut for a date range. Default last_7d when no start_date/end_date given.`,required:!1,valueType:`string`,enum:[`today`,`yesterday`,`last_7d`,`last_14d`,`last_30d`,`this_month`,`last_month`],location:`body`},{name:`start_date`,flag:`--start-date`,description:`First day, YYYY-MM-DD, in the account's time zone.`,required:!1,valueType:`string`,location:`body`},{name:`end_date`,flag:`--end-date`,description:`Last day (inclusive), YYYY-MM-DD, in the account's time zone. The exclusive end X wants is computed for you.`,required:!1,valueType:`string`,location:`body`},{name:`granularity`,flag:`--granularity`,description:`DAY buckets are midnight-to-midnight in the account's time zone; HOUR is hourly; TOTAL is one bucket.`,required:!1,valueType:`string`,defaultValue:`DAY`,enum:[`DAY`,`HOUR`,`TOTAL`],location:`body`},{name:`placement`,flag:`--placement`,description:`One placement per stats request (X accepts a single value). Default ALL_ON_TWITTER; other placements are separate calls.`,required:!1,valueType:`string`,defaultValue:`ALL_ON_TWITTER`,enum:[`ALL_ON_TWITTER`,`PUBLISHER_NETWORK`,`SPOTLIGHT`,`TREND`],location:`body`},{name:`metric_groups`,flag:`--metric-groups`,description:`X metric groups to request. MOBILE_CONVERSION must be requested alone.`,required:!1,valueType:`json`,location:`body`},{name:`segmentation_type`,flag:`--segmentation-type`,description:`One segmentation per job (AGE, GENDER, METROS + country, PLATFORMS, CONVERSION_TAGS). Caps the window at 45 days. CAUTION: since April 2026 segmented jobs often return null metrics or 500s on X's side.`,required:!1,valueType:`string`,enum:[`AGE`,`GENDER`,`METROS`,`PLATFORMS`,`CONVERSION_TAGS`],location:`body`},{name:`country`,flag:`--country`,description:`Required with segmentation_type METROS.`,required:!1,valueType:`string`,location:`body`}],examples:[{description:`Example`,command:`adside x stats-job create --workspace-id <workspaceId> --entity-ids '{}'`}],output:{kind:`json`,description:`Start an asynchronous stats job for up to 20 entities over up to 90 days (45 if segmented), one placement, optional segmentation. Returns the job id; poll it with get_x_stats_job and download with fetch_x_stats_job_result. Read-like (no spend). Costs 1 request; X allows 100 concurrent jobs per account.`},transport:{type:`rest`,method:`POST`,path:`/v1/workspaces/{workspaceId}/x/stats-job/create`,auth:`user`,requestContentType:`application/json`}},{id:`x.get_x_stats_job`,path:[`x`,`stats-job`,`get`],summary:`Status of up to 200 async stats jobs (PROCESSING / SUCCESS / FAILED) with what each covers and when a finished result expires.`,description:``,source:`rest`,options:[{name:`workspaceId`,flag:`--workspace-id`,description:``,required:!0,valueType:`string`,location:`path`},{name:`account_id`,flag:`--account-id`,description:`X ads account id (e.g. 18ce55xcrlv). Omit it: it defaults to the ads account this client is connected to, and any other account is refused.`,required:!1,valueType:`string`,location:`body`},{name:`job_ids`,flag:`--job-ids`,description:`Job ids from create_x_stats_job.`,required:!0,valueType:`json`,location:`body`}],examples:[{description:`Example`,command:`adside x stats-job get --workspace-id <workspaceId> --job-ids '{}'`}],output:{kind:`json`,description:`Status of up to 200 async stats jobs (PROCESSING / SUCCESS / FAILED) with what each covers and when a finished result expires.`},transport:{type:`rest`,method:`POST`,path:`/v1/workspaces/{workspaceId}/x/stats-job/get`,auth:`user`,requestContentType:`application/json`}},{id:`x.fetch_x_stats_job_result`,path:[`x`,`stats-job-result`,`fetch`],summary:`Download a finished stats job's result (gzip JSON on X's CDN) and render it like get_x_stats: table under the byte budget, summary, derived metrics with formulas. Flags an all-null result explicitly. Costs 2 requests.`,description:``,source:`rest`,options:[{name:`workspaceId`,flag:`--workspace-id`,description:``,required:!0,valueType:`string`,location:`path`},{name:`account_id`,flag:`--account-id`,description:`X ads account id (e.g. 18ce55xcrlv). Omit it: it defaults to the ads account this client is connected to, and any other account is refused.`,required:!1,valueType:`string`,location:`body`},{name:`job_id`,flag:`--job-id`,description:`A job whose status is SUCCESS (get_x_stats_job).`,required:!0,valueType:`string`,location:`body`},{name:`metrics`,flag:`--metrics`,description:`Friendly metric names: spend, impressions, engagements, clicks, url_clicks, likes, follows, video_total_views, conversion_purchases, … plus derived ones (cpm, cpe, cplc, ctr, engagement_rate, cpv, cpa, roas) computed here. Default: the ENGAGEMENT + BILLING groups. See list_x_metrics.`,required:!1,valueType:`json`,location:`body`},{name:`format`,flag:`--format`,description:``,required:!1,valueType:`string`,defaultValue:`markdown`,enum:[`markdown`,`json`],location:`body`}],examples:[{description:`Example`,command:`adside x stats-job-result fetch --workspace-id <workspaceId> --job-id <job_id>`}],output:{kind:`json`,description:`Download a finished stats job's result (gzip JSON on X's CDN) and render it like get_x_stats: table under the byte budget, summary, derived metrics with formulas. Flags an all-null result explicitly. Costs 2 requests.`},transport:{type:`rest`,method:`POST`,path:`/v1/workspaces/{workspaceId}/x/stats-job-result/fetch`,auth:`user`,requestContentType:`application/json`}},{id:`x.suggest_x_targeting`,path:[`x`,`targeting`,`suggest`],summary:`X's targeting suggestions from seed keywords (more keywords) or seed user ids (similar accounts for FOLLOWERS_OF_USER / SIMILAR_TO_FOLLOWERS_OF_USER targeting). Costs 1 request.`,description:``,source:`rest`,options:[{name:`workspaceId`,flag:`--workspace-id`,description:``,required:!0,valueType:`string`,location:`path`},{name:`account_id`,flag:`--account-id`,description:`X ads account id (e.g. 18ce55xcrlv). Omit it: it defaults to the ads account this client is connected to, and any other account is refused.`,required:!1,valueType:`string`,location:`body`},{name:`suggestion_type`,flag:`--suggestion-type`,description:`What to suggest: keywords or user ids (handles' ids for follower targeting).`,required:!0,valueType:`string`,enum:[`KEYWORD`,`USER_ID`],location:`body`},{name:`targeting_values`,flag:`--targeting-values`,description:`Seeds of the same type: keywords, or numeric user ids.`,required:!0,valueType:`json`,location:`body`},{name:`count`,flag:`--count`,description:``,required:!1,valueType:`number`,defaultValue:30,location:`body`}],examples:[{description:`Example`,command:`adside x targeting suggest --workspace-id <workspaceId> --suggestion-type KEYWORD --targeting-values '{}'`}],output:{kind:`json`,description:`X's targeting suggestions from seed keywords (more keywords) or seed user ids (similar accounts for FOLLOWERS_OF_USER / SIMILAR_TO_FOLLOWERS_OF_USER targeting). Costs 1 request.`},transport:{type:`rest`,method:`POST`,path:`/v1/workspaces/{workspaceId}/x/targeting/suggest`,auth:`user`,requestContentType:`application/json`}},{id:`x.list_x_targeting_criteria`,path:[`x`,`targeting-criteria`,`list`],summary:`Every targeting criterion on the given line items (type, value, name, include/exclude), one block per line item with the combined-targeting summary. Primary types (followers, audiences, interests, keywords, TV) are OR'd across types; location / gender / language / device / platform / age are AND'd; same type OR'd; a line item with no criteria targets all users worldwide.`,description:``,source:`rest`,options:[{name:`workspaceId`,flag:`--workspace-id`,description:``,required:!0,valueType:`string`,location:`path`},{name:`account_id`,flag:`--account-id`,description:`X ads account id (e.g. 18ce55xcrlv). Omit it: it defaults to the ads account this client is connected to, and any other account is refused.`,required:!1,valueType:`string`,location:`body`},{name:`line_item_ids`,flag:`--line-item-ids`,description:`Line items whose criteria to list (X requires at least one; ≤200).`,required:!0,valueType:`json`,location:`body`},{name:`with_deleted`,flag:`--with-deleted`,description:``,required:!1,valueType:`boolean`,defaultValue:!1,location:`body`}],examples:[{description:`Example`,command:`adside x targeting-criteria list --workspace-id <workspaceId> --line-item-ids '{}'`}],output:{kind:`json`,description:`Every targeting criterion on the given line items (type, value, name, include/exclude), one block per line item with the combined-targeting summary. Primary types (followers, audiences, interests, keywords, TV) are OR'd across types; location / gender / language / device / platform / age are AND'd; same type OR'd; a line item with no criteria targets all users worldwide.`},transport:{type:`rest`,method:`POST`,path:`/v1/workspaces/{workspaceId}/x/targeting-criteria/list`,auth:`user`,requestContentType:`application/json`}},{id:`x.search_x_targeting_interests`,path:[`x`,`targeting-interests`,`search`],summary:`Interest categories X offers for INTEREST targeting (id + name, nested by 'Parent - Child'), optionally filtered by a search term. Put the id in a targeting criterion's targeting_value. X recommends refreshing taxonomy weekly.`,description:``,source:`rest`,options:[{name:`workspaceId`,flag:`--workspace-id`,description:``,required:!0,valueType:`string`,location:`path`},{name:`q`,flag:`--q`,description:`Search term, e.g. 'personal finance'. Omit for the full list.`,required:!1,valueType:`string`,location:`body`},{name:`limit`,flag:`--limit`,description:``,required:!1,valueType:`number`,defaultValue:50,location:`body`}],examples:[{description:`Example`,command:`adside x targeting-interests search --workspace-id <workspaceId>`}],output:{kind:`json`,description:`Interest categories X offers for INTEREST targeting (id + name, nested by 'Parent - Child'), optionally filtered by a search term. Put the id in a targeting criterion's targeting_value. X recommends refreshing taxonomy weekly.`},transport:{type:`rest`,method:`POST`,path:`/v1/workspaces/{workspaceId}/x/targeting-interests/search`,auth:`user`,requestContentType:`application/json`}},{id:`x.search_x_targeting_locations`,path:[`x`,`targeting-locations`,`search`],summary:`Resolve LOCATION targeting values (countries, regions, metros / DMAs, cities, postal codes) by name; the returned targeting_value is what a LOCATION criterion needs. Up to 2,000 locations per line item.`,description:``,source:`rest`,options:[{name:`workspaceId`,flag:`--workspace-id`,description:``,required:!0,valueType:`string`,location:`path`},{name:`q`,flag:`--q`,description:`Location name to search, e.g. 'Paris' or 'California'.`,required:!0,valueType:`string`,location:`body`},{name:`location_type`,flag:`--location-type`,description:`Narrow to one granularity.`,required:!1,valueType:`string`,enum:[`COUNTRIES`,`REGIONS`,`METROS`,`CITIES`,`POSTAL_CODES`],location:`body`},{name:`country_code`,flag:`--country-code`,description:`ISO-3166 country to search within.`,required:!1,valueType:`string`,location:`body`},{name:`limit`,flag:`--limit`,description:``,required:!1,valueType:`number`,defaultValue:50,location:`body`}],examples:[{description:`Example`,command:`adside x targeting-locations search --workspace-id <workspaceId> --q <q>`}],output:{kind:`json`,description:`Resolve LOCATION targeting values (countries, regions, metros / DMAs, cities, postal codes) by name; the returned targeting_value is what a LOCATION criterion needs. Up to 2,000 locations per line item.`},transport:{type:`rest`,method:`POST`,path:`/v1/workspaces/{workspaceId}/x/targeting-locations/search`,auth:`user`,requestContentType:`application/json`}},{id:`x.list_x_targeting_options`,path:[`x`,`targeting-options`,`list`],summary:`Static targeting vocabularies: devices, platforms, platform_versions, languages, network_operators, events, conversations, tv_shows, tv_markets, app_store_categories. Returns the name and the targeting_value each criterion needs. Global reads are rate-limited (400 / 15 min per category); tv_shows needs a tv_market_locale.`,description:``,source:`rest`,options:[{name:`workspaceId`,flag:`--workspace-id`,description:``,required:!0,valueType:`string`,location:`path`},{name:`kind`,flag:`--kind`,description:``,required:!0,valueType:`string`,enum:[`devices`,`platforms`,`platform_versions`,`languages`,`network_operators`,`events`,`conversations`,`tv_shows`,`tv_markets`,`app_store_categories`],location:`body`},{name:`q`,flag:`--q`,description:`Search term where the endpoint supports it (devices, platforms, events, conversations, tv_shows).`,required:!1,valueType:`string`,location:`body`},{name:`country_code`,flag:`--country-code`,description:`network_operators, events, tv_markets: ISO country filter.`,required:!1,valueType:`string`,location:`body`},{name:`tv_market_locale`,flag:`--tv-market-locale`,description:`tv_shows: locale from list_x_targeting_options(kind: tv_markets), e.g. en-US.`,required:!1,valueType:`string`,location:`body`},{name:`os_type`,flag:`--os-type`,description:`app_store_categories / platform_versions: platform filter.`,required:!1,valueType:`string`,enum:[`IOS`,`ANDROID`],location:`body`},{name:`limit`,flag:`--limit`,description:``,required:!1,valueType:`number`,defaultValue:200,location:`body`}],examples:[{description:`Example`,command:`adside x targeting-options list --workspace-id <workspaceId> --kind devices`}],output:{kind:`json`,description:`Static targeting vocabularies: devices, platforms, platform_versions, languages, network_operators, events, conversations, tv_shows, tv_markets, app_store_categories. Returns the name and the targeting_value each criterion needs. Global reads are rate-limited (400 / 15 min per category); tv_shows needs a tv_market_locale.`},transport:{type:`rest`,method:`POST`,path:`/v1/workspaces/{workspaceId}/x/targeting-options/list`,auth:`user`,requestContentType:`application/json`}},{id:`x.check_x_tracking_health`,path:[`x`,`tracking-health`,`check`],summary:`Is measurement wired up? Lists the account's web event tags (pixel events — if the endpoint answers), app event tags and third-party tracking tags, and which line items reference each. Pixel creation and event definitions live in Events Manager on ads.x.com, not the API. Costs 3–4 requests.`,description:``,source:`rest`,options:[{name:`workspaceId`,flag:`--workspace-id`,description:``,required:!0,valueType:`string`,location:`path`},{name:`account_id`,flag:`--account-id`,description:`X ads account id (e.g. 18ce55xcrlv). Omit it: it defaults to the ads account this client is connected to, and any other account is refused.`,required:!1,valueType:`string`,location:`body`}],examples:[{description:`Example`,command:`adside x tracking-health check --workspace-id <workspaceId>`}],output:{kind:`json`,description:`Is measurement wired up? Lists the account's web event tags (pixel events — if the endpoint answers), app event tags and third-party tracking tags, and which line items reference each. Pixel creation and event definitions live in Events Manager on ads.x.com, not the API. Costs 3–4 requests.`},transport:{type:`rest`,method:`POST`,path:`/v1/workspaces/{workspaceId}/x/tracking-health/check`,auth:`user`,requestContentType:`application/json`}},{id:`x.list_x_tracking_tags`,path:[`x`,`tracking-tags`,`list`],summary:`Third-party impression / click tracking tags attached to line items on the connected account (type, URL, line item). Pixel events themselves are web event tags — see check_x_tracking_health.`,description:``,source:`rest`,options:[{name:`workspaceId`,flag:`--workspace-id`,description:``,required:!0,valueType:`string`,location:`path`},{name:`account_id`,flag:`--account-id`,description:`X ads account id (e.g. 18ce55xcrlv). Omit it: it defaults to the ads account this client is connected to, and any other account is refused.`,required:!1,valueType:`string`,location:`body`},{name:`line_item_ids`,flag:`--line-item-ids`,description:`Only tags on these line items.`,required:!1,valueType:`json`,location:`body`},{name:`with_deleted`,flag:`--with-deleted`,description:``,required:!1,valueType:`boolean`,defaultValue:!1,location:`body`}],examples:[{description:`Example`,command:`adside x tracking-tags list --workspace-id <workspaceId>`}],output:{kind:`json`,description:`Third-party impression / click tracking tags attached to line items on the connected account (type, URL, line item). Pixel events themselves are web event tags — see check_x_tracking_health.`},transport:{type:`rest`,method:`POST`,path:`/v1/workspaces/{workspaceId}/x/tracking-tags/list`,auth:`user`,requestContentType:`application/json`}}]};function Ke(e=process.env,t=process.platform){return e.ADSIDE_CONFIG_DIR?e.ADSIDE_CONFIG_DIR:t===`win32`?h.join(qe(e.APPDATA,h.win32)??h.join(y.homedir(),`AppData`,`Roaming`),`adside`):h.join(qe(e.XDG_CONFIG_HOME,h.posix)??h.join(y.homedir(),`.config`),`adside`)}function qe(e,t){return e&&t.isAbsolute(e)?e:void 0}async function U(e){await a(e,{recursive:!0,mode:448}),process.platform!==`win32`&&await i(e,448)}async function Je(e,t){let n=`${e}.${r()}.tmp`;try{await f(n,t,{mode:384,flag:`wx`}),process.platform!==`win32`&&await i(n,384),await c(n,e)}catch(e){throw await l(n,{force:!0}),e}}const Ye={profile:`default`,profiles:{}};async function Xe(e){try{let t=JSON.parse(await s(h.join(e,`config.json`),`utf8`));if(!t||typeof t!=`object`)return{...Ye};let n=t;return{profile:typeof n.profile==`string`?n.profile:`default`,profiles:n.profiles&&typeof n.profiles==`object`?n.profiles:{},warnedFileStore:n.warnedFileStore===!0}}catch(t){if(t.code===`ENOENT`)return{...Ye,profiles:{}};throw Error(`Cannot read ${h.join(e,`config.json`)}: ${t.message}`)}}async function Ze(e,t){await U(e),await Je(h.join(e,`config.json`),`${JSON.stringify(t,null,2)}\n`)}const Qe={heartbeatMs:5e3,staleMs:3e4,waitMs:45e3};async function W(e,t,n={}){let i=n.timing??Qe,a=n.sleep??(e=>new Promise(t=>setTimeout(t,e))),o=h.join(e,`login.lock`),s=r();await U(e);let c=Date.now()+i.waitMs;for(;;)try{await f(o,s,{flag:`wx`,mode:384});break}catch(e){if(e.code!==`EEXIST`)throw e;let t=await tt(o);if(!t||Date.now()-t.touchedAt>i.staleMs&&await $e(o,t.owner,s,i))continue;if(Date.now()>c)throw Error(`Another adside command is still refreshing the login. Try again in a moment.`);await a(100)}let u=setInterval(()=>{let e=new Date;d(o,e,e).catch(()=>void 0)},i.heartbeatMs);u.unref();try{return await t()}finally{clearInterval(u),await et(o)===s&&await l(o,{force:!0})}}async function $e(e,t,n,r){let i=`${e}.${/^[\w-]{1,64}$/.test(t)?t:`unknown`}.takeover`;try{await f(i,n,{flag:`wx`,mode:384})}catch(e){if(e.code!==`EEXIST`)throw e;return await u(i).then(e=>Date.now()-e.mtimeMs,()=>0)<=r.staleMs?!1:(await l(i,{force:!0}),!0)}try{let n=await tt(e);n?.owner===t&&Date.now()-n.touchedAt>r.staleMs&&await l(e,{force:!0})}finally{await l(i,{force:!0})}return!0}async function et(e){return s(e,`utf8`).catch(()=>null)}async function tt(e){let t;try{t=await o(e,`r`)}catch(e){if(e.code===`ENOENT`)return null;throw e}try{let e=await t.stat();return{owner:await t.readFile(`utf8`),touchedAt:e.mtimeMs}}finally{await t.close()}}const G=`adside-cli`;function nt(e,t){let n=new URL(e),r=[`localhost`,`127.0.0.1`,`[::1]`].includes(n.hostname);if(n.protocol!==`https:`&&!(n.protocol===`http:`&&r))throw Error(`${t} must use https: ${n.origin}`);return n}function rt(){let e=n(32).toString(`base64url`);return{verifier:e,challenge:t(`sha256`).update(e).digest(`base64url`)}}function it(e){let t=new URL(`/api/auth/oauth2/authorize`,e.authUrl);return t.search=new URLSearchParams({client_id:G,response_type:`code`,redirect_uri:e.redirectUri,scope:`openid offline_access adside`,code_challenge:e.challenge,code_challenge_method:`S256`,resource:e.resource,state:e.state}).toString(),t.toString()}async function at(e){let t,n,r=new Promise((e,r)=>{t=e,n=r}),i=b((r,i)=>{let a=new URL(r.url??`/`,`http://127.0.0.1`);if(a.pathname!==`/callback`){i.writeHead(404).end();return}let o=a.searchParams.get(`error`),s=a.searchParams.get(`code`);if(a.searchParams.get(`state`)!==e.state){i.writeHead(400).end(`This login was started elsewhere.`),n(Error(`Login refused: the callback's state did not match`));return}if(o||!s){i.writeHead(400).end(`Login was not approved.`),n(Error(o===`access_denied`?`Login cancelled in the browser`:`Login failed: ${o??`no code returned`}`));return}i.writeHead(200,{"content-type":`text/html; charset=utf-8`}),i.end(`<!doctype html><meta charset="utf-8"><title>Adside CLI</title>
22
+ <body style="font-family:system-ui,sans-serif;max-width:32rem;margin:15vh auto;padding:0 1.5rem;color:#3a3c40">
23
+ <h1 style="color:#0c0c0c;font-size:1.5rem">You're logged in</h1>
24
+ <p>You can close this tab and go back to your terminal.</p></body>`),t(s)});await new Promise(e=>i.listen(0,`127.0.0.1`,e));let a=i.address();if(!a||typeof a==`string`)throw i.close(),Error(`Could not open a local port for the login`);let{port:o}=a,s=setTimeout(()=>n(Error(`Login timed out; run adside login again`)),e.timeoutMs),c=()=>{clearTimeout(s),i.close()};return r.then(c,c),{redirectUri:`http://127.0.0.1:${o}/callback`,code:r,close:c}}var K=class extends Error{constructor(e,t){super(e),this.code=t,this.name=`OAuthError`}};async function ot(e,t,n,r,i){let a=await n(new URL(`/api/auth/oauth2/token`,e),{method:`POST`,headers:{"content-type":`application/x-www-form-urlencoded`},body:new URLSearchParams(t),redirect:`error`}),o=await a.json().catch(()=>({}));if(!a.ok||typeof o.access_token!=`string`)throw new K(typeof o.error_description==`string`?o.error_description:`Token request failed (HTTP ${a.status})`,typeof o.error==`string`?o.error:`server_error`);let s=typeof o.refresh_token==`string`?o.refresh_token:i;if(!s)throw new K(`The server returned no refresh token`,`invalid`);return{accessToken:o.access_token,refreshToken:s,...typeof o.id_token==`string`?{idToken:o.id_token}:{},expiresAt:r()+(typeof o.expires_in==`number`?o.expires_in:900)*1e3}}function st(e){return ot(e.authUrl,{grant_type:`authorization_code`,client_id:G,code:e.code,code_verifier:e.verifier,redirect_uri:e.redirectUri,resource:e.resource},e.fetch??fetch,e.now??Date.now)}function ct(e){return ot(e.authUrl,{grant_type:`refresh_token`,client_id:G,refresh_token:e.refreshToken,resource:e.resource},e.fetch??fetch,e.now??Date.now,e.refreshToken)}async function lt(e){try{let t=await(e.fetch??fetch)(new URL(`/api/auth/oauth2/revoke`,e.authUrl),{method:`POST`,headers:{"content-type":`application/x-www-form-urlencoded`},body:new URLSearchParams({client_id:G,token:e.refreshToken,token_type_hint:`refresh_token`}),redirect:`error`,signal:AbortSignal.timeout(3e4)});return await t.body?.cancel(),t.ok}catch{return!1}}const ut=6e4,q="Not logged in. Run `adside login`.";function dt(e){let t=e.now??Date.now,n=e.sleep??(e=>new Promise(t=>setTimeout(t,e)));async function r(r){return W(e.dir,async()=>{let n=await e.store.read(e.key);if(!n)throw Error(q);let i=n.expiresAt-t()>ut;if(r===void 0?i:n.accessToken!==r)return n.accessToken;let a;try{a=await ct({authUrl:e.authUrl,refreshToken:n.refreshToken,resource:e.resource,fetch:e.fetch,now:t})}catch(t){throw t instanceof K&&t.code===`invalid_grant`?(await e.store.remove(e.key),Error("Your login has expired or was revoked. Run `adside login`.")):t}return await e.store.write(e.key,a),a.accessToken},{sleep:n})}return{async accessToken(){let n=await e.store.read(e.key);if(!n)throw Error(q);return n.expiresAt-t()>ut?n.accessToken:r()},refreshAfterRejection(e){return r(e)}}}function ft(e){return W(e.dir,async()=>{let t=await e.store.read(e.key);if(!t)return{loggedOut:!1,revoked:!1};let n=await lt({authUrl:e.authUrl,refreshToken:t.refreshToken,fetch:e.fetch});return await e.store.remove(e.key),{loggedOut:!0,revoked:n}})}function pt(e){if(!e)return null;try{let t=JSON.parse(e);return typeof t.accessToken==`string`&&typeof t.refreshToken==`string`&&typeof t.expiresAt==`number`?t:null}catch{return null}}function mt(e){let t=t=>new e.AsyncEntry(`adside-cli`,t,{linux:{store:`secret-service`}});return{kind:`keychain`,async read(e){return pt(await t(e).getPassword())},async write(e,n){await t(e).setPassword(JSON.stringify(n))},async remove(e){await t(e).deletePassword()}}}function ht(e){let t=h.join(e,`credentials.json`),n=async()=>{try{let e=JSON.parse(await s(t,`utf8`));return e&&typeof e==`object`?e:{}}catch(e){if(e.code===`ENOENT`)return{};throw Error(`Cannot read ${t}: ${e.message}`)}},r=async n=>{if(await U(e),Object.keys(n).length===0){await l(t,{force:!0});return}await Je(t,`${JSON.stringify(n,null,2)}\n`)};return{kind:`file`,async read(e){return pt(JSON.stringify((await n())[e]??null))},async write(e,t){await r({...await n(),[e]:t})},async remove(e){let{[e]:t,...i}=await n();await r(i)}}}async function J(e,t=()=>import(`@napi-rs/keyring`)){let n=ht(e);if(process.env.ADSIDE_CREDENTIAL_STORE===`file`||await u(h.join(e,`credentials.json`)).then(()=>!0,()=>!1))return n;try{let e=mt(await t());return await e.read(`adside-cli-probe`),e}catch{return n}}function Y(e,t){let n=e.profiles[t]??{},r=(process.env.API_GATEWAY_URL||n.apiUrl||`https://api.adside.ai`).replace(/\/+$/,``),i=(process.env.ADSIDE_AUTH_URL||n.authUrl||`https://app.adside.ai`).replace(/\/+$/,``);return nt(r,`The API URL`),nt(i,`The login URL`),{apiUrl:r,authUrl:i,resource:process.env.ADSIDE_API_RESOURCE_URL||`${r}/v1`,key:`${t}@${new URL(r).host}`}}function X(e){return process.env.ADSIDE_PROFILE||e.profile}function Z(e){process.stdout.write(`${JSON.stringify(e,null,2)}\n`)}function Q(e){process.stderr.write(`${e}\n`)}function gt(e){let[t,n]=process.platform===`darwin`?[`open`,[e]]:process.platform===`win32`?[`rundll32`,[`url.dll,FileProtocolHandler`,e]]:[`xdg-open`,[e]];try{_(t,n,{stdio:`ignore`,detached:!0}).on(`error`,()=>void 0).unref()}catch{}}async function _t(e){let t=v({input:process.stdin,output:process.stderr});try{return(await t.question(e)).trim()}finally{t.close()}}async function $(e,t){let n=await x(E(e,t),`me.get`,{}),r=S(n.user),i=(Array.isArray(n.organizations)?n.organizations.map(S):[]).flatMap(e=>(Array.isArray(e.workspaces)?e.workspaces.map(S):[]).map(t=>({id:String(t.id),name:String(t.name),organizationId:String(e.id),organizationName:String(e.name)})));return{email:String(r.email),workspaces:i}}async function vt(e){if(e.length===1)return e[0];if(!process.stdin.isTTY||e.length===0)return;Q(`
25
+ Which workspace should commands use by default?`),e.forEach((e,t)=>Q(` ${t+1}. ${e.name} (${e.organizationName})`));let t=Number(await _t(`Number [1-${e.length}]: `));return Number.isInteger(t)?e[t-1]:void 0}function yt(){let e=Ke(),t,r=()=>t??=Xe(e),i={async configure(t){let n=await r(),{apiUrl:i,authUrl:a,resource:o,key:s}=Y(n,X(n)),c,l=async()=>c??=dt({store:await J(e),key:s,authUrl:a,resource:o,dir:e});return{...t,apiGatewayUrl:i,missingCredentialMessage:q,login:{accessToken:async()=>(await l()).accessToken(),refreshAfterRejection:async e=>(await l()).refreshAfterRejection(e)}}},async defaults(){let e=await r(),t=e.profiles[X(e)]??{};return{workspaceId:t.workspaceId,organizationId:t.organizationId}},register(t,a){t.command(`login`).description(`Log in to Adside in your browser`).option(`--no-browser`,`Print a link to open on another device, then paste the code it shows`).option(`--profile <name>`,`Save this login under a profile name`).action(async t=>{let i=await r(),o=t.profile||process.env.ADSIDE_PROFILE||i.profile,{apiUrl:s,authUrl:c,resource:l,key:u}=Y(i,o),{verifier:d,challenge:f}=rt(),p=n(16).toString(`base64url`),m,h;if(t.browser){let e=await at({state:p,timeoutMs:3e5});h=e.redirectUri;let t=it({authUrl:c,redirectUri:h,state:p,challenge:f,resource:l});Q(`Opening your browser to log in. If it does not open, visit:\n\n ${t}\n`),gt(t),m=await e.code}else{h=`${c}/cli/callback`,Q(`Open this link, log in, and paste the code it shows:\n\n ${it({authUrl:c,redirectUri:h,state:p,challenge:f,resource:l})}\n`);let[e,t]=(await _t(`Code: `)).split(`#`);if(!e||t===void 0)throw Error(`Paste the whole code the page shows, with the part after #; run adside login --no-browser again`);if(t!==p)throw Error(`This code belongs to another login attempt; run adside login again`);m=e}let g=await st({authUrl:c,code:m,verifier:d,redirectUri:h,resource:l}),_=await J(e);await W(e,()=>_.write(u,g));let v=await $({apiGatewayUrl:s,apiKey:g.accessToken},a),y={...i.profiles[o]??{},...process.env.API_GATEWAY_URL?{}:{apiUrl:s},...process.env.ADSIDE_AUTH_URL?{}:{authUrl:c}};if(!v.workspaces.some(({id:e})=>e===y.workspaceId)){let e=await vt(v.workspaces);y.workspaceId=e?.id,y.organizationId=e?.organizationId}let b=_.kind===`file`&&!i.warnedFileStore;b&&Q(`No credential store is available: the login is saved in ${e}/credentials.json, readable only by you.`),await Ze(e,{...i,profile:o,profiles:{...i.profiles,[o]:y},warnedFileStore:i.warnedFileStore||b}),!y.workspaceId&&v.workspaces.length>1&&Q(`Choose a default workspace with: adside use <workspace>`),Q(`Logged in as ${v.email}.`),Z({email:v.email,profile:o,workspaceId:y.workspaceId??null,credentialStore:_.kind})}),t.command(`logout`).description(`Log out and revoke this login`).action(async()=>{let t=await r(),n=X(t),{authUrl:i,key:a}=Y(t,n),{loggedOut:o,revoked:s}=await ft({store:await J(e),key:a,authUrl:i,dir:e});if(!o){Q(`Not logged in.`),Z({loggedOut:!1,profile:n});return}Q(s?`Logged out.`:`Logged out on this computer, but the server did not confirm the revocation: revoke the login in Settings → Sessions.`),Z({loggedOut:!0,profile:n,revoked:s})}),t.command(`use`).description(`Choose the workspace commands use by default, or list them`).argument(`[workspace]`,`Workspace ID or exact name`).action(async t=>{let n=await r(),o=X(n),{workspaces:s}=await $(await i.configure(le(`json`)),a),c=n.profiles[o]??{};if(!t){Z(s.map(e=>({...e,default:e.id===c.workspaceId})));return}let l=s.filter(({id:e,name:n})=>e===t||n.toLowerCase()===t.toLowerCase());if(l.length!==1)throw Error(l.length?`Several workspaces are named "${t}": use an ID (${l.map(({id:e})=>e).join(`, `)})`:`No workspace "${t}" in your account; adside use lists them`);let[u]=l;await Ze(e,{...n,profiles:{...n.profiles,[o]:{...c,workspaceId:u.id,organizationId:u.organizationId}}}),Q(`Commands now use ${u.name}.`),Z(u)})}};return i}Ee(Ge,yt());export{};