OmniSocials
Server Details
Official OmniSocials MCP server — schedule and publish posts, stories, and reels across 11 platforms (Instagram, Facebook, LinkedIn, YouTube, TikTok, X, Pinterest, Bluesky, Threads, Mastodon, Google Business), plus media, analytics, hashtag sets, inbox, and webhooks.
- Status
- Healthy
- Uptime
- 41.1% over 58 days
- OAuth
- Works in Glama
- Last Tested
- Transport
- Streamable HTTP · MCP 2025-11-25
- URL
TDQS
Scored across 57 tools
Most tools have clearly distinct resource/action boundaries, and the descriptions do a good job separating the post lifecycle, analytics scopes, inbox moderation, approvals, automations, and webhooks. There are some overlaps: create_post vs create_and_publish_post vs publish_post vs retry_post, several analytics tools, and get_post_status is explicitly redundant with get_post.
Tool names consistently use snake_case with verb-first patterns (list_*, get_*, create_*, update_*, delete_*, reply_*, upload_*). A few compound names like create_and_publish_post and get_next_unanswered deviate in length but remain predictable and readable.
57 tools is far beyond a typical well-scoped MCP surface and will create substantial selection overhead for an agent. The domain is broad, but many niche tools could be consolidated or scoped behind fewer entry points.
The server covers post creation, scheduling, publishing, retrying, approvals, media, folders, hashtag sets, inbox, analytics, automations, webhooks, workspaces, Pinterest products, audio, and locations. Minor gaps remain, such as no folder rename/delete and read-only approval workflows, but core workflows are well covered.
Available Tools
57 toolsapprove_postADestructiveInspect
Approve the current step of a post's approval workflow. Only works on a post with approval_status 'pending' (post status in_approval) — check get_post first. IMPORTANT: only succeeds if the connected user is a listed approver for the workflow's CURRENT step (steps approve in order); a forbidden error means the user isn't an approver for this step yet — tell them who needs to approve instead, don't retry. If this is the last step, the post is finalized immediately (moves to scheduled or posting). If steps remain, the post stays in_approval and the next step's approvers are notified.
| Name | Required | Description | Default |
|---|---|---|---|
| id | Yes | The post ID to approve (must have approval_status 'pending') |
TDQS
Does the description disclose side effects, auth requirements, rate limits, or destructive behavior?
Annotations only give the safety profile (readOnlyHint=false, destructiveHint=true, openWorldHint=true); the description adds substantial context beyond them: ordered step approval, the auth requirement that the user must be a listed approver for the CURRENT step, the meaning of a forbidden error, and the exact resulting state transitions. This goes well past what the structured fields convey.
Agents need to know what a tool does to the world before calling it. Descriptions should go beyond structured annotations to explain consequences.
Is the description appropriately sized, front-loaded, and free of redundancy?
Dense but front-loaded: purpose first, then precondition, then auth/error semantics, then outcome. Every sentence carries operational weight, though the 'approval_status pending (post status in_approval)' phrasing and the id precondition are mildly redundant with the schema.
Shorter descriptions cost fewer tokens and are easier for agents to parse. Every sentence should earn its place.
Given the tool's complexity, does the description cover enough for an agent to succeed on first attempt?
For a mutating workflow tool with no output schema, the description covers everything needed to call it correctly: precondition, prerequisite read, authorization rules, failure interpretation, and post-condition state changes. Nothing material is missing.
Complex tools with many parameters or behaviors need more documentation. Simple tools need less. This dimension scales expectations accordingly.
Does the description clarify parameter syntax, constraints, interactions, or defaults beyond what the schema provides?
Schema coverage is 100% with a single parameter whose schema description already states the 'pending' approval_status constraint, so the description's restatement of that constraint adds little. Baseline 3 is appropriate when the schema fully documents the parameter.
Input schemas describe structure but not intent. Descriptions should explain non-obvious parameter relationships and valid value ranges.
Does the description clearly state what the tool does and how it differs from similar tools?
States a specific verb (approve) and resource (the current step of a post's approval workflow), and explicitly frames it as a step-wise action distinct from reject_post or publish_post. An agent can distinguish it from all siblings without opening a schema.
Agents choose between tools based on descriptions. A clear purpose with a specific verb and resource helps agents select the right tool.
Does the description explain when to use this tool, when not to, or what alternatives exist?
Explicit preconditions ('Only works on a post with approval_status pending'), a prerequisite action ('check get_post first'), and error handling guidance ('a forbidden error means the user isn't an approver for this step yet — tell them who needs to approve instead, don't retry'). This is textbook when/when-not guidance.
Agents often have multiple tools that could apply. Explicit usage guidance like "use X instead of Y when Z" prevents misuse.
check_media_compatibilityARead-onlyInspect
Check whether a video/image will be accepted by the platforms CONNECTED to this workspace, BEFORE uploading or posting. Use this when the user gives you a file (URL) so you can warn them upfront — e.g. "this 995 MB video won't post to Instagram (max 300 MB), continue?" — then confirm before uploading. Provide ONE of: a public 'url' (size/type read via HEAD), an existing 'media_id', or 'size_bytes' + 'mime'. For an image with a known size (a library file) the answer also has IMAGE FIT rows: per connected channel, whether its feed shows the image uncropped and what a post does by default (Instagram crops a 9:16 / wide image to 4:5 / 1.91:1 around the subject; Pinterest keeps a tall Pin and reports it). When a row says fits: false, ask the user "crop to (recommended for Instagram: Meta can boost it) or keep the original (the channel cuts it itself)?" and pass the answer as media_fit on create_post.
| Name | Required | Description | Default |
|---|---|---|---|
| url | No | Public URL of the file to check. Use this OR media_id OR size_bytes+mime. | |
| mime | No | MIME type, e.g. 'video/mp4' (use with size_bytes). | |
| media_id | No | Id of an already-uploaded library item to check. | |
| size_bytes | No | File size in bytes (use with mime). |
TDQS
Does the description disclose side effects, auth requirements, rate limits, or destructive behavior?
Annotations only declare readOnly=true, destructive=false, openWorld=true. The description goes well beyond them: it explains the HEAD-based size/type read, the IMAGE FIT rows returned per channel, and the semantics of fits: false with the crop vs. keep choice. This is substantial behavioral detail an agent cannot get from the annotations.
Agents need to know what a tool does to the world before calling it. Descriptions should go beyond structured annotations to explain consequences.
Is the description appropriately sized, front-loaded, and free of redundancy?
Front-loaded with the core purpose, and most sentences earn their place. It is on the long side, and the crop-handling / media_fit instructions lean toward create_post's territory, but the density is high and nothing is pure filler.
Shorter descriptions cost fewer tokens and are easier for agents to parse. Every sentence should earn its place.
Given the tool's complexity, does the description cover enough for an agent to succeed on first attempt?
There is no output schema, so the description carries the return-value burden, and it does: it describes the size/type acceptance result and the per-channel IMAGE FIT rows including the fits flag. Combined with the read-only annotations, an agent has enough to call it and interpret the response.
Complex tools with many parameters or behaviors need more documentation. Simple tools need less. This dimension scales expectations accordingly.
Does the description clarify parameter syntax, constraints, interactions, or defaults beyond what the schema provides?
Schema coverage is 100%, so the baseline is 3, but the description adds genuine value by clarifying the mutual-exclusion grouping: 'Provide ONE of: a public url (size/type read via HEAD), an existing media_id, or size_bytes + mime.' That constrains invocation mode beyond the individual field descriptions.
Input schemas describe structure but not intent. Descriptions should explain non-obvious parameter relationships and valid value ranges.
Does the description clearly state what the tool does and how it differs from similar tools?
States a specific verb and resource ('Check whether a video/image will be accepted by the platforms CONNECTED to this workspace') and pins the timing ('BEFORE uploading or posting'). This clearly distinguishes it from siblings like upload_media and create_post without needing to open a schema.
Agents choose between tools based on descriptions. A clear purpose with a specific verb and resource helps agents select the right tool.
Does the description explain when to use this tool, when not to, or what alternatives exist?
Explicit when-to-use: 'Use this when the user gives you a file (URL) so you can warn them upfront.' It also sequences the workflow (check, then confirm before uploading) and routes the follow-up action ('pass the answer as media_fit on create_post'), so the agent knows both when to call it and what to do with the result.
Agents often have multiple tools that could apply. Explicit usage guidance like "use X instead of Y when Z" prevents misuse.
create_and_publish_postADestructiveInspect
Create a new post and publish it immediately (no scheduling). Same media rules, channel IDs, and workspace selection rule as create_post apply (only one workspace → use it; multiple workspaces with no named one → ask first; named workspace → use and remember; mention workspace name on success). linkedin (personal profile) and linkedin_page (company page) are independent channels.
Pinterest board (auto-default to first board): If Pinterest is in channels and pinterest.board_id is NOT provided, do NOT block on asking — and do NOT skip Pinterest. Call get_account on the Pinterest account, take the FIRST board from the returned boards list, and pass its id as pinterest.board_id. In your reply, mention which board you used (e.g. "Published to your 'Marketing' board on Pinterest — let me know if you'd prefer a different one.") so the user can redirect. If the user named a specific board in the request, match it (case-insensitive) against the list and use that one instead.
X threads: For a chained X thread, pass x.thread_parts (2–25 { text } parts, each <= 280 chars). Do NOT split into "1/", "2/" inside content — that posts a single tweet, not a thread.
X posts containing a link: X treats a post whose text contains a link written with http:// or https:// as a link post (a bare domain or a www. link does not count). Link posts on X are a feature the organisation enables on its OmniSocials account. When it is not enabled, the request is refused up front with an x_feature_not_enabled error, or the X target alone fails while the other platforms still publish: tell the user, offer to post without the link or without X, and do not retry as is. Never remove a user's link without asking them.
| Name | Required | Description | Default |
|---|---|---|---|
| x | No | X (Twitter) options: thread mode via `thread_parts`, a poll via `poll`. | |
| type | No | ||
| tiktok | No | TikTok options | |
| bluesky | No | Bluesky options, including thread mode via `thread_parts`. | |
| content | Yes | Post caption. String or object with platform keys for per-channel captions: { "default": "fallback", "linkedin": "long", "threads": "short" }. Prefer one call per topic. | |
| discord | No | Discord options. The post goes to the connected Discord channel through its webhook and shows the webhook's name and picture. Text up to 2,000 chars. Up to 10 images, GIFs and videos per message (they may mix); a video or GIF over Discord's 20 MB file limit is sent as a link in the text. No Stories; a 'reel' is sent as one video message. | |
| threads | No | Threads options: thread mode via `thread_parts`, location tag via `location_id`, a poll via `poll`, the topic via `topic_tag`. | |
| youtube | No | YouTube Shorts options. Only applies when type is 'reel' and youtube is among the selected channels. A custom Shorts thumbnail is set with the top-level `video_cover` (a `youtube` override for a YouTube-only image); it shows on Shorts only on channels where YouTube has enabled custom Shorts thumbnails (Partner Program channels first, since July 2026), other channels show a frame from the video. | |
| channels | No | Array of channel IDs to post to (e.g. linkedin, linkedin_page, instagram). | |
| No | Facebook options | ||
| link_url | No | URL to share as a rich preview card on platforms that support link-share posts (LinkedIn and Facebook). Renders as a tile with thumbnail/title/description instead of plain text. Ignored on platforms that don't support link shares, and ignored on posts that already have media attached (media wins). | |
| No | LinkedIn Profile options | ||
| mastodon | No | Mastodon options: thread mode via `thread_parts`, a poll via `poll`. | |
| telegram | No | Telegram options. Text up to 4,096 chars; with media, text over 1,024 chars is sent as a reply under the media. Up to 10 photos and videos per album, videos up to 50 MB, no Stories. A 'reel' is sent as a video message. | |
| No | Instagram options | ||
| media_fit | No | Image fit per channel, for feed images (type 'post') whose ratio is outside what a channel shows uncropped: { instagram: 'auto' | 'crop' | 'keep', pinterest: ... }. 'auto' (the default when omitted) takes the channel's rule: Instagram crops a tall (9:16) or wide image to 4:5 / 1.91:1 around the subject (Instagram cuts it to that window anyway, and Meta cannot boost a feed post outside it); Pinterest keeps a Pin taller than 2:3 and only reports it. 'crop' / 'keep' force it for that channel. Every decision comes back in the response `warnings` with code `image_fit` (relay it). The crop is a separate file for that channel only; 'default' and the other channels keep the original. On update_post, media_fit alone (no media) re-decides the stored images: 'keep' gives the original back, 'crop' crops an image that was kept. | |
| media_ids | No | ||
| No | |||
| user_tags | No | Instagram only. Tag public accounts at x/y positions on a PHOTO (not video/reels/stories). For a single image omit image_index; for a carousel, set image_index to the slide each tag belongs to. Private/non-existent usernames are rejected at publish time. Ignored by other platforms. | |
| link_title | No | Optional title for the link-share preview. LinkedIn uses this when set; Facebook ignores it and fetches OG metadata server-side. Omit to let LinkedIn auto-fetch the page title. | |
| media_urls | No | External image/video/PDF URLs — flat array or per-platform object. Max 10 total (Pinterest: max 5 images per carousel pin), each file ≤ 100 MB. Entries are URL strings or { url, alt } objects (alt = accessibility description, delivered to Mastodon/Bluesky/X/Pinterest/Instagram (images)/LinkedIn (images)). For larger files (up to 1 GB): upload_media with method 'url' first, then pass the returned media id in `media`. | |
| hashtag_set | No | Name of a saved hashtag set (from list_hashtag_sets, matched case-insensitively) to apply to this post. The set's tags are merged in once at create time; tags already present in a caption are skipped. When the user says something like 'add my usual hashtags', check list_hashtag_sets first. Instagram's 5-hashtag cap is enforced with a clear error (hashtag_limit_exceeded). | |
| location_id | No | Instagram only. Facebook Place ID for a single physical venue (with a street address) to tag the post's location. Find it via the location search in the OmniSocials dashboard. Ignored by other platforms. | |
| video_cover | No | Video thumbnail for a post whose media is ONE video. Applied on Instagram (feed videos and reels), Facebook (feed videos and reels), LinkedIn Profile and Page, TikTok, Pinterest and YouTube Shorts. YouTube Shorts: the cover shows on Shorts only on channels where YouTube has enabled custom Shorts thumbnails (rolling out since July 2026, Partner Program channels first); on other channels YouTube stores it as the default thumbnail but shows a frame from the video on Shorts. Say that it depends on the channel; do not promise it. TikTok only takes a frame: a 'custom' cover is skipped there, so add a tiktok override with type 'frame' when the user wants a specific TikTok frame. The per-platform reel fields (instagram.thumb_offset / cover_url, tiktok.video_cover_timestamp_ms, pinterest.video_cover) keep working and win over the base cover for their platform. get_post reads it back as `video_cover`. | |
| collaborators | No | Instagram only. Up to 3 public Instagram usernames to invite as co-authors (the 'Collab' feature). Works on image, carousel, and reel posts — NOT Stories. Invited users get an invite in the Instagram app; once they accept, the post also appears on their profile and feed. A leading '@' is stripped; usernames are case-insensitive. Private or non-existent usernames are rejected by Instagram at publish time. Ignored by other platforms. | |
| linkedin_page | No | LinkedIn Company Page options | |
| linkedin_poll | No | Non-sponsored LinkedIn poll(s) — independent per channel, keyed by `linkedin` (personal profile) / `linkedin_page` (company page). A poll is mutually exclusive with media and a link share on that channel's post — a poll takes priority over both at publish time. Still requires `content.linkedin` (or `content.default`) as that channel's caption; the poll itself only carries the question/options/duration. On update_post, set a channel's key to `null` to clear that channel's poll and revert it to a normal post — send the full desired state for both channels, since the whole object replaces wholesale. | |
| google_business | No | Google Business Profile options. Use to publish EVENT or OFFER posts, attach a CTA button, or both. Shape mirrors Google's LocalPost resource (see https://developers.google.com/my-business/reference/rest/v4/accounts.locations.localPosts#LocalPost). Google Business caption rules (enforced at scheduling — text that violates these will return a `validation_error` 400 before the post is saved): • Phone numbers in the caption are rejected — use a CALL button instead. • Inline URLs / bare domains / emails are rejected — use LEARN_MORE / BOOK / SHOP / SIGN_UP / ORDER buttons instead. • Caption max 1500 characters. • Media is optional (text-only posts are allowed). If attached: exactly one JPEG/PNG/WebP image (no video, no carousels). • The workspace must have a Google Business location selected (Settings → Organisation → Workspaces → Google Business) before scheduling — otherwise returns a 400. | |
| link_description | No | Optional description for the link-share preview. LinkedIn uses this when set; Facebook auto-fetches the OG description. | |
| hashtag_placement | No | Where the set's tags land. caption_append (default): appended to each target caption after a blank line. first_comment: posted as the auto first comment on Instagram/Facebook/LinkedIn/LinkedIn Page/YouTube/TikTok (TikTok only when the workspace enabled TikTok comments) (keeps hashtags out of the caption — appended after any explicit first_comment); platforms without a comment API fall back to caption_append. Stories always use captions. | |
| hashtag_platforms | No | Optional subset of the post's channels to apply the hashtag set to (e.g. ["instagram", "tiktok"]). Defaults to all selected channels. | |
| link_thumbnail_url | No | Optional thumbnail image URL for the preview card. Currently applied on Facebook; reserved for LinkedIn. | |
| comment_dm_automation | No | Comment-to-DM automation on this post: when somebody comments one of trigger.keywords on the post once it is live on Instagram or the Facebook Page, the account DMs them actions.dm.text once (on Facebook the DM lands in Messenger), and optionally posts one of actions.public_reply.variations under the comment. Instagram or Facebook must be in channels; platforms picks which ones get it. Show the user the keywords and the exact DM text before creating it. The created automations come back as comment_dm_automation on the post (automations lists the id of each channel); manage them later with update_automation / get_automation_activity. |
TDQS
Does the description disclose side effects, auth requirements, rate limits, or destructive behavior?
Annotations already flag this as non-read-only, destructive, and open-world, but the description adds substantial operational context: workspace-asking rules, Pinterest auto-default behavior, X link-post failure handling, and the instruction not to retry or remove links without asking. These are exactly the kind of publish-time behavioral traits an agent needs.
Agents need to know what a tool does to the world before calling it. Descriptions should go beyond structured annotations to explain consequences.
Is the description appropriately sized, front-loaded, and free of redundancy?
It is long and dense, but front-loads the core purpose and uses bold headers to separate exceptional cases. Most sentences earn their place given the tool's complexity, though some workspace/media rule repetition could be trimmed.
Shorter descriptions cost fewer tokens and are easier for agents to parse. Every sentence should earn its place.
Given the tool's complexity, does the description cover enough for an agent to succeed on first attempt?
For a 33-parameter nested publishing tool with no output schema, the description covers the most error-prone scenarios and references create_post for shared media/workspace rules. It is nearly complete, but the lack of explicit draft/schedule/publish routing against create_post and publish_post leaves a meaningful contextual gap.
Complex tools with many parameters or behaviors need more documentation. Simple tools need less. This dimension scales expectations accordingly.
Does the description clarify parameter syntax, constraints, interactions, or defaults beyond what the schema provides?
Schema coverage is already 91%, so the schema carries most parameter documentation. The description still adds meaningful cross-parameter semantics for tricky cases like pinterest.board_id fallback, linkedin vs linkedin_page independence, x.thread_parts behavior, and link-post handling.
Input schemas describe structure but not intent. Descriptions should explain non-obvious parameter relationships and valid value ranges.
Does the description clearly state what the tool does and how it differs from similar tools?
The description opens with a specific verb+resource and scope: 'Create a new post and publish it immediately (no scheduling).' This clearly distinguishes it from a scheduling/draft workflow, though it does not explicitly distinguish it from siblings like publish_post or create_post.
Agents choose between tools based on descriptions. A clear purpose with a specific verb and resource helps agents select the right tool.
Does the description explain when to use this tool, when not to, or what alternatives exist?
It gives clear context for immediate publishing and extensive scenario guidance for Pinterest, X threads, links, and workspace selection. It does not explicitly name create_post or publish_post as alternatives for scheduled or existing posts, leaving that routing inference to the agent.
Agents often have multiple tools that could apply. Explicit usage guidance like "use X instead of Y when Z" prevents misuse.
create_automationAInspect
Create a comment-to-DM automation on the connected Instagram account (default), on the connected Facebook Page (platform 'facebook') or on the connected X account (platform 'x'): when somebody comments one of the keywords on the post (or sends it in a DM, or in an Instagram story reply, see triggers), the account DMs them dm_text once, and optionally posts one of public_replies under the comment. On Facebook the DM lands in Messenger. Before creating one, show the user the keyword(s) and the exact DM text and get a yes: the DM goes out in their name. Meta rules, the same on Instagram and Facebook: one private reply per comment, within 7 days of the comment; a follow-up only after the person answers (24-hour window); OmniSocials caps sends at 180 DMs an hour per account and platform, and an answer over the cap waits in a queue and goes out within the hour. For scope 'post' pass one of post_id (an OmniSocials post, scheduled or live), instagram_media_id (an Instagram post published outside OmniSocials) or facebook_post_id (a Page post published outside OmniSocials). On X the automation answers DMs only: triggers ['dm'] (the default there; X allows an automated DM only after the person wrote first), so a DM to the X account with a keyword, or any first message with match 'any', gets dm_text once per person; no post fields and no public replies. An X automation runs only while X DMs are turned on for the workspace in OmniSocials (Social Inbox, X DMs card, or the automation editor): an active create without them answers 409 x_dms_off, so tell the user where to turn them on, or create it with status 'paused'. 409 x_not_connected means the workspace has no X account. Every X answer ends with the line 'Reply STOP to stop automatic messages.', and a person who replies STOP gets no automatic DM from that X account again (the stop list belongs to the account: it holds after the automation is deleted, for later automations and in every workspace with that account). X takes at most 15 answers per 15 minutes and 450 a day per account; more wait in the queue for up to an hour. X does not give apps the messages of an encrypted X Chat conversation, so those get no answer. To attach automations to a NEW post, pass comment_dm_automation on create_post instead (Instagram and Facebook).
| Name | Required | Description | Default |
|---|---|---|---|
| name | No | A label for the automations list, e.g. 'Free guide'. | |
| match | No | word (default): the keyword stands on its own ('guide', 'Guide!' match; 'linkedin' does not match 'link'). contains: the keyword appears anywhere. any: every comment or message with text (ask the user before using it). | |
| scope | No | For the comment trigger (Instagram and Facebook; an X automation has no post): 'post' (default) = one post (pass post_id, instagram_media_id or facebook_post_id), 'next_post' = the next post the workspace publishes on this platform, 'any' = every post of the account or Page. | |
| status | No | 'paused' creates it without turning it on (default 'active'). A paused X automation saves even while X DMs are off; turn it on later with update_automation. | |
| dm_text | No | The DM sent to the person (max 1000 characters), once per person. On Facebook it lands in Messenger. On X, OmniSocials adds the line 'Reply STOP to stop automatic messages.' under it. Required on create. Confirm the text with the user before creating the automation: it goes out in the account's name. | |
| post_id | No | For scope 'post' (Instagram and Facebook): the OmniSocials post id (from list_posts) that goes to the automation's platform. A scheduled post starts listening once it is live. One automation per post and platform: a post that goes to Instagram and Facebook can have one of each. | |
| stop_at | No | Stop at this time (ISO 8601). null = no end. | |
| keywords | No | Keywords that start the automation (up to 20, matched case-insensitively), e.g. ["guide", "link"]. Required unless match is 'any'. | |
| platform | No | Where the automation runs: 'instagram' (default) = the connected Instagram account, 'facebook' = the connected Facebook Page (the DM lands in Messenger), 'x' = the connected X account (it answers DMs only; see create_automation). instagram_media_id implies 'instagram', facebook_post_id implies 'facebook'. It cannot change after create. | |
| triggers | No | What starts the automation. 'comment' (default on Instagram and Facebook) = a comment on an Instagram post or reel, or on a Facebook Page post; 'dm' = a keyword in a DM to the Instagram account, in a Messenger message to the Facebook Page, or in a DM to the X account; 'story_reply' = a keyword in a reply to an Instagram story (Instagram only: Facebook has no story replies). On X only 'dm' exists, and it is the default there. One automation can listen to several. | |
| max_sends | No | Stop after this many DMs (the automation becomes 'completed'). null = no limit. | |
| public_replies | No | Optional public replies posted under the comment (one is picked at random per comment), e.g. ["Sent you a DM!", "Check your inbox"]. Comment trigger only (Instagram and Facebook; X has none). An empty array turns the public reply off. | |
| facebook_post_id | No | For scope 'post' on Facebook: the id of a Facebook Page post that was NOT published through OmniSocials ({page-id}_{post-id}, or the post id alone). OmniSocials reads it from Facebook to check it belongs to the connected Page. Implies platform 'facebook'. Pass only one of post_id, instagram_media_id or facebook_post_id. | |
| instagram_media_id | No | For scope 'post' on Instagram: the numeric Instagram media id of a post or reel that was NOT published through OmniSocials. OmniSocials reads it from Instagram to check it belongs to the connected account. Pass only one of post_id, instagram_media_id or facebook_post_id. |
TDQS
Does the description disclose side effects, auth requirements, rate limits, or destructive behavior?
Beyond the annotations, the description discloses substantial behavior: DMs are sent in the user's name, Meta's one-private-reply and 7-day/24-hour follow-up rules, the 180-DM-per-hour cap and queueing behavior, and X-specific limits and STOP-list persistence. It also documents concrete error conditions such as 409 x_dms_off and 409 x_not_connected, which is exactly the kind of operational context annotations do not provide.
Agents need to know what a tool does to the world before calling it. Descriptions should go beyond structured annotations to explain consequences.
Is the description appropriately sized, front-loaded, and free of redundancy?
The definition is front-loaded with the core purpose and then proceeds through platform rules, scope selection, X caveats, and the create_post alternative. It is dense and delivered as a single long paragraph, but given the 14-parameter surface and complex platform behavior, most sentences carry relevant operational meaning rather than filler.
Shorter descriptions cost fewer tokens and are easier for agents to parse. Every sentence should earn its place.
Given the tool's complexity, does the description cover enough for an agent to succeed on first attempt?
The description covers the prerequisites, platform differences, trigger semantics, scope selection, rate limits, error responses, and the alternative tool for attaching automations to new posts. With no output schema, the only minor omission is the response shape, but nothing needed to select or invoke the tool correctly is missing.
Complex tools with many parameters or behaviors need more documentation. Simple tools need less. This dimension scales expectations accordingly.
Does the description clarify parameter syntax, constraints, interactions, or defaults beyond what the schema provides?
Schema coverage is 100%, so the schema already documents all 14 parameters in detail, making 3 the baseline. The description adds useful cross-parameter meaning, especially the exclusivity of post_id, instagram_media_id, and facebook_post_id for scope 'post', and the X-specific constraints that remove post fields and public replies from consideration.
Input schemas describe structure but not intent. Descriptions should explain non-obvious parameter relationships and valid value ranges.
Does the description clearly state what the tool does and how it differs from similar tools?
The first sentence states a specific verb and resource: creating a comment-to-DM automation on Instagram, Facebook, or X, including the core trigger-to-DM behavior. It also distinguishes platform-specific variants and points to related tools such as create_post for new posts, so the agent can identify the tool's role without opening the schema.
Agents choose between tools based on descriptions. A clear purpose with a specific verb and resource helps agents select the right tool.
Does the description explain when to use this tool, when not to, or what alternatives exist?
The description gives explicit usage conditions: which platform to choose, how scope 'post' maps to post_id/instagram_media_id/facebook_post_id, that X supports only DM triggers, and that a paused X automation can be created while X DMs are off. It also names an alternative path for new posts via create_post and says update_automation is used later to turn a paused automation on.
Agents often have multiple tools that could apply. Explicit usage guidance like "use X instead of Y when Z" prevents misuse.
create_folderAInspect
Create a media-library folder. Use it to organize assets (e.g. a 'win-graphics' folder), then upload into it with upload_media (folder) or move files with update_media (folder_id).
| Name | Required | Description | Default |
|---|---|---|---|
| name | Yes | Folder name, e.g. 'win-graphics' | |
| parent_id | No | Optional parent folder id to nest under (from list_folders). Omit for a top-level folder. |
TDQS
Does the description disclose side effects, auth requirements, rate limits, or destructive behavior?
Annotations already declare readOnlyHint=false, destructiveHint=false, and openWorldHint=false, so the mutation/safety profile is covered. The description adds the workflow role of a folder (a container for later uploads/moves), but says nothing about permissions, whether folders are renameable/removable, or naming constraints. Useful but modest context on top of the annotations.
Agents need to know what a tool does to the world before calling it. Descriptions should go beyond structured annotations to explain consequences.
Is the description appropriately sized, front-loaded, and free of redundancy?
Two tightly packed sentences with zero filler: the purpose is front-loaded and the second sentence carries only actionable workflow routing. Every clause earns its place.
Shorter descriptions cost fewer tokens and are easier for agents to parse. Every sentence should earn its place.
Given the tool's complexity, does the description cover enough for an agent to succeed on first attempt?
For a simple two-parameter create tool with full annotation coverage and no output schema, the description supplies enough to call it correctly and to know what to do next. Minor omissions (permissions, whether the folder name must be unique) are non-blocking.
Complex tools with many parameters or behaviors need more documentation. Simple tools need less. This dimension scales expectations accordingly.
Does the description clarify parameter syntax, constraints, interactions, or defaults beyond what the schema provides?
Schema description coverage is 100%, and the schema already documents both 'name' and 'parent_id' including the nesting behavior and the list_folders source. The description's example ('win-graphics') merely echoes the schema's own example, adding no syntax or constraint detail beyond it. Baseline 3 is appropriate when the schema does the heavy lifting.
Input schemas describe structure but not intent. Descriptions should explain non-obvious parameter relationships and valid value ranges.
Does the description clearly state what the tool does and how it differs from similar tools?
The description states a specific verb and resource ('Create a media-library folder'), which is clearly distinct from sibling create_* tools that operate on posts, hashtags, and webhooks. It does not explicitly contrast itself against those siblings, but the resource noun makes the target unambiguous.
Agents choose between tools based on descriptions. A clear purpose with a specific verb and resource helps agents select the right tool.
Does the description explain when to use this tool, when not to, or what alternatives exist?
It gives concrete usage context ('Use it to organize assets') and routes the agent to the correct follow-up tools: upload_media (folder) for uploads and update_media (folder_id) for moving files. There is no explicit when-not-to-use guidance or prerequisite/permission note, so it stops short of a 5.
Agents often have multiple tools that could apply. Explicit usage guidance like "use X instead of Y when Z" prevents misuse.
create_hashtag_setAInspect
Save a reusable, named group of hashtags (e.g. 'Fitness Brand' -> #fitness #gym #workout). Tags may include or omit the leading '#'; they are deduped case-insensitively and kept in order (max 100). Then apply the set to any new post via create_post (hashtag_set).
| Name | Required | Description | Default |
|---|---|---|---|
| name | Yes | Set name, unique per workspace, e.g. 'Fitness Brand' | |
| hashtags | Yes | Tags in order, with or without the leading "#", e.g. ["fitness", "#gym", "workout"] |
TDQS
Does the description disclose side effects, auth requirements, rate limits, or destructive behavior?
Annotations already establish this is a non-destructive, non-open-world write, so the safety profile is covered. The description adds genuinely useful behavior beyond that: '#' prefix optional, case-insensitive dedup, order preservation, and a max of 100 tags — all things an agent must know to build a valid call. It omits what happens on a duplicate set name (the schema says unique per workspace) or what is returned.
Agents need to know what a tool does to the world before calling it. Descriptions should go beyond structured annotations to explain consequences.
Is the description appropriately sized, front-loaded, and free of redundancy?
Two sentences, zero filler. The core behavior and the example come first, and the follow-up usage note is placed at the end where it belongs.
Shorter descriptions cost fewer tokens and are easier for agents to parse. Every sentence should earn its place.
Given the tool's complexity, does the description cover enough for an agent to succeed on first attempt?
For a two-parameter write tool with no output schema, the description covers creation semantics, normalization rules, and how the set is consumed later. It leaves open the duplicate-name failure mode and the return payload, but nothing essential to invoking it correctly is missing.
Complex tools with many parameters or behaviors need more documentation. Simple tools need less. This dimension scales expectations accordingly.
Does the description clarify parameter syntax, constraints, interactions, or defaults beyond what the schema provides?
Schema coverage is 100%, so baseline is 3, and the description goes beyond the schema by specifying normalization semantics for the hashtags array (optional '#', case-insensitive dedup, order retention, 100-item cap). The name parameter gets no extra clarification beyond the schema's 'unique per workspace' note.
Input schemas describe structure but not intent. Descriptions should explain non-obvious parameter relationships and valid value ranges.
Does the description clearly state what the tool does and how it differs from similar tools?
States a specific verb and resource ('Save a reusable, named group of hashtags') and grounds it with a concrete example ('Fitness Brand' -> #fitness #gym #workout), which separates it cleanly from list_hashtag_sets, update_hashtag_set, and delete_hashtag_set.
Agents choose between tools based on descriptions. A clear purpose with a specific verb and resource helps agents select the right tool.
Does the description explain when to use this tool, when not to, or what alternatives exist?
Gives clear downstream context: the set is meant to be applied to a new post via create_post (hashtag_set). It does not, however, mention when to use this versus update_hashtag_set for editing an existing set, so the alternative-selection guidance is partial.
Agents often have multiple tools that could apply. Explicit usage guidance like "use X instead of Y when Z" prevents misuse.
create_postAInspect
Create a new social media post, story, or reel.
IMPORTANT — Before calling this tool, make sure you have all required information from the user. If anything is missing, ASK the user before calling:
Workspace: If the user has only one workspace, just use it (no need to ask). If the user has named a workspace in their request, switch to it once and remember it for the rest of the conversation. If multiple workspaces exist and the user has NOT named one, call
list_workspacesand ASK which workspace to post to before continuing. Never silently pick a workspace when more than one exists — each workspace has different connected channels and different audiences. After a successful create/schedule/publish, mention the workspace name in your reply for clarity (e.g. "Scheduled to the Acme workspace for Tuesday 3pm").Content/caption: What text should the post have? If captions differ per platform, use one call with an object: { "default": "fallback text", "linkedin": "long version", "threads": "short version", "x": "short version", "bluesky": "short version" }. Always prefer one call per topic. RESPECT character limits per platform (see below).
Channels: Which platforms to post to? Call
list_accountsto show available options for the active workspace. Ask the user which channels to use.Schedule: When should it be published? (Or save as draft?)
Media (REQUIRED for some types):
Stories: ALWAYS require an image or video. A story can carry up to 10 media items: each item is one slide, published as its own story in the order given. Ask the user which slides and in what order.
Reels: ALWAYS require a video.
Instagram posts: ALWAYS require at least one image or video.
TikTok posts: ALWAYS require at least one image or video.
Pinterest posts: ALWAYS require an image AND a board_id.
Other platforms (LinkedIn Profile, LinkedIn Page, X, Bluesky, etc.): Media is optional.
Image fit (aspect ratio): a feed image outside what a channel shows uncropped is handled PER CHANNEL. Instagram shows feed images between 4:5 and 1.91:1: a 9:16 (story-style) image posted to the Instagram feed is CROPPED to 4:5 around the subject by default, because Instagram cuts it to that window anyway and Meta cannot boost a feed post outside it. Pinterest keeps a Pin taller than 2:3 and reports it. Before posting a tall image to Instagram, run
check_media_compatibility(its fit rows say per connected channel whether the image fits and what the default does) and ASK the user: crop to 4:5 (recommended: Meta can boost it) or keep the original (Instagram cuts it itself, no boost)? Pass the answer asmedia_fit: { instagram: "crop" | "keep" }. If the user gave no preference, let the default run and RELAY theimage_fitwarning from the response (it names the crop and how to undo it with update_post). Stories, reels and videos are never cropped; 'default' and the other channels keep the original. Never drop a channel over this.
Platform-specific options (ask only when relevant):
Pinterest board (auto-default to first board): If Pinterest is in
channelsandpinterest.board_idis NOT provided, do NOT block on asking the user — and do NOT skip Pinterest. Instead:Call
get_accounton the Pinterest account — the response includes aPinterest Boardstable with each board's name and ID.Use the FIRST board in that list as
pinterest.board_idautomatically.In your reply, explicitly mention which board you used (e.g. "Posted to your 'Marketing' board on Pinterest — let me know if you'd prefer a different one and I'll move it.") so the user can correct course. If the user named a board ("post to my Marketing board") or specified one in the request, match it (case-insensitive) against the list and use that one instead of the first.
YouTube: Title, privacy status, tags?
TikTok: Privacy level?
X threads vs long-form: A chained "thread" (the user explicitly asks for one) → pass
x.thread_partsas an array of 2–25{ text }objects (each ≤ 280 chars); the top-levelcontentis then ignored for X. A single long-form post on a Basic, Premium or Premium+ account → just put the full text (up to 25,000 chars) incontent— no threading needed (checkplatform_details.subscription_typevia list_accounts). On a free account, X caps a single post at 280 chars, so either split into a thread or shorten. Never cram "1/", "2/" prefixes intocontent— that posts one tweet, not a thread.X posts containing a link: X treats a post whose text contains a link written with http:// or https:// as a link post (a bare domain such as brand.com or a www. link does not count; in a thread, every part with such a link). Link posts on X are a feature the organisation enables on its OmniSocials account. When it is not enabled, the request is refused with an
x_feature_not_enablederror that says so: tell the user, offer to post without the link or without X, and do not retry as is. Never remove a user's link without asking them.
VIDEO DURATION CAPS — MUST RESPECT THESE (returns 400 validation_error when exceeded):
Platform | Post mode | Reel mode |
240 min | 240 min (the old 90 s Reel cap is gone) | |
YouTube Short | (no Post mode) | 3 min |
X | 140 s | N/A |
Bluesky | 10 min | N/A |
Threads | 5 min | N/A |
TikTok | 10 min | 10 min |
LinkedIn / LinkedIn Page | 30 min | N/A |
15 min | 15 min | |
15 min | N/A | |
15 min | N/A | |
Mastodon | (instance-dependent) | N/A |
Telegram | (no cap, 50 MB file limit) | (no cap, 50 MB file limit) |
Discord | (no cap) | (no cap) |
VIDEO FILE-SIZE CAPS — MUST RESPECT THESE (validated via ffprobe at schedule/publish time; drafts exempt):
Platform | Video cap |
Telegram | 50 MB |
Mastodon | 99 MB |
Discord | 1 GB (a file over 20 MB goes as a link in the message) |
Bluesky | 300 MB |
300 MB | |
X (free tier) | 512 MB |
Threads / Reddit | 1 GB |
2 GB | |
Facebook / TikTok | 4 GB |
LinkedIn / LinkedIn Page | 5 GB |
YouTube | 256 GB |
Upload requests are capped at 100 MB on top of these; anything bigger gets rejected with code: file_too_large before the validator runs.
Cap-violation error shape (one sentence per offending platform):
{ "error": { "code": "validation_error", "message": "YouTube only allows videos up to 3min; yours is 3min 12s. Trim the video or deselect YouTube." } }Before sending an oversized video, warn the user and offer to trim, deselect that platform, or split. Drafts can still be created without media — the validator only runs when transitioning to scheduled or publish_now.
CHARACTER LIMITS — MUST RESPECT THESE:
Platform | Max chars | Notes |
X (free / Basic) | 280 | Long posts require Premium or Premium+ — Basic does NOT count |
X (Premium / Premium+) | 25,000 | Check platform_details.subscription_type on the account |
Bluesky | 300 | Counted in graphemes |
Mastodon | 500 | Default (mastodon.social); the connected server's own limit applies, links count as 23 |
Threads | 500 | |
YouTube | 500 | Description field |
800 | Pin description | |
2,200 | Caption | |
TikTok | 2,200 (videos) / 4,000 (photo posts) | Videos have a single caption field |
3,000 | ||
63,206 | Very generous | |
Telegram | 4,096 | With media, text over 1,024 goes as a reply under the media; a poll question is max 300 |
Discord | 2,000 | A poll question is max 300 |
When posting to multiple platforms with different limits, ALWAYS use per-platform captions. For example, if posting to LinkedIn (3000 chars) and X (280 chars), use: { "default": "full version", "x": "shortened version" }. Never post content that exceeds a platform's limit.
Channel IDs you can pass: instagram, facebook, threads, linkedin (personal profile), linkedin_page (company page), youtube, tiktok, pinterest, x, bluesky, mastodon, telegram (a Telegram channel or group), discord (a Discord channel). linkedin and linkedin_page are independent. A workspace can have both connected and post to each separately. Always confirm with list_accounts which are actually connected.
Do NOT call this tool without media when creating stories, reels, Instagram posts, TikTok posts, or Pinterest posts — it will fail.
IMPORTANT - When the user shares an image or screenshot in chat: You MUST upload it before creating the post. Do NOT skip the image. Do NOT create a text-only draft when an image was provided. Follow these steps:
Call
upload_mediawithmethod="upload_url"to get upload instructionsUse code execution to upload the image file to OmniSocials
Use the returned media ID in
media_idswhen creating the post Only if code execution is completely unavailable, save as a draft and tell the user to add the image at app.omnisocials.com.
| Name | Required | Description | Default |
|---|---|---|---|
| x | No | X (Twitter) options: thread mode via `thread_parts`, a poll via `poll`. | |
| type | No | Content type. 'story' takes 1 to 10 media items; each is one slide, published in order. | |
| tiktok | No | TikTok options | |
| bluesky | No | Bluesky options, including thread mode via `thread_parts`. | |
| content | Yes | Post caption. String for same text on all channels, or object with platform keys for per-channel captions: { "default": "fallback", "linkedin": "long version", "threads": "short version" }. The "default" key is used for any selected channel without its own key. Always prefer one call per topic, even when captions differ across platforms. | |
| discord | No | Discord options. The post goes to the connected Discord channel through its webhook and shows the webhook's name and picture. Text up to 2,000 chars. Up to 10 images, GIFs and videos per message (they may mix); a video or GIF over Discord's 20 MB file limit is sent as a link in the text. No Stories; a 'reel' is sent as one video message. | |
| threads | No | Threads options: thread mode via `thread_parts`, location tag via `location_id`, a poll via `poll`, the topic via `topic_tag`. | |
| youtube | No | YouTube Shorts options. Only applies when type is 'reel' and youtube is among the selected channels. A custom Shorts thumbnail is set with the top-level `video_cover` (a `youtube` override for a YouTube-only image); it shows on Shorts only on channels where YouTube has enabled custom Shorts thumbnails (Partner Program channels first, since July 2026), other channels show a frame from the video. | |
| channels | No | Array of channel IDs to post to (e.g. linkedin, linkedin_page, instagram). Get available IDs from list_accounts. | |
| No | Facebook options | ||
| link_url | No | URL to share as a rich preview card on platforms that support link-share posts (LinkedIn and Facebook). Renders as a tile with thumbnail/title/description instead of plain text. Ignored on platforms that don't support link shares, and ignored on posts that already have media attached (media wins). | |
| No | LinkedIn Profile options | ||
| mastodon | No | Mastodon options: thread mode via `thread_parts`, a poll via `poll`. | |
| telegram | No | Telegram options. Text up to 4,096 chars; with media, text over 1,024 chars is sent as a reply under the media. Up to 10 photos and videos per album, videos up to 50 MB, no Stories. A 'reel' is sent as a video message. | |
| No | Instagram options | ||
| media_fit | No | Image fit per channel, for feed images (type 'post') whose ratio is outside what a channel shows uncropped: { instagram: 'auto' | 'crop' | 'keep', pinterest: ... }. 'auto' (the default when omitted) takes the channel's rule: Instagram crops a tall (9:16) or wide image to 4:5 / 1.91:1 around the subject (Instagram cuts it to that window anyway, and Meta cannot boost a feed post outside it); Pinterest keeps a Pin taller than 2:3 and only reports it. 'crop' / 'keep' force it for that channel. Every decision comes back in the response `warnings` with code `image_fit` (relay it). The crop is a separate file for that channel only; 'default' and the other channels keep the original. On update_post, media_fit alone (no media) re-decides the stored images: 'keep' gives the original back, 'crop' crops an image that was kept. | |
| media_ids | No | Media IDs — flat array or per-platform object | |
| No | |||
| user_tags | No | Instagram only. Tag public accounts at x/y positions on a PHOTO (not video/reels/stories). For a single image omit image_index; for a carousel, set image_index to the slide each tag belongs to. Private/non-existent usernames are rejected at publish time. Ignored by other platforms. | |
| link_title | No | Optional title for the link-share preview. LinkedIn uses this when set; Facebook ignores it and fetches OG metadata server-side. Omit to let LinkedIn auto-fetch the page title. | |
| media_urls | No | External image/video/PDF URLs — flat array or per-platform object. Max 10 total (Pinterest: max 5 images per carousel pin), each file ≤ 100 MB. Entries are URL strings or { url, alt } objects (alt = accessibility description, delivered to Mastodon/Bluesky/X/Pinterest/Instagram (images)/LinkedIn (images)). For larger files (up to 1 GB): upload_media with method 'url' first, then pass the returned media id in `media`. | |
| hashtag_set | No | Name of a saved hashtag set (from list_hashtag_sets, matched case-insensitively) to apply to this post. The set's tags are merged in once at create time; tags already present in a caption are skipped. When the user says something like 'add my usual hashtags', check list_hashtag_sets first. Instagram's 5-hashtag cap is enforced with a clear error (hashtag_limit_exceeded). | |
| location_id | No | Instagram only. Facebook Place ID for a single physical venue (with a street address) to tag the post's location. Find it via the location search in the OmniSocials dashboard. Ignored by other platforms. | |
| video_cover | No | Video thumbnail for a post whose media is ONE video. Applied on Instagram (feed videos and reels), Facebook (feed videos and reels), LinkedIn Profile and Page, TikTok, Pinterest and YouTube Shorts. YouTube Shorts: the cover shows on Shorts only on channels where YouTube has enabled custom Shorts thumbnails (rolling out since July 2026, Partner Program channels first); on other channels YouTube stores it as the default thumbnail but shows a frame from the video on Shorts. Say that it depends on the channel; do not promise it. TikTok only takes a frame: a 'custom' cover is skipped there, so add a tiktok override with type 'frame' when the user wants a specific TikTok frame. The per-platform reel fields (instagram.thumb_offset / cover_url, tiktok.video_cover_timestamp_ms, pinterest.video_cover) keep working and win over the base cover for their platform. get_post reads it back as `video_cover`. | |
| scheduled_at | No | ISO 8601 date for scheduled publishing | |
| collaborators | No | Instagram only. Up to 3 public Instagram usernames to invite as co-authors (the 'Collab' feature). Works on image, carousel, and reel posts — NOT Stories. Invited users get an invite in the Instagram app; once they accept, the post also appears on their profile and feed. A leading '@' is stripped; usernames are case-insensitive. Private or non-existent usernames are rejected by Instagram at publish time. Ignored by other platforms. | |
| linkedin_page | No | LinkedIn Company Page options | |
| linkedin_poll | No | Non-sponsored LinkedIn poll(s) — independent per channel, keyed by `linkedin` (personal profile) / `linkedin_page` (company page). A poll is mutually exclusive with media and a link share on that channel's post — a poll takes priority over both at publish time. Still requires `content.linkedin` (or `content.default`) as that channel's caption; the poll itself only carries the question/options/duration. On update_post, set a channel's key to `null` to clear that channel's poll and revert it to a normal post — send the full desired state for both channels, since the whole object replaces wholesale. | |
| google_business | No | Google Business Profile options. Use to publish EVENT or OFFER posts, attach a CTA button, or both. Shape mirrors Google's LocalPost resource (see https://developers.google.com/my-business/reference/rest/v4/accounts.locations.localPosts#LocalPost). Google Business caption rules (enforced at scheduling — text that violates these will return a `validation_error` 400 before the post is saved): • Phone numbers in the caption are rejected — use a CALL button instead. • Inline URLs / bare domains / emails are rejected — use LEARN_MORE / BOOK / SHOP / SIGN_UP / ORDER buttons instead. • Caption max 1500 characters. • Media is optional (text-only posts are allowed). If attached: exactly one JPEG/PNG/WebP image (no video, no carousels). • The workspace must have a Google Business location selected (Settings → Organisation → Workspaces → Google Business) before scheduling — otherwise returns a 400. | |
| link_description | No | Optional description for the link-share preview. LinkedIn uses this when set; Facebook auto-fetches the OG description. | |
| hashtag_placement | No | Where the set's tags land. caption_append (default): appended to each target caption after a blank line. first_comment: posted as the auto first comment on Instagram/Facebook/LinkedIn/LinkedIn Page/YouTube/TikTok (TikTok only when the workspace enabled TikTok comments) (keeps hashtags out of the caption — appended after any explicit first_comment); platforms without a comment API fall back to caption_append. Stories always use captions. | |
| hashtag_platforms | No | Optional subset of the post's channels to apply the hashtag set to (e.g. ["instagram", "tiktok"]). Defaults to all selected channels. | |
| link_thumbnail_url | No | Optional thumbnail image URL for the preview card. Currently applied on Facebook; reserved for LinkedIn. | |
| approval_workflow_id | No | Route the post through a saved approval workflow (id from list_approval_workflows). The post is created as `in_approval` instead of `scheduled`: its approvers are notified, they review it on the Approvals page, and it publishes at schedule_at only once the workflow's last step approves it (or approve_post). Use this whenever the user wants to review/approve agent-created posts before they go out. Requires schedule_at; not allowed with publish_now (use create_post, never create_and_publish_post). A workflow with no approvers on its first step is rejected with validation_error. | |
| comment_dm_automation | No | Comment-to-DM automation on this post: when somebody comments one of trigger.keywords on the post once it is live on Instagram or the Facebook Page, the account DMs them actions.dm.text once (on Facebook the DM lands in Messenger), and optionally posts one of actions.public_reply.variations under the comment. Instagram or Facebook must be in channels; platforms picks which ones get it. Show the user the keywords and the exact DM text before creating it. The created automations come back as comment_dm_automation on the post (automations lists the id of each channel); manage them later with update_automation / get_automation_activity. |
TDQS
Does the description disclose side effects, auth requirements, rate limits, or destructive behavior?
Annotations only declare readOnly=false, destructive=false, openWorld=false; the description adds far more: validation runs only on schedule/publish (drafts exempt), per-platform 400 validation_error shapes, the x_feature_not_enabled refusal with a 'do not retry as is' instruction, the 100 MB upload ceiling on top of per-platform caps, and exactly which post types fail without media. This is substantial context an agent cannot get from the structured fields.
Agents need to know what a tool does to the world before calling it. Descriptions should go beyond structured annotations to explain consequences.
Is the description appropriately sized, front-loaded, and free of redundancy?
Front-loaded correctly with the must-know checklist before the reference tables, and the bold headers make a long body navigable. It is still quite long and some limit tables partly restate constraints already present in the schema (poll option counts, some char limits), which is redundant for a 97%-coverage schema.
Shorter descriptions cost fewer tokens and are easier for agents to parse. Every sentence should earn its place.
Given the tool's complexity, does the description cover enough for an agent to succeed on first attempt?
For a 35-parameter, deeply nested mutation tool with no output schema, the description covers validation timing, failure modes, per-platform prerequisites, and the upload-before-create flow for chat images. Nothing an agent needs to call it correctly is missing.
Complex tools with many parameters or behaviors need more documentation. Simple tools need less. This dimension scales expectations accordingly.
Does the description clarify parameter syntax, constraints, interactions, or defaults beyond what the schema provides?
With 97% schema coverage the baseline is 3, but the description contributes operational semantics the schema does not carry: the video duration and file-size cap tables, the character-limit table per platform, the per-platform caption object pattern, the thread_parts vs long-form X content distinction, and the media_fit crop/keep decision flow. These directly change how parameters must be filled.
Input schemas describe structure but not intent. Descriptions should explain non-obvious parameter relationships and valid value ranges.
Does the description clearly state what the tool does and how it differs from similar tools?
The opening line names a specific verb and resource ('Create a new social media post, story, or reel') and enumerates the three types the tool produces. It never explicitly contrasts with the closest sibling, create_and_publish_post (draft/schedule vs. immediate publish), so an agent must open both schemas to be sure which one to call.
Agents choose between tools based on descriptions. A clear purpose with a specific verb and resource helps agents select the right tool.
Does the description explain when to use this tool, when not to, or what alternatives exist?
A numbered pre-flight checklist states exactly what to gather (workspace, content, channels, schedule, media) and when to ask the user versus act, including the workspace rule (never silently pick when multiple exist) and the Pinterest board auto-default. It routes to specific alternatives by name: list_workspaces, list_accounts, check_media_compatibility, get_account, upload_media.
Agents often have multiple tools that could apply. Explicit usage guidance like "use X instead of Y when Z" prevents misuse.
create_webhookBInspect
Create a new webhook. Available events: post.scheduled, post.published, post.failed, post.approved (the last approval of a post's approval workflow is in), post.rejected (an approver rejected the post)
| Name | Required | Description | Default |
|---|---|---|---|
| url | Yes | The HTTPS URL to send events to | |
| events | Yes | Events to subscribe to |
TDQS
Does the description disclose side effects, auth requirements, rate limits, or destructive behavior?
Annotations already declare readOnlyHint=false, destructiveHint=false, and openWorldHint=false, so the safety profile is covered structurally. The description adds domain behavior by explaining what triggers each event (e.g., post.approved fires on the last workflow approval), but says nothing about auth needs, whether a signing secret is issued, or delivery semantics — useful additions against a low annotation-derived bar.
Agents need to know what a tool does to the world before calling it. Descriptions should go beyond structured annotations to explain consequences.
Is the description appropriately sized, front-loaded, and free of redundancy?
Two sentences, front-loaded with the action, and the dense event enumeration earns its space by disambiguating valid values. Slightly parenthetical annotation of a couple events could be tightened but nothing is wasteful.
Shorter descriptions cost fewer tokens and are easier for agents to parse. Every sentence should earn its place.
Given the tool's complexity, does the description cover enough for an agent to succeed on first attempt?
There is no output schema, so the description could reasonably explain what a successful creation returns (e.g., an ID or signing secret). For a low-complexity two-parameter tool it is mostly adequate, but the post-creation contract is left unstated.
Complex tools with many parameters or behaviors need more documentation. Simple tools need less. This dimension scales expectations accordingly.
Does the description clarify parameter syntax, constraints, interactions, or defaults beyond what the schema provides?
Schema coverage is 100%, so the baseline is 3, but the description goes further by enumerating the valid event values and clarifying their trigger conditions, which the schema only calls 'Events to subscribe to'. It does not elaborate on the url parameter, which the schema already defines as an HTTPS URL.
Input schemas describe structure but not intent. Descriptions should explain non-obvious parameter relationships and valid value ranges.
Does the description clearly state what the tool does and how it differs from similar tools?
States a specific verb and resource ('Create a new webhook'), making it clearly distinguishable from the sibling delete_webhook, get_webhook, list_webhooks, and update_webhook. It does not name a sibling explicitly, but the create/list/get/delete verb family makes the intent unambiguous.
Agents choose between tools based on descriptions. A clear purpose with a specific verb and resource helps agents select the right tool.
Does the description explain when to use this tool, when not to, or what alternatives exist?
The description gives no when-to-use guidance, no prerequisites, and no comparison to alternatives like update_webhook (for modifying an existing hook) or list_webhooks (for inspecting them). The event list informs invocation but not tool selection.
Agents often have multiple tools that could apply. Explicit usage guidance like "use X instead of Y when Z" prevents misuse.
delete_automationADestructiveInspect
Delete a comment-to-DM automation (Instagram, Facebook Page or X) and its activity log. DMs that were already sent stay sent. To stop it for a while, use update_automation with status 'paused' instead. Confirm with the user first.
| Name | Required | Description | Default |
|---|---|---|---|
| automation_id | Yes | The automation id (from list_automations). |
TDQS
Does the description disclose side effects, auth requirements, rate limits, or destructive behavior?
Annotations already declare destructiveHint=true, so the danger is known. The description adds real value beyond them by naming what is destroyed (activity log), what is preserved (already-sent DMs stay sent), and requiring user confirmation. That is genuine disclosure of consequences, but it stops short of stating irreversibility, permission requirements, or the response shape.
Agents need to know what a tool does to the world before calling it. Descriptions should go beyond structured annotations to explain consequences.
Is the description appropriately sized, front-loaded, and free of redundancy?
Three short sentences, each carrying a distinct fact: scope/effect, the safer alternative, the confirmation requirement. Front-loaded with the action and with zero padding.
Shorter descriptions cost fewer tokens and are easier for agents to parse. Every sentence should earn its place.
Given the tool's complexity, does the description cover enough for an agent to succeed on first attempt?
For a one-parameter destructive tool, annotations cover the safety profile and the description covers consequences, the alternative path, and the pre-call safeguard. No output schema is needed for a delete, so nothing an agent requires is missing.
Complex tools with many parameters or behaviors need more documentation. Simple tools need less. This dimension scales expectations accordingly.
Does the description clarify parameter syntax, constraints, interactions, or defaults beyond what the schema provides?
A single parameter at 100% schema coverage, with the schema itself documenting that the id comes from list_automations. The description adds no format or sourcing detail beyond that, so the baseline applies.
Input schemas describe structure but not intent. Descriptions should explain non-obvious parameter relationships and valid value ranges.
Does the description clearly state what the tool does and how it differs from similar tools?
Specific verb (delete) plus the exact resource (comment-to-DM automation), the supported platforms, and the collateral (activity log). It also implicitly separates itself from update_automation and list_automations by naming the latter as the id source.
Agents choose between tools based on descriptions. A clear purpose with a specific verb and resource helps agents select the right tool.
Does the description explain when to use this tool, when not to, or what alternatives exist?
Explicitly routes the agent to update_automation with status 'paused' when the intent is only temporary, and adds a 'confirm with the user first' precondition. When-to-use-not and the alternative are both stated, not inferred.
Agents often have multiple tools that could apply. Explicit usage guidance like "use X instead of Y when Z" prevents misuse.
delete_hashtag_setADestructiveInspect
Delete a saved hashtag set. Posts that already used it keep their hashtags — the tags were merged into their captions at create time.
| Name | Required | Description | Default |
|---|---|---|---|
| set_id | Yes | The hashtag set id (from list_hashtag_sets) |
TDQS
Does the description disclose side effects, auth requirements, rate limits, or destructive behavior?
Annotations already declare destructiveHint=true, readOnlyHint=false, openWorldHint=false, so the safety profile is covered structurally. The description adds genuine value beyond them by disclosing the blast radius: posts that already used the set retain their hashtags because tags were merged into captions at create time. It does not address reversibility, permissions, or error behavior.
Agents need to know what a tool does to the world before calling it. Descriptions should go beyond structured annotations to explain consequences.
Is the description appropriately sized, front-loaded, and free of redundancy?
Two short sentences, front-loaded with the action, and the second sentence earns its place by preventing a likely misconception about published posts. No filler.
Shorter descriptions cost fewer tokens and are easier for agents to parse. Every sentence should earn its place.
Given the tool's complexity, does the description cover enough for an agent to succeed on first attempt?
For a single-parameter destructive tool with no output schema, the description covers the action and the side-effect scope, which is what an agent most needs before calling it. It omits what happens on an invalid or already-deleted set_id and whether the delete is permanent, minor gaps given annotations carry the destructiveness signal.
Complex tools with many parameters or behaviors need more documentation. Simple tools need less. This dimension scales expectations accordingly.
Does the description clarify parameter syntax, constraints, interactions, or defaults beyond what the schema provides?
Schema description coverage is 100% for the single parameter, and the schema already documents set_id including its provenance ("from list_hashtag_sets"). The description adds nothing about the parameter, so the baseline 3 for fully documented params applies.
Input schemas describe structure but not intent. Descriptions should explain non-obvious parameter relationships and valid value ranges.
Does the description clearly state what the tool does and how it differs from similar tools?
States a specific verb and resource ("Delete a saved hashtag set"), and the resource name is unique enough among the 48 siblings (delete_post, delete_media, delete_webhook) that an agent can tell it apart without opening schemas. It stops short of explicitly naming related siblings such as update_hashtag_set or list_hashtag_sets, so it does not fully earn a 5.
Agents choose between tools based on descriptions. A clear purpose with a specific verb and resource helps agents select the right tool.
Does the description explain when to use this tool, when not to, or what alternatives exist?
Usage is only implied: the description tells the agent the effect of deleting (posts keep their tags), which implicitly reassures that deletion is scoped to the saved set, but never states when to delete versus update, nor any prerequisite such as needing a valid set_id. No alternatives or when-not conditions are given.
Agents often have multiple tools that could apply. Explicit usage guidance like "use X instead of Y when Z" prevents misuse.
delete_inbox_commentADestructiveInspect
Permanently delete a comment someone left on one of the workspace's posts, on the platform and from the inbox. Facebook, Instagram and TikTok comments only (YouTube's API cannot delete other people's comments; use hide_inbox_comment there). Replies under the comment are deleted with it. This cannot be undone: confirm with the user before calling. Takes the message id (the #id in the thread), not the conversation id. A 403 reconnect_required means the account must be reconnected in the dashboard to grant the moderation permission.
| Name | Required | Description | Default |
|---|---|---|---|
| message_id | Yes | The inbox message id of the comment (the #id in the thread) |
TDQS
Does the description disclose side effects, auth requirements, rate limits, or destructive behavior?
Annotations already declare destructiveHint=true and openWorldHint=true, and the description goes well beyond them: it discloses the cascade effect (replies under the comment are deleted too), irreversibility, the required user confirmation, and the meaning of a 403 reconnect_required error including the remediation path. That is exactly the extra context annotations cannot carry.
Agents need to know what a tool does to the world before calling it. Descriptions should go beyond structured annotations to explain consequences.
Is the description appropriately sized, front-loaded, and free of redundancy?
Five short sentences, front-loaded with the action and scope, then cascade behavior, safety, parameter clarification and error handling. Every sentence carries information absent from the schema or annotations; nothing is padding.
Shorter descriptions cost fewer tokens and are easier for agents to parse. Every sentence should earn its place.
Given the tool's complexity, does the description cover enough for an agent to succeed on first attempt?
Single-required-parameter tool with no output schema and complete annotations; the description covers scope, side effects, irreversibility, confirmation requirements and the one documented error path. Nothing an agent needs in order to call this correctly is missing.
Complex tools with many parameters or behaviors need more documentation. Simple tools need less. This dimension scales expectations accordingly.
Does the description clarify parameter syntax, constraints, interactions, or defaults beyond what the schema provides?
Schema coverage is 100% on the single parameter, so the baseline is 3, but the description adds a genuine disambiguation: it warns that message_id is the #id in the thread, not the conversation id — a real confusion source given siblings like get_inbox_conversation. It stops short of any id format example, so not a 5.
Input schemas describe structure but not intent. Descriptions should explain non-obvious parameter relationships and valid value ranges.
Does the description clearly state what the tool does and how it differs from similar tools?
The first sentence names a specific verb (delete), the exact resource (a comment on one of the workspace's posts), and the two surfaces affected (platform and inbox). It also carves out platform scope (Facebook, Instagram, TikTok) and explicitly names the sibling it is not (hide_inbox_comment for YouTube). An agent can distinguish this from every other inbox tool without opening a schema.
Agents choose between tools based on descriptions. A clear purpose with a specific verb and resource helps agents select the right tool.
Does the description explain when to use this tool, when not to, or what alternatives exist?
It gives explicit when-to-use (FB/IG/TikTok comments), when-not (YouTube, because the API cannot delete others' comments, use hide_inbox_comment), and a mandatory pre-call step ('confirm with the user before calling'). That is the full when/when-not/alternative triad.
Agents often have multiple tools that could apply. Explicit usage guidance like "use X instead of Y when Z" prevents misuse.
delete_mediaBDestructiveInspect
Delete a media file by ID.
| Name | Required | Description | Default |
|---|---|---|---|
| id | Yes | The media ID to delete |
TDQS
Does the description disclose side effects, auth requirements, rate limits, or destructive behavior?
Annotations already declare destructiveHint=true and readOnlyHint=false, so the safety profile is carried structurally. The description adds no behavioral context beyond that: it does not say whether deletion is permanent or reversible, whether it cascades (e.g. to scheduled posts referencing the media), or whether it requires elevated permissions.
Agents need to know what a tool does to the world before calling it. Descriptions should go beyond structured annotations to explain consequences.
Is the description appropriately sized, front-loaded, and free of redundancy?
One short, front-loaded sentence with zero padding. The verb and the discriminator (by ID) come first.
Shorter descriptions cost fewer tokens and are easier for agents to parse. Every sentence should earn its place.
Given the tool's complexity, does the description cover enough for an agent to succeed on first attempt?
The tool is simple (one required string param, no output schema, no nesting) and annotations carry the destructive signal, so little prose is needed. However, for a permanent destructive operation on media, the absence of any statement about irreversibility or side effects leaves a meaningful gap.
Complex tools with many parameters or behaviors need more documentation. Simple tools need less. This dimension scales expectations accordingly.
Does the description clarify parameter syntax, constraints, interactions, or defaults beyond what the schema provides?
Schema description coverage is 100% and the single parameter is fully documented as "The media ID to delete." The description's "by ID" merely restates the schema, so the baseline 3 applies with no added semantics.
Input schemas describe structure but not intent. Descriptions should explain non-obvious parameter relationships and valid value ranges.
Does the description clearly state what the tool does and how it differs from similar tools?
States a specific verb and resource ("Delete a media file") with the identifying parameter, so the agent can distinguish it from update_media, upload_media, and list_media. It does not explicitly name or contrast with those siblings, but the operation is unambiguous.
Agents choose between tools based on descriptions. A clear purpose with a specific verb and resource helps agents select the right tool.
Does the description explain when to use this tool, when not to, or what alternatives exist?
"by ID" implies an ID must already be known (presumably from list_media), but there is no explicit when-to-use guidance, no prerequisites, and no mention of alternatives or how to recover the ID. Nothing tells the agent when deletion is appropriate versus updating.
Agents often have multiple tools that could apply. Explicit usage guidance like "use X instead of Y when Z" prevents misuse.
delete_postADestructiveInspect
Delete a post by ID. This action cannot be undone.
| Name | Required | Description | Default |
|---|---|---|---|
| id | Yes | The post ID to delete |
TDQS
Does the description disclose side effects, auth requirements, rate limits, or destructive behavior?
Annotations already declare destructiveHint=true and readOnlyHint=false, so safety is covered. The description adds a specific behavioral fact beyond that: 'This action cannot be undone,' which tells the agent the deletion is irreversible. It does not mention auth requirements or side effects, but the added irreversibility note is valuable.
Agents need to know what a tool does to the world before calling it. Descriptions should go beyond structured annotations to explain consequences.
Is the description appropriately sized, front-loaded, and free of redundancy?
Two short sentences with zero waste; the action and irreversible warning are both front-loaded and easy to scan.
Shorter descriptions cost fewer tokens and are easier for agents to parse. Every sentence should earn its place.
Given the tool's complexity, does the description cover enough for an agent to succeed on first attempt?
For a simple one-parameter delete tool with a complete input schema and annotations covering the destructive nature, the description supplies what an agent needs: what it does, how it identifies the target, and that the result is irreversible. Nothing material is missing.
Complex tools with many parameters or behaviors need more documentation. Simple tools need less. This dimension scales expectations accordingly.
Does the description clarify parameter syntax, constraints, interactions, or defaults beyond what the schema provides?
Schema description coverage is 100%, and the single 'id' parameter is already documented as the post ID to delete. The description repeats 'by ID' without adding format, source, or validation details beyond the schema, so the baseline is appropriate.
Input schemas describe structure but not intent. Descriptions should explain non-obvious parameter relationships and valid value ranges.
Does the description clearly state what the tool does and how it differs from similar tools?
States a specific verb and resource ('Delete a post') plus the required identifier, so the action is unambiguous. The sibling set contains several delete_* tools for other resources (media, webhook, hashtag set), and naming 'post' is enough to distinguish this tool from them.
Agents choose between tools based on descriptions. A clear purpose with a specific verb and resource helps agents select the right tool.
Does the description explain when to use this tool, when not to, or what alternatives exist?
The description says what the tool does but gives no guidance on when to use it versus alternatives like update_post or other delete_* tools, nor any exclusions or prerequisites. Usage is only implied by the verb.
Agents often have multiple tools that could apply. Explicit usage guidance like "use X instead of Y when Z" prevents misuse.
delete_webhookCDestructiveInspect
Delete a webhook by ID.
| Name | Required | Description | Default |
|---|---|---|---|
| id | Yes | The webhook ID to delete |
TDQS
Does the description disclose side effects, auth requirements, rate limits, or destructive behavior?
Annotations already declare destructiveHint=true and readOnlyHint=false, so the safety profile is covered. The description adds nothing beyond that: it does not say the deletion is permanent, whether it can be undone, whether it revokes any associated delivery endpoints, or what permissions are required. For a destructive operation it contributes no behavioral context of its own.
Agents need to know what a tool does to the world before calling it. Descriptions should go beyond structured annotations to explain consequences.
Is the description appropriately sized, front-loaded, and free of redundancy?
A single four-word sentence with zero padding, front-loaded with verb and resource. It is efficient rather than verbose; the only cost is that the brevity leaves behavioral gaps unaddressed elsewhere.
Shorter descriptions cost fewer tokens and are easier for agents to parse. Every sentence should earn its place.
Given the tool's complexity, does the description cover enough for an agent to succeed on first attempt?
The tool is simple (one fully documented parameter, no output schema) and annotations carry the destructive/safety signal, so the description is close to sufficient. It is still missing the two things an agent would want before an irreversible delete: confirmation that the operation is permanent and whether related resources are affected.
Complex tools with many parameters or behaviors need more documentation. Simple tools need less. This dimension scales expectations accordingly.
Does the description clarify parameter syntax, constraints, interactions, or defaults beyond what the schema provides?
Schema description coverage is 100% and the single id parameter is already documented as 'The webhook ID to delete'. The description's 'by ID' phrasing adds no format, source, or lookup guidance beyond the schema, so the baseline 3 applies.
Input schemas describe structure but not intent. Descriptions should explain non-obvious parameter relationships and valid value ranges.
Does the description clearly state what the tool does and how it differs from similar tools?
States a specific verb (Delete) and resource (webhook) with the keying parameter (by ID), so an agent can distinguish it from update_webhook, get_webhook, and the unrelated delete_post/delete_media siblings without opening the schema. It stops short of any scope detail (e.g. workspace/account ownership of the webhook), but the purpose itself is unambiguous.
Agents choose between tools based on descriptions. A clear purpose with a specific verb and resource helps agents select the right tool.
Does the description explain when to use this tool, when not to, or what alternatives exist?
There is no guidance on when to use this tool versus alternatives such as update_webhook (which could disable rather than remove) or rotate_webhook_secret, and no prerequisites or warnings about irreversibility. The agent must infer usage entirely from the name.
Agents often have multiple tools that could apply. Explicit usage guidance like "use X instead of Y when Z" prevents misuse.
get_accountBRead-onlyInspect
Get details of a specific connected social media account.
| Name | Required | Description | Default |
|---|---|---|---|
| id | Yes | The account ID |
TDQS
Does the description disclose side effects, auth requirements, rate limits, or destructive behavior?
Annotations already declare readOnlyHint=true, destructiveHint=false, and openWorldHint=false, so the safety profile is covered. The description adds nothing beyond that: it doesn't say what 'details' are returned, whether access is scoped to the workspace, or any rate/permission behavior. With annotations doing the work, the description contributes no extra behavioral context.
Agents need to know what a tool does to the world before calling it. Descriptions should go beyond structured annotations to explain consequences.
Is the description appropriately sized, front-loaded, and free of redundancy?
A single front-loaded sentence with no filler; the verb and resource lead and nothing is wasted.
Shorter descriptions cost fewer tokens and are easier for agents to parse. Every sentence should earn its place.
Given the tool's complexity, does the description cover enough for an agent to succeed on first attempt?
There is no output schema, so the description would need to convey what a 'detail' response contains, and it does not — 'details' remains undefined. For a trivial one-parameter read tool with annotations covering safety, this is adequate but leaves the return payload opaque.
Complex tools with many parameters or behaviors need more documentation. Simple tools need less. This dimension scales expectations accordingly.
Does the description clarify parameter syntax, constraints, interactions, or defaults beyond what the schema provides?
Schema description coverage is 100% and the single parameter 'id' is documented as 'The account ID'. The description adds no format, sourcing, or naming detail beyond the schema, so the baseline 3 for high coverage applies.
Input schemas describe structure but not intent. Descriptions should explain non-obvious parameter relationships and valid value ranges.
Does the description clearly state what the tool does and how it differs from similar tools?
States a specific verb ('Get') and resource ('details of a specific connected social media account'), which implicitly contrasts with the sibling list_accounts (plural enumeration vs. single fetch). It is clear but never explicitly names or differentiates itself from list_accounts.
Agents choose between tools based on descriptions. A clear purpose with a specific verb and resource helps agents select the right tool.
Does the description explain when to use this tool, when not to, or what alternatives exist?
The required 'id' parameter implies the caller must already know the account ID, but the description never says when to use this vs. list_accounts to discover IDs, nor states any prerequisite or exclusion. Usage is only implied.
Agents often have multiple tools that could apply. Explicit usage guidance like "use X instead of Y when Z" prevents misuse.
get_account_analyticsARead-onlyInspect
Get account-level analytics for all connected platforms: followers, following, posts, and the day values the platform reports for the snapshot date (impressions/views, reach, engagement, profile_views, link_clicks, follows_gained, follows_lost, Google Business calls/direction_requests/website_clicks/average_rating/review_count, Pinterest monthly_views). Rows with day values carry period: "daily". Audience objects appear when available: demographics (+ demographics_unit) and online_followers (UTC hour to followers online). Present as a sorted table by follower count. Metric semantics: LinkedIn profile rows keep a lifetime total under impressions_lifetime (all content ever, including posts published outside OmniSocials) and period: "lifetime" when no daily breakdown is served. A missing key means the platform does not report it. Each metrics object carries a note explaining its scope where semantics are non-obvious; always relay that note to the user.
| Name | Required | Description | Default |
|---|---|---|---|
| date | No | Date (YYYY-MM-DD, defaults to today) | |
| platform | No | Filter by platform |
TDQS
Does the description disclose side effects, auth requirements, rate limits, or destructive behavior?
Annotations already declare readOnlyHint=true, destructiveHint=false, and openWorldHint=false, so safety is covered. The description adds substantial context beyond that: daily vs lifetime periods, the meaning of a missing key, and a per-object `note` field the caller must relay. It does not discuss auth or rate limits, but the metric-interpretation guidance is genuinely valuable.
Agents need to know what a tool does to the world before calling it. Descriptions should go beyond structured annotations to explain consequences.
Is the description appropriately sized, front-loaded, and free of redundancy?
Front-loaded with the core purpose before diving into metric semantics. It is long for a two-parameter tool and reads as a dense run-on, but with no output schema present most sentences carry needed return-interpretation detail rather than filler.
Shorter descriptions cost fewer tokens and are easier for agents to parse. Every sentence should earn its place.
Given the tool's complexity, does the description cover enough for an agent to succeed on first attempt?
With no output schema, the description bears the burden of explaining the return shape and does so thoroughly – platform metrics, audience objects, period values, and the note-relaying requirement. The main gap is the absence of any usage routing relative to the sibling analytics tools.
Complex tools with many parameters or behaviors need more documentation. Simple tools need less. This dimension scales expectations accordingly.
Does the description clarify parameter syntax, constraints, interactions, or defaults beyond what the schema provides?
Schema description coverage is 100%, so the date and platform parameters are already documented in the schema. The description references 'the snapshot date' but adds no filtering syntax or defaults beyond what the schema provides. Baseline 3 applies.
Input schemas describe structure but not intent. Descriptions should explain non-obvious parameter relationships and valid value ranges.
Does the description clearly state what the tool does and how it differs from similar tools?
States a specific verb+resource ('Get account-level analytics') and enumerates the metrics returned (followers, impressions, reach, engagement, etc.). 'Account-level' implicitly distinguishes it from post-level siblings like get_post_analytics, but it never names them, so the differentiation is left to inference.
Agents choose between tools based on descriptions. A clear purpose with a specific verb and resource helps agents select the right tool.
Does the description explain when to use this tool, when not to, or what alternatives exist?
There is no when-to-use/when-not guidance and no routing to alternatives. Siblings get_analytics_overview, get_post_analytics, and get_best_times are never mentioned, so an agent must guess which analytics tool to pick. Only the implicit 'account-level' scope hints at selection.
Agents often have multiple tools that could apply. Explicit usage guidance like "use X instead of Y when Z" prevents misuse.
get_analytics_overviewARead-onlyInspect
Get analytics overview with total posts, impressions, engagements, engagement rate, and per-platform breakdown. Use period for a rolling window (7d / 30d / 90d) or start_date + end_date for a custom range. The response echoes the resolved range and today's date — read those before assuming a year from training data (e.g. when the user says 'April', use the most recent April, not April from your training cutoff).
| Name | Required | Description | Default |
|---|---|---|---|
| period | No | Rolling window: 7d, 30d, 90d (default: 30d). Ignored if start_date/end_date are provided. | |
| end_date | No | Custom end date. Same formats as start_date; "YYYY-MM" expands to the last day of the month. | |
| start_date | No | Custom start date. Accepts "YYYY-MM-DD" (e.g. "2026-04-01") or "YYYY-MM" month-shorthand (e.g. "2026-04" → first of the month). |
TDQS
Does the description disclose side effects, auth requirements, rate limits, or destructive behavior?
Annotations already cover the safety profile (readOnly, non-destructive, closed-world), so the bar is lower, and the description still adds substantive behavior: the response echoes the resolved range plus today's date, and the agent is told to read those before assuming dates from training data. That is a concrete, non-obvious operational trait that annotations cannot express.
Agents need to know what a tool does to the world before calling it. Descriptions should go beyond structured annotations to explain consequences.
Is the description appropriately sized, front-loaded, and free of redundancy?
Front-loaded with the return contents, then parameter modes, then the date-interpretation caveat. Three sentences with no filler; the final sentence is longer but carries a genuinely useful warning that would otherwise be lost.
Shorter descriptions cost fewer tokens and are easier for agents to parse. Every sentence should earn its place.
Given the tool's complexity, does the description cover enough for an agent to succeed on first attempt?
No output schema exists, so the description carries the burden of describing returns, and it does list the metrics and the echoed resolved range. Combined with annotations covering safety and a fully documented parameter schema, an agent has enough to call and interpret this correctly; only the sibling boundary remains unaddressed.
Complex tools with many parameters or behaviors need more documentation. Simple tools need less. This dimension scales expectations accordingly.
Does the description clarify parameter syntax, constraints, interactions, or defaults beyond what the schema provides?
Schema description coverage is 100%, so the schema already documents period defaults, the 7d/30d/90d options, date formats, and the YYYY-MM expansion. The description restates the period values and range combination but adds no syntax or precedence detail beyond the schema, so baseline 3 applies.
Input schemas describe structure but not intent. Descriptions should explain non-obvious parameter relationships and valid value ranges.
Does the description clearly state what the tool does and how it differs from similar tools?
States a specific verb and resource (analytics overview) and enumerates the metrics returned: total posts, impressions, engagements, engagement rate, per-platform breakdown. It implicitly differs from per-post siblings, but never names get_account_analytics or get_post_analytics to make the boundary explicit.
Agents choose between tools based on descriptions. A clear purpose with a specific verb and resource helps agents select the right tool.
Does the description explain when to use this tool, when not to, or what alternatives exist?
Explains how to drive the two date modes (rolling `period` vs `start_date`+`end_date`) and how to interpret the resolved range, which is real usage guidance. However, it gives no guidance on when to pick this overview tool over get_account_analytics, get_post_analytics, or get_posts_analytics, leaving the alternative-selection decision to inference.
Agents often have multiple tools that could apply. Explicit usage guidance like "use X instead of Y when Z" prevents misuse.
get_automationARead-onlyInspect
Get one comment-to-DM automation: its platform (Instagram, the Facebook Page or X), its trigger, the DM text, the public replies, the limits and the counts.
| Name | Required | Description | Default |
|---|---|---|---|
| automation_id | Yes | The automation id (from list_automations). |
TDQS
Does the description disclose side effects, auth requirements, rate limits, or destructive behavior?
The annotations already establish that this is a safe, read-only, non-destructive operation. The description adds useful context by naming the configuration fields returned, but it does not cover error behavior, missing IDs, or other operational details.
Agents need to know what a tool does to the world before calling it. Descriptions should go beyond structured annotations to explain consequences.
Is the description appropriately sized, front-loaded, and free of redundancy?
The description is a single front-loaded sentence with no wasted phrasing. The enumerated return fields are relevant and compact.
Shorter descriptions cost fewer tokens and are easier for agents to parse. Every sentence should earn its place.
Given the tool's complexity, does the description cover enough for an agent to succeed on first attempt?
For a one-parameter read tool with read-only annotations and no output schema, the description is largely complete because it explains what the returned automation contains. Minor gaps remain around error cases and how this relates to automation activity.
Complex tools with many parameters or behaviors need more documentation. Simple tools need less. This dimension scales expectations accordingly.
Does the description clarify parameter syntax, constraints, interactions, or defaults beyond what the schema provides?
Schema description coverage is 100%, and the single parameter is documented as an automation id 'from list_automations.' The description itself adds no further parameter-level detail, so the baseline of 3 is appropriate.
Input schemas describe structure but not intent. Descriptions should explain non-obvious parameter relationships and valid value ranges.
Does the description clearly state what the tool does and how it differs from similar tools?
The description uses a specific verb and resource: 'Get one comment-to-DM automation.' It makes the single-resource scope explicit and lists the returned configuration fields, which distinguishes it from list_automations and get_automation_activity.
Agents choose between tools based on descriptions. A clear purpose with a specific verb and resource helps agents select the right tool.
Does the description explain when to use this tool, when not to, or what alternatives exist?
The phrase 'Get one' implies retrieving an individual automation, and the schema notes that the id comes from list_automations. However, the description does not explicitly state when to use this versus list_automations or get_automation_activity.
Agents often have multiple tools that could apply. Explicit usage guidance like "use X instead of Y when Z" prevents misuse.
get_automation_activityARead-onlyInspect
The activity of a comment-to-DM automation, newest first: one row per comment or message it acted on, with the DM sent, an answer that waits in the queue (queued: the send cap is full or X asked to wait; it goes out within the hour), a skip and its reason (already got the DM, limit reached, comment older than 7 days, the send cap stayed full for an hour, the person does not accept DMs from the X account, the person replied STOP earlier, the automation was paused while the answer waited), a person who replied STOP on X (opted_out: no automatic DMs to them from that X account again, in any workspace or automation), or a failure with the platform's error. On the Facebook Page the person shows by name (Facebook has no @handle). Use it to answer 'how many people got the DM' or 'why did this person not get it'.
| Name | Required | Description | Default |
|---|---|---|---|
| limit | No | Rows per page (default 25, max 100). | |
| offset | No | Rows to skip (for the next page). | |
| outcome | No | Only rows with this outcome. | |
| automation_id | Yes | The automation id (from list_automations). |
TDQS
Does the description disclose side effects, auth requirements, rate limits, or destructive behavior?
Annotations only declare it is a safe read; the description adds real operational semantics beyond that: queued answers are gated by the send cap or an X wait request and drain within the hour, opted_out suppresses automatic DMs across every workspace and automation, and failures carry the platform error. It also discloses the return shape (person shown by name on Facebook since there is no @handle), which annotations cannot convey.
Agents need to know what a tool does to the world before calling it. Descriptions should go beyond structured annotations to explain consequences.
Is the description appropriately sized, front-loaded, and free of redundancy?
The core identity is front-loaded in the first clause, but the tool is described in one very long run-on sentence with a seven-item parenthetical of skip reasons. Each item is substantively useful for the 'why did this person not get it' use case, yet the wall of text hurts scannability and would benefit from being broken into separate sentences or a list.
Shorter descriptions cost fewer tokens and are easier for agents to parse. Every sentence should earn its place.
Given the tool's complexity, does the description cover enough for an agent to succeed on first attempt?
No output schema exists, and the description compensates by describing the row contents (comment/message acted on, DM text, queue state, skip reason, opt-out, failure error) and ordering. Combined with annotations covering the safety profile and a fully documented schema, an agent has everything needed to call and interpret it.
Complex tools with many parameters or behaviors need more documentation. Simple tools need less. This dimension scales expectations accordingly.
Does the description clarify parameter syntax, constraints, interactions, or defaults beyond what the schema provides?
Schema coverage is 100%, so limit/offset/automation_id are already documented and the baseline is 3. The description earns above baseline by defining the meaning of each outcome value used in the `outcome` enum filter (queued vs skipped vs opted_out vs failed), which is the one parameter whose semantics the schema alone cannot explain.
Input schemas describe structure but not intent. Descriptions should explain non-obvious parameter relationships and valid value ranges.
Does the description clearly state what the tool does and how it differs from similar tools?
States a specific resource (the activity log of a comment-to-DM automation), the ordering (newest first), and the row granularity (one row per comment or message acted on). The enumerated outcome taxonomy makes it unmistakable versus get_automation or list_automations, which an agent could otherwise confuse it with.
Agents choose between tools based on descriptions. A clear purpose with a specific verb and resource helps agents select the right tool.
Does the description explain when to use this tool, when not to, or what alternatives exist?
Gives concrete answering scenarios: 'how many people got the DM' and 'why did this person not get it', which map directly to counting rows and reading skip reasons. It does not explicitly exclude alternatives (e.g. use get_automation for config rather than activity), so it stops short of a 5.
Agents often have multiple tools that could apply. Explicit usage guidance like "use X instead of Y when Z" prevents misuse.
get_best_timesARead-onlyInspect
Get recommended posting times (day + hour) for one platform, computed from the workspace's own posting history: publish time × engagement of every post published there, recency-weighted and outlier-damped, bucketed in the user's timezone, and blended with when the account's followers are online when the platform provides that (Instagram, TikTok Business; basis: own_data_and_audience, response carries audience_online). Returns the top 3 recommended slots plus a per-day breakdown. When the workspace has fewer than 15 analyzed posts on the platform, the audience-online profile alone is used (basis: audience) or industry-average defaults are returned (basis: defaults) with how many more posts unlock personalized recommendations — tell the user that so the numbers aren't mistaken for their own audience data. Use this before scheduling when the user asks 'when should I post?' or hasn't specified a time. Requires the analytics:read scope.
| Name | Required | Description | Default |
|---|---|---|---|
| platform | Yes | Platform identifier, e.g. instagram, tiktok, linkedin, linkedin_page, x, facebook, youtube, pinterest, threads, bluesky, mastodon, google_business, telegram, discord | |
| timezone | No | IANA timezone for the buckets (e.g. Europe/Amsterdam). Defaults to the account's timezone. |
TDQS
Does the description disclose side effects, auth requirements, rate limits, or destructive behavior?
Annotations already mark it read-only and non-destructive, and the description adds substantial behavioral context beyond that: the recency-weighted, outlier-damped methodology, the audience-online blending for Instagram and TikTok Business, the basis values (`own_data_and_audience`, `audience`, `defaults`), the 15-post threshold, and the required analytics:read scope.
Agents need to know what a tool does to the world before calling it. Descriptions should go beyond structured annotations to explain consequences.
Is the description appropriately sized, front-loaded, and free of redundancy?
The purpose and usage trigger are front-loaded, and nearly every clause carries useful information. It is dense and long, but the detail about fallbacks and basis values earns its place; only minor restructuring would improve readability.
Shorter descriptions cost fewer tokens and are easier for agents to parse. Every sentence should earn its place.
Given the tool's complexity, does the description cover enough for an agent to succeed on first attempt?
With no output schema, the description steps in to explain the return shape (top 3 slots plus per-day breakdown) and the `basis` and `audience_online` fields. It also covers the sparse-data case and the permission requirement, leaving no major gap for a read-only recommendation tool.
Complex tools with many parameters or behaviors need more documentation. Simple tools need less. This dimension scales expectations accordingly.
Does the description clarify parameter syntax, constraints, interactions, or defaults beyond what the schema provides?
Schema description coverage is 100%, so both parameters are already documented. The description still adds meaning by emphasizing that results are for one platform, that audience-online support varies by platform, and that bucketing uses the user's timezone.
Input schemas describe structure but not intent. Descriptions should explain non-obvious parameter relationships and valid value ranges.
Does the description clearly state what the tool does and how it differs from similar tools?
The description states a specific verb and resource: it returns recommended posting times (day + hour) for one platform, computed from the workspace's posting history. It clearly distinguishes itself from analytics siblings by focusing on recommendations rather than raw metrics, and it names the exact output (top 3 slots plus per-day breakdown).
Agents choose between tools based on descriptions. A clear purpose with a specific verb and resource helps agents select the right tool.
Does the description explain when to use this tool, when not to, or what alternatives exist?
It explicitly says to use this before scheduling when the user asks 'when should I post?' or has not specified a time. It also explains fallback behavior when history is sparse, including what to tell the user so defaults are not mistaken for personalized data.
Agents often have multiple tools that could apply. Explicit usage guidance like "use X instead of Y when Z" prevents misuse.
get_calendarARead-onlyInspect
Get a content calendar showing scheduled and published posts organized by day of the week.
| Name | Required | Description | Default |
|---|---|---|---|
| status | No | Filter: scheduled, published, or omit for both | |
| end_date | No | End date (YYYY-MM-DD). Defaults to end of current week (Sunday). | |
| start_date | No | Start date (YYYY-MM-DD). Defaults to start of current week (Monday). |
TDQS
Does the description disclose side effects, auth requirements, rate limits, or destructive behavior?
Annotations already declare readOnlyHint=true, destructiveHint=false, and openWorldHint=false, so the safety profile is covered. The description usefully adds the grouping semantics (organized by day of the week) and that both scheduled and published posts appear, but says nothing about pagination, ordering, or limits.
Agents need to know what a tool does to the world before calling it. Descriptions should go beyond structured annotations to explain consequences.
Is the description appropriately sized, front-loaded, and free of redundancy?
A single, front-loaded sentence with no filler. Every clause (scheduled, published, organized by day of the week) carries information an agent can use.
Shorter descriptions cost fewer tokens and are easier for agents to parse. Every sentence should earn its place.
Given the tool's complexity, does the description cover enough for an agent to succeed on first attempt?
For a read-only tool with full annotation coverage and complete parameter docs, the description supplies the essential return-shape context (a calendar grouped by weekday). No output schema exists, so it should ideally say a bit more about what each calendar entry contains, but it is close to sufficient.
Complex tools with many parameters or behaviors need more documentation. Simple tools need less. This dimension scales expectations accordingly.
Does the description clarify parameter syntax, constraints, interactions, or defaults beyond what the schema provides?
Schema description coverage is 100% — all three parameters (status, start_date, end_date) are documented in the schema, including defaults. The description adds no parameter-level detail, so the baseline 3 applies.
Input schemas describe structure but not intent. Descriptions should explain non-obvious parameter relationships and valid value ranges.
Does the description clearly state what the tool does and how it differs from similar tools?
States a specific verb (Get) and resource (content calendar) and clarifies the shape of the result: scheduled and published posts organized by day of the week. This framing distinguishes it from the flat list_posts sibling, though no sibling is named explicitly.
Agents choose between tools based on descriptions. A clear purpose with a specific verb and resource helps agents select the right tool.
Does the description explain when to use this tool, when not to, or what alternatives exist?
The calendar framing implies the use case (viewing posts in a weekly calendar layout rather than a flat list), but the description never states when to prefer this over list_posts or get_post, nor any prerequisites or exclusions. Usage must be inferred.
Agents often have multiple tools that could apply. Explicit usage guidance like "use X instead of Y when Z" prevents misuse.
get_inbox_conversationARead-onlyInspect
Get the full message history of one inbox conversation, oldest first, with the post it belongs to (caption, link, image) for comment/mention threads. Each message shows its inbox id (#id); that id is what hide_inbox_comment and delete_inbox_comment take. Use the conversation_id from list_inbox_conversations. Replies sent from the native apps appear as outgoing messages too.
| Name | Required | Description | Default |
|---|---|---|---|
| limit | No | Max messages per page (1-100, default 50) | |
| cursor | No | Pagination cursor from a previous response | |
| conversation_id | Yes | The conversation ID to fetch |
TDQS
Does the description disclose side effects, auth requirements, rate limits, or destructive behavior?
Annotations already declare readOnlyHint=true, destructiveHint=false, openWorldHint=false, so safety is covered. The description adds real behavior: oldest-first ordering, inclusion of the parent post's caption/link/image, the #id format that other tools consume, and the non-obvious fact that native-app replies surface as outgoing messages.
Agents need to know what a tool does to the world before calling it. Descriptions should go beyond structured annotations to explain consequences.
Is the description appropriately sized, front-loaded, and free of redundancy?
Three tight sentences, front-loaded with what is returned and ordered before workflow details. Dense but almost every clause carries information; the parenthetical field list is the only slightly heavy part.
Shorter descriptions cost fewer tokens and are easier for agents to parse. Every sentence should earn its place.
Given the tool's complexity, does the description cover enough for an agent to succeed on first attempt?
With no output schema, the description carries the burden of describing the return shape and does so (message ids, per-message data, attached post fields, ordering). Pagination is handled by the schema's limit/cursor, so nothing essential for correct invocation is missing.
Complex tools with many parameters or behaviors need more documentation. Simple tools need less. This dimension scales expectations accordingly.
Does the description clarify parameter syntax, constraints, interactions, or defaults beyond what the schema provides?
Schema coverage is 100%, so limit, cursor, and conversation_id are already documented in the schema; baseline is 3. The description adds provenance for conversation_id (source it from list_inbox_conversations) but says nothing extra about limit or cursor semantics.
Input schemas describe structure but not intent. Descriptions should explain non-obvious parameter relationships and valid value ranges.
Does the description clearly state what the tool does and how it differs from similar tools?
States a specific verb and resource ('Get the full message history of one inbox conversation'), plus ordering ('oldest first') and included payload ('the post it belongs to ... for comment/mention threads'). It is clearly distinguishable from list_inbox_conversations, which enumerates conversations rather than one thread.
Agents choose between tools based on descriptions. A clear purpose with a specific verb and resource helps agents select the right tool.
Does the description explain when to use this tool, when not to, or what alternatives exist?
Explicitly routes the agent: 'Use the conversation_id from list_inbox_conversations,' and names the downstream consumers of the returned ids (hide_inbox_comment, delete_inbox_comment). No explicit when-not or exclusion criteria are given, but the workflow context is clear.
Agents often have multiple tools that could apply. Explicit usage guidance like "use X instead of Y when Z" prevents misuse.
get_next_unansweredARead-onlyInspect
Get the next inbox item that needs an answer, with the whole conversation and the post it is on, in one call. An item needs an answer when it is the customer's latest DM with no reply after it, or a comment/mention nobody replied to and that is not hidden. Order: DMs that can still be answered first (Instagram/Facebook DMs inside Meta's 24-hour window, the one closing soonest first, plus X DMs), then Instagram/Facebook DMs whose window has closed (reply_window.open = false: OmniSocials cannot reply, tell the user to answer from the native app or skip with mark_inbox_read), then comments and mentions, oldest first. Replies typed in the native apps count as answered (they are mirrored into the inbox), so a thread a colleague answered on their phone is not served again. Instagram mentions are skipped (no reply path). Only unread items are served by default: to skip one for good, mark_inbox_read it; pass include_read to also see read-but-unanswered items. Looks back 30 days. Loop: get_next_unanswered → draft a reply → reply_to_inbox with the conversation id, message_id = the served message's #id, and include_next: true → repeat until nothing is waiting.
| Name | Required | Description | Default |
|---|---|---|---|
| type | No | Only items of one type | |
| order | No | oldest (default): the item that has waited longest first; newest: the most recent first. Applies within each group (answerable DMs, then expired Instagram/Facebook DMs, then comments); the groups keep their order | |
| exclude | No | Comma-separated conversation ids to leave out of this call (a temporary skip; up to 100) | |
| platform | No | Only items from one platform | |
| include_read | No | Also serve items that were marked read but never answered |
TDQS
Does the description disclose side effects, auth requirements, rate limits, or destructive behavior?
Annotations already declare readOnlyHint=true, destructiveHint=false, and openWorldHint=false, so the safety profile is covered. The description adds substantial behavioral context the annotations cannot: the 30-day lookback, the three-tier ordering with 24-hour window logic, that native-app replies count as answered, and that Instagram mentions are skipped. However it does not state return format or pagination, so against a lower bar it is solid but not exhaustive.
Agents need to know what a tool does to the world before calling it. Descriptions should go beyond structured annotations to explain consequences.
Is the description appropriately sized, front-loaded, and free of redundancy?
Long but front-loaded: the first sentence gives the core purpose and payload, and every subsequent sentence carries needed ordering, window, or loop semantics with no filler. The information density justifies the length for a tool with this much selection logic.
Shorter descriptions cost fewer tokens and are easier for agents to parse. Every sentence should earn its place.
Given the tool's complexity, does the description cover enough for an agent to succeed on first attempt?
There is no output schema, and the description compensates by stating the return payload (whole conversation plus the post) and the identifiers the agent needs for the follow-up call (conversation id, message #id). Combined with the lookback limit and ordering rules, an agent can invoke this correctly without further context.
Complex tools with many parameters or behaviors need more documentation. Simple tools need less. This dimension scales expectations accordingly.
Does the description clarify parameter syntax, constraints, interactions, or defaults beyond what the schema provides?
Schema coverage is 100%, so the baseline is 3, but the description adds semantic nuance beyond the schema: it explains that ordering preserves group order, that skip-via-exclude is temporary while mark_inbox_read is permanent, and clarifies include_read's role in the workflow.
Input schemas describe structure but not intent. Descriptions should explain non-obvious parameter relationships and valid value ranges.
Does the description clearly state what the tool does and how it differs from similar tools?
States a specific verb and resource ('get the next inbox item that needs an answer') and precisely defines the selection predicate (customer's latest unanswered DM, or unhidden unreplied comment/mention), which clearly separates it from list_inbox_conversations and get_inbox_conversation.
Agents choose between tools based on descriptions. A clear purpose with a specific verb and resource helps agents select the right tool.
Does the description explain when to use this tool, when not to, or what alternatives exist?
Explicit when-to-use with a full decision flow: it defines what 'needs an answer' means, names the alternatives for skipping (mark_inbox_read for permanent, include_read for read items), tells the agent what to do when the reply window is closed, and closes with the get_next_unanswered → reply_to_inbox loop.
Agents often have multiple tools that could apply. Explicit usage guidance like "use X instead of Y when Z" prevents misuse.
get_postARead-onlyInspect
Get full details of a specific post including content, channels, media (with URLs), first comment, Instagram collaborators/user tags/location/Trial Reel state/Reel cover (thumbnail_type + thumb_offset in ms), dates, live URLs, per-platform publish errors, and retry linkage (retry_of / retries — a published post with empty published_urls and retries set is a resolved failure whose live URLs live on the retry post) — enough to fully verify a scheduled post without opening the dashboard. When a post has per-platform caption overrides (e.g. a shorter X version alongside the default), every variant is rendered as its own labeled block under ### Content so you can see exactly what each platform will publish. X threads are rendered under ### X Thread with each tweet labeled in publish order — read this to see the full chained tweet text, since thread-only posts have no caption in content. A LinkedIn poll is rendered under ### LinkedIn Profile Poll and/or ### LinkedIn Page Poll (independent per channel) with the question, options, and duration. After a post is published, published_urls maps each platform to the live post URL (only platforms that successfully posted appear).
| Name | Required | Description | Default |
|---|---|---|---|
| id | Yes | The post ID |
TDQS
Does the description disclose side effects, auth requirements, rate limits, or destructive behavior?
Annotations already cover the safety profile (readOnlyHint, destructiveHint=false, openWorldHint=false), and the description goes further by disclosing return semantics: per-platform publish errors, how `retry_of`/`retries` indicate a resolved failure, and that `published_urls` only lists platforms that successfully posted. This is genuine behavioral context an agent cannot get from the annotations.
Agents need to know what a tool does to the world before calling it. Descriptions should go beyond structured annotations to explain consequences.
Is the description appropriately sized, front-loaded, and free of redundancy?
The opening clause is well front-loaded, but the body is one sprawling, unparagraphed run-on that mixes content rendering rules, thread handling, poll rendering, and retry semantics. The information is relevant, yet its density and lack of structure make it hard to scan for the one parameter an agent must supply.
Shorter descriptions cost fewer tokens and are easier for agents to parse. Every sentence should earn its place.
Given the tool's complexity, does the description cover enough for an agent to succeed on first attempt?
With no output schema, the description shoulders the return-value burden and does so thoroughly, covering content, media URLs, threads, polls, errors, and published URL mapping. It omits only edge behavior such as an invalid or missing post ID, which is a minor gap for a single-resource getter.
Complex tools with many parameters or behaviors need more documentation. Simple tools need less. This dimension scales expectations accordingly.
Does the description clarify parameter syntax, constraints, interactions, or defaults beyond what the schema provides?
Schema description coverage is 100% and there is a single `id` parameter already documented as 'The post ID.' The description adds no format, source, or lookup guidance for the ID, so the baseline 3 applies – the schema carries the full burden.
Input schemas describe structure but not intent. Descriptions should explain non-obvious parameter relationships and valid value ranges.
Does the description clearly state what the tool does and how it differs from similar tools?
States a specific verb and resource: 'Get full details of a specific post' with an enumerated scope (content, channels, media, errors, retry linkage). An agent can tell this is a single-post detail fetch, not a list or analytics call, though it never names the sibling it differs from (get_post_analytics, list_posts) to sharpen the distinction.
Agents choose between tools based on descriptions. A clear purpose with a specific verb and resource helps agents select the right tool.
Does the description explain when to use this tool, when not to, or what alternatives exist?
Usage is only implied via the phrase 'enough to fully verify a scheduled post without opening the dashboard.' There is no explicit when-to-use, when-not-to-use, or named alternative such as get_post_analytics for metrics; the agent must infer the boundary itself.
Agents often have multiple tools that could apply. Explicit usage guidance like "use X instead of Y when Z" prevents misuse.
get_post_analyticsARead-onlyInspect
Get detailed analytics for a specific published post. Renders every metric the platform reported — impressions, reach, views, saves, likes, comments, shares, clicks, engagements, and more — per platform. TikTok videos also carry average_time_watched, full_video_watched_rate, total_time_watched, favorites and reach when the workspace enabled TikTok comments (Business API authorization).
| Name | Required | Description | Default |
|---|---|---|---|
| post_id | Yes | The numeric OmniSocials post id (the `id` field from list_posts). NOT a platform post id such as a YouTube video id or tweet id. |
TDQS
Does the description disclose side effects, auth requirements, rate limits, or destructive behavior?
Annotations already establish readOnly/openWorld=false/destructive=false, so the description's job is additive — and it delivers: it enumerates the returned metric families and discloses that certain TikTok fields (average_time_watched, full_video_watched_rate, etc.) are conditional on workspace TikTok Business API authorization. That conditional-data caveat is real behavioral context beyond the annotations.
Agents need to know what a tool does to the world before calling it. Descriptions should go beyond structured annotations to explain consequences.
Is the description appropriately sized, front-loaded, and free of redundancy?
Two sentences, front-loaded with the core purpose, then the metric inventory and the conditional TikTok caveat. The long metric list ('impressions, reach, views, saves, likes, comments, shares, clicks, engagements, and more') is somewhat enumerative but serves the no-output-schema case, so it earns most of its space.
Shorter descriptions cost fewer tokens and are easier for agents to parse. Every sentence should earn its place.
Given the tool's complexity, does the description cover enough for an agent to succeed on first attempt?
With no output schema, the description compensates by describing the return payload per platform, which is exactly what an agent needs to interpret the result. It omits any note on authentication scope or whether metrics can be empty for older posts, minor gaps given the annotation coverage.
Complex tools with many parameters or behaviors need more documentation. Simple tools need less. This dimension scales expectations accordingly.
Does the description clarify parameter syntax, constraints, interactions, or defaults beyond what the schema provides?
Schema description coverage is 100% and the single parameter already explains that post_id is the numeric OmniSocials id from list_posts, not a platform id. The description adds nothing about the parameter, so the baseline of 3 applies.
Input schemas describe structure but not intent. Descriptions should explain non-obvious parameter relationships and valid value ranges.
Does the description clearly state what the tool does and how it differs from similar tools?
States a specific verb ('Get') plus resource ('detailed analytics') scoped to 'a specific published post', which implicitly sets it apart from the plural sibling get_posts_analytics and from get_analytics_overview. It stops short of naming those siblings, so the differentiation is inferential rather than explicit.
Agents choose between tools based on descriptions. A clear purpose with a specific verb and resource helps agents select the right tool.
Does the description explain when to use this tool, when not to, or what alternatives exist?
The phrase 'specific published post' weakly implies the per-post scenario and that drafts are excluded, but there is no explicit when-to-use versus get_posts_analytics, get_analytics_overview, or get_account_analytics, and no stated prerequisites beyond the required id.
Agents often have multiple tools that could apply. Explicit usage guidance like "use X instead of Y when Z" prevents misuse.
get_post_approvalARead-onlyInspect
Read the approval review of a post: every workflow step with its approvers and their decisions, the rejection with its reason, and the comment thread. Use it when get_post shows status rejected (who rejected it and why, what to change before sending it again) or in_approval (who the post waits for, what the reviewers wrote). Read-only. A post without an approval workflow returns status none.
| Name | Required | Description | Default |
|---|---|---|---|
| id | Yes | The post ID |
TDQS
Does the description disclose side effects, auth requirements, rate limits, or destructive behavior?
Annotations already declare readOnlyHint=true, destructiveHint=false, and openWorldHint=false, so safety is covered; the description's 'Read-only' line is largely redundant. It does add genuine behavioral context by describing the returned content and the edge case where a post has no workflow and returns status `none`.
Agents need to know what a tool does to the world before calling it. Descriptions should go beyond structured annotations to explain consequences.
Is the description appropriately sized, front-loaded, and free of redundancy?
Front-loaded with the payload description, then the usage trigger, then edge cases; each sentence earns its place. The standalone 'Read-only.' fragment restates the readOnlyHint annotation and is the one piece of low-value content.
Shorter descriptions cost fewer tokens and are easier for agents to parse. Every sentence should earn its place.
Given the tool's complexity, does the description cover enough for an agent to succeed on first attempt?
There is no output schema, so the description carries the return-value burden, and it does so by enumerating what the approval review contains plus the `none` status for posts without a workflow. Combined with annotation-covered safety, an agent has everything needed to call and interpret it.
Complex tools with many parameters or behaviors need more documentation. Simple tools need less. This dimension scales expectations accordingly.
Does the description clarify parameter syntax, constraints, interactions, or defaults beyond what the schema provides?
Schema description coverage is 100% and there is a single required `id` parameter already documented in the schema, so per calibration the baseline is 3. The description adds no syntax or format detail about the post ID beyond what the schema provides.
Input schemas describe structure but not intent. Descriptions should explain non-obvious parameter relationships and valid value ranges.
Does the description clearly state what the tool does and how it differs from similar tools?
States a specific verb (read) and resource (the approval review of a post) and enumerates the exact payload: workflow steps, approvers, decisions, rejection reason, and comment thread. This clearly distinguishes it from approve_post, reject_post, and get_post, which an agent can tell apart without opening the schema.
Agents choose between tools based on descriptions. A clear purpose with a specific verb and resource helps agents select the right tool.
Does the description explain when to use this tool, when not to, or what alternatives exist?
Gives explicit trigger conditions keyed to a sibling's output: use it when get_post shows status `rejected` or `in_approval`, with the purpose spelled out for each case. It also names the fallback behavior (a post without an approval workflow returns `none`), leaving nothing to inference.
Agents often have multiple tools that could apply. Explicit usage guidance like "use X instead of Y when Z" prevents misuse.
get_posts_analyticsARead-onlyInspect
Get analytics for several published posts at once (up to 100), each totalled into impressions and engagements. Use this instead of calling get_post_analytics in a loop — it is a single request rather than one per post.
| Name | Required | Description | Default |
|---|---|---|---|
| post_ids | Yes | Numeric OmniSocials post ids (the `id` field from list_posts), up to 100. NOT platform post ids such as YouTube video ids or tweet ids. |
TDQS
Does the description disclose side effects, auth requirements, rate limits, or destructive behavior?
Annotations already declare readOnlyHint=true, destructiveHint=false and openWorldHint=false, so safety is covered. The description adds real behavioral context beyond that: results are aggregated (totalled into impressions and engagements), the batch cap is 100, and the call is a single request rather than N. It does not discuss pagination, partial failures, or permission requirements, so not a full 5.
Agents need to know what a tool does to the world before calling it. Descriptions should go beyond structured annotations to explain consequences.
Is the description appropriately sized, front-loaded, and free of redundancy?
Two sentences, zero waste. The scope and cap are front-loaded, and the routing instruction to get_post_analytics follows immediately after.
Shorter descriptions cost fewer tokens and are easier for agents to parse. Every sentence should earn its place.
Given the tool's complexity, does the description cover enough for an agent to succeed on first attempt?
For a one-parameter read tool with annotations covering the safety profile and no output schema, the description supplies what an agent needs: the batching semantics, the cap, the aggregation into impressions/engagements, and the alternative it replaces. Nothing material is missing.
Complex tools with many parameters or behaviors need more documentation. Simple tools need less. This dimension scales expectations accordingly.
Does the description clarify parameter syntax, constraints, interactions, or defaults beyond what the schema provides?
Schema description coverage is 100% and the single parameter is already documented in the schema, including the numeric-OmniSocials-id vs platform-id distinction and the maxItems=100 cap. The description's 'up to 100' and 'published posts' restate the schema rather than adding syntax or format meaning, so the baseline 3 applies.
Input schemas describe structure but not intent. Descriptions should explain non-obvious parameter relationships and valid value ranges.
Does the description clearly state what the tool does and how it differs from similar tools?
States a specific verb (Get) and resource (analytics) with an explicit scope: several published posts at once, up to 100, totalled into impressions and engagements. It names the sibling get_post_analytics and explains how it differs, so an agent can select it without opening either schema.
Agents choose between tools based on descriptions. A clear purpose with a specific verb and resource helps agents select the right tool.
Does the description explain when to use this tool, when not to, or what alternatives exist?
Explicitly says to use this instead of calling get_post_analytics in a loop, and gives the reason (single request rather than one per post). This is a clear when-to-use directive with the alternative named.
Agents often have multiple tools that could apply. Explicit usage guidance like "use X instead of Y when Z" prevents misuse.
get_post_statusPost Card StatusARead-onlyInspect
Used by the OmniSocials post card to follow a post while it publishes. Agents: use get_post instead.
| Name | Required | Description | Default |
|---|---|---|---|
| id | Yes | The post ID |
TDQS
Does the description disclose side effects, auth requirements, rate limits, or destructive behavior?
The annotations already declare readOnlyHint=true, destructiveHint=false, and openWorldHint=false. The description adds that it follows a post while publishing, implying a status/polling behavior, but does not disclose return format, polling expectations, or other behavioral traits beyond the annotations.
Agents need to know what a tool does to the world before calling it. Descriptions should go beyond structured annotations to explain consequences.
Is the description appropriately sized, front-loaded, and free of redundancy?
Two short sentences with zero waste, and the most important routing instruction is placed clearly at the end. Nothing extraneous is included.
Shorter descriptions cost fewer tokens and are easier for agents to parse. Every sentence should earn its place.
Given the tool's complexity, does the description cover enough for an agent to succeed on first attempt?
For a simple, read-only, single-parameter status tool with no output schema and clear annotations, the description is nearly complete. It tells agents to avoid it and names the alternative, though it does not describe the status values or polling behavior, which is a minor gap.
Complex tools with many parameters or behaviors need more documentation. Simple tools need less. This dimension scales expectations accordingly.
Does the description clarify parameter syntax, constraints, interactions, or defaults beyond what the schema provides?
The schema has 100% description coverage for the single id parameter. The description adds no additional meaning about the post ID or its format, so the baseline of 3 is appropriate because the schema fully documents the parameter.
Input schemas describe structure but not intent. Descriptions should explain non-obvious parameter relationships and valid value ranges.
Does the description clearly state what the tool does and how it differs from similar tools?
States a specific verb and resource: following a post while it publishes. It also distinguishes itself from the sibling get_post by telling agents to use that instead. An agent can identify the tool's intended role without opening the schema.
Agents choose between tools based on descriptions. A clear purpose with a specific verb and resource helps agents select the right tool.
Does the description explain when to use this tool, when not to, or what alternatives exist?
Explicitly states when the tool is used (by the OmniSocials post card while publishing) and gives a direct when-not instruction: 'Agents: use get_post instead.' This is unambiguous routing guidance with a named alternative.
Agents often have multiple tools that could apply. Explicit usage guidance like "use X instead of Y when Z" prevents misuse.
get_recent_platform_postsARead-onlyInspect
Fetch the user's most recent posts straight from their connected platform APIs (Instagram, TikTok, X, YouTube, Facebook, LinkedIn, and more), INCLUDING content published outside OmniSocials. Use this when list_posts is empty — e.g. a brand-new workspace that has not published through OmniSocials yet — so you can still analyze the user's real content. Each post includes normalized engagement plus every raw metric the platform reported (Instagram: reach/views/saves/shares from per-post insights; TikTok: average_time_watched/full_video_watched_rate/total_time_watched/favorites/reach when the workspace enabled TikTok comments). Metrics only appear where the platform exposes them for historical posts (X, TikTok, Bluesky, Mastodon, Instagram, Facebook, YouTube); Threads, Pinterest, and Google Business return captions only. Records also carry duration_seconds — the video length in whole seconds — where the platform's listing API reports it (currently TikTok and YouTube); null for images and platforms that don't expose it. LinkedIn personal profiles can't be listed live (LinkedIn grants apps no such permission), so their results are posts published through OmniSocials with their latest collected stats. Fetched live for most platforms, so expect a few seconds of latency; X results may come from a snapshot up to 24h old (X bills per returned post) — the snapshot refreshes right after the user publishes to X through OmniSocials. Output is a human-readable summary table PLUS a 'Structured data' JSON block carrying, for every post, the platform's own post id (the stable dedupe key), a permalink, the FULL untruncated caption, and exact-integer metrics — use that block when ingesting or storing native posts rather than the rounded/truncated table. Requires the analytics:read scope.
| Name | Required | Description | Default |
|---|---|---|---|
| limit | No | Max posts per connected platform (1-50, default 25; X defaults to 10 unless set explicitly — its API bills per returned post). | |
| platforms | No | Optional comma-separated platform filter, e.g. "instagram,tiktok". Defaults to every connected platform. |
TDQS
Does the description disclose side effects, auth requirements, rate limits, or destructive behavior?
Annotations only cover the safety profile (readOnly/openWorld/non-destructive), and the description adds substantial behavioral context: live-fetch latency, a possible 24h snapshot staleness for X with the billing rationale, the LinkedIn personal-profile permission limitation, which platforms actually expose metrics, and the required analytics:read scope.
Agents need to know what a tool does to the world before calling it. Descriptions should go beyond structured annotations to explain consequences.
Is the description appropriately sized, front-loaded, and free of redundancy?
Well front-loaded — the core purpose and the list_posts routing come first, caveats after. It is dense and long, but nearly every clause (snapshot staleness, metric availability, duration_seconds, output block) carries actionable information, so little is wasted.
Shorter descriptions cost fewer tokens and are easier for agents to parse. Every sentence should earn its place.
Given the tool's complexity, does the description cover enough for an agent to succeed on first attempt?
With no output schema, the description carries the return-value burden and does so thoroughly: a summary table plus a 'Structured data' JSON block with stable post id, permalink, untruncated caption, and exact-integer metrics. Combined with the per-platform metric caveats, an agent has everything needed to call and consume it.
Complex tools with many parameters or behaviors need more documentation. Simple tools need less. This dimension scales expectations accordingly.
Does the description clarify parameter syntax, constraints, interactions, or defaults beyond what the schema provides?
Schema coverage is 100%, so the schema already documents both params, giving a baseline of 3. The description reinforces why limit defaults differ for X (billing) and clarifies platform-filtering intent, adding marginal value over the schema rather than restating it.
Input schemas describe structure but not intent. Descriptions should explain non-obvious parameter relationships and valid value ranges.
Does the description clearly state what the tool does and how it differs from similar tools?
States a specific verb+resource ('Fetch the user's most recent posts') with precise scope ('straight from their connected platform APIs... INCLUDING content published outside OmniSocials'). It explicitly distinguishes itself from the sibling list_posts, so an agent can separate the two without opening either schema.
Agents choose between tools based on descriptions. A clear purpose with a specific verb and resource helps agents select the right tool.
Does the description explain when to use this tool, when not to, or what alternatives exist?
Gives an explicit trigger condition: 'Use this when list_posts is empty — e.g. a brand-new workspace that has not published through OmniSocials yet.' The alternative (list_posts) is named and the selecting condition is spelled out, leaving nothing to inference.
Agents often have multiple tools that could apply. Explicit usage guidance like "use X instead of Y when Z" prevents misuse.
get_webhookBRead-onlyInspect
Get details of a specific webhook by ID.
| Name | Required | Description | Default |
|---|---|---|---|
| id | Yes | The webhook ID |
TDQS
Does the description disclose side effects, auth requirements, rate limits, or destructive behavior?
Annotations already declare readOnlyHint=true, destructiveHint=false, and openWorldHint=false. The description adds no behavioral context such as error handling, permissions, or response shape beyond what the structured annotations already provide.
Agents need to know what a tool does to the world before calling it. Descriptions should go beyond structured annotations to explain consequences.
Is the description appropriately sized, front-loaded, and free of redundancy?
A single front-loaded sentence with verb, resource, and scope. No filler or wasted words.
Shorter descriptions cost fewer tokens and are easier for agents to parse. Every sentence should earn its place.
Given the tool's complexity, does the description cover enough for an agent to succeed on first attempt?
For a simple read tool backed by full annotation coverage and a 100%-documented schema, the description is complete enough to invoke correctly. It does not need to explain return values because no output schema exists, though it lacks routing and error context.
Complex tools with many parameters or behaviors need more documentation. Simple tools need less. This dimension scales expectations accordingly.
Does the description clarify parameter syntax, constraints, interactions, or defaults beyond what the schema provides?
The single id parameter has 100% schema description coverage, so the schema already documents it. The description's 'by ID' adds no format or constraint detail beyond the schema, making the baseline 3 appropriate.
Input schemas describe structure but not intent. Descriptions should explain non-obvious parameter relationships and valid value ranges.
Does the description clearly state what the tool does and how it differs from similar tools?
States a specific GET operation on a webhook resource, scoped by ID, which separates it from list_webhooks. No explicit sibling is named, but the by-ID scope gives sufficient differentiation.
Agents choose between tools based on descriptions. A clear purpose with a specific verb and resource helps agents select the right tool.
Does the description explain when to use this tool, when not to, or what alternatives exist?
Usage is implied by 'by ID'—call this when you have a known webhook ID—but there is no when-to-use or when-not-to-use guidance, and no alternative routing among get/list/update siblings.
Agents often have multiple tools that could apply. Explicit usage guidance like "use X instead of Y when Z" prevents misuse.
hide_inbox_commentAInspect
Hide (or unhide) a comment someone left on one of the workspace's posts, on the platform, as the post owner. Facebook, Instagram, TikTok, YouTube and Threads comments. On YouTube, hide sets the comment to 'rejected' (removed from public view together with its replies) and unhide publishes it again. Takes the message id (the #id shown by get_inbox_conversation and get_next_unanswered), not the conversation id. A hidden comment no longer counts as unanswered. If the comment was already deleted on the platform (its author removed it, etc.), this still succeeds — the response says so — and the item is marked handled; do not retry it. A 403 reconnect_required means the account was connected without the comment-moderation permission and must be reconnected in the dashboard; relay that to the user rather than retrying. A 422 cannot_hide means Facebook does not let the Page hide this particular comment (the commenter blocked the Page, their account is deactivated or restricted, or the comment sits on a shared copy of the post): retrying never changes it — tell the user, and use mark_inbox_read on the conversation if it should stop coming up. A 502 hide_not_applied means Instagram accepted the call but still reports the comment as visible (this happens with comments shown under 'Comments from Facebook' on a reel shared to Facebook; they live on Facebook and Instagram's hide does not reach them): nothing changed in the inbox, tell the user to hide it in the Instagram or Facebook app, do not retry.
| Name | Required | Description | Default |
|---|---|---|---|
| hide | No | true (default) to hide, false to unhide | |
| message_id | Yes | The inbox message id of the comment (the #id in the thread) |
TDQS
Does the description disclose side effects, auth requirements, rate limits, or destructive behavior?
Annotations declare the safety profile (readOnlyHint=false, destructiveHint=false, openWorldHint=true), and the description adds substantial context beyond it: platform-specific semantics (YouTube 'rejected' plus replies), idempotency when the comment was already deleted, the 'no longer counts as unanswered' side effect, and precise handling for 403 reconnect_required, 422 cannot_hide and 502 hide_not_applied.
Agents need to know what a tool does to the world before calling it. Descriptions should go beyond structured annotations to explain consequences.
Is the description appropriately sized, front-loaded, and free of redundancy?
Front-loads the core action and is information-dense with essentially no wasted sentence, but it is delivered as one very long run-on paragraph that is harder to scan than a structured breakdown of error cases would be.
Shorter descriptions cost fewer tokens and are easier for agents to parse. Every sentence should earn its place.
Given the tool's complexity, does the description cover enough for an agent to succeed on first attempt?
No output schema exists, yet the description still tells the agent what the success response indicates and how each error code should be handled. For a two-parameter mutation tool with open-world behavior, nothing an agent needs to invoke it correctly is missing.
Complex tools with many parameters or behaviors need more documentation. Simple tools need less. This dimension scales expectations accordingly.
Does the description clarify parameter syntax, constraints, interactions, or defaults beyond what the schema provides?
Schema coverage is 100% so the baseline is 3, but the description adds real disambiguation the schema lacks: it stresses the message id (#id) from get_inbox_conversation/get_next_unanswered is required, not the conversation id, and confirms the default hide=true toggle semantics. It stops short of new syntax detail but clearly earns above baseline.
Input schemas describe structure but not intent. Descriptions should explain non-obvious parameter relationships and valid value ranges.
Does the description clearly state what the tool does and how it differs from similar tools?
States a specific verb pair (hide/unhide) and resource (a comment someone left on the workspace's posts), names the platforms, and clarifies the actor scope ('as the post owner'). An agent can distinguish it from delete_inbox_comment, mark_inbox_read and reply_to_inbox immediately.
Agents choose between tools based on descriptions. A clear purpose with a specific verb and resource helps agents select the right tool.
Does the description explain when to use this tool, when not to, or what alternatives exist?
Explicitly states the identifier to pass (message id, not conversation id) and names get_inbox_conversation and get_next_unanswered as the sources. It also gives when-not-to-retry conditions and routes to mark_inbox_read for the 422 case, so alternatives and exclusions are covered.
Agents often have multiple tools that could apply. Explicit usage guidance like "use X instead of Y when Z" prevents misuse.
list_accountsARead-onlyInspect
List all connected social media accounts for the active workspace. If the user has multiple workspaces, call list_workspaces first so they can pick which one to work with.
| Name | Required | Description | Default |
|---|---|---|---|
No parameters | |||
TDQS
Does the description disclose side effects, auth requirements, rate limits, or destructive behavior?
Annotations already declare readOnlyHint=true, destructiveHint=false and openWorldHint=false, so the safety profile is covered. The description adds useful behavioral context beyond that: results are scoped to the active workspace and workspace selection may need to happen first. It omits any note on result volume or pagination.
Agents need to know what a tool does to the world before calling it. Descriptions should go beyond structured annotations to explain consequences.
Is the description appropriately sized, front-loaded, and free of redundancy?
Two sentences, no filler. The core action and its scope are front-loaded, and the workspace prerequisite follows immediately after.
Shorter descriptions cost fewer tokens and are easier for agents to parse. Every sentence should earn its place.
Given the tool's complexity, does the description cover enough for an agent to succeed on first attempt?
For a parameterless read-only list tool with annotations carrying the safety profile and no output schema, the description covers action, scope and the one workflow dependency an agent needs. Nothing required to invoke it correctly is missing.
Complex tools with many parameters or behaviors need more documentation. Simple tools need less. This dimension scales expectations accordingly.
Does the description clarify parameter syntax, constraints, interactions, or defaults beyond what the schema provides?
The tool takes zero parameters, so per the rubric the baseline is 4. The description correctly implies no filtering or selection arguments are needed, and there is nothing for it to compensate for.
Input schemas describe structure but not intent. Descriptions should explain non-obvious parameter relationships and valid value ranges.
Does the description clearly state what the tool does and how it differs from similar tools?
States a specific verb (list) and resource (connected social media accounts) and constrains scope to the active workspace. That scope constraint is what separates it from the singular get_account sibling without needing to name it.
Agents choose between tools based on descriptions. A clear purpose with a specific verb and resource helps agents select the right tool.
Does the description explain when to use this tool, when not to, or what alternatives exist?
Gives an explicit prerequisite and routes to list_workspaces when the user has multiple workspaces, which is real when-to-use guidance. It does not, however, state when to prefer this over get_account or what to do if no workspace is active.
Agents often have multiple tools that could apply. Explicit usage guidance like "use X instead of Y when Z" prevents misuse.
list_approval_workflowsARead-onlyInspect
List the approval workflows this workspace can use (company-wide ones plus workspace-bound ones), with their steps and named approvers. Workflows are created in the OmniSocials dashboard (Approvals); this tool only lists them. Pass a workflow's id as approval_workflow_id on create_post to hold a scheduled post for review: it is created as in_approval, the approvers are notified, and it publishes at schedule_at once the last step approves. Call this first when the user wants agent-created posts to be reviewed/approved before publishing; if the list is empty, tell the user to create a workflow under Approvals in the dashboard.
| Name | Required | Description | Default |
|---|---|---|---|
No parameters | |||
TDQS
Does the description disclose side effects, auth requirements, rate limits, or destructive behavior?
Annotations already declare readOnlyHint=true, destructiveHint=false and openWorldHint=false, so safety is covered. The description adds real behavioral context beyond them: that workflows are created only in the dashboard and this tool merely lists them, plus the side effects (created as in_approval, approvers notified, publishes at schedule_at after final approval) of using a returned id.
Agents need to know what a tool does to the world before calling it. Descriptions should go beyond structured annotations to explain consequences.
Is the description appropriately sized, front-loaded, and free of redundancy?
Three sentences, front-loaded with what is listed, then the create-vs-list boundary, then the operational guidance and empty-state instruction. No filler; every sentence changes agent behavior.
Shorter descriptions cost fewer tokens and are easier for agents to parse. Every sentence should earn its place.
Given the tool's complexity, does the description cover enough for an agent to succeed on first attempt?
Despite no output schema, the description specifies the returned content (steps, named approvers) and the empty-list handling. For a zero-parameter read tool with annotations already covering the safety profile, nothing an agent needs is missing.
Complex tools with many parameters or behaviors need more documentation. Simple tools need less. This dimension scales expectations accordingly.
Does the description clarify parameter syntax, constraints, interactions, or defaults beyond what the schema provides?
The tool takes zero parameters, so the baseline is 4. The only identifier mentioned (approval_workflow_id) belongs to create_post, not this tool, and the description correctly frames it as a value this tool produces to be consumed elsewhere.
Input schemas describe structure but not intent. Descriptions should explain non-obvious parameter relationships and valid value ranges.
Does the description clearly state what the tool does and how it differs from similar tools?
States a specific verb and resource with explicit scope: company-wide plus workspace-bound workflows, including that steps and named approvers are returned. No sibling tool overlaps this resource, so differentiation is inherent.
Agents choose between tools based on descriptions. A clear purpose with a specific verb and resource helps agents select the right tool.
Does the description explain when to use this tool, when not to, or what alternatives exist?
Tells the agent exactly when to call it ('Call this first when the user wants agent-created posts to be reviewed/approved before publishing') and what to do on the empty case ('tell the user to create a workflow under Approvals in the dashboard'). It also names the downstream alternative path via create_post's approval_workflow_id.
Agents often have multiple tools that could apply. Explicit usage guidance like "use X instead of Y when Z" prevents misuse.
list_automationsARead-onlyInspect
List the comment-to-DM automations of this workspace, on Instagram, on the Facebook Page and on X. An automation DMs a person once when they comment a keyword on a post (or send it in a DM, or in an Instagram story reply), with an optional public reply under the comment; on X it answers DMs only. Use it to answer 'which automations run', before creating one on a post that may have one already, or to find the id for update_automation / get_automation_activity.
| Name | Required | Description | Default |
|---|---|---|---|
| status | No | Only automations with this status. | |
| post_id | No | Only the automations bound to this OmniSocials post (one per platform at most). | |
| platform | No | Only the automations of this platform. |
TDQS
Does the description disclose side effects, auth requirements, rate limits, or destructive behavior?
Annotations already declare readOnlyHint=true, destructiveHint=false, openWorldHint=false, so safety is covered. The description goes beyond them by disclosing domain behavior an agent needs: an automation fires once per matching comment, an optional public reply may accompany the DM, and on X it answers DMs only. Pagination/return shape is not covered, keeping it below a 5.
Agents need to know what a tool does to the world before calling it. Descriptions should go beyond structured annotations to explain consequences.
Is the description appropriately sized, front-loaded, and free of redundancy?
Purpose is front-loaded in the first clause, and the second and third sentences each carry distinct load (domain model, then usage triggers). Slightly dense in the middle, but no sentence is expendable.
Shorter descriptions cost fewer tokens and are easier for agents to parse. Every sentence should earn its place.
Given the tool's complexity, does the description cover enough for an agent to succeed on first attempt?
Read-only tool with no output schema and fully documented optional filters; the description supplies the domain context the schema cannot (what an automation does, cross-platform differences) plus id-reuse guidance. Only the shape of the returned list is unspecified, which is a minor gap given the read-only annotations.
Complex tools with many parameters or behaviors need more documentation. Simple tools need less. This dimension scales expectations accordingly.
Does the description clarify parameter syntax, constraints, interactions, or defaults beyond what the schema provides?
Schema description coverage is 100% and two of three parameters carry enums, so the schema already documents status, post_id (including the one-per-platform hint), and platform. The description adds no filter syntax or combination guidance beyond that, so baseline 3 applies.
Input schemas describe structure but not intent. Descriptions should explain non-obvious parameter relationships and valid value ranges.
Does the description clearly state what the tool does and how it differs from similar tools?
Specific verb+resource ("List the comment-to-DM automations of this workspace") with platform scope enumerated (Instagram, Facebook Page, X). It also defines what an automation is, which lets an agent distinguish this from get_automation, create_automation, and get_automation_activity without opening a schema.
Agents choose between tools based on descriptions. A clear purpose with a specific verb and resource helps agents select the right tool.
Does the description explain when to use this tool, when not to, or what alternatives exist?
Gives three concrete when-to-use triggers: answering "which automations run", pre-checking before creating one on a post that may already have one, and resolving an id for update_automation / get_automation_activity. It names the downstream siblings but doesn't explicitly state when to prefer get_automation (single-record lookup) instead.
Agents often have multiple tools that could apply. Explicit usage guidance like "use X instead of Y when Z" prevents misuse.
list_foldersARead-onlyInspect
List the media-library folders in this workspace (Finder-style organization). Returns each folder's id, name, parent, and item count. Use a folder id with list_media (folder_id) or update_media (folder_id), or a folder name with upload_media (folder).
| Name | Required | Description | Default |
|---|---|---|---|
No parameters | |||
TDQS
Does the description disclose side effects, auth requirements, rate limits, or destructive behavior?
Annotations already declare readOnlyHint=true, destructiveHint=false, and openWorldHint=false, so the safety profile is covered. The description adds real value by enumerating the returned fields (id, name, parent, item count), which matters because there is no output schema. It does not mention ordering, pagination, or empty-workspace behavior.
Agents need to know what a tool does to the world before calling it. Descriptions should go beyond structured annotations to explain consequences.
Is the description appropriately sized, front-loaded, and free of redundancy?
Two sentences, no filler, and the core purpose is front-loaded before the return-value and downstream-usage details. Every clause carries information the agent needs.
Shorter descriptions cost fewer tokens and are easier for agents to parse. Every sentence should earn its place.
Given the tool's complexity, does the description cover enough for an agent to succeed on first attempt?
For a zero-parameter read-only listing tool with annotations covering safety, the description supplies the one thing not in structured data — the shape of the result — via the enumerated return fields. Nothing essential to calling it correctly is missing.
Complex tools with many parameters or behaviors need more documentation. Simple tools need less. This dimension scales expectations accordingly.
Does the description clarify parameter syntax, constraints, interactions, or defaults beyond what the schema provides?
The tool takes zero parameters, so the baseline is 4; there is nothing for the description to disambiguate. The mention of folder_id/folder applies to sibling tools rather than this one's inputs, so no additional credit is warranted.
Input schemas describe structure but not intent. Descriptions should explain non-obvious parameter relationships and valid value ranges.
Does the description clearly state what the tool does and how it differs from similar tools?
States a specific verb and resource ('List the media-library folders in this workspace') and adds scope qualifier ('Finder-style organization'), which distinguishes it from create_folder and list_media. An agent immediately knows what it returns and that it enumerates rather than filters.
Agents choose between tools based on descriptions. A clear purpose with a specific verb and resource helps agents select the right tool.
Does the description explain when to use this tool, when not to, or what alternatives exist?
Gives clear downstream context: folder ids feed list_media and update_media, folder names feed upload_media. That tells the agent why to call it, but it never states when not to call it or names an alternative folder-listing route (there effectively is none among the siblings), so it falls short of explicit when/when-not guidance.
Agents often have multiple tools that could apply. Explicit usage guidance like "use X instead of Y when Z" prevents misuse.
list_hashtag_setsARead-onlyInspect
List the saved hashtag sets in this workspace. Apply one to a new post by passing its name via create_post (hashtag_set) — the tags are appended to the captions or, with hashtag_placement='first_comment', posted as the auto first comment.
| Name | Required | Description | Default |
|---|---|---|---|
No parameters | |||
TDQS
Does the description disclose side effects, auth requirements, rate limits, or destructive behavior?
With readOnlyHint=true and destructiveHint=false already declaring the safety profile, the description adds useful behavioral context about what applying a set does (append to captions, or post as auto first comment with hashtag_placement='first_comment'). This goes beyond what annotations cover.
Agents need to know what a tool does to the world before calling it. Descriptions should go beyond structured annotations to explain consequences.
Is the description appropriately sized, front-loaded, and free of redundancy?
Two tightly written sentences; the core purpose leads, and the follow-on workflow note earns its place without filler.
Shorter descriptions cost fewer tokens and are easier for agents to parse. Every sentence should earn its place.
Given the tool's complexity, does the description cover enough for an agent to succeed on first attempt?
No output schema exists, yet the description implicitly conveys the return (saved hashtag sets usable by name) and the workflow around them. Adequate for a zero-param list tool, though it could note whether sets are ordered or include counts.
Complex tools with many parameters or behaviors need more documentation. Simple tools need less. This dimension scales expectations accordingly.
Does the description clarify parameter syntax, constraints, interactions, or defaults beyond what the schema provides?
Zero parameters, so baseline is 4. The description still adds semantic value by explaining the hashtag_set and hashtag_placement parameters of the related create_post tool, clarifying how the names returned here are meant to be consumed.
Input schemas describe structure but not intent. Descriptions should explain non-obvious parameter relationships and valid value ranges.
Does the description clearly state what the tool does and how it differs from similar tools?
States a specific verb (List) and resource (saved hashtag sets) scoped to the workspace, which cleanly distinguishes it from create_hashtag_set, update_hashtag_set, and delete_hashtag_set.
Agents choose between tools based on descriptions. A clear purpose with a specific verb and resource helps agents select the right tool.
Does the description explain when to use this tool, when not to, or what alternatives exist?
Explains the downstream use case: apply a set to a new post by passing its name via create_post. It gives clear consumption context but does not state explicit when-not-to-use conditions or point to a direct alternative listing tool.
Agents often have multiple tools that could apply. Explicit usage guidance like "use X instead of Y when Z" prevents misuse.
list_inbox_conversationsARead-onlyInspect
List social inbox conversations (Instagram/Facebook DMs, comments, mentions, LinkedIn company-page comments/mentions, TikTok video comments, YouTube video comments, X DMs where the workspace has opted into X DMs, and Threads replies on the workspace's posts plus mentions), newest activity first. Cursor-paginated: pass the returned cursor to get the next page. To work through what needs answering one item at a time, use get_next_unanswered instead.
| Name | Required | Description | Default |
|---|---|---|---|
| type | No | Filter to one conversation type | |
| limit | No | Max conversations per page (1-100, default 25) | |
| cursor | No | Pagination cursor from a previous response | |
| unread | No | Only conversations with unread incoming messages | |
| platform | No | Filter to one platform | |
| unanswered | No | Only conversations that still need an answer: the customer's latest DM has no reply after it (Instagram/Facebook DMs past the 24-hour reply window included; they cannot be answered through the API but the customer is still waiting), or a comment/mention nobody replied to and that is not hidden. Replies typed in the native apps count as answers. |
TDQS
Does the description disclose side effects, auth requirements, rate limits, or destructive behavior?
Annotations already declare readOnlyHint=true, destructiveHint=false and openWorldHint=false, so safety is covered; the description adds real behavioral context on ordering ('newest activity first') and pagination mechanics ('pass the returned cursor to get the next page'). It does not describe the shape or size of an individual conversation record, but the added pagination/ordering detail goes beyond the annotations.
Agents need to know what a tool does to the world before calling it. Descriptions should go beyond structured annotations to explain consequences.
Is the description appropriately sized, front-loaded, and free of redundancy?
The core operation and ordering are front-loaded, followed by pagination mechanics and the sibling routing. The long parenthetical platform inventory is dense but each item is load-bearing for scope. Slightly heavy in one sentence, but no filler.
Shorter descriptions cost fewer tokens and are easier for agents to parse. Every sentence should earn its place.
Given the tool's complexity, does the description cover enough for an agent to succeed on first attempt?
With no output schema, the description still tells the agent the ordering and the cursor-pagination contract, and the six optional filters are fully documented in the schema. Combined with annotations covering the read-only profile, nothing essential for correct invocation is missing.
Complex tools with many parameters or behaviors need more documentation. Simple tools need less. This dimension scales expectations accordingly.
Does the description clarify parameter syntax, constraints, interactions, or defaults beyond what the schema provides?
Schema description coverage is 100%, with the 'unanswered' filter even spelled out in detail at the schema level, so the description does not need to re-explain parameters. It adds no syntax or format nuance beyond what the schema already provides, making the baseline 3 appropriate.
Input schemas describe structure but not intent. Descriptions should explain non-obvious parameter relationships and valid value ranges.
Does the description clearly state what the tool does and how it differs from similar tools?
States a specific verb+resource ('List social inbox conversations') and enumerates exactly which sources are covered (IG/FB DMs, comments, mentions, LinkedIn, TikTok, YouTube, X, Threads). It also draws the boundary against the nearest sibling by contrasting bulk listing with one-at-a-time triage. An agent can identify the tool without opening the schema.
Agents choose between tools based on descriptions. A clear purpose with a specific verb and resource helps agents select the right tool.
Does the description explain when to use this tool, when not to, or what alternatives exist?
It explicitly routes the agent to get_next_unanswered when the goal is working through items one at a time, which is a clear when-to-use-alternative statement. It stops short of covering other adjacent siblings (get_inbox_conversation, mark_inbox_read) or when to prefer the 'unanswered' filter over the sibling triage tool, so it is clear but not exhaustive.
Agents often have multiple tools that could apply. Explicit usage guidance like "use X instead of Y when Z" prevents misuse.
list_mediaARead-onlyInspect
List media files in the workspace. Shows each file's name, folder, type (image, video, or document: a PDF kept as one item whose ID in media_ids expands into every page), size, a preview link, and its media ID for use when creating posts. To reuse an existing graphic, SEARCH for it by name here FIRST instead of re-uploading — re-uploading the same image creates duplicates. Organize assets into folders with create_folder / list_folders.
| Name | Required | Description | Default |
|---|---|---|---|
| limit | No | Max results | |
| offset | No | Offset for pagination | |
| search | No | Find a file by name or filename, e.g. "play5get50". Use this before uploading to check if the graphic already exists. | |
| folder_id | No | Only return media in this folder id (from list_folders). Use "root" for unfiled items. |
TDQS
Does the description disclose side effects, auth requirements, rate limits, or destructive behavior?
Annotations already declare this as a safe read operation (readOnlyHint=true, destructiveHint=false). The description adds useful non-annotation context: the exact fields returned, the PDF-as-one-item expansion behavior, and the duplicate-creation warning. It does not cover pagination defaults, but the added behavioral detail is substantial.
Agents need to know what a tool does to the world before calling it. Descriptions should go beyond structured annotations to explain consequences.
Is the description appropriately sized, front-loaded, and free of redundancy?
Three sentences, front-loaded with purpose and output summary. The parenthetical about PDF expansion is dense but valuable, and all sentences earn their place. Minor length but no wasted prose.
Shorter descriptions cost fewer tokens and are easier for agents to parse. Every sentence should earn its place.
Given the tool's complexity, does the description cover enough for an agent to succeed on first attempt?
For a list tool with four optional params and no output schema, the description compensates by naming the returned fields and giving usage guidance. Annotations cover the safety profile. It is complete enough for correct invocation, with only pagination behavior left implicit.
Complex tools with many parameters or behaviors need more documentation. Simple tools need less. This dimension scales expectations accordingly.
Does the description clarify parameter syntax, constraints, interactions, or defaults beyond what the schema provides?
Schema description coverage is 100%, so the schema already fully documents all four optional parameters. The description reinforces the search-before-upload guidance but adds no new syntax or meaning beyond what the schema provides.
Input schemas describe structure but not intent. Descriptions should explain non-obvious parameter relationships and valid value ranges.
Does the description clearly state what the tool does and how it differs from similar tools?
States a specific verb and resource: 'List media files in the workspace,' and enumerates the returned fields. It does not explicitly contrast with sibling list tools like list_folders or list_posts, but the 'media files' resource is distinct enough to be clear.
Agents choose between tools based on descriptions. A clear purpose with a specific verb and resource helps agents select the right tool.
Does the description explain when to use this tool, when not to, or what alternatives exist?
Gives a concrete when-to-use: search here before uploading to avoid duplicates. Also points to create_folder / list_folders for organizing assets. It lacks explicit exclusions or comparison to other list tools, but the context is clear.
Agents often have multiple tools that could apply. Explicit usage guidance like "use X instead of Y when Z" prevents misuse.
list_pinterest_productsARead-onlyInspect
List the product Pins of the connected Pinterest account, to tag products on a Pin (Pinterest shows the tagged items on the image). Use this whenever the user wants to tag products on a Pinterest post.
Flow: call it → show the products to the user → pass the chosen pin_id values (max 24) as pinterest.product_tags on create_post / create_and_publish_post / update_post. If the user gives a Pin link or Pin ID of a product, pass it as check_pin to check it first, or put it straight in pinterest.product_tags.
Notes:
Only the account's own product Pins can be tagged: a public product Pin with a link on a website the account claimed on Pinterest. Products of other merchants cannot be tagged through the API.
source"catalog" reads the Pinterest catalog. It needs catalog access, which the user gives one time in OmniSocials: create a post, open the Pinterest options, select Add products, then Connect catalog.source"pins" reads the account's own Pins and returns the product Pins; one call scans up to 250 Pins, so an empty result with a bookmark means: call again with that bookmark. Withoutsource, the catalog is used when the connection has catalog access, else the Pins.A product that Pinterest refuses never fails the post; get_post shows which products were tagged.
| Name | Required | Description | Default |
|---|---|---|---|
| source | No | Where to read product Pins from. Default: catalog when the Pinterest connection has catalog access, else pins. | |
| bookmark | No | Cursor from an earlier result, to get the next page. | |
| check_pin | No | A Pin ID or Pin link (https://www.pinterest.com/pin/<id>/) to check instead of listing: answers whether that Pin can be tagged as a product. | |
| product_group_id | No | Catalog source only. A product group ID from an earlier result. Default: the group named All Products. |
TDQS
Does the description disclose side effects, auth requirements, rate limits, or destructive behavior?
Annotations already declare readOnlyHint=true, openWorldHint=true, destructiveHint=false, so safety is covered. The description adds substantial non-obvious behavior: only the account's own product Pins can be tagged, catalog access requires a one-time user setup in OmniSocials, one call scans up to 250 Pins so an empty result with a bookmark means paginate, and a Pinterest-rejected product never fails the post.
Agents need to know what a tool does to the world before calling it. Descriptions should go beyond structured annotations to explain consequences.
Is the description appropriately sized, front-loaded, and free of redundancy?
Front-loads the purpose and the action flow, then separates caveats into a Notes block, which is well organized. It is on the long side and the notes are dense, but nearly every sentence carries operational information an agent needs.
Shorter descriptions cost fewer tokens and are easier for agents to parse. Every sentence should earn its place.
Given the tool's complexity, does the description cover enough for an agent to succeed on first attempt?
For a four-parameter, paginated, dual-source listing tool with no output schema, the description covers the resolution logic, pagination signal, and refusal behavior well. It could say slightly more about the shape of returned product entries, but an agent has enough to call it correctly.
Complex tools with many parameters or behaviors need more documentation. Simple tools need less. This dimension scales expectations accordingly.
Does the description clarify parameter syntax, constraints, interactions, or defaults beyond what the schema provides?
Schema coverage is 100%, so the baseline is 3, but the description genuinely adds meaning: it explains the default resolution order for `source` (catalog when catalog access exists, else pins), the pagination implication of `bookmark`, and that `check_pin` accepts a Pin link or ID and answers a yes/no taggability question.
Input schemas describe structure but not intent. Descriptions should explain non-obvious parameter relationships and valid value ranges.
Does the description clearly state what the tool does and how it differs from similar tools?
States a specific verb and resource ('List the product Pins of the connected Pinterest account') plus the reason it exists (tagging products on a Pin). This is clearly distinguishable from siblings like list_posts or list_media without opening any schema.
Agents choose between tools based on descriptions. A clear purpose with a specific verb and resource helps agents select the right tool.
Does the description explain when to use this tool, when not to, or what alternatives exist?
Explicitly says to use it 'whenever the user wants to tag products on a Pinterest post,' then gives the exact flow (list → show → pass pin_id values as pinterest.product_tags on create_post/create_and_publish_post/update_post). It also names the check_pin alternative and when to use it, so nothing is left to inference.
Agents often have multiple tools that could apply. Explicit usage guidance like "use X instead of Y when Z" prevents misuse.
list_postsARead-onlyInspect
List posts in the workspace. Filter by status to see drafts, scheduled, published, or failed posts. Returns a formatted table with content preview, channels, dates, and post IDs. The content cell shows the default caption; if a post has per-platform overrides (e.g. a custom X version) the preview is suffixed with (per-platform) — call get_post to see every variant.
| Name | Required | Description | Default |
|---|---|---|---|
| limit | No | Max results (default: 20) | |
| offset | No | Offset for pagination | |
| status | No | Filter by status: draft, scheduled, published, failed |
TDQS
Does the description disclose side effects, auth requirements, rate limits, or destructive behavior?
Annotations already declare readOnlyHint=true, destructiveHint=false, and openWorldHint=false, so the safety profile is covered. The description adds genuinely useful behavior beyond that: the exact shape of the returned table (content preview, channels, dates, post IDs), plus the non-obvious *(per-platform)* marker convention that governs how the preview should be read.
Agents need to know what a tool does to the world before calling it. Descriptions should go beyond structured annotations to explain consequences.
Is the description appropriately sized, front-loaded, and free of redundancy?
Four sentences, each carrying distinct payload: scope, filtering, return shape, and the per-platform reading rule with a routing instruction. Nothing is repeated and the per-platform caveat — the hardest thing to get wrong — is given last as an explicit action.
Shorter descriptions cost fewer tokens and are easier for agents to parse. Every sentence should earn its place.
Given the tool's complexity, does the description cover enough for an agent to succeed on first attempt?
There is no output schema, so the description correctly compensates by describing the returned table columns and the preview convention. With annotations covering safety and the schema covering all three parameters, an agent has everything needed to call this correctly.
Complex tools with many parameters or behaviors need more documentation. Simple tools need less. This dimension scales expectations accordingly.
Does the description clarify parameter syntax, constraints, interactions, or defaults beyond what the schema provides?
Schema description coverage is 100% — limit, offset, and the four status values are all documented in the schema itself. The description restates the status filter but adds no syntax, default, or format detail beyond it, so the baseline of 3 applies.
Input schemas describe structure but not intent. Descriptions should explain non-obvious parameter relationships and valid value ranges.
Does the description clearly state what the tool does and how it differs from similar tools?
States a specific verb and resource ('List posts in the workspace') and immediately distinguishes itself from the sibling get_post by naming it as the tool to call for full per-platform variants. An agent can tell this apart from list_media, list_folders, and other list_* siblings without opening a schema.
Agents choose between tools based on descriptions. A clear purpose with a specific verb and resource helps agents select the right tool.
Does the description explain when to use this tool, when not to, or what alternatives exist?
Gives clear usage context: filter by status for drafts/scheduled/published/failed, and route to get_post when the *(per-platform)* suffix appears. It names the alternative and the condition that selects it, though it does not explicitly state when not to use this tool (e.g. for a single known post ID).
Agents often have multiple tools that could apply. Explicit usage guidance like "use X instead of Y when Z" prevents misuse.
list_webhooksARead-onlyInspect
List all configured webhooks with their status, events, and last trigger time.
| Name | Required | Description | Default |
|---|---|---|---|
No parameters | |||
TDQS
Does the description disclose side effects, auth requirements, rate limits, or destructive behavior?
Annotations already declare readOnlyHint=true, destructiveHint=false and openWorldHint=false, so the safety profile is fully covered without the description. The description usefully adds what a webhook record contains, but says nothing about pagination, ordering, or whether disabled/inactive hooks are included — gaps that matter for a listing tool.
Agents need to know what a tool does to the world before calling it. Descriptions should go beyond structured annotations to explain consequences.
Is the description appropriately sized, front-loaded, and free of redundancy?
A single front-loaded sentence with no filler. The verb, resource, scope, and returned payload are all packed in without repetition of the title.
Shorter descriptions cost fewer tokens and are easier for agents to parse. Every sentence should earn its place.
Given the tool's complexity, does the description cover enough for an agent to succeed on first attempt?
For a no-parameter, read-only list tool with annotations covering safety and no output schema, the description is nearly complete — it even describes the return fields in lieu of an output schema. The only missing piece is pagination/ordering behavior on large webhook lists.
Complex tools with many parameters or behaviors need more documentation. Simple tools need less. This dimension scales expectations accordingly.
Does the description clarify parameter syntax, constraints, interactions, or defaults beyond what the schema provides?
The tool takes zero parameters, so there is nothing for the description to disambiguate and the baseline of 4 applies. The mention of returned fields is a small bonus rather than parameter guidance.
Input schemas describe structure but not intent. Descriptions should explain non-obvious parameter relationships and valid value ranges.
Does the description clearly state what the tool does and how it differs from similar tools?
States a specific verb (List) and resource (webhooks) and adds scope ('all configured') plus the fields returned (status, events, last trigger time). It implicitly separates itself from the singular get_webhook sibling, but never names it explicitly, so the differentiation is left to inference.
Agents choose between tools based on descriptions. A clear purpose with a specific verb and resource helps agents select the right tool.
Does the description explain when to use this tool, when not to, or what alternatives exist?
Usage is only implied: 'List all configured webhooks' suggests enumeration, but there is no explicit when-to-use, when-not-to-use, or pointer to the alternatives (get_webhook for a single hook, create_webhook/delete_webhook/update_webhook for other lifecycle operations). An agent can guess the context but is not guided.
Agents often have multiple tools that could apply. Explicit usage guidance like "use X instead of Y when Z" prevents misuse.
list_workspacesARead-onlyInspect
List all workspaces the user has access to. Workspace selection rule: if only one workspace is available, just use it (no need to ask). If the user has named a workspace in their request (e.g. 'post to my Acme workspace'), proceed with that workspace and remember it for the rest of the conversation. If multiple workspaces exist and the user has NOT named one, call this tool, present the list, and ASK the user which one to use before posting, switching, or fetching analytics. After a successful action, mention the workspace name in your reply for clarity.
| Name | Required | Description | Default |
|---|---|---|---|
No parameters | |||
TDQS
Does the description disclose side effects, auth requirements, rate limits, or destructive behavior?
Annotations already declare readOnlyHint=true, destructiveHint=false, and openWorldHint=false, so safety is covered. The description adds workflow-level behavior beyond that: it tells the agent to surface the list to the user and to mention the workspace name after a successful action. It stops short of describing what a workspace record contains, but the added behavioral context is real.
Agents need to know what a tool does to the world before calling it. Descriptions should go beyond structured annotations to explain consequences.
Is the description appropriately sized, front-loaded, and free of redundancy?
Purpose is front-loaded in the first sentence, followed by an ordered rule set that reads as a decision tree rather than filler. It runs longer than a one-line lister normally would, but every sentence maps to a distinct usage case, so the length is largely justified.
Shorter descriptions cost fewer tokens and are easier for agents to parse. Every sentence should earn its place.
Given the tool's complexity, does the description cover enough for an agent to succeed on first attempt?
With no output schema, the description should ideally hint at what the list returns (e.g. workspace identifiers usable with switch_workspace), and it does not. It is otherwise complete: purpose, usage routing, and post-call behavior are all covered for a zero-parameter read tool.
Complex tools with many parameters or behaviors need more documentation. Simple tools need less. This dimension scales expectations accordingly.
Does the description clarify parameter syntax, constraints, interactions, or defaults beyond what the schema provides?
The tool takes zero parameters, so the baseline is 4; there is no parameter syntax for the description to compensate for, and schema coverage is 100% on an empty object. Nothing further is required here.
Input schemas describe structure but not intent. Descriptions should explain non-obvious parameter relationships and valid value ranges.
Does the description clearly state what the tool does and how it differs from similar tools?
States a specific verb and resource ('List all workspaces') and scopes it precisely ('the user has access to'), which separates it from siblings like list_accounts, list_folders, and list_hashtag_sets that also list resources. An agent can identify the tool's output domain without opening the schema.
Agents choose between tools based on descriptions. A clear purpose with a specific verb and resource helps agents select the right tool.
Does the description explain when to use this tool, when not to, or what alternatives exist?
Explicitly covers all three decision branches: single workspace (use it, don't ask), user-named workspace (proceed and remember it), and multiple unnamed workspaces (call this tool, present the list, ask before posting/switching/fetching analytics). It also names the downstream actions that require confirmation, which is exactly the routing guidance an agent needs.
Agents often have multiple tools that could apply. Explicit usage guidance like "use X instead of Y when Z" prevents misuse.
mark_inbox_readBInspect
Mark all incoming messages in a conversation as read.
| Name | Required | Description | Default |
|---|---|---|---|
| conversation_id | Yes | The conversation ID to mark read |
TDQS
Does the description disclose side effects, auth requirements, rate limits, or destructive behavior?
Annotations already declare readOnlyHint=false and destructiveHint=false, so the mutation/safety profile is covered structurally. The description adds genuine value by stating the operation is bulk ('all incoming messages in a conversation') rather than per-message, but it does not say whether the change is reversible or what permissions are required.
Agents need to know what a tool does to the world before calling it. Descriptions should go beyond structured annotations to explain consequences.
Is the description appropriately sized, front-loaded, and free of redundancy?
A single front-loaded sentence with zero filler, though its brevity also reflects the missing usage and behavioral detail rather than tight editing of richer content.
Shorter descriptions cost fewer tokens and are easier for agents to parse. Every sentence should earn its place.
Given the tool's complexity, does the description cover enough for an agent to succeed on first attempt?
For a one-parameter mutation with full schema coverage and annotations carrying the safety profile, this is minimally adequate. The gaps are the absence of guidance about read-state reversibility and any when-to-use context among the crowded inbox siblings.
Complex tools with many parameters or behaviors need more documentation. Simple tools need less. This dimension scales expectations accordingly.
Does the description clarify parameter syntax, constraints, interactions, or defaults beyond what the schema provides?
Schema coverage is 100% for the single conversation_id parameter, so the baseline is 3. The description's phrase 'all incoming messages in a conversation' does clarify the blast radius of that ID (bulk vs single message), which is a modest addition over the schema's one-line description.
Input schemas describe structure but not intent. Descriptions should explain non-obvious parameter relationships and valid value ranges.
Does the description clearly state what the tool does and how it differs from similar tools?
States a specific verb (mark read), resource (incoming messages), and scope (all messages in a conversation), which distinguishes it from get_inbox_conversation and list_inbox_conversations. It does not explicitly name a sibling or an alternative, so it falls short of a 5.
Agents choose between tools based on descriptions. A clear purpose with a specific verb and resource helps agents select the right tool.
Does the description explain when to use this tool, when not to, or what alternatives exist?
The description offers no when-to-use context, no prerequisites, and no routing against the many inbox siblings (hide_inbox_comment, delete_inbox_comment, reply_to_inbox, get_inbox_conversation). Usage is only inferable from the verb itself.
Agents often have multiple tools that could apply. Explicit usage guidance like "use X instead of Y when Z" prevents misuse.
publish_postADestructiveInspect
Publish a draft or scheduled post immediately. Only draft and scheduled posts can be published — for a failed or partially failed (warning) post use retry_post instead, which re-publishes only the failed platforms.
| Name | Required | Description | Default |
|---|---|---|---|
| id | Yes | The post ID to publish |
TDQS
Does the description disclose side effects, auth requirements, rate limits, or destructive behavior?
Annotations already declare readOnlyHint=false, destructiveHint=true and openWorldHint=true, so the mutation and safety profile is covered structurally. The description adds genuinely new behavioral context: only posts in draft or scheduled state are eligible, which constrains invocation. It does not state whether publishing is reversible or what happens to the scheduled time, so it falls short of a 5.
Agents need to know what a tool does to the world before calling it. Descriptions should go beyond structured annotations to explain consequences.
Is the description appropriately sized, front-loaded, and free of redundancy?
Two sentences, no filler, with the eligibility rule front-loaded ahead of the alternative-tool routing. Every clause earns its place.
Shorter descriptions cost fewer tokens and are easier for agents to parse. Every sentence should earn its place.
Given the tool's complexity, does the description cover enough for an agent to succeed on first attempt?
For a one-parameter action tool with full schema coverage and annotations carrying the safety profile, the description covers purpose, eligibility and routing adequately. It omits any indication of what publishing returns or whether the action is queued versus immediate beyond the word 'immediately', a minor gap given no output schema exists.
Complex tools with many parameters or behaviors need more documentation. Simple tools need less. This dimension scales expectations accordingly.
Does the description clarify parameter syntax, constraints, interactions, or defaults beyond what the schema provides?
There is a single required 'id' parameter whose schema description ('The post ID to publish') already covers it at 100% coverage. The description adds no format, source, or retrieval guidance for the ID beyond the schema, so the baseline of 3 applies.
Input schemas describe structure but not intent. Descriptions should explain non-obvious parameter relationships and valid value ranges.
Does the description clearly state what the tool does and how it differs from similar tools?
States a specific verb (publish) plus the resource (post) and an explicit precondition (draft or scheduled, published immediately). It also names the sibling retry_post and the state condition that selects it, so an agent can distinguish it from neighboring post tools without opening any schema.
Agents choose between tools based on descriptions. A clear purpose with a specific verb and resource helps agents select the right tool.
Does the description explain when to use this tool, when not to, or what alternatives exist?
Gives both when-to-use (draft or scheduled posts) and when-not-to-use with a named alternative ('for a failed or partially failed (warning) post use retry_post instead'), including why that alternative exists. Nothing about tool selection is left to inference.
Agents often have multiple tools that could apply. Explicit usage guidance like "use X instead of Y when Z" prevents misuse.
reject_postAInspect
Reject a post's approval workflow. Only works on a post with approval_status 'pending' (post status in_approval) — check get_post first. IMPORTANT: only succeeds if the connected user is a listed approver for the workflow's CURRENT step (same requirement as approve_post). Unlike approval, a rejection stops the WHOLE workflow immediately, not just the current step — the post's status becomes rejected and it will not publish. Pass comment to explain why; it's shown to the requester and other approvers in the post's review thread.
| Name | Required | Description | Default |
|---|---|---|---|
| id | Yes | The post ID to reject (must have approval_status 'pending') | |
| comment | No | Optional reason for the rejection, shown to the requester and other approvers. |
TDQS
Does the description disclose side effects, auth requirements, rate limits, or destructive behavior?
Annotations cover safety flags (readOnly=false, destructive=false, openWorld=false), but the description adds substantial behavioral context beyond them: the post must be in_approval, only a current-step approver may succeed, and rejection terminates the entire workflow so the post becomes 'rejected' and never publishes. That is exactly the destructive-adjacent consequence an agent needs.
Agents need to know what a tool does to the world before calling it. Descriptions should go beyond structured annotations to explain consequences.
Is the description appropriately sized, front-loaded, and free of redundancy?
Four dense sentences, front-loaded with the core action and precondition before the divergence from approval. Slightly long, but each sentence carries distinct operational information rather than repeating the schema.
Shorter descriptions cost fewer tokens and are easier for agents to parse. Every sentence should earn its place.
Given the tool's complexity, does the description cover enough for an agent to succeed on first attempt?
With no output schema, the description still tells the agent the resulting state (status becomes 'rejected', no publish) and the permission model. Nothing needed to call the tool correctly is missing.
Complex tools with many parameters or behaviors need more documentation. Simple tools need less. This dimension scales expectations accordingly.
Does the description clarify parameter syntax, constraints, interactions, or defaults beyond what the schema provides?
Schema coverage is 100%, so the baseline is 3, but the description adds meaning beyond the schema by explaining that the comment is surfaced to the requester and other approvers in the review thread, clarifying its audience and intent.
Input schemas describe structure but not intent. Descriptions should explain non-obvious parameter relationships and valid value ranges.
Does the description clearly state what the tool does and how it differs from similar tools?
States a specific verb (reject) and resource (a post's approval workflow) and immediately scopes it. An agent can distinguish it from approve_post without opening the schema.
Agents choose between tools based on descriptions. A clear purpose with a specific verb and resource helps agents select the right tool.
Does the description explain when to use this tool, when not to, or what alternatives exist?
Explicit preconditions: only works on approval_status 'pending', instructs to check get_post first, and names the sibling approve_post with the shared approver requirement. The when/when-not conditions are fully spelled out.
Agents often have multiple tools that could apply. Explicit usage guidance like "use X instead of Y when Z" prevents misuse.
reply_to_inboxADestructiveInspect
Reply to an existing inbox conversation (DM, comment, or mention) on Instagram, Facebook, LinkedIn, TikTok, YouTube, X, or Threads. You can only reply to conversations that already exist. For a comment or mention, pass message_id (the #id of the comment being answered): comments on one post share a conversation and without it the reply goes under the newest comment on the post. Meta direct-message replies must be within the platform's 24-hour messaging window: a 422 outside_messaging_window means the window has closed, nothing was sent, and the user must answer that DM from the Instagram or Facebook app (mirrored into the inbox) or skip it with mark_inbox_read; do not retry. TikTok replies are comments only, text-only, and capped at 150 characters; they can take a few minutes to appear on TikTok while they pass spam review. YouTube replies are comments only. Threads replies are on the workspace's posts and mentions; a 401 reauth_required means the Threads connection must be reconnected to grant the reply permission. X replies are DM-only; an x_feature_not_enabled error means X direct messages are not enabled on this organisation's OmniSocials account at the moment: nothing was sent, tell the user and do not retry. attachment_url/attachment_type let you send media on a Facebook or Instagram DM (text is optional when an attachment is set); other platforms are text-only. Set include_next: true to get the next conversation that needs an answer back in the same call (same as get_next_unanswered), so the inbox can be worked through as: get_next_unanswered → draft → reply_to_inbox(include_next) → draft → repeat. A 409 duplicate_reply means this exact reply already went out to this conversation in the last 10 minutes (an earlier call that looked slow or failed did succeed) or is being sent right now: nothing was sent again, do NOT retry it — continue with get_next_unanswered. A 422 reply_not_allowed means the platform refuses replies to this item for good (Facebook #1705: the comment sits on a share or boosted copy of the post, or the commenter restricts replies; YouTube: the thread's canReply is false because comments are off on the video or the comment was removed or held for review): the item is dropped from get_next_unanswered automatically, tell the user, and do NOT retry.
| Name | Required | Description | Default |
|---|---|---|---|
| text | No | The reply text (max 2000 characters; TikTok comments max 150). Optional when attachment_url is set. | |
| message_id | No | For comment/mention threads: the inbox id of the comment you are answering (the 'Message to answer' #id from get_next_unanswered, or a #id from get_inbox_conversation). Every comment on a post shares one conversation, so without it the reply is posted under the newest comment on the post, which can be a different person than the one you drafted for. Always pass it for comments. Ignored for DMs. | |
| include_next | No | After sending, also return the next conversation that needs an answer (full thread + post context), or 'nothing waiting' | |
| attachment_url | No | Media URL to send (Facebook and Instagram DMs only) | |
| attachment_type | No | image, video, audio, or file — required if attachment_url is set | |
| conversation_id | Yes | The conversation ID to reply to |
TDQS
Does the description disclose side effects, auth requirements, rate limits, or destructive behavior?
Annotations only flag destructiveHint/openWorldHint; the description goes far beyond them, disclosing the Meta 24-hour window and its 422 outcome, TikTok's 150-char text-only comment limit and spam-review delay, YouTube comment-only scope, X DM-only scope, the 10-minute 409 duplicate_reply semantics, and the permanent 422 reply_not_allowed causes (Facebook #1705, YouTube canReply=false) with the note that the item is auto-dropped from get_next_unanswered.
Agents need to know what a tool does to the world before calling it. Descriptions should go beyond structured annotations to explain consequences.
Is the description appropriately sized, front-loaded, and free of redundancy?
Purpose and the core reply constraint are front-loaded, and every clause carries actionable error-handling information rather than filler. It is nonetheless a very long single paragraph; a small amount of the platform-by-platform error prose could be tightened without loss.
Shorter descriptions cost fewer tokens and are easier for agents to parse. Every sentence should earn its place.
Given the tool's complexity, does the description cover enough for an agent to succeed on first attempt?
For a destructive, open-world mutation tool with no output schema, the description covers prerequisites (existing conversation, 24h window, Threads reauth), platform limits, per-error recovery paths, and what include_next returns ('nothing waiting' or the next thread), leaving nothing an agent needs before calling it.
Complex tools with many parameters or behaviors need more documentation. Simple tools need less. This dimension scales expectations accordingly.
Does the description clarify parameter syntax, constraints, interactions, or defaults beyond what the schema provides?
Schema coverage is 100% so the baseline is 3, but the description adds genuine meaning: it explains why message_id matters for comment threads (all comments on a post share one conversation, so omitting it posts under the newest comment) and that attachment_url/attachment_type apply only to Facebook/Instagram DMs with text optional.
Input schemas describe structure but not intent. Descriptions should explain non-obvious parameter relationships and valid value ranges.
Does the description clearly state what the tool does and how it differs from similar tools?
States a specific verb (reply) and resource (inbox conversation), enumerates the supported platforms, and draws the boundary 'You can only reply to conversations that already exist.' It clearly distinguishes itself from siblings like get_inbox_conversation, mark_inbox_read, and delete_inbox_comment.
Agents choose between tools based on descriptions. A clear purpose with a specific verb and resource helps agents select the right tool.
Does the description explain when to use this tool, when not to, or what alternatives exist?
Explicit when-to-use and when-not-to-use: names the alternative flow (get_next_unanswered → draft → reply_to_inbox(include_next) → draft), tells the agent to pass message_id for comments but not DMs, and gives concrete do-not-retry instructions for 422/409/401/x_feature_not_enabled cases with the correct fallback (mark_inbox_read, reconnect, tell the user).
Agents often have multiple tools that could apply. Explicit usage guidance like "use X instead of Y when Z" prevents misuse.
retry_postADestructiveInspect
Retry the failed platforms of a failed or partially failed post — on the same post, no duplicate created. Use when a post has status failed (every platform failed) or warning (some failed, some published): only the FAILED platforms are re-published; platforms that already succeeded are never posted again. Runs asynchronously (usually within a few minutes) — poll get_post afterwards: on success the status becomes published and published_urls gains the platform's live URL. Max 3 retries per platform; after that, recreate the post. Note publish_post refuses failed posts; this is the tool for them.
| Name | Required | Description | Default |
|---|---|---|---|
| id | Yes | The failed or partially failed post ID to retry |
TDQS
Does the description disclose side effects, auth requirements, rate limits, or destructive behavior?
Beyond the annotations (readOnlyHint=false, destructiveHint=true, openWorldHint=true), the description discloses that only FAILED platforms are re-published, that succeeded platforms are never reposted, that execution is asynchronous, that the agent must poll get_post, and that there is a max of 3 retries per platform. That is the kind of operational detail annotations cannot express.
Agents need to know what a tool does to the world before calling it. Descriptions should go beyond structured annotations to explain consequences.
Is the description appropriately sized, front-loaded, and free of redundancy?
Every sentence earns its place: scope, eligibility, platform-level behavior, async semantics, polling target, retry cap, and sibling contrast. The key constraint (same post, no duplicate) is front-loaded rather than buried.
Shorter descriptions cost fewer tokens and are easier for agents to parse. Every sentence should earn its place.
Given the tool's complexity, does the description cover enough for an agent to succeed on first attempt?
No output schema exists, yet the description still tells the agent what to expect after the call (status becomes `published`, `published_urls` gains the live URL) and how to observe it via get_post. For a one-parameter async mutation tool, nothing an agent needs to invoke and follow up correctly is missing.
Complex tools with many parameters or behaviors need more documentation. Simple tools need less. This dimension scales expectations accordingly.
Does the description clarify parameter syntax, constraints, interactions, or defaults beyond what the schema provides?
Only one parameter, and schema coverage is 100%, so the schema already documents `id` fully; the description adds no format, ID-source, or validation detail. Baseline 3 is appropriate when the schema carries the parameter burden.
Input schemas describe structure but not intent. Descriptions should explain non-obvious parameter relationships and valid value ranges.
Does the description clearly state what the tool does and how it differs from similar tools?
States a specific verb and resource ('Retry the failed platforms of a failed or partially failed post') and immediately scopes it ('on the same post, no duplicate created'). It explicitly contrasts itself with the sibling publish_post ('publish_post refuses failed posts; this is the tool for them'), so an agent can route correctly without opening either schema.
Agents choose between tools based on descriptions. A clear purpose with a specific verb and resource helps agents select the right tool.
Does the description explain when to use this tool, when not to, or what alternatives exist?
Gives explicit triggering conditions (status `failed` or `warning`) plus what happens in each case, names the alternative (publish_post) and its limitation, and states the escalation path after retries are exhausted ('after that, recreate the post'). Both when-to-use and when-not-to-use are covered.
Agents often have multiple tools that could apply. Explicit usage guidance like "use X instead of Y when Z" prevents misuse.
rotate_webhook_secretADestructiveInspect
Rotate the signing secret for a webhook. The new secret will only be shown once.
| Name | Required | Description | Default |
|---|---|---|---|
| id | Yes | The webhook ID |
TDQS
Does the description disclose side effects, auth requirements, rate limits, or destructive behavior?
Annotations already declare destructiveHint=true and readOnlyHint=false, so the safety profile is partly covered. The description adds a genuinely important behavioral fact beyond that: the new secret is returned only once and is unrecoverable afterward, which changes how the agent must handle the response. It stops short of saying whether the old secret is invalidated immediately and whether existing webhook consumers break.
Agents need to know what a tool does to the world before calling it. Descriptions should go beyond structured annotations to explain consequences.
Is the description appropriately sized, front-loaded, and free of redundancy?
Two short sentences, front-loaded with the operation and followed by the one critical caveat. Nothing is padded and every clause carries information.
Shorter descriptions cost fewer tokens and are easier for agents to parse. Every sentence should earn its place.
Given the tool's complexity, does the description cover enough for an agent to succeed on first attempt?
For a one-parameter destructive mutation with no output schema, the definition covers the essentials and flags the one-time visibility of the returned secret. The remaining gap is the effect on the previous secret and existing integrations, which matters for a destructive rotation.
Complex tools with many parameters or behaviors need more documentation. Simple tools need less. This dimension scales expectations accordingly.
Does the description clarify parameter syntax, constraints, interactions, or defaults beyond what the schema provides?
Schema description coverage is 100% and the single 'id' parameter is already documented as the webhook ID, so the schema carries the load. The description adds no format, prefix, or lookup guidance beyond it; baseline 3 is appropriate.
Input schemas describe structure but not intent. Descriptions should explain non-obvious parameter relationships and valid value ranges.
Does the description clearly state what the tool does and how it differs from similar tools?
Names a specific verb (rotate) and resource (webhook signing secret), which is immediately separable from the sibling webhook tools (create_webhook, update_webhook, delete_webhook, get_webhook, list_webhooks). No ambiguity about what operation is performed.
Agents choose between tools based on descriptions. A clear purpose with a specific verb and resource helps agents select the right tool.
Does the description explain when to use this tool, when not to, or what alternatives exist?
The description states what happens but gives no guidance on when to rotate versus using update_webhook, nor any prerequisite or trigger condition (e.g. suspected compromise, scheduled rotation). Usage must be inferred entirely from the tool name.
Agents often have multiple tools that could apply. Explicit usage guidance like "use X instead of Y when Z" prevents misuse.
search_instagram_audioARead-onlyInspect
Search Instagram's licensed music catalog for a track to attach to a REEL. Use this whenever the user wants to post a reel WITH music/a song/a sound (e.g. "post this reel with trending audio", "add that song to it").
Flow: call with a song/artist/keyword (or NO query for currently trending audio) → present the options → once the user picks, pass that result's audio_id as instagram.audio_id on create_post / create_and_publish_post / update_post. Optionally mix with instagram.audio_volume / instagram.video_volume (0-100; set video_volume 0 to fully replace the video's own sound). Instagram Reels only — feed posts, carousels, and Stories can't take music via the API (Meta limitation).
Notes: only tracks Meta licenses for third-party publishing appear, so the selection can differ from the Instagram app. Requires the workspace to have a Facebook account connected whose Page is linked to this Instagram account — if results say Facebook is needed, tell the user to connect it under Settings → Organisation → Workspaces.
| Name | Required | Description | Default |
|---|---|---|---|
| type | No | Catalog to search: licensed music (default) or original sounds created by Instagram users. | |
| query | No | Song title, artist, or keyword. OMIT for currently trending audio. |
TDQS
Does the description disclose side effects, auth requirements, rate limits, or destructive behavior?
Although annotations already declare readOnlyHint/openWorldHint/destructiveHint, the description adds substantial behavioral context beyond them: the licensing limitation that results differ from the Instagram app, and the prerequisite that the workspace must have a Facebook account connected with a linked Page, including an error-handling instruction. This is exactly the kind of hidden constraint that saves an agent from a failed call.
Agents need to know what a tool does to the world before calling it. Descriptions should go beyond structured annotations to explain consequences.
Is the description appropriately sized, front-loaded, and free of redundancy?
The description is front-loaded with purpose, then organized into a Flow and a Notes block. Despite its length, every sentence carries actionable content (examples, the Reels-only limitation, the Facebook prerequisite), so nothing is wasted.
Shorter descriptions cost fewer tokens and are easier for agents to parse. Every sentence should earn its place.
Given the tool's complexity, does the description cover enough for an agent to succeed on first attempt?
For a search tool with no output schema, the description supplies the missing pieces: what to do with results (present options, pass audio_id downstream), the return-relevant field name, and the auth/prerequisite conditions. Nothing an agent needs to call it correctly appears to be missing.
Complex tools with many parameters or behaviors need more documentation. Simple tools need less. This dimension scales expectations accordingly.
Does the description clarify parameter syntax, constraints, interactions, or defaults beyond what the schema provides?
Schema description coverage is 100%, so both parameters (type, query) are already fully documented, including the "OMIT for trending" behavior that the description repeats. The description adds downstream context (audio_id, volume params) but little new meaning about this tool's own parameters, so the baseline 3 applies.
Input schemas describe structure but not intent. Descriptions should explain non-obvious parameter relationships and valid value ranges.
Does the description clearly state what the tool does and how it differs from similar tools?
The description opens with a specific verb and resource ("Search Instagram's licensed music catalog for a track") and scopes it to a REEL, which clearly separates it from media/post/list siblings. An agent can identify the tool's function without opening the schema.
Agents choose between tools based on descriptions. A clear purpose with a specific verb and resource helps agents select the right tool.
Does the description explain when to use this tool, when not to, or what alternatives exist?
It states exactly when to use it ("whenever the user wants to post a reel WITH music/a song/a sound") with concrete examples, and it also gives an explicit exclusion ("Instagram Reels only — feed posts, carousels, and Stories can't take music via the API"). It further routes the agent to the downstream tools where the result is consumed.
Agents often have multiple tools that could apply. Explicit usage guidance like "use X instead of Y when Z" prevents misuse.
search_locationsARead-onlyInspect
Search for a location to tag on a post. Use this whenever the user wants to post WITH a place/location (e.g. "tag my dealership", "post this at the café"). It returns matching real venues with their addresses and a location ID.
Pick the platform with platform: "instagram" (default) or "threads". The two use DIFFERENT ids (a Facebook Place ID is not a Threads location id), so search with the platform you will tag. If the user wants both, search twice.
Flow (Instagram): call with the place name → present the options → once the user picks, pass that result's id as the top-level location_id on create_post / create_and_publish_post / update_post.
Flow (Threads): same, but pass the id as threads.location_id. On a multi-post thread the tag goes on the first post.
Notes: use a SPECIFIC venue name (a broad brand like "Starbucks" returns individual store locations). Instagram: if the user already has a numeric Facebook Place ID, you can pass it straight to create_post; it's validated at publish and a bad one returns a clear error. If results are empty with a permission note, the workspace's Facebook app can't search arbitrary places — tell the user to use their own business Page's ID. Threads: needs the workspace's Threads connection to have the location permission; if the result says to reconnect Threads, tell the user to reconnect it under Settings → Organisation → Workspaces.
| Name | Required | Description | Default |
|---|---|---|---|
| query | Yes | Place name to search (min 2 chars) — a dealership, café, venue, etc. | |
| platform | No | Which platform the location will be tagged on. Defaults to instagram. Use threads to get a Threads location id for threads.location_id. |
TDQS
Does the description disclose side effects, auth requirements, rate limits, or destructive behavior?
Annotations cover safety (readOnlyHint, openWorldHint, destructiveHint), and the description goes further by disclosing failure modes: empty results with a permission note mean the Facebook app can't search arbitrary places, Threads needs a location permission that may require reconnecting, and bad Place IDs are validated at publish. It stops short of describing pagination or result limits, but the behavioral context is rich.
Agents need to know what a tool does to the world before calling it. Descriptions should go beyond structured annotations to explain consequences.
Is the description appropriately sized, front-loaded, and free of redundancy?
Well front-loaded (purpose, then platform choice, then per-platform flows, then edge-case notes) and every paragraph carries actionable content. It is long, but the density is justified by the multi-step tagging workflow it has to support.
Shorter descriptions cost fewer tokens and are easier for agents to parse. Every sentence should earn its place.
Given the tool's complexity, does the description cover enough for an agent to succeed on first attempt?
No output schema exists, so the description carries the return burden and does so ("matching real venues with their addresses and a location ID"), plus error/permission paths and the handoff to post-creation tools. Nothing an agent needs to call this correctly is missing.
Complex tools with many parameters or behaviors need more documentation. Simple tools need less. This dimension scales expectations accordingly.
Does the description clarify parameter syntax, constraints, interactions, or defaults beyond what the schema provides?
Schema coverage is 100%, so the baseline is 3, but the description adds real meaning beyond it: the two platforms return DIFFERENT id namespaces, so you must search with the platform you'll tag, and it advises using a specific venue name since a broad brand returns individual stores.
Input schemas describe structure but not intent. Descriptions should explain non-obvious parameter relationships and valid value ranges.
Does the description clearly state what the tool does and how it differs from similar tools?
States a specific verb+resource ("Search for a location to tag on a post") and its role in a larger flow, clearly distinct from siblings like search_instagram_audio. An agent knows exactly what it does without opening the schema.
Agents choose between tools based on descriptions. A clear purpose with a specific verb and resource helps agents select the right tool.
Does the description explain when to use this tool, when not to, or what alternatives exist?
Gives explicit trigger conditions ("whenever the user wants to post WITH a place/location") plus worked examples, then spells out the per-platform flow and how the returned id feeds create_post / create_and_publish_post / update_post. Alternatives and follow-up routing are unambiguous.
Agents often have multiple tools that could apply. Explicit usage guidance like "use X instead of Y when Z" prevents misuse.
switch_workspaceAInspect
Switch the active workspace by NAME. All subsequent tool calls (posts, media, analytics, etc.) will operate on the selected workspace. Pass the workspace name exactly as shown in list_workspaces (its id or list position also work, but the name is preferred and unambiguous). Only call this when the user has explicitly named the target workspace, or after the user has picked one from list_workspaces. Never call switch_workspace silently when the user hasn't specified a workspace - ask first.
| Name | Required | Description | Default |
|---|---|---|---|
| workspace | Yes | The workspace to switch to: its name (preferred, e.g. "Daily Edge Sports"), or its id/list number. |
TDQS
Does the description disclose side effects, auth requirements, rate limits, or destructive behavior?
Discloses a significant behavioral trait beyond the annotations: that all subsequent tool calls (posts, media, analytics) operate on the selected workspace, i.e. a session-wide state change. Annotations only carry the generic readOnlyHint=false/destructiveHint=false/openWorldHint=false safety profile, so the state-scoping note is genuinely additive. It stops short of describing reversibility or any confirmation/error behavior, so not a 5.
Agents need to know what a tool does to the world before calling it. Descriptions should go beyond structured annotations to explain consequences.
Is the description appropriately sized, front-loaded, and free of redundancy?
Front-loads purpose, then the side effect, then the parameter format, then the usage rules. Four sentences, each carrying distinct information (what, effect, format, guardrail) with no filler.
Shorter descriptions cost fewer tokens and are easier for agents to parse. Every sentence should earn its place.
Given the tool's complexity, does the description cover enough for an agent to succeed on first attempt?
For a single-param tool with 100% schema coverage, annotations, and no output schema, the description covers purpose, session-wide side effect, value format, and a consent guardrail. Nothing an agent needs to invoke it correctly is missing.
Complex tools with many parameters or behaviors need more documentation. Simple tools need less. This dimension scales expectations accordingly.
Does the description clarify parameter syntax, constraints, interactions, or defaults beyond what the schema provides?
Schema coverage is 100%, so 3 is the baseline, but the description adds useful format guidance beyond the schema: pass the name 'exactly as shown in list_workspaces' and that the name is preferred because it is unambiguous. That cross-reference to the source-of-truth lister is real added meaning, though the name/id/list-number alternatives largely duplicate the schema.
Input schemas describe structure but not intent. Descriptions should explain non-obvious parameter relationships and valid value ranges.
Does the description clearly state what the tool does and how it differs from similar tools?
States a specific verb and resource ('Switch the active workspace') and immediately differentiates itself from the sibling list_workspaces by referencing it as the source of valid values. An agent can distinguish this state-changing tool from read-only listers without opening a schema.
Agents choose between tools based on descriptions. A clear purpose with a specific verb and resource helps agents select the right tool.
Does the description explain when to use this tool, when not to, or what alternatives exist?
Gives explicit when-to-use ('only when the user has explicitly named the target workspace, or after the user has picked one from list_workspaces') and explicit when-not-to-use ('Never call switch_workspace silently... ask first'). The alternative (list_workspaces) is named and the routing condition is spelled out.
Agents often have multiple tools that could apply. Explicit usage guidance like "use X instead of Y when Z" prevents misuse.
update_automationAInspect
Change a comment-to-DM automation: pause or resume it (status), new keywords or match, a new DM text or public replies, new limits, or move it to another post (post_id, instagram_media_id or facebook_post_id). Only the fields you pass change. The platform cannot change: to move to another channel (Instagram, the Facebook Page or X), create a new automation. Turning an X automation on (status 'active') needs X DMs on for the workspace, else 409 x_dms_off. A 'completed' automation starts again when its limits or trigger change.
| Name | Required | Description | Default |
|---|---|---|---|
| name | No | A label for the automations list, e.g. 'Free guide'. | |
| match | No | word (default): the keyword stands on its own ('guide', 'Guide!' match; 'linkedin' does not match 'link'). contains: the keyword appears anywhere. any: every comment or message with text (ask the user before using it). | |
| scope | No | For the comment trigger (Instagram and Facebook; an X automation has no post): 'post' (default) = one post (pass post_id, instagram_media_id or facebook_post_id), 'next_post' = the next post the workspace publishes on this platform, 'any' = every post of the account or Page. | |
| status | No | 'paused' stops it without deleting it; 'active' resumes it (on X only while X DMs are on for the workspace). | |
| dm_text | No | The DM sent to the person (max 1000 characters), once per person. On Facebook it lands in Messenger. On X, OmniSocials adds the line 'Reply STOP to stop automatic messages.' under it. Required on create. Confirm the text with the user before creating the automation: it goes out in the account's name. | |
| post_id | No | For scope 'post' (Instagram and Facebook): the OmniSocials post id (from list_posts) that goes to the automation's platform. A scheduled post starts listening once it is live. One automation per post and platform: a post that goes to Instagram and Facebook can have one of each. | |
| stop_at | No | Stop at this time (ISO 8601). null = no end. | |
| keywords | No | Keywords that start the automation (up to 20, matched case-insensitively), e.g. ["guide", "link"]. Required unless match is 'any'. | |
| platform | No | Where the automation runs: 'instagram' (default) = the connected Instagram account, 'facebook' = the connected Facebook Page (the DM lands in Messenger), 'x' = the connected X account (it answers DMs only; see create_automation). instagram_media_id implies 'instagram', facebook_post_id implies 'facebook'. It cannot change after create. | |
| triggers | No | What starts the automation. 'comment' (default on Instagram and Facebook) = a comment on an Instagram post or reel, or on a Facebook Page post; 'dm' = a keyword in a DM to the Instagram account, in a Messenger message to the Facebook Page, or in a DM to the X account; 'story_reply' = a keyword in a reply to an Instagram story (Instagram only: Facebook has no story replies). On X only 'dm' exists, and it is the default there. One automation can listen to several. | |
| max_sends | No | Stop after this many DMs (the automation becomes 'completed'). null = no limit. | |
| automation_id | Yes | The automation id (from list_automations). | |
| public_replies | No | Optional public replies posted under the comment (one is picked at random per comment), e.g. ["Sent you a DM!", "Check your inbox"]. Comment trigger only (Instagram and Facebook; X has none). An empty array turns the public reply off. | |
| facebook_post_id | No | For scope 'post' on Facebook: the id of a Facebook Page post that was NOT published through OmniSocials ({page-id}_{post-id}, or the post id alone). OmniSocials reads it from Facebook to check it belongs to the connected Page. Implies platform 'facebook'. Pass only one of post_id, instagram_media_id or facebook_post_id. | |
| instagram_media_id | No | For scope 'post' on Instagram: the numeric Instagram media id of a post or reel that was NOT published through OmniSocials. OmniSocials reads it from Instagram to check it belongs to the connected account. Pass only one of post_id, instagram_media_id or facebook_post_id. |
TDQS
Does the description disclose side effects, auth requirements, rate limits, or destructive behavior?
Adds real behavior beyond the annotations: partial-update semantics, the 409 x_dms_off failure mode, and the non-obvious state transition where a 'completed' automation restarts when limits or trigger change. Annotations only supply the readOnly/destructive/openWorld flags, so this extra context is genuinely additive, though it does not describe the response or how the DMs already sent are affected.
Agents need to know what a tool does to the world before calling it. Descriptions should go beyond structured annotations to explain consequences.
Is the description appropriately sized, front-loaded, and free of redundancy?
Front-loaded with the updateable fields, then constraints, then the error/state caveats — no filler sentences. It is dense and somewhat long for a description, but each sentence (partial update, platform immutability, 409, completed restart) contributes distinct information.
Shorter descriptions cost fewer tokens and are easier for agents to parse. Every sentence should earn its place.
Given the tool's complexity, does the description cover enough for an agent to succeed on first attempt?
For a 15-parameter mutation tool with no output schema, the description covers mutation semantics, a prerequisite failure, and a status edge case. It leaves unaddressed what the call returns and whether moving/max_sends changes affect an in-flight automation, which keeps it from a 5.
Complex tools with many parameters or behaviors need more documentation. Simple tools need less. This dimension scales expectations accordingly.
Does the description clarify parameter syntax, constraints, interactions, or defaults beyond what the schema provides?
Schema coverage is 100%, so the baseline is 3; the description still adds value by grouping post_id/instagram_media_id/facebook_post_id as the mutually exclusive 'move to another post' path and by framing status as pause/resume rather than a raw enum. It stops short of explaining the interaction between scope and those ids beyond a pointer.
Input schemas describe structure but not intent. Descriptions should explain non-obvious parameter relationships and valid value ranges.
Does the description clearly state what the tool does and how it differs from similar tools?
Opens with a concrete verb+resource ('Change a comment-to-DM automation') and immediately enumerates the changeable dimensions (status, keywords/match, dm_text, limits, target post). This clearly separates it from create_automation and delete_automation in the sibling list.
Agents choose between tools based on descriptions. A clear purpose with a specific verb and resource helps agents select the right tool.
Does the description explain when to use this tool, when not to, or what alternatives exist?
States partial-update semantics ('Only the fields you pass change'), an explicit exclusion with a redirect ('The platform cannot change: to move to another channel ... create a new automation'), and a precondition for a specific use (status 'active' on X needs X DMs on, else 409 x_dms_off).
Agents often have multiple tools that could apply. Explicit usage guidance like "use X instead of Y when Z" prevents misuse.
update_hashtag_setAInspect
Rename a hashtag set and/or replace its tags. 'hashtags' replaces the FULL list — to add or remove tags, pass the complete new list (see list_hashtag_sets for the current tags). Posts that already used the set are unaffected.
| Name | Required | Description | Default |
|---|---|---|---|
| name | No | New name for the set | |
| set_id | Yes | The hashtag set id (from list_hashtag_sets) | |
| hashtags | No | Full replacement tag list, in order |
TDQS
Does the description disclose side effects, auth requirements, rate limits, or destructive behavior?
Annotations already declare non-read-only, non-destructive, closed-world, and the description adds behavior beyond them: hashtags is a full replacement, not a merge, and existing posts that used the set are unaffected. It does not cover permissions or error behavior, so it is strong but not exhaustive.
Agents need to know what a tool does to the world before calling it. Descriptions should go beyond structured annotations to explain consequences.
Is the description appropriately sized, front-loaded, and free of redundancy?
Three front-loaded sentences with zero filler: purpose first, then the critical replacement caveat, then the side-effect note. Every sentence earns its place.
Shorter descriptions cost fewer tokens and are easier for agents to parse. Every sentence should earn its place.
Given the tool's complexity, does the description cover enough for an agent to succeed on first attempt?
For a small mutation tool with no output schema and full schema coverage, the description supplies the essential semantics: optionality ('and/or'), replacement behavior, and non-retroactivity. Remaining minor gaps (empty-list handling, permission requirements) are not critical.
Complex tools with many parameters or behaviors need more documentation. Simple tools need less. This dimension scales expectations accordingly.
Does the description clarify parameter syntax, constraints, interactions, or defaults beyond what the schema provides?
Schema description coverage is 100%, so the baseline is 3, but the description goes further by spelling out the replacement semantics operationally (pass the complete list) and routing the agent to list_hashtag_sets for current values. That adds usable meaning beyond the schema's terse field descriptions.
Input schemas describe structure but not intent. Descriptions should explain non-obvious parameter relationships and valid value ranges.
Does the description clearly state what the tool does and how it differs from similar tools?
States a specific verb and resource ('Rename a hashtag set and/or replace its tags'), listing exactly which fields it mutates. This clearly separates it from create_hashtag_set, delete_hashtag_set, and list_hashtag_sets among the siblings.
Agents choose between tools based on descriptions. A clear purpose with a specific verb and resource helps agents select the right tool.
Does the description explain when to use this tool, when not to, or what alternatives exist?
Explains the key operational condition: to add or remove tags you must pass the complete new list, and it points to list_hashtag_sets to obtain the current tags. It gives clear context but stops short of stating when to use this versus other mutation alternatives (e.g. delete/recreate).
Agents often have multiple tools that could apply. Explicit usage guidance like "use X instead of Y when Z" prevents misuse.
update_mediaAInspect
Rename an existing media file or move it into a folder (so it's findable later instead of re-uploading it). Only the fields you pass are changed.
| Name | Required | Description | Default |
|---|---|---|---|
| id | Yes | The media ID to update | |
| name | No | New human-readable label, e.g. "pp-play5get50". Pass an empty string to clear it. | |
| folder_id | No | Move the file into this folder id (from list_folders). Pass an empty string to move it to the root ("All media"). |
TDQS
Does the description disclose side effects, auth requirements, rate limits, or destructive behavior?
Annotations already declare readOnlyHint=false, destructiveHint=false and openWorldHint=false, so the safety profile is covered. The description adds a genuinely useful trait beyond that: "Only the fields you pass are changed," disclosing partial-update semantics rather than full overwrite.
Agents need to know what a tool does to the world before calling it. Descriptions should go beyond structured annotations to explain consequences.
Is the description appropriately sized, front-loaded, and free of redundancy?
Two tight sentences with the operation front-loaded and the non-clobbering behavior immediately following; nothing is wasted.
Shorter descriptions cost fewer tokens and are easier for agents to parse. Every sentence should earn its place.
Given the tool's complexity, does the description cover enough for an agent to succeed on first attempt?
For a simple 3-param update with full schema coverage, annotations and no output schema, the description is essentially complete. It could still mention that folder_id comes from list_folders, but the schema covers that.
Complex tools with many parameters or behaviors need more documentation. Simple tools need less. This dimension scales expectations accordingly.
Does the description clarify parameter syntax, constraints, interactions, or defaults beyond what the schema provides?
Schema description coverage is 100%, so the schema already documents id, name and folder_id including the empty-string clear/move-to-root behavior. The description adds no parameter detail beyond what the schema provides, making the baseline 3 appropriate.
Input schemas describe structure but not intent. Descriptions should explain non-obvious parameter relationships and valid value ranges.
Does the description clearly state what the tool does and how it differs from similar tools?
States a specific verb+resource (rename/move a media file) with a clear scope, and the parenthetical hints at why. It is readily distinguishable from upload_media and delete_media, though it never names a sibling explicitly.
Agents choose between tools based on descriptions. A clear purpose with a specific verb and resource helps agents select the right tool.
Does the description explain when to use this tool, when not to, or what alternatives exist?
The phrase "instead of re-uploading it" implies the use case (fixing an existing asset rather than re-uploading), but there is no explicit when-to-use/when-not or pointer to an alternative tool such as list_folders for the folder_id lookup.
Agents often have multiple tools that could apply. Explicit usage guidance like "use X instead of Y when Z" prevents misuse.
update_postAInspect
Update an existing post. Only draft and scheduled posts can be updated.
Per-platform options (youtube, pinterest, instagram, tiktok, google_business) are accepted here, same shape as in create_post. Pass an object — never a JSON-encoded string. For YouTube Shorts, the title lives at youtube.title; the video description lives in content (or content.youtube for a per-platform override). They are not the same field — changing the caption does NOT rename the Short.
X threads: To convert an existing draft into a chained X thread, pass x.thread_parts as a 2–25 entry array of { text } objects (each ≤ 280 chars). Pass x.thread_parts: null to revert to single-tweet mode. Do NOT shove "1/", "2/" into content — that's a single tweet, not a thread.
| Name | Required | Description | Default |
|---|---|---|---|
| x | No | X (Twitter) options: thread mode via `thread_parts`, a poll via `poll`. | |
| id | Yes | The post ID to update | |
| tiktok | No | TikTok options | |
| bluesky | No | Bluesky options, including thread mode via `thread_parts`. | |
| content | No | Updated post caption / body text. For YouTube Shorts this becomes the video description, NOT the title — to rename the Short, use `youtube.title`. String or object with platform keys: { "default": "fallback", "linkedin": "long" }. | |
| discord | No | Discord options. The post goes to the connected Discord channel through its webhook and shows the webhook's name and picture. Text up to 2,000 chars. Up to 10 images, GIFs and videos per message (they may mix); a video or GIF over Discord's 20 MB file limit is sent as a link in the text. No Stories; a 'reel' is sent as one video message. | |
| threads | No | Threads options: thread mode via `thread_parts`, location tag via `location_id`, a poll via `poll`, the topic via `topic_tag`. | |
| youtube | No | YouTube Shorts options. Only applies when type is 'reel' and youtube is among the selected channels. A custom Shorts thumbnail is set with the top-level `video_cover` (a `youtube` override for a YouTube-only image); it shows on Shorts only on channels where YouTube has enabled custom Shorts thumbnails (Partner Program channels first, since July 2026), other channels show a frame from the video. | |
| channels | No | Updated channel IDs. Note: `linkedin` (personal profile) and `linkedin_page` (company page) are independent channels. | |
| No | Facebook options | ||
| link_url | No | URL to share as a rich preview card on platforms that support link-share posts (LinkedIn and Facebook). Renders as a tile with thumbnail/title/description instead of plain text. Ignored on platforms that don't support link shares, and ignored on posts that already have media attached (media wins). | |
| No | LinkedIn Profile options | ||
| mastodon | No | Mastodon options: thread mode via `thread_parts`, a poll via `poll`. | |
| telegram | No | Telegram options. Text up to 4,096 chars; with media, text over 1,024 chars is sent as a reply under the media. Up to 10 photos and videos per album, videos up to 50 MB, no Stories. A 'reel' is sent as a video message. | |
| No | Instagram options | ||
| media_fit | No | Image fit per channel, for feed images (type 'post') whose ratio is outside what a channel shows uncropped: { instagram: 'auto' | 'crop' | 'keep', pinterest: ... }. 'auto' (the default when omitted) takes the channel's rule: Instagram crops a tall (9:16) or wide image to 4:5 / 1.91:1 around the subject (Instagram cuts it to that window anyway, and Meta cannot boost a feed post outside it); Pinterest keeps a Pin taller than 2:3 and only reports it. 'crop' / 'keep' force it for that channel. Every decision comes back in the response `warnings` with code `image_fit` (relay it). The crop is a separate file for that channel only; 'default' and the other channels keep the original. On update_post, media_fit alone (no media) re-decides the stored images: 'keep' gives the original back, 'crop' crops an image that was kept. | |
| media_ids | No | ||
| No | |||
| user_tags | No | Instagram only. Tag public accounts at x/y positions on a PHOTO (not video/reels/stories). For a single image omit image_index; for a carousel, set image_index to the slide each tag belongs to. Private/non-existent usernames are rejected at publish time. Ignored by other platforms. | |
| link_title | No | Optional title for the link-share preview. LinkedIn uses this when set; Facebook ignores it and fetches OG metadata server-side. Omit to let LinkedIn auto-fetch the page title. | |
| media_urls | No | External image/video/PDF URLs — flat array or per-platform object. Max 10 total (Pinterest: max 5 images per carousel pin), each file ≤ 100 MB. Entries are URL strings or { url, alt } objects (alt = accessibility description, delivered to Mastodon/Bluesky/X/Pinterest/Instagram (images)/LinkedIn (images)). For larger files (up to 1 GB): upload_media with method 'url' first, then pass the returned media id in `media`. | |
| location_id | No | Instagram only. Facebook Place ID for a single physical venue (with a street address) to tag the post's location. Find it via the location search in the OmniSocials dashboard. Ignored by other platforms. | |
| video_cover | No | Replaces the stored video cover wholesale; pass null to remove it; omit to leave it untouched. facebook.thumbnail_type / thumb_offset / cover_url merge into overrides.facebook on their own. | |
| scheduled_at | No | Updated scheduled date (ISO 8601) | |
| collaborators | No | Instagram only. Up to 3 public Instagram usernames to invite as co-authors (the 'Collab' feature). Works on image, carousel, and reel posts — NOT Stories. Invited users get an invite in the Instagram app; once they accept, the post also appears on their profile and feed. A leading '@' is stripped; usernames are case-insensitive. Private or non-existent usernames are rejected by Instagram at publish time. Ignored by other platforms. | |
| linkedin_page | No | LinkedIn Company Page options | |
| linkedin_poll | No | Non-sponsored LinkedIn poll(s) — independent per channel, keyed by `linkedin` (personal profile) / `linkedin_page` (company page). A poll is mutually exclusive with media and a link share on that channel's post — a poll takes priority over both at publish time. Still requires `content.linkedin` (or `content.default`) as that channel's caption; the poll itself only carries the question/options/duration. On update_post, set a channel's key to `null` to clear that channel's poll and revert it to a normal post — send the full desired state for both channels, since the whole object replaces wholesale. | |
| google_business | No | Google Business Profile options. Use to publish EVENT or OFFER posts, attach a CTA button, or both. Shape mirrors Google's LocalPost resource (see https://developers.google.com/my-business/reference/rest/v4/accounts.locations.localPosts#LocalPost). Google Business caption rules (enforced at scheduling — text that violates these will return a `validation_error` 400 before the post is saved): • Phone numbers in the caption are rejected — use a CALL button instead. • Inline URLs / bare domains / emails are rejected — use LEARN_MORE / BOOK / SHOP / SIGN_UP / ORDER buttons instead. • Caption max 1500 characters. • Media is optional (text-only posts are allowed). If attached: exactly one JPEG/PNG/WebP image (no video, no carousels). • The workspace must have a Google Business location selected (Settings → Organisation → Workspaces → Google Business) before scheduling — otherwise returns a 400. | |
| link_description | No | Optional description for the link-share preview. LinkedIn uses this when set; Facebook auto-fetches the OG description. | |
| link_thumbnail_url | No | Optional thumbnail image URL for the preview card. Currently applied on Facebook; reserved for LinkedIn. | |
| comment_dm_automation | No | Replaces the post's comment-to-DM setup (keywords, DM text, public replies, limits, platforms); a channel no longer listed in platforms loses its automation; pass null to remove them all; omit to leave them untouched. |
TDQS
Does the description disclose side effects, auth requirements, rate limits, or destructive behavior?
Annotations already establish that this is a non-read-only, non-destructive, closed-world mutation. The description adds meaningful behavioral context beyond that: update eligibility, per-platform object shape rather than JSON-encoded strings, and thread conversion/reversion semantics for X via `x.thread_parts`. It does not globally explain partial-update merge/replace behavior, but the annotations lower the bar.
Agents need to know what a tool does to the world before calling it. Descriptions should go beyond structured annotations to explain consequences.
Is the description appropriately sized, front-loaded, and free of redundancy?
The purpose and eligibility constraint are front-loaded, followed by targeted platform pitfalls. It is reasonably lean for a 31-parameter tool, though it spends notable space on X threads and YouTube while leaving broader update semantics unstated.
Shorter descriptions cost fewer tokens and are easier for agents to parse. Every sentence should earn its place.
Given the tool's complexity, does the description cover enough for an agent to succeed on first attempt?
This is a large, deeply nested mutation tool with no output schema, so the description cannot cover everything. It addresses purpose, eligibility, and selected platform traps, but it does not state overall partial-update semantics, such as which omitted fields are preserved versus replaced, even though some individual schema fields document merge/replace behavior.
Complex tools with many parameters or behaviors need more documentation. Simple tools need less. This dimension scales expectations accordingly.
Does the description clarify parameter syntax, constraints, interactions, or defaults beyond what the schema provides?
Schema description coverage is 94%, so the baseline is 3. The description adds some non-schema guidance, especially that per-platform options share the `create_post` shape and must be passed as objects, never JSON-encoded strings. Much of the YouTube and X detail is repeated from the schema, but the cross-tool shape reference and serialization warning add real value.
Input schemas describe structure but not intent. Descriptions should explain non-obvious parameter relationships and valid value ranges.
Does the description clearly state what the tool does and how it differs from similar tools?
The description states a specific verb and resource ('Update an existing post') and immediately adds the key scope constraint ('Only draft and scheduled posts can be updated'). This clearly separates it from create_post, publish_post, and delete_post without requiring the agent to infer intent.
Agents choose between tools based on descriptions. A clear purpose with a specific verb and resource helps agents select the right tool.
Does the description explain when to use this tool, when not to, or what alternatives exist?
It gives a concrete usage condition: only draft and scheduled posts are eligible. It does not explicitly name alternatives such as create_post for new posts or publish_post for publishing, but the eligibility rule is strong enough to guide selection in most cases.
Agents often have multiple tools that could apply. Explicit usage guidance like "use X instead of Y when Z" prevents misuse.
update_webhookCInspect
Update a webhook's URL, events, or active status.
| Name | Required | Description | Default |
|---|---|---|---|
| id | Yes | The webhook ID to update | |
| url | No | Updated HTTPS URL | |
| events | No | Updated event list | |
| is_active | No | Enable or disable |
TDQS
Does the description disclose side effects, auth requirements, rate limits, or destructive behavior?
Annotations already declare this is a non-read-only, non-destructive, closed-world write, so the safety profile is covered. The description adds nothing behavioral beyond that: it does not say whether omitted fields are preserved or cleared, whether changes take effect immediately, or what permissions are needed for a mutation.
Agents need to know what a tool does to the world before calling it. Descriptions should go beyond structured annotations to explain consequences.
Is the description appropriately sized, front-loaded, and free of redundancy?
A single, front-loaded sentence with no filler; the verb and resource lead. It is efficient, though the brevity is partly why behavioral and usage detail are absent.
Shorter descriptions cost fewer tokens and are easier for agents to parse. Every sentence should earn its place.
Given the tool's complexity, does the description cover enough for an agent to succeed on first attempt?
With four fully documented parameters, annotations covering the safety profile, and no output schema, the essentials are present. The notable gap for a mutation tool is partial-update semantics (what happens to fields not supplied), which neither schema nor description addresses.
Complex tools with many parameters or behaviors need more documentation. Simple tools need less. This dimension scales expectations accordingly.
Does the description clarify parameter syntax, constraints, interactions, or defaults beyond what the schema provides?
Schema description coverage is 100%, so the baseline is 3; the schema already documents id, url, events and is_active with types and the HTTPS constraint. The description merely restates the mutable fields in prose and adds no format or semantic detail beyond the schema.
Input schemas describe structure but not intent. Descriptions should explain non-obvious parameter relationships and valid value ranges.
Does the description clearly state what the tool does and how it differs from similar tools?
States a specific verb (update) and resource (webhook) plus the three mutable fields, so an agent can distinguish it from create_webhook, delete_webhook, get_webhook and rotate_webhook_secret. It does not explicitly name a sibling it is not, but the verb+resource pairing is unambiguous.
Agents choose between tools based on descriptions. A clear purpose with a specific verb and resource helps agents select the right tool.
Does the description explain when to use this tool, when not to, or what alternatives exist?
There is no when-to-use guidance, no prerequisites (e.g. that the webhook must already exist, or that the ID comes from list_webhooks), and no mention of alternatives such as rotate_webhook_secret for credential changes. Usage is only implied by the tool name.
Agents often have multiple tools that could apply. Explicit usage guidance like "use X instead of Y when Z" prevents misuse.
upload_mediaAInspect
Upload media to the library. Three methods supported:
url — import from a PUBLIC https URL (e.g. a hosted image link). NEVER pass a local sandbox path — the URL must be reachable from our servers.
base64_data — pass base64-encoded file data directly. ONLY use this for tiny files (≲50 KB). MCP tool inputs are token-capped — anything larger gets silently truncated and uploads a corrupted file. For any user-pasted image, use upload_url instead.
upload_url — PREFERRED for any file the user attached to the chat. Call with method="upload_url" to get a one-time presigned URL plus a ready-to-run snippet. Execute the snippet in your code-execution tool against the actual file path. The response JSON contains the media id you pass to create_post.
Size limits: base64/direct uploads are capped at 100 MB. For anything larger — up to 1 GB — use a public url (fetched server-side, bypasses the cap), OR have the user upload the file in the OmniSocials Library UI at https://app.omnisocials.com/library . IMPORTANT: if the user has a large LOCAL file (over ~100 MB) with no public url, do NOT tell them to compress it — point them to the Library UI link above. Large videos (over 100 MB) are processed in the background — the response status is "processing" and the file is NOT usable in a post until it becomes "ready" (re-check with list_media).
Compatibility: every upload response includes a "compatibility" summary of any CONNECTED platforms that would reject the file (e.g. too large for Instagram). If there are warnings, RELAY them and ask the user whether to continue before posting — the file still uploads and can post to platforms that accept it. To check BEFORE uploading, call check_media_compatibility first.
PDF = carousel: upload a PDF (via a public url, or base64_data with mime_type "application/pdf", or the upload_url snippet) and it is split into one image slide per page (max 20). The response lists a Media ID for EVERY slide — pass ALL of them, in order, as media_ids to create_post to post the deck as a carousel. On LinkedIn the slides post as a native swipeable DOCUMENT made from the ORIGINAL PDF file (the file is kept: text stays sharp, in-document links work, viewers download the real file, and every page is included even past the 20-slide cap) as long as the slides are posted unchanged and in order; on Instagram, TikTok, Threads and Pinterest as an image carousel. Set linkedin.document_source to 'slides' on the post to send a document rebuilt from the slide images instead. This is how a user posts an existing slide deck (Canva/PowerPoint/Figma exported to PDF) as a carousel. Prefer pdf_mode "document" when the user wants ONE library item for the deck (no per-page clutter): the response then has a single Media ID whose media_ids entry expands into every page at post time.
Supported: JPEG, PNG, GIF, WebP, MP4, MOV, AVI, PDF.
For user-attached files: ALWAYS try upload_url first. Call upload_media with method="upload_url", then in your code-execution sandbox run the returned Python (ChatGPT Code Interpreter, file at /mnt/data/) or curl (Claude Code Execution) snippet against the actual file path. Only react to a failure AFTER actually executing the snippet.
| Name | Required | Description | Default |
|---|---|---|---|
| url | No | Public URL of the media file (method=url). Use this when the user pasted an image link or you generated one via DALL·E. | |
| file | No | OpenAI Apps SDK file reference. Set when the user attached a file in ChatGPT — the platform fills this in automatically. | |
| name | No | Human-readable label so you can find this asset by name later instead of re-uploading it, e.g. "pp-play5get50". Strongly recommended on every upload. | |
| folder | No | Optional folder name to file this asset under (created at the top level if it does not exist), e.g. "win-graphics". Use list_folders to see existing folders. | |
| method | No | Upload method: "file" (ChatGPT user-attached image — preferred), "url", "base64_data", or "upload_url". Auto-detected from which arg you pass. | |
| filename | No | Optional filename with extension | |
| pdf_mode | No | PDF uploads only. "slides" (default): one image media item per page, one Media ID each (pass ALL of media_ids to create_post). "document": ONE media item for the whole PDF (type "document"); pass its single Media ID in media_ids and the post gets every page in order. Both keep the original file, which LinkedIn receives. For method="upload_url", send it as a form field: -F pdf_mode=document. | |
| mime_type | No | MIME type (e.g. 'image/jpeg'). Required for base64_data and upload_url. | |
| base64_data | No | Base64-encoded file data (method=base64_data). Only safe for files <50 KB. |
TDQS
Does the description disclose side effects, auth requirements, rate limits, or destructive behavior?
Annotations declare only readOnlyHint=false, openWorldHint=true, destructiveHint=false. The description adds substantial non-obvious behavior: token-cap truncation on base64, the 100 MB/1 GB size ceilings, background 'processing' status for large videos, compatibility warnings, PDF page-splitting, and LinkedIn document preservation. These are exactly the traits an agent cannot infer from annotations.
Agents need to know what a tool does to the world before calling it. Descriptions should go beyond structured annotations to explain consequences.
Is the description appropriately sized, front-loaded, and free of redundancy?
Front-loaded and well-organized with a numbered method list and labeled sections (size limits, compatibility, PDF, supported formats). It is long but largely justified by the 9-parameter, multi-method surface; the only cost is mild repetition of the 'always try upload_url first' guidance.
Shorter descriptions cost fewer tokens and are easier for agents to parse. Every sentence should earn its place.
Given the tool's complexity, does the description cover enough for an agent to succeed on first attempt?
With no output schema, the description carries the burden of describing returns and does so thoroughly: media id, compatibility summary, 'processing' status with list_media re-check, and per-slide media_ids. Given the tool's complexity and nested file object, nothing critical appears missing.
Complex tools with many parameters or behaviors need more documentation. Simple tools need less. This dimension scales expectations accordingly.
Does the description clarify parameter syntax, constraints, interactions, or defaults beyond what the schema provides?
Schema coverage is 100%, so the baseline is 3, but the description adds genuine operational semantics beyond the schema: it explains method selection, warns that base64 silently truncates above ~50 KB, and clarifies pdf_mode 'slides' vs 'document' downstream effects. It slightly exceeds the baseline by tying parameter choices to failure modes.
Input schemas describe structure but not intent. Descriptions should explain non-obvious parameter relationships and valid value ranges.
Does the description clearly state what the tool does and how it differs from similar tools?
Opens with a precise verb+resource ('Upload media to the library') and immediately enumerates the three supported input methods with concrete examples. It clearly distinguishes itself from siblings like list_media, delete_media, and update_media, and even names check_media_compatibility and create_post as adjacent steps.
Agents choose between tools based on descriptions. A clear purpose with a specific verb and resource helps agents select the right tool.
Does the description explain when to use this tool, when not to, or what alternatives exist?
Explicitly states when to use each method (url for public links, base64 for tiny files, upload_url for user-attached files), gives a clear preference order, and names conditions and alternatives (check_media_compatibility before uploading, Library UI for >1 GB local files, do NOT compress). This is textbook when/when-not guidance.
Agents often have multiple tools that could apply. Explicit usage guidance like "use X instead of Y when Z" prevents misuse.
Tool Schema Changelog
Recent tool additions, removals, and schema changes observed during successful MCP inspections.
3 tool updates
- Changed
create_and_publish_post7 fields changed- changed
Input schema / properties / mastodon / descriptionPrevious value: -"Mastodon options, including thread mode via `thread_parts`."New value: +"Mastodon options: thread mode via `thread_parts`, a poll via `poll`." - added
Input schema / properties / mastodon / properties / pollAdded value: +{ + "anyOf": [ + { + "properties": { + "expires_in": { + "description": "How long the poll runs, in seconds, within the instance's range (Mastodon's defaults: 5 minutes to 1 month). Default 86400 (one day).", + "maximum": 9007199254740991, + "minimum": 300, + "type": "integer" + }, + "hide_totals": { + "description": "Hide the vote counts until the poll ends.", + "type": "boolean" + }, + "multiple": { + "description": "Allow several answers per person.", + "type": "boolean" + }, + "options": { + "description": "The answer options, all different; count and length within the instance's limits (Mastodon's defaults: 4 options of 50 characters).", + "items": { + "minLength": 1, + "type": "string" + }, + "minItems": 2, + "type": "array" + } + }, + "required": [ + "options" + ], + "type": "object" + }, + { + "type": "null" + } + ], + "description": "Attach a poll to the status; the status text is the question. No media on Mastodon together with a poll. On a thread the poll goes on the first status. On update_post, null removes it." +} - changed
Input schema / properties / threads / descriptionPrevious value: -"Threads options: thread mode via `thread_parts`, location tag via `location_id`."New value: +"Threads options: thread mode via `thread_parts`, location tag via `location_id`, a poll via `poll`, the topic via `topic_tag`." - added
Input schema / properties / threads / properties / pollAdded value: +{ + "anyOf": [ + { + "properties": { + "options": { + "description": "2 to 4 answer options of 1 to 25 characters, all different.", + "items": { + "maxLength": 25, + "minLength": 1, + "type": "string" + }, + "maxItems": 4, + "minItems": 2, + "type": "array" + } + }, + "required": [ + "options" + ], + "type": "object" + }, + { + "type": "null" + } + ], + "description": "Attach a poll to the post; the post text is the question. Threads closes the poll 24 hours after it is published (no duration). Polls go on text-only posts: no media on Threads together with a poll. On a thread the poll goes on the first post. On update_post, null removes it." +} - added
Input schema / properties / threads / properties / topic_tagAdded value: +{ + "anyOf": [ + { + "maxLength": 50, + "type": "string" + }, + { + "type": "null" + } + ], + "description": "The topic of the post on Threads, one per post, e.g. \"Build in public\". Unlike a #tag in the text it can hold spaces. 1 to 50 characters, no period (.) and no ampersand (&); a leading # is dropped. On a multi-post thread the topic goes on the first post. On update_post, pass null to remove it." +} - changed
Input schema / properties / x / descriptionPrevious value: -"X (Twitter) options, including thread mode via `thread_parts`."New value: +"X (Twitter) options: thread mode via `thread_parts`, a poll via `poll`." - added
Input schema / properties / x / properties / pollAdded value: +{ + "anyOf": [ + { + "properties": { + "duration_minutes": { + "description": "How long the poll runs, in minutes (5 to 10080 = 7 days). Default 1440 (one day).", + "maximum": 10080, + "minimum": 5, + "type": "integer" + }, + "options": { + "description": "2 to 4 answer options of up to 25 characters, all different.", + "items": { + "maxLength": 25, + "minLength": 1, + "type": "string" + }, + "maxItems": 4, + "minItems": 2, + "type": "array" + } + }, + "required": [ + "options" + ], + "type": "object" + }, + { + "type": "null" + } + ], + "description": "Attach a poll to the tweet; the tweet text is the question. No media on X together with a poll. On a thread the poll goes on the first tweet. On update_post, null removes it." +}
- Changed
create_post7 fields changed- changed
Input schema / properties / mastodon / descriptionPrevious value: -"Mastodon options, including thread mode via `thread_parts`."New value: +"Mastodon options: thread mode via `thread_parts`, a poll via `poll`." - added
Input schema / properties / mastodon / properties / pollAdded value: +{ + "anyOf": [ + { + "properties": { + "expires_in": { + "description": "How long the poll runs, in seconds, within the instance's range (Mastodon's defaults: 5 minutes to 1 month). Default 86400 (one day).", + "maximum": 9007199254740991, + "minimum": 300, + "type": "integer" + }, + "hide_totals": { + "description": "Hide the vote counts until the poll ends.", + "type": "boolean" + }, + "multiple": { + "description": "Allow several answers per person.", + "type": "boolean" + }, + "options": { + "description": "The answer options, all different; count and length within the instance's limits (Mastodon's defaults: 4 options of 50 characters).", + "items": { + "minLength": 1, + "type": "string" + }, + "minItems": 2, + "type": "array" + } + }, + "required": [ + "options" + ], + "type": "object" + }, + { + "type": "null" + } + ], + "description": "Attach a poll to the status; the status text is the question. No media on Mastodon together with a poll. On a thread the poll goes on the first status. On update_post, null removes it." +} - changed
Input schema / properties / threads / descriptionPrevious value: -"Threads options: thread mode via `thread_parts`, location tag via `location_id`."New value: +"Threads options: thread mode via `thread_parts`, location tag via `location_id`, a poll via `poll`, the topic via `topic_tag`." - added
Input schema / properties / threads / properties / pollAdded value: +{ + "anyOf": [ + { + "properties": { + "options": { + "description": "2 to 4 answer options of 1 to 25 characters, all different.", + "items": { + "maxLength": 25, + "minLength": 1, + "type": "string" + }, + "maxItems": 4, + "minItems": 2, + "type": "array" + } + }, + "required": [ + "options" + ], + "type": "object" + }, + { + "type": "null" + } + ], + "description": "Attach a poll to the post; the post text is the question. Threads closes the poll 24 hours after it is published (no duration). Polls go on text-only posts: no media on Threads together with a poll. On a thread the poll goes on the first post. On update_post, null removes it." +} - added
Input schema / properties / threads / properties / topic_tagAdded value: +{ + "anyOf": [ + { + "maxLength": 50, + "type": "string" + }, + { + "type": "null" + } + ], + "description": "The topic of the post on Threads, one per post, e.g. \"Build in public\". Unlike a #tag in the text it can hold spaces. 1 to 50 characters, no period (.) and no ampersand (&); a leading # is dropped. On a multi-post thread the topic goes on the first post. On update_post, pass null to remove it." +} - changed
Input schema / properties / x / descriptionPrevious value: -"X (Twitter) options, including thread mode via `thread_parts`."New value: +"X (Twitter) options: thread mode via `thread_parts`, a poll via `poll`." - added
Input schema / properties / x / properties / pollAdded value: +{ + "anyOf": [ + { + "properties": { + "duration_minutes": { + "description": "How long the poll runs, in minutes (5 to 10080 = 7 days). Default 1440 (one day).", + "maximum": 10080, + "minimum": 5, + "type": "integer" + }, + "options": { + "description": "2 to 4 answer options of up to 25 characters, all different.", + "items": { + "maxLength": 25, + "minLength": 1, + "type": "string" + }, + "maxItems": 4, + "minItems": 2, + "type": "array" + } + }, + "required": [ + "options" + ], + "type": "object" + }, + { + "type": "null" + } + ], + "description": "Attach a poll to the tweet; the tweet text is the question. No media on X together with a poll. On a thread the poll goes on the first tweet. On update_post, null removes it." +}
- Changed
update_post7 fields changed- changed
Input schema / properties / mastodon / descriptionPrevious value: -"Mastodon options, including thread mode via `thread_parts`."New value: +"Mastodon options: thread mode via `thread_parts`, a poll via `poll`." - added
Input schema / properties / mastodon / properties / pollAdded value: +{ + "anyOf": [ + { + "properties": { + "expires_in": { + "description": "How long the poll runs, in seconds, within the instance's range (Mastodon's defaults: 5 minutes to 1 month). Default 86400 (one day).", + "maximum": 9007199254740991, + "minimum": 300, + "type": "integer" + }, + "hide_totals": { + "description": "Hide the vote counts until the poll ends.", + "type": "boolean" + }, + "multiple": { + "description": "Allow several answers per person.", + "type": "boolean" + }, + "options": { + "description": "The answer options, all different; count and length within the instance's limits (Mastodon's defaults: 4 options of 50 characters).", + "items": { + "minLength": 1, + "type": "string" + }, + "minItems": 2, + "type": "array" + } + }, + "required": [ + "options" + ], + "type": "object" + }, + { + "type": "null" + } + ], + "description": "Attach a poll to the status; the status text is the question. No media on Mastodon together with a poll. On a thread the poll goes on the first status. On update_post, null removes it." +} - changed
Input schema / properties / threads / descriptionPrevious value: -"Threads options: thread mode via `thread_parts`, location tag via `location_id`."New value: +"Threads options: thread mode via `thread_parts`, location tag via `location_id`, a poll via `poll`, the topic via `topic_tag`." - added
Input schema / properties / threads / properties / pollAdded value: +{ + "anyOf": [ + { + "properties": { + "options": { + "description": "2 to 4 answer options of 1 to 25 characters, all different.", + "items": { + "maxLength": 25, + "minLength": 1, + "type": "string" + }, + "maxItems": 4, + "minItems": 2, + "type": "array" + } + }, + "required": [ + "options" + ], + "type": "object" + }, + { + "type": "null" + } + ], + "description": "Attach a poll to the post; the post text is the question. Threads closes the poll 24 hours after it is published (no duration). Polls go on text-only posts: no media on Threads together with a poll. On a thread the poll goes on the first post. On update_post, null removes it." +} - added
Input schema / properties / threads / properties / topic_tagAdded value: +{ + "anyOf": [ + { + "maxLength": 50, + "type": "string" + }, + { + "type": "null" + } + ], + "description": "The topic of the post on Threads, one per post, e.g. \"Build in public\". Unlike a #tag in the text it can hold spaces. 1 to 50 characters, no period (.) and no ampersand (&); a leading # is dropped. On a multi-post thread the topic goes on the first post. On update_post, pass null to remove it." +} - changed
Input schema / properties / x / descriptionPrevious value: -"X (Twitter) options, including thread mode via `thread_parts`."New value: +"X (Twitter) options: thread mode via `thread_parts`, a poll via `poll`." - added
Input schema / properties / x / properties / pollAdded value: +{ + "anyOf": [ + { + "properties": { + "duration_minutes": { + "description": "How long the poll runs, in minutes (5 to 10080 = 7 days). Default 1440 (one day).", + "maximum": 10080, + "minimum": 5, + "type": "integer" + }, + "options": { + "description": "2 to 4 answer options of up to 25 characters, all different.", + "items": { + "maxLength": 25, + "minLength": 1, + "type": "string" + }, + "maxItems": 4, + "minItems": 2, + "type": "array" + } + }, + "required": [ + "options" + ], + "type": "object" + }, + { + "type": "null" + } + ], + "description": "Attach a poll to the tweet; the tweet text is the question. No media on X together with a poll. On a thread the poll goes on the first tweet. On update_post, null removes it." +}
5 tool updates
- Changed
create_and_publish_post10 fields changed- removed
Input schema / properties / comment_dm_automation / properties / limits / properties / stop_at / anyOfRemoved value: -[ - { - "type": "string" - }, - { - "type": "null" - } -] - added
Input schema / properties / comment_dm_automation / properties / limits / properties / stop_at / typeAdded value: +[ + "string", + "null" +] - changed
Input schema / properties / discord / anyOfPrevious value: -[ - { - "properties": { - "allow_mentions": { - "anyOf": [ - { - "type": "boolean" - }, - { - "type": "null" - } - ], - "description": "true lets @everyone, @here, role and user mentions in the text notify people. Off by default: mentions show as text and ping nobody. Only turn it on when the user asks to ping." - }, - "buttons": { - "anyOf": [ - { - "items": { - "properties": { - "text": { - "description": "Button label (1 to 80 chars).", - "maxLength": 80, - "type": "string" - }, - "url": { - "description": "Link the button opens: https:// or http://.", - "type": "string" - } - }, - "required": [ - "text", - "url" - ], - "type": "object" - }, - "maxItems": 5, - "type": "array" - }, - { - "type": "null" - } - ], - "description": "Up to 5 link buttons in one row under the message. Not with a poll." - }, - "link_preview": { - "anyOf": [ - { - "type": "boolean" - }, - { - "type": "null" - } - ], - "description": "false hides the previews of the links in the text (shown by default)." - }, - "poll": { - "anyOf": [ - { - "properties": { - "duration_hours": { - "description": "Hours the poll stays open (1 to 768, 32 days). Default 24.", - "maximum": 768, - "minimum": 1, - "type": "integer" - }, - "multiple": { - "description": "Allow several answers per person.", - "type": "boolean" - }, - "options": { - "description": "2 to 10 answer options of up to 55 chars, all different.", - "items": { - "maxLength": 55, - "type": "string" - }, - "maxItems": 10, - "minItems": 2, - "type": "array" - } - }, - "required": [ - "options" - ], - "type": "object" - }, - { - "type": "null" - } - ], - "description": "A native Discord poll. The post text is the question (max 300 chars). No media and no buttons with a poll. On update_post, null removes it." - }, - "silent": { - "anyOf": [ - { - "type": "boolean" - }, - { - "type": "null" - } - ], - "description": "Send without a push or desktop notification (Discord's @silent)." - }, - "spoiler": { - "anyOf": [ - { - "type": "boolean" - }, - { - "type": "null" - } - ], - "description": "Blur every image and video until someone clicks it." - }, - "thread_name": { - "anyOf": [ - { - "maxLength": 100, - "type": "string" - }, - { - "type": "null" - } - ], - "description": "The post title in a forum or media channel, where Discord requires one (max 100 chars). Only for those channels: a text channel takes none, so the post goes out there without it (warning thread_name_ignored)." - } - }, - "type": "object" - }, - { - "type": "null" - } -]New value: +[ + { + "properties": { + "allow_mentions": { + "description": "true lets @everyone, @here, role and user mentions in the text notify people. Off by default: mentions show as text and ping nobody. Only turn it on when the user asks to ping.", + "type": [ + "boolean", + "null" + ] + }, + "buttons": { + "anyOf": [ + { + "items": { + "properties": { + "text": { + "description": "Button label (1 to 80 chars).", + "maxLength": 80, + "type": "string" + }, + "url": { + "description": "Link the button opens: https:// or http://.", + "type": "string" + } + }, + "required": [ + "text", + "url" + ], + "type": "object" + }, + "maxItems": 5, + "type": "array" + }, + { + "type": "null" + } + ], + "description": "Up to 5 link buttons in one row under the message. Not with a poll." + }, + "link_preview": { + "description": "false hides the previews of the links in the text (shown by default).", + "type": [ + "boolean", + "null" + ] + }, + "poll": { + "anyOf": [ + { + "properties": { + "duration_hours": { + "description": "Hours the poll stays open (1 to 768, 32 days). Default 24.", + "maximum": 768, + "minimum": 1, + "type": "integer" + }, + "multiple": { + "description": "Allow several answers per person.", + "type": "boolean" + }, + "options": { + "description": "2 to 10 answer options of up to 55 chars, all different.", + "items": { + "maxLength": 55, + "type": "string" + }, + "maxItems": 10, + "minItems": 2, + "type": "array" + } + }, + "required": [ + "options" + ], + "type": "object" + }, + { + "type": "null" + } + ], + "description": "A native Discord poll. The post text is the question (max 300 chars). No media and no buttons with a poll. On update_post, null removes it." + }, + "silent": { + "description": "Send without a push or desktop notification (Discord's @silent).", + "type": [ + "boolean", + "null" + ] + }, + "spoiler": { + "description": "Blur every image and video until someone clicks it.", + "type": [ + "boolean", + "null" + ] + }, + "thread_name": { + "anyOf": [ + { + "maxLength": 100, + "type": "string" + }, + { + "type": "null" + } + ], + "description": "The post title in a forum or media channel, where Discord requires one (max 100 chars). Only for those channels: a text channel takes none, so the post goes out there without it (warning thread_name_ignored)." + } + }, + "type": "object" + }, + { + "type": "null" + } +] - removed
Input schema / properties / linkedin / properties / carousel_as_images / anyOfRemoved value: -[ - { - "type": "boolean" - }, - { - "type": "null" - } -] - added
Input schema / properties / linkedin / properties / carousel_as_images / typeAdded value: +[ + "boolean", + "null" +] - removed
Input schema / properties / linkedin_page / properties / carousel_as_images / anyOfRemoved value: -[ - { - "type": "boolean" - }, - { - "type": "null" - } -] - added
Input schema / properties / linkedin_page / properties / carousel_as_images / typeAdded value: +[ + "boolean", + "null" +] - changed
Input schema / properties / telegram / anyOfPrevious value: -[ - { - "properties": { - "buttons": { - "anyOf": [ - { - "items": { - "properties": { - "text": { - "description": "Button label (max 64 chars).", - "maxLength": 64, - "type": "string" - }, - "url": { - "description": "Link the button opens: https://, http:// or tg://.", - "type": "string" - } - }, - "required": [ - "text", - "url" - ], - "type": "object" - }, - "maxItems": 3, - "type": "array" - }, - { - "type": "null" - } - ], - "description": "Up to 3 link buttons under the post, one per row. Not on an album (2+ media) or a poll." - }, - "caption_above_media": { - "anyOf": [ - { - "type": "boolean" - }, - { - "type": "null" - } - ], - "description": "Show the text above the media instead of below." - }, - "first_comment": { - "description": "A reply the bot sends under the post right after it is published.", - "maxLength": 4096, - "type": "string" - }, - "link_preview": { - "anyOf": [ - { - "type": "boolean" - }, - { - "type": "null" - } - ], - "description": "false hides the link preview of a text-only post (shown by default)." - }, - "pin": { - "anyOf": [ - { - "type": "boolean" - }, - { - "type": "null" - } - ], - "description": "Pin the post in the chat after it is sent. Needs the bot's Edit messages right in a channel (Pin messages in a group); without it the post is sent unpinned." - }, - "poll": { - "anyOf": [ - { - "properties": { - "multiple": { - "description": "Allow several answers per person.", - "type": "boolean" - }, - "open_period": { - "description": "Seconds the poll stays open (5 s to about 30 days). Omit to keep it open.", - "maximum": 2628000, - "minimum": 5, - "type": "integer" - }, - "options": { - "description": "2 to 12 answer options of up to 100 chars, all different.", - "items": { - "maxLength": 100, - "type": "string" - }, - "maxItems": 12, - "minItems": 2, - "type": "array" - } - }, - "required": [ - "options" - ], - "type": "object" - }, - { - "type": "null" - } - ], - "description": "A native Telegram poll. The post text is the question (max 300 chars). No media with a poll. On update_post, null removes it." - }, - "protect_content": { - "anyOf": [ - { - "type": "boolean" - }, - { - "type": "null" - } - ], - "description": "Stop forwarding and saving of the post in Telegram apps." - }, - "silent": { - "anyOf": [ - { - "type": "boolean" - }, - { - "type": "null" - } - ], - "description": "Send without a notification sound." - }, - "spoiler": { - "anyOf": [ - { - "type": "boolean" - }, - { - "type": "null" - } - ], - "description": "Blur the photos and videos until someone taps them." - } - }, - "type": "object" - }, - { - "type": "null" - } -]New value: +[ + { + "properties": { + "buttons": { + "anyOf": [ + { + "items": { + "properties": { + "text": { + "description": "Button label (max 64 chars).", + "maxLength": 64, + "type": "string" + }, + "url": { + "description": "Link the button opens: https://, http:// or tg://.", + "type": "string" + } + }, + "required": [ + "text", + "url" + ], + "type": "object" + }, + "maxItems": 3, + "type": "array" + }, + { + "type": "null" + } + ], + "description": "Up to 3 link buttons under the post, one per row. Not on an album (2+ media) or a poll." + }, + "caption_above_media": { + "description": "Show the text above the media instead of below.", + "type": [ + "boolean", + "null" + ] + }, + "first_comment": { + "description": "A reply the bot sends under the post right after it is published.", + "maxLength": 4096, + "type": "string" + }, + "link_preview": { + "description": "false hides the link preview of a text-only post (shown by default).", + "type": [ + "boolean", + "null" + ] + }, + "pin": { + "description": "Pin the post in the chat after it is sent. Needs the bot's Edit messages right in a channel (Pin messages in a group); without it the post is sent unpinned.", + "type": [ + "boolean", + "null" + ] + }, + "poll": { + "anyOf": [ + { + "properties": { + "multiple": { + "description": "Allow several answers per person.", + "type": "boolean" + }, + "open_period": { + "description": "Seconds the poll stays open (5 s to about 30 days). Omit to keep it open.", + "maximum": 2628000, + "minimum": 5, + "type": "integer" + }, + "options": { + "description": "2 to 12 answer options of up to 100 chars, all different.", + "items": { + "maxLength": 100, + "type": "string" + }, + "maxItems": 12, + "minItems": 2, + "type": "array" + } + }, + "required": [ + "options" + ], + "type": "object" + }, + { + "type": "null" + } + ], + "description": "A native Telegram poll. The post text is the question (max 300 chars). No media with a poll. On update_post, null removes it." + }, + "protect_content": { + "description": "Stop forwarding and saving of the post in Telegram apps.", + "type": [ + "boolean", + "null" + ] + }, + "silent": { + "description": "Send without a notification sound.", + "type": [ + "boolean", + "null" + ] + }, + "spoiler": { + "description": "Blur the photos and videos until someone taps them.", + "type": [ + "boolean", + "null" + ] + } + }, + "type": "object" + }, + { + "type": "null" + } +] - removed
Input schema / properties / threads / properties / location_id / anyOfRemoved value: -[ - { - "type": "string" - }, - { - "type": "null" - } -] - added
Input schema / properties / threads / properties / location_id / typeAdded value: +[ + "string", + "null" +]
- Changed
create_automation2 fields changed- removed
Input schema / properties / stop_at / anyOfRemoved value: -[ - { - "type": "string" - }, - { - "type": "null" - } -] - added
Input schema / properties / stop_at / typeAdded value: +[ + "string", + "null" +]
- Changed
create_post10 fields changed- removed
Input schema / properties / comment_dm_automation / properties / limits / properties / stop_at / anyOfRemoved value: -[ - { - "type": "string" - }, - { - "type": "null" - } -] - added
Input schema / properties / comment_dm_automation / properties / limits / properties / stop_at / typeAdded value: +[ + "string", + "null" +] - changed
Input schema / properties / discord / anyOfPrevious value: -[ - { - "properties": { - "allow_mentions": { - "anyOf": [ - { - "type": "boolean" - }, - { - "type": "null" - } - ], - "description": "true lets @everyone, @here, role and user mentions in the text notify people. Off by default: mentions show as text and ping nobody. Only turn it on when the user asks to ping." - }, - "buttons": { - "anyOf": [ - { - "items": { - "properties": { - "text": { - "description": "Button label (1 to 80 chars).", - "maxLength": 80, - "type": "string" - }, - "url": { - "description": "Link the button opens: https:// or http://.", - "type": "string" - } - }, - "required": [ - "text", - "url" - ], - "type": "object" - }, - "maxItems": 5, - "type": "array" - }, - { - "type": "null" - } - ], - "description": "Up to 5 link buttons in one row under the message. Not with a poll." - }, - "link_preview": { - "anyOf": [ - { - "type": "boolean" - }, - { - "type": "null" - } - ], - "description": "false hides the previews of the links in the text (shown by default)." - }, - "poll": { - "anyOf": [ - { - "properties": { - "duration_hours": { - "description": "Hours the poll stays open (1 to 768, 32 days). Default 24.", - "maximum": 768, - "minimum": 1, - "type": "integer" - }, - "multiple": { - "description": "Allow several answers per person.", - "type": "boolean" - }, - "options": { - "description": "2 to 10 answer options of up to 55 chars, all different.", - "items": { - "maxLength": 55, - "type": "string" - }, - "maxItems": 10, - "minItems": 2, - "type": "array" - } - }, - "required": [ - "options" - ], - "type": "object" - }, - { - "type": "null" - } - ], - "description": "A native Discord poll. The post text is the question (max 300 chars). No media and no buttons with a poll. On update_post, null removes it." - }, - "silent": { - "anyOf": [ - { - "type": "boolean" - }, - { - "type": "null" - } - ], - "description": "Send without a push or desktop notification (Discord's @silent)." - }, - "spoiler": { - "anyOf": [ - { - "type": "boolean" - }, - { - "type": "null" - } - ], - "description": "Blur every image and video until someone clicks it." - }, - "thread_name": { - "anyOf": [ - { - "maxLength": 100, - "type": "string" - }, - { - "type": "null" - } - ], - "description": "The post title in a forum or media channel, where Discord requires one (max 100 chars). Only for those channels: a text channel takes none, so the post goes out there without it (warning thread_name_ignored)." - } - }, - "type": "object" - }, - { - "type": "null" - } -]New value: +[ + { + "properties": { + "allow_mentions": { + "description": "true lets @everyone, @here, role and user mentions in the text notify people. Off by default: mentions show as text and ping nobody. Only turn it on when the user asks to ping.", + "type": [ + "boolean", + "null" + ] + }, + "buttons": { + "anyOf": [ + { + "items": { + "properties": { + "text": { + "description": "Button label (1 to 80 chars).", + "maxLength": 80, + "type": "string" + }, + "url": { + "description": "Link the button opens: https:// or http://.", + "type": "string" + } + }, + "required": [ + "text", + "url" + ], + "type": "object" + }, + "maxItems": 5, + "type": "array" + }, + { + "type": "null" + } + ], + "description": "Up to 5 link buttons in one row under the message. Not with a poll." + }, + "link_preview": { + "description": "false hides the previews of the links in the text (shown by default).", + "type": [ + "boolean", + "null" + ] + }, + "poll": { + "anyOf": [ + { + "properties": { + "duration_hours": { + "description": "Hours the poll stays open (1 to 768, 32 days). Default 24.", + "maximum": 768, + "minimum": 1, + "type": "integer" + }, + "multiple": { + "description": "Allow several answers per person.", + "type": "boolean" + }, + "options": { + "description": "2 to 10 answer options of up to 55 chars, all different.", + "items": { + "maxLength": 55, + "type": "string" + }, + "maxItems": 10, + "minItems": 2, + "type": "array" + } + }, + "required": [ + "options" + ], + "type": "object" + }, + { + "type": "null" + } + ], + "description": "A native Discord poll. The post text is the question (max 300 chars). No media and no buttons with a poll. On update_post, null removes it." + }, + "silent": { + "description": "Send without a push or desktop notification (Discord's @silent).", + "type": [ + "boolean", + "null" + ] + }, + "spoiler": { + "description": "Blur every image and video until someone clicks it.", + "type": [ + "boolean", + "null" + ] + }, + "thread_name": { + "anyOf": [ + { + "maxLength": 100, + "type": "string" + }, + { + "type": "null" + } + ], + "description": "The post title in a forum or media channel, where Discord requires one (max 100 chars). Only for those channels: a text channel takes none, so the post goes out there without it (warning thread_name_ignored)." + } + }, + "type": "object" + }, + { + "type": "null" + } +] - removed
Input schema / properties / linkedin / properties / carousel_as_images / anyOfRemoved value: -[ - { - "type": "boolean" - }, - { - "type": "null" - } -] - added
Input schema / properties / linkedin / properties / carousel_as_images / typeAdded value: +[ + "boolean", + "null" +] - removed
Input schema / properties / linkedin_page / properties / carousel_as_images / anyOfRemoved value: -[ - { - "type": "boolean" - }, - { - "type": "null" - } -] - added
Input schema / properties / linkedin_page / properties / carousel_as_images / typeAdded value: +[ + "boolean", + "null" +] - changed
Input schema / properties / telegram / anyOfPrevious value: -[ - { - "properties": { - "buttons": { - "anyOf": [ - { - "items": { - "properties": { - "text": { - "description": "Button label (max 64 chars).", - "maxLength": 64, - "type": "string" - }, - "url": { - "description": "Link the button opens: https://, http:// or tg://.", - "type": "string" - } - }, - "required": [ - "text", - "url" - ], - "type": "object" - }, - "maxItems": 3, - "type": "array" - }, - { - "type": "null" - } - ], - "description": "Up to 3 link buttons under the post, one per row. Not on an album (2+ media) or a poll." - }, - "caption_above_media": { - "anyOf": [ - { - "type": "boolean" - }, - { - "type": "null" - } - ], - "description": "Show the text above the media instead of below." - }, - "first_comment": { - "description": "A reply the bot sends under the post right after it is published.", - "maxLength": 4096, - "type": "string" - }, - "link_preview": { - "anyOf": [ - { - "type": "boolean" - }, - { - "type": "null" - } - ], - "description": "false hides the link preview of a text-only post (shown by default)." - }, - "pin": { - "anyOf": [ - { - "type": "boolean" - }, - { - "type": "null" - } - ], - "description": "Pin the post in the chat after it is sent. Needs the bot's Edit messages right in a channel (Pin messages in a group); without it the post is sent unpinned." - }, - "poll": { - "anyOf": [ - { - "properties": { - "multiple": { - "description": "Allow several answers per person.", - "type": "boolean" - }, - "open_period": { - "description": "Seconds the poll stays open (5 s to about 30 days). Omit to keep it open.", - "maximum": 2628000, - "minimum": 5, - "type": "integer" - }, - "options": { - "description": "2 to 12 answer options of up to 100 chars, all different.", - "items": { - "maxLength": 100, - "type": "string" - }, - "maxItems": 12, - "minItems": 2, - "type": "array" - } - }, - "required": [ - "options" - ], - "type": "object" - }, - { - "type": "null" - } - ], - "description": "A native Telegram poll. The post text is the question (max 300 chars). No media with a poll. On update_post, null removes it." - }, - "protect_content": { - "anyOf": [ - { - "type": "boolean" - }, - { - "type": "null" - } - ], - "description": "Stop forwarding and saving of the post in Telegram apps." - }, - "silent": { - "anyOf": [ - { - "type": "boolean" - }, - { - "type": "null" - } - ], - "description": "Send without a notification sound." - }, - "spoiler": { - "anyOf": [ - { - "type": "boolean" - }, - { - "type": "null" - } - ], - "description": "Blur the photos and videos until someone taps them." - } - }, - "type": "object" - }, - { - "type": "null" - } -]New value: +[ + { + "properties": { + "buttons": { + "anyOf": [ + { + "items": { + "properties": { + "text": { + "description": "Button label (max 64 chars).", + "maxLength": 64, + "type": "string" + }, + "url": { + "description": "Link the button opens: https://, http:// or tg://.", + "type": "string" + } + }, + "required": [ + "text", + "url" + ], + "type": "object" + }, + "maxItems": 3, + "type": "array" + }, + { + "type": "null" + } + ], + "description": "Up to 3 link buttons under the post, one per row. Not on an album (2+ media) or a poll." + }, + "caption_above_media": { + "description": "Show the text above the media instead of below.", + "type": [ + "boolean", + "null" + ] + }, + "first_comment": { + "description": "A reply the bot sends under the post right after it is published.", + "maxLength": 4096, + "type": "string" + }, + "link_preview": { + "description": "false hides the link preview of a text-only post (shown by default).", + "type": [ + "boolean", + "null" + ] + }, + "pin": { + "description": "Pin the post in the chat after it is sent. Needs the bot's Edit messages right in a channel (Pin messages in a group); without it the post is sent unpinned.", + "type": [ + "boolean", + "null" + ] + }, + "poll": { + "anyOf": [ + { + "properties": { + "multiple": { + "description": "Allow several answers per person.", + "type": "boolean" + }, + "open_period": { + "description": "Seconds the poll stays open (5 s to about 30 days). Omit to keep it open.", + "maximum": 2628000, + "minimum": 5, + "type": "integer" + }, + "options": { + "description": "2 to 12 answer options of up to 100 chars, all different.", + "items": { + "maxLength": 100, + "type": "string" + }, + "maxItems": 12, + "minItems": 2, + "type": "array" + } + }, + "required": [ + "options" + ], + "type": "object" + }, + { + "type": "null" + } + ], + "description": "A native Telegram poll. The post text is the question (max 300 chars). No media with a poll. On update_post, null removes it." + }, + "protect_content": { + "description": "Stop forwarding and saving of the post in Telegram apps.", + "type": [ + "boolean", + "null" + ] + }, + "silent": { + "description": "Send without a notification sound.", + "type": [ + "boolean", + "null" + ] + }, + "spoiler": { + "description": "Blur the photos and videos until someone taps them.", + "type": [ + "boolean", + "null" + ] + } + }, + "type": "object" + }, + { + "type": "null" + } +] - removed
Input schema / properties / threads / properties / location_id / anyOfRemoved value: -[ - { - "type": "string" - }, - { - "type": "null" - } -] - added
Input schema / properties / threads / properties / location_id / typeAdded value: +[ + "string", + "null" +]
- Changed
update_automation2 fields changed- removed
Input schema / properties / stop_at / anyOfRemoved value: -[ - { - "type": "string" - }, - { - "type": "null" - } -] - added
Input schema / properties / stop_at / typeAdded value: +[ + "string", + "null" +]
- Changed
update_post9 fields changed- changed
Input schema / properties / comment_dm_automation / anyOfPrevious value: -[ - { - "description": "Comment-to-DM automation on this post: when somebody comments one of trigger.keywords on the post once it is live on Instagram or the Facebook Page, the account DMs them actions.dm.text once (on Facebook the DM lands in Messenger), and optionally posts one of actions.public_reply.variations under the comment. Instagram or Facebook must be in channels; platforms picks which ones get it. Show the user the keywords and the exact DM text before creating it. The created automations come back as comment_dm_automation on the post (automations lists the id of each channel); manage them later with update_automation / get_automation_activity.", - "properties": { - "actions": { - "properties": { - "dm": { - "properties": { - "text": { - "description": "The DM the person receives, once (max 1000 characters). Confirm the text with the user: it goes out in their name.", - "maxLength": 1000, - "type": "string" - } - }, - "required": [ - "text" - ], - "type": "object" - }, - "public_reply": { - "properties": { - "enabled": { - "type": "boolean" - }, - "variations": { - "description": "Public replies posted under the comment, one picked at random per comment.", - "items": { - "maxLength": 300, - "type": "string" - }, - "maxItems": 10, - "type": "array" - } - }, - "type": "object" - } - }, - "required": [ - "dm" - ], - "type": "object" - }, - "limits": { - "properties": { - "max_sends": { - "anyOf": [ - { - "exclusiveMinimum": 0, - "maximum": 9007199254740991, - "type": "integer" - }, - { - "type": "null" - } - ], - "description": "Stop after this many DMs." - }, - "stop_at": { - "anyOf": [ - { - "type": "string" - }, - { - "type": "null" - } - ], - "description": "Stop at this time (ISO 8601)." - } - }, - "type": "object" - }, - "platforms": { - "description": "The channels that get the automation: 'instagram', 'facebook' (the Facebook Page; the DM lands in Messenger) or both. One automation per channel, each with the same keywords, DM, public reply and limits. Each one must be in channels. Omit it for one automation: Instagram when the post goes there, else Facebook.", - "items": { - "enum": [ - "instagram", - "facebook" - ], - "type": "string" - }, - "minItems": 1, - "type": "array" - }, - "trigger": { - "properties": { - "keywords": { - "description": "Keywords that start the automation, matched case-insensitively (up to 20). Required unless match is 'any'.", - "items": { - "type": "string" - }, - "maxItems": 20, - "type": "array" - }, - "match": { - "description": "word (default): the keyword stands on its own. contains: anywhere in the comment. any: every comment (ask the user first).", - "enum": [ - "word", - "contains", - "any" - ], - "type": "string" - } - }, - "type": "object" - } - }, - "required": [ - "actions" - ], - "type": "object" - }, - { - "type": "null" - } -]New value: +[ + { + "description": "Comment-to-DM automation on this post: when somebody comments one of trigger.keywords on the post once it is live on Instagram or the Facebook Page, the account DMs them actions.dm.text once (on Facebook the DM lands in Messenger), and optionally posts one of actions.public_reply.variations under the comment. Instagram or Facebook must be in channels; platforms picks which ones get it. Show the user the keywords and the exact DM text before creating it. The created automations come back as comment_dm_automation on the post (automations lists the id of each channel); manage them later with update_automation / get_automation_activity.", + "properties": { + "actions": { + "properties": { + "dm": { + "properties": { + "text": { + "description": "The DM the person receives, once (max 1000 characters). Confirm the text with the user: it goes out in their name.", + "maxLength": 1000, + "type": "string" + } + }, + "required": [ + "text" + ], + "type": "object" + }, + "public_reply": { + "properties": { + "enabled": { + "type": "boolean" + }, + "variations": { + "description": "Public replies posted under the comment, one picked at random per comment.", + "items": { + "maxLength": 300, + "type": "string" + }, + "maxItems": 10, + "type": "array" + } + }, + "type": "object" + } + }, + "required": [ + "dm" + ], + "type": "object" + }, + "limits": { + "properties": { + "max_sends": { + "anyOf": [ + { + "exclusiveMinimum": 0, + "maximum": 9007199254740991, + "type": "integer" + }, + { + "type": "null" + } + ], + "description": "Stop after this many DMs." + }, + "stop_at": { + "description": "Stop at this time (ISO 8601).", + "type": [ + "string", + "null" + ] + } + }, + "type": "object" + }, + "platforms": { + "description": "The channels that get the automation: 'instagram', 'facebook' (the Facebook Page; the DM lands in Messenger) or both. One automation per channel, each with the same keywords, DM, public reply and limits. Each one must be in channels. Omit it for one automation: Instagram when the post goes there, else Facebook.", + "items": { + "enum": [ + "instagram", + "facebook" + ], + "type": "string" + }, + "minItems": 1, + "type": "array" + }, + "trigger": { + "properties": { + "keywords": { + "description": "Keywords that start the automation, matched case-insensitively (up to 20). Required unless match is 'any'.", + "items": { + "type": "string" + }, + "maxItems": 20, + "type": "array" + }, + "match": { + "description": "word (default): the keyword stands on its own. contains: anywhere in the comment. any: every comment (ask the user first).", + "enum": [ + "word", + "contains", + "any" + ], + "type": "string" + } + }, + "type": "object" + } + }, + "required": [ + "actions" + ], + "type": "object" + }, + { + "type": "null" + } +] - changed
Input schema / properties / discord / anyOfPrevious value: -[ - { - "properties": { - "allow_mentions": { - "anyOf": [ - { - "type": "boolean" - }, - { - "type": "null" - } - ], - "description": "true lets @everyone, @here, role and user mentions in the text notify people. Off by default: mentions show as text and ping nobody. Only turn it on when the user asks to ping." - }, - "buttons": { - "anyOf": [ - { - "items": { - "properties": { - "text": { - "description": "Button label (1 to 80 chars).", - "maxLength": 80, - "type": "string" - }, - "url": { - "description": "Link the button opens: https:// or http://.", - "type": "string" - } - }, - "required": [ - "text", - "url" - ], - "type": "object" - }, - "maxItems": 5, - "type": "array" - }, - { - "type": "null" - } - ], - "description": "Up to 5 link buttons in one row under the message. Not with a poll." - }, - "link_preview": { - "anyOf": [ - { - "type": "boolean" - }, - { - "type": "null" - } - ], - "description": "false hides the previews of the links in the text (shown by default)." - }, - "poll": { - "anyOf": [ - { - "properties": { - "duration_hours": { - "description": "Hours the poll stays open (1 to 768, 32 days). Default 24.", - "maximum": 768, - "minimum": 1, - "type": "integer" - }, - "multiple": { - "description": "Allow several answers per person.", - "type": "boolean" - }, - "options": { - "description": "2 to 10 answer options of up to 55 chars, all different.", - "items": { - "maxLength": 55, - "type": "string" - }, - "maxItems": 10, - "minItems": 2, - "type": "array" - } - }, - "required": [ - "options" - ], - "type": "object" - }, - { - "type": "null" - } - ], - "description": "A native Discord poll. The post text is the question (max 300 chars). No media and no buttons with a poll. On update_post, null removes it." - }, - "silent": { - "anyOf": [ - { - "type": "boolean" - }, - { - "type": "null" - } - ], - "description": "Send without a push or desktop notification (Discord's @silent)." - }, - "spoiler": { - "anyOf": [ - { - "type": "boolean" - }, - { - "type": "null" - } - ], - "description": "Blur every image and video until someone clicks it." - }, - "thread_name": { - "anyOf": [ - { - "maxLength": 100, - "type": "string" - }, - { - "type": "null" - } - ], - "description": "The post title in a forum or media channel, where Discord requires one (max 100 chars). Only for those channels: a text channel takes none, so the post goes out there without it (warning thread_name_ignored)." - } - }, - "type": "object" - }, - { - "type": "null" - } -]New value: +[ + { + "properties": { + "allow_mentions": { + "description": "true lets @everyone, @here, role and user mentions in the text notify people. Off by default: mentions show as text and ping nobody. Only turn it on when the user asks to ping.", + "type": [ + "boolean", + "null" + ] + }, + "buttons": { + "anyOf": [ + { + "items": { + "properties": { + "text": { + "description": "Button label (1 to 80 chars).", + "maxLength": 80, + "type": "string" + }, + "url": { + "description": "Link the button opens: https:// or http://.", + "type": "string" + } + }, + "required": [ + "text", + "url" + ], + "type": "object" + }, + "maxItems": 5, + "type": "array" + }, + { + "type": "null" + } + ], + "description": "Up to 5 link buttons in one row under the message. Not with a poll." + }, + "link_preview": { + "description": "false hides the previews of the links in the text (shown by default).", + "type": [ + "boolean", + "null" + ] + }, + "poll": { + "anyOf": [ + { + "properties": { + "duration_hours": { + "description": "Hours the poll stays open (1 to 768, 32 days). Default 24.", + "maximum": 768, + "minimum": 1, + "type": "integer" + }, + "multiple": { + "description": "Allow several answers per person.", + "type": "boolean" + }, + "options": { + "description": "2 to 10 answer options of up to 55 chars, all different.", + "items": { + "maxLength": 55, + "type": "string" + }, + "maxItems": 10, + "minItems": 2, + "type": "array" + } + }, + "required": [ + "options" + ], + "type": "object" + }, + { + "type": "null" + } + ], + "description": "A native Discord poll. The post text is the question (max 300 chars). No media and no buttons with a poll. On update_post, null removes it." + }, + "silent": { + "description": "Send without a push or desktop notification (Discord's @silent).", + "type": [ + "boolean", + "null" + ] + }, + "spoiler": { + "description": "Blur every image and video until someone clicks it.", + "type": [ + "boolean", + "null" + ] + }, + "thread_name": { + "anyOf": [ + { + "maxLength": 100, + "type": "string" + }, + { + "type": "null" + } + ], + "description": "The post title in a forum or media channel, where Discord requires one (max 100 chars). Only for those channels: a text channel takes none, so the post goes out there without it (warning thread_name_ignored)." + } + }, + "type": "object" + }, + { + "type": "null" + } +] - removed
Input schema / properties / linkedin / properties / carousel_as_images / anyOfRemoved value: -[ - { - "type": "boolean" - }, - { - "type": "null" - } -] - added
Input schema / properties / linkedin / properties / carousel_as_images / typeAdded value: +[ + "boolean", + "null" +] - removed
Input schema / properties / linkedin_page / properties / carousel_as_images / anyOfRemoved value: -[ - { - "type": "boolean" - }, - { - "type": "null" - } -] - added
Input schema / properties / linkedin_page / properties / carousel_as_images / typeAdded value: +[ + "boolean", + "null" +] - changed
Input schema / properties / telegram / anyOfPrevious value: -[ - { - "properties": { - "buttons": { - "anyOf": [ - { - "items": { - "properties": { - "text": { - "description": "Button label (max 64 chars).", - "maxLength": 64, - "type": "string" - }, - "url": { - "description": "Link the button opens: https://, http:// or tg://.", - "type": "string" - } - }, - "required": [ - "text", - "url" - ], - "type": "object" - }, - "maxItems": 3, - "type": "array" - }, - { - "type": "null" - } - ], - "description": "Up to 3 link buttons under the post, one per row. Not on an album (2+ media) or a poll." - }, - "caption_above_media": { - "anyOf": [ - { - "type": "boolean" - }, - { - "type": "null" - } - ], - "description": "Show the text above the media instead of below." - }, - "first_comment": { - "description": "A reply the bot sends under the post right after it is published.", - "maxLength": 4096, - "type": "string" - }, - "link_preview": { - "anyOf": [ - { - "type": "boolean" - }, - { - "type": "null" - } - ], - "description": "false hides the link preview of a text-only post (shown by default)." - }, - "pin": { - "anyOf": [ - { - "type": "boolean" - }, - { - "type": "null" - } - ], - "description": "Pin the post in the chat after it is sent. Needs the bot's Edit messages right in a channel (Pin messages in a group); without it the post is sent unpinned." - }, - "poll": { - "anyOf": [ - { - "properties": { - "multiple": { - "description": "Allow several answers per person.", - "type": "boolean" - }, - "open_period": { - "description": "Seconds the poll stays open (5 s to about 30 days). Omit to keep it open.", - "maximum": 2628000, - "minimum": 5, - "type": "integer" - }, - "options": { - "description": "2 to 12 answer options of up to 100 chars, all different.", - "items": { - "maxLength": 100, - "type": "string" - }, - "maxItems": 12, - "minItems": 2, - "type": "array" - } - }, - "required": [ - "options" - ], - "type": "object" - }, - { - "type": "null" - } - ], - "description": "A native Telegram poll. The post text is the question (max 300 chars). No media with a poll. On update_post, null removes it." - }, - "protect_content": { - "anyOf": [ - { - "type": "boolean" - }, - { - "type": "null" - } - ], - "description": "Stop forwarding and saving of the post in Telegram apps." - }, - "silent": { - "anyOf": [ - { - "type": "boolean" - }, - { - "type": "null" - } - ], - "description": "Send without a notification sound." - }, - "spoiler": { - "anyOf": [ - { - "type": "boolean" - }, - { - "type": "null" - } - ], - "description": "Blur the photos and videos until someone taps them." - } - }, - "type": "object" - }, - { - "type": "null" - } -]New value: +[ + { + "properties": { + "buttons": { + "anyOf": [ + { + "items": { + "properties": { + "text": { + "description": "Button label (max 64 chars).", + "maxLength": 64, + "type": "string" + }, + "url": { + "description": "Link the button opens: https://, http:// or tg://.", + "type": "string" + } + }, + "required": [ + "text", + "url" + ], + "type": "object" + }, + "maxItems": 3, + "type": "array" + }, + { + "type": "null" + } + ], + "description": "Up to 3 link buttons under the post, one per row. Not on an album (2+ media) or a poll." + }, + "caption_above_media": { + "description": "Show the text above the media instead of below.", + "type": [ + "boolean", + "null" + ] + }, + "first_comment": { + "description": "A reply the bot sends under the post right after it is published.", + "maxLength": 4096, + "type": "string" + }, + "link_preview": { + "description": "false hides the link preview of a text-only post (shown by default).", + "type": [ + "boolean", + "null" + ] + }, + "pin": { + "description": "Pin the post in the chat after it is sent. Needs the bot's Edit messages right in a channel (Pin messages in a group); without it the post is sent unpinned.", + "type": [ + "boolean", + "null" + ] + }, + "poll": { + "anyOf": [ + { + "properties": { + "multiple": { + "description": "Allow several answers per person.", + "type": "boolean" + }, + "open_period": { + "description": "Seconds the poll stays open (5 s to about 30 days). Omit to keep it open.", + "maximum": 2628000, + "minimum": 5, + "type": "integer" + }, + "options": { + "description": "2 to 12 answer options of up to 100 chars, all different.", + "items": { + "maxLength": 100, + "type": "string" + }, + "maxItems": 12, + "minItems": 2, + "type": "array" + } + }, + "required": [ + "options" + ], + "type": "object" + }, + { + "type": "null" + } + ], + "description": "A native Telegram poll. The post text is the question (max 300 chars). No media with a poll. On update_post, null removes it." + }, + "protect_content": { + "description": "Stop forwarding and saving of the post in Telegram apps.", + "type": [ + "boolean", + "null" + ] + }, + "silent": { + "description": "Send without a notification sound.", + "type": [ + "boolean", + "null" + ] + }, + "spoiler": { + "description": "Blur the photos and videos until someone taps them.", + "type": [ + "boolean", + "null" + ] + } + }, + "type": "object" + }, + { + "type": "null" + } +] - removed
Input schema / properties / threads / properties / location_id / anyOfRemoved value: -[ - { - "type": "string" - }, - { - "type": "null" - } -] - added
Input schema / properties / threads / properties / location_id / typeAdded value: +[ + "string", + "null" +]
4 tool updates
- Changed
create_automation8 fields changed- changed
Input schema / properties / dm_text / descriptionPrevious value: -"The DM sent to the person (max 1000 characters), once per person. On Facebook it lands in Messenger. Required on create. Confirm the text with the user before creating the automation: it goes out in the account's name."New value: +"The DM sent to the person (max 1000 characters), once per person. On Facebook it lands in Messenger. On X, OmniSocials adds the line 'Reply STOP to stop automatic messages.' under it. Required on create. Confirm the text with the user before creating the automation: it goes out in the account's name." - changed
Input schema / properties / platform / descriptionPrevious value: -"Where the automation runs: 'instagram' (default) = the connected Instagram account, 'facebook' = the connected Facebook Page (the DM lands in Messenger). instagram_media_id implies 'instagram', facebook_post_id implies 'facebook'. It cannot change after create."New value: +"Where the automation runs: 'instagram' (default) = the connected Instagram account, 'facebook' = the connected Facebook Page (the DM lands in Messenger), 'x' = the connected X account (it answers DMs only; see create_automation). instagram_media_id implies 'instagram', facebook_post_id implies 'facebook'. It cannot change after create." - changed
Input schema / properties / platform / enumPrevious value: -[ - "instagram", - "facebook" -]New value: +[ + "instagram", + "facebook", + "x" +] - changed
Input schema / properties / post_id / descriptionPrevious value: -"For scope 'post': the OmniSocials post id (from list_posts) that goes to the automation's platform. A scheduled post starts listening once it is live. One automation per post and platform: a post that goes to Instagram and Facebook can have one of each."New value: +"For scope 'post' (Instagram and Facebook): the OmniSocials post id (from list_posts) that goes to the automation's platform. A scheduled post starts listening once it is live. One automation per post and platform: a post that goes to Instagram and Facebook can have one of each." - changed
Input schema / properties / public_replies / descriptionPrevious value: -"Optional public replies posted under the comment (one is picked at random per comment), e.g. [\"Sent you a DM!\", \"Check your inbox\"]. Comment trigger only. An empty array turns the public reply off."New value: +"Optional public replies posted under the comment (one is picked at random per comment), e.g. [\"Sent you a DM!\", \"Check your inbox\"]. Comment trigger only (Instagram and Facebook; X has none). An empty array turns the public reply off." - changed
Input schema / properties / scope / descriptionPrevious value: -"For the comment trigger: 'post' (default) = one post (pass post_id, instagram_media_id or facebook_post_id), 'next_post' = the next post the workspace publishes on this platform, 'any' = every post of the account or Page."New value: +"For the comment trigger (Instagram and Facebook; an X automation has no post): 'post' (default) = one post (pass post_id, instagram_media_id or facebook_post_id), 'next_post' = the next post the workspace publishes on this platform, 'any' = every post of the account or Page." - added
Input schema / properties / statusAdded value: +{ + "description": "'paused' creates it without turning it on (default 'active'). A paused X automation saves even while X DMs are off; turn it on later with update_automation.", + "enum": [ + "active", + "paused" + ], + "type": "string" +} - changed
Input schema / properties / triggers / descriptionPrevious value: -"What starts the automation. 'comment' (default) = a comment on an Instagram post or reel, or on a Facebook Page post; 'dm' = a keyword in a DM to the Instagram account, or in a Messenger message to the Facebook Page; 'story_reply' = a keyword in a reply to an Instagram story (Instagram only: Facebook has no story replies). One automation can listen to several."New value: +"What starts the automation. 'comment' (default on Instagram and Facebook) = a comment on an Instagram post or reel, or on a Facebook Page post; 'dm' = a keyword in a DM to the Instagram account, in a Messenger message to the Facebook Page, or in a DM to the X account; 'story_reply' = a keyword in a reply to an Instagram story (Instagram only: Facebook has no story replies). On X only 'dm' exists, and it is the default there. One automation can listen to several."
- Changed
get_automation_activity1 field changed- changed
Input schema / properties / outcome / enumPrevious value: -[ - "sent", - "skipped", - "failed", - "pending" -]New value: +[ + "sent", + "skipped", + "failed", + "pending", + "queued", + "opted_out" +]
- Changed
list_automations1 field changed- changed
Input schema / properties / platform / enumPrevious value: -[ - "instagram", - "facebook" -]New value: +[ + "instagram", + "facebook", + "x" +]
- Changed
update_automation8 fields changed- changed
Input schema / properties / dm_text / descriptionPrevious value: -"The DM sent to the person (max 1000 characters), once per person. On Facebook it lands in Messenger. Required on create. Confirm the text with the user before creating the automation: it goes out in the account's name."New value: +"The DM sent to the person (max 1000 characters), once per person. On Facebook it lands in Messenger. On X, OmniSocials adds the line 'Reply STOP to stop automatic messages.' under it. Required on create. Confirm the text with the user before creating the automation: it goes out in the account's name." - changed
Input schema / properties / platform / descriptionPrevious value: -"Where the automation runs: 'instagram' (default) = the connected Instagram account, 'facebook' = the connected Facebook Page (the DM lands in Messenger). instagram_media_id implies 'instagram', facebook_post_id implies 'facebook'. It cannot change after create."New value: +"Where the automation runs: 'instagram' (default) = the connected Instagram account, 'facebook' = the connected Facebook Page (the DM lands in Messenger), 'x' = the connected X account (it answers DMs only; see create_automation). instagram_media_id implies 'instagram', facebook_post_id implies 'facebook'. It cannot change after create." - changed
Input schema / properties / platform / enumPrevious value: -[ - "instagram", - "facebook" -]New value: +[ + "instagram", + "facebook", + "x" +] - changed
Input schema / properties / post_id / descriptionPrevious value: -"For scope 'post': the OmniSocials post id (from list_posts) that goes to the automation's platform. A scheduled post starts listening once it is live. One automation per post and platform: a post that goes to Instagram and Facebook can have one of each."New value: +"For scope 'post' (Instagram and Facebook): the OmniSocials post id (from list_posts) that goes to the automation's platform. A scheduled post starts listening once it is live. One automation per post and platform: a post that goes to Instagram and Facebook can have one of each." - changed
Input schema / properties / public_replies / descriptionPrevious value: -"Optional public replies posted under the comment (one is picked at random per comment), e.g. [\"Sent you a DM!\", \"Check your inbox\"]. Comment trigger only. An empty array turns the public reply off."New value: +"Optional public replies posted under the comment (one is picked at random per comment), e.g. [\"Sent you a DM!\", \"Check your inbox\"]. Comment trigger only (Instagram and Facebook; X has none). An empty array turns the public reply off." - changed
Input schema / properties / scope / descriptionPrevious value: -"For the comment trigger: 'post' (default) = one post (pass post_id, instagram_media_id or facebook_post_id), 'next_post' = the next post the workspace publishes on this platform, 'any' = every post of the account or Page."New value: +"For the comment trigger (Instagram and Facebook; an X automation has no post): 'post' (default) = one post (pass post_id, instagram_media_id or facebook_post_id), 'next_post' = the next post the workspace publishes on this platform, 'any' = every post of the account or Page." - changed
Input schema / properties / status / descriptionPrevious value: -"'paused' stops it without deleting it; 'active' resumes it."New value: +"'paused' stops it without deleting it; 'active' resumes it (on X only while X DMs are on for the workspace)." - changed
Input schema / properties / triggers / descriptionPrevious value: -"What starts the automation. 'comment' (default) = a comment on an Instagram post or reel, or on a Facebook Page post; 'dm' = a keyword in a DM to the Instagram account, or in a Messenger message to the Facebook Page; 'story_reply' = a keyword in a reply to an Instagram story (Instagram only: Facebook has no story replies). One automation can listen to several."New value: +"What starts the automation. 'comment' (default on Instagram and Facebook) = a comment on an Instagram post or reel, or on a Facebook Page post; 'dm' = a keyword in a DM to the Instagram account, in a Messenger message to the Facebook Page, or in a DM to the X account; 'story_reply' = a keyword in a reply to an Instagram story (Instagram only: Facebook has no story replies). On X only 'dm' exists, and it is the default there. One automation can listen to several."
7 tool updates
- Changed
create_and_publish_post3 fields changed- changed
Input schema / properties / comment_dm_automation / descriptionPrevious value: -"Comment-to-DM automation on this post: when somebody comments one of trigger.keywords on the post once it is live on Instagram, the account DMs them actions.dm.text once, and optionally posts one of actions.public_reply.variations under the comment. Instagram must be in channels. Show the user the keywords and the exact DM text before creating it. The created automation comes back as comment_dm_automation on the post; manage it later with update_automation / get_automation_activity."New value: +"Comment-to-DM automation on this post: when somebody comments one of trigger.keywords on the post once it is live on Instagram or the Facebook Page, the account DMs them actions.dm.text once (on Facebook the DM lands in Messenger), and optionally posts one of actions.public_reply.variations under the comment. Instagram or Facebook must be in channels; platforms picks which ones get it. Show the user the keywords and the exact DM text before creating it. The created automations come back as comment_dm_automation on the post (automations lists the id of each channel); manage them later with update_automation / get_automation_activity." - added
Input schema / properties / comment_dm_automation / properties / platformsAdded value: +{ + "description": "The channels that get the automation: 'instagram', 'facebook' (the Facebook Page; the DM lands in Messenger) or both. One automation per channel, each with the same keywords, DM, public reply and limits. Each one must be in channels. Omit it for one automation: Instagram when the post goes there, else Facebook.", + "items": { + "enum": [ + "instagram", + "facebook" + ], + "type": "string" + }, + "minItems": 1, + "type": "array" +} - added
Input schema / properties / discordAdded value: +{ + "anyOf": [ + { + "properties": { + "allow_mentions": { + "anyOf": [ + { + "type": "boolean" + }, + { + "type": "null" + } + ], + "description": "true lets @everyone, @here, role and user mentions in the text notify people. Off by default: mentions show as text and ping nobody. Only turn it on when the user asks to ping." + }, + "buttons": { + "anyOf": [ + { + "items": { + "properties": { + "text": { + "description": "Button label (1 to 80 chars).", + "maxLength": 80, + "type": "string" + }, + "url": { + "description": "Link the button opens: https:// or http://.", + "type": "string" + } + }, + "required": [ + "text", + "url" + ], + "type": "object" + }, + "maxItems": 5, + "type": "array" + }, + { + "type": "null" + } + ], + "description": "Up to 5 link buttons in one row under the message. Not with a poll." + }, + "link_preview": { + "anyOf": [ + { + "type": "boolean" + }, + { + "type": "null" + } + ], + "description": "false hides the previews of the links in the text (shown by default)." + }, + "poll": { + "anyOf": [ + { + "properties": { + "duration_hours": { + "description": "Hours the poll stays open (1 to 768, 32 days). Default 24.", + "maximum": 768, + "minimum": 1, + "type": "integer" + }, + "multiple": { + "description": "Allow several answers per person.", + "type": "boolean" + }, + "options": { + "description": "2 to 10 answer options of up to 55 chars, all different.", + "items": { + "maxLength": 55, + "type": "string" + }, + "maxItems": 10, + "minItems": 2, + "type": "array" + } + }, + "required": [ + "options" + ], + "type": "object" + }, + { + "type": "null" + } + ], + "description": "A native Discord poll. The post text is the question (max 300 chars). No media and no buttons with a poll. On update_post, null removes it." + }, + "silent": { + "anyOf": [ + { + "type": "boolean" + }, + { + "type": "null" + } + ], + "description": "Send without a push or desktop notification (Discord's @silent)." + }, + "spoiler": { + "anyOf": [ + { + "type": "boolean" + }, + { + "type": "null" + } + ], + "description": "Blur every image and video until someone clicks it." + }, + "thread_name": { + "anyOf": [ + { + "maxLength": 100, + "type": "string" + }, + { + "type": "null" + } + ], + "description": "The post title in a forum or media channel, where Discord requires one (max 100 chars). Only for those channels: a text channel takes none, so the post goes out there without it (warning thread_name_ignored)." + } + }, + "type": "object" + }, + { + "type": "null" + } + ], + "description": "Discord options. The post goes to the connected Discord channel through its webhook and shows the webhook's name and picture. Text up to 2,000 chars. Up to 10 images, GIFs and videos per message (they may mix); a video or GIF over Discord's 20 MB file limit is sent as a link in the text. No Stories; a 'reel' is sent as one video message." +}
- Changed
create_automation7 fields changed- changed
Input schema / properties / dm_text / descriptionPrevious value: -"The DM sent to the person (max 1000 characters), once per person. Required on create. Confirm the text with the user before creating the automation: it goes out in the account's name."New value: +"The DM sent to the person (max 1000 characters), once per person. On Facebook it lands in Messenger. Required on create. Confirm the text with the user before creating the automation: it goes out in the account's name." - added
Input schema / properties / facebook_post_idAdded value: +{ + "description": "For scope 'post' on Facebook: the id of a Facebook Page post that was NOT published through OmniSocials ({page-id}_{post-id}, or the post id alone). OmniSocials reads it from Facebook to check it belongs to the connected Page. Implies platform 'facebook'. Pass only one of post_id, instagram_media_id or facebook_post_id.", + "type": "string" +} - changed
Input schema / properties / instagram_media_id / descriptionPrevious value: -"For scope 'post': the numeric Instagram media id of a post or reel that was NOT published through OmniSocials. OmniSocials reads it from Instagram to check it belongs to the connected account. Pass post_id OR instagram_media_id."New value: +"For scope 'post' on Instagram: the numeric Instagram media id of a post or reel that was NOT published through OmniSocials. OmniSocials reads it from Instagram to check it belongs to the connected account. Pass only one of post_id, instagram_media_id or facebook_post_id." - added
Input schema / properties / platformAdded value: +{ + "description": "Where the automation runs: 'instagram' (default) = the connected Instagram account, 'facebook' = the connected Facebook Page (the DM lands in Messenger). instagram_media_id implies 'instagram', facebook_post_id implies 'facebook'. It cannot change after create.", + "enum": [ + "instagram", + "facebook" + ], + "type": "string" +} - changed
Input schema / properties / post_id / descriptionPrevious value: -"For scope 'post': the OmniSocials post id (from list_posts) that goes to Instagram. A scheduled post starts listening once it is live. One automation per post."New value: +"For scope 'post': the OmniSocials post id (from list_posts) that goes to the automation's platform. A scheduled post starts listening once it is live. One automation per post and platform: a post that goes to Instagram and Facebook can have one of each." - changed
Input schema / properties / scope / descriptionPrevious value: -"For the comment trigger: 'post' (default) = one post (pass post_id or instagram_media_id), 'next_post' = the next Instagram post the workspace publishes, 'any' = every post of the account."New value: +"For the comment trigger: 'post' (default) = one post (pass post_id, instagram_media_id or facebook_post_id), 'next_post' = the next post the workspace publishes on this platform, 'any' = every post of the account or Page." - changed
Input schema / properties / triggers / descriptionPrevious value: -"What starts the automation. 'comment' (default) = a comment on an Instagram post or reel; 'dm' = a keyword in a DM to the account; 'story_reply' = a keyword in a reply to a story. One automation can listen to several."New value: +"What starts the automation. 'comment' (default) = a comment on an Instagram post or reel, or on a Facebook Page post; 'dm' = a keyword in a DM to the Instagram account, or in a Messenger message to the Facebook Page; 'story_reply' = a keyword in a reply to an Instagram story (Instagram only: Facebook has no story replies). One automation can listen to several."
- Changed
create_post3 fields changed- changed
Input schema / properties / comment_dm_automation / descriptionPrevious value: -"Comment-to-DM automation on this post: when somebody comments one of trigger.keywords on the post once it is live on Instagram, the account DMs them actions.dm.text once, and optionally posts one of actions.public_reply.variations under the comment. Instagram must be in channels. Show the user the keywords and the exact DM text before creating it. The created automation comes back as comment_dm_automation on the post; manage it later with update_automation / get_automation_activity."New value: +"Comment-to-DM automation on this post: when somebody comments one of trigger.keywords on the post once it is live on Instagram or the Facebook Page, the account DMs them actions.dm.text once (on Facebook the DM lands in Messenger), and optionally posts one of actions.public_reply.variations under the comment. Instagram or Facebook must be in channels; platforms picks which ones get it. Show the user the keywords and the exact DM text before creating it. The created automations come back as comment_dm_automation on the post (automations lists the id of each channel); manage them later with update_automation / get_automation_activity." - added
Input schema / properties / comment_dm_automation / properties / platformsAdded value: +{ + "description": "The channels that get the automation: 'instagram', 'facebook' (the Facebook Page; the DM lands in Messenger) or both. One automation per channel, each with the same keywords, DM, public reply and limits. Each one must be in channels. Omit it for one automation: Instagram when the post goes there, else Facebook.", + "items": { + "enum": [ + "instagram", + "facebook" + ], + "type": "string" + }, + "minItems": 1, + "type": "array" +} - added
Input schema / properties / discordAdded value: +{ + "anyOf": [ + { + "properties": { + "allow_mentions": { + "anyOf": [ + { + "type": "boolean" + }, + { + "type": "null" + } + ], + "description": "true lets @everyone, @here, role and user mentions in the text notify people. Off by default: mentions show as text and ping nobody. Only turn it on when the user asks to ping." + }, + "buttons": { + "anyOf": [ + { + "items": { + "properties": { + "text": { + "description": "Button label (1 to 80 chars).", + "maxLength": 80, + "type": "string" + }, + "url": { + "description": "Link the button opens: https:// or http://.", + "type": "string" + } + }, + "required": [ + "text", + "url" + ], + "type": "object" + }, + "maxItems": 5, + "type": "array" + }, + { + "type": "null" + } + ], + "description": "Up to 5 link buttons in one row under the message. Not with a poll." + }, + "link_preview": { + "anyOf": [ + { + "type": "boolean" + }, + { + "type": "null" + } + ], + "description": "false hides the previews of the links in the text (shown by default)." + }, + "poll": { + "anyOf": [ + { + "properties": { + "duration_hours": { + "description": "Hours the poll stays open (1 to 768, 32 days). Default 24.", + "maximum": 768, + "minimum": 1, + "type": "integer" + }, + "multiple": { + "description": "Allow several answers per person.", + "type": "boolean" + }, + "options": { + "description": "2 to 10 answer options of up to 55 chars, all different.", + "items": { + "maxLength": 55, + "type": "string" + }, + "maxItems": 10, + "minItems": 2, + "type": "array" + } + }, + "required": [ + "options" + ], + "type": "object" + }, + { + "type": "null" + } + ], + "description": "A native Discord poll. The post text is the question (max 300 chars). No media and no buttons with a poll. On update_post, null removes it." + }, + "silent": { + "anyOf": [ + { + "type": "boolean" + }, + { + "type": "null" + } + ], + "description": "Send without a push or desktop notification (Discord's @silent)." + }, + "spoiler": { + "anyOf": [ + { + "type": "boolean" + }, + { + "type": "null" + } + ], + "description": "Blur every image and video until someone clicks it." + }, + "thread_name": { + "anyOf": [ + { + "maxLength": 100, + "type": "string" + }, + { + "type": "null" + } + ], + "description": "The post title in a forum or media channel, where Discord requires one (max 100 chars). Only for those channels: a text channel takes none, so the post goes out there without it (warning thread_name_ignored)." + } + }, + "type": "object" + }, + { + "type": "null" + } + ], + "description": "Discord options. The post goes to the connected Discord channel through its webhook and shows the webhook's name and picture. Text up to 2,000 chars. Up to 10 images, GIFs and videos per message (they may mix); a video or GIF over Discord's 20 MB file limit is sent as a link in the text. No Stories; a 'reel' is sent as one video message." +}
- Changed
get_best_times1 field changed- changed
Input schema / properties / platform / descriptionPrevious value: -"Platform identifier, e.g. instagram, tiktok, linkedin, linkedin_page, x, facebook, youtube, pinterest, threads, bluesky, mastodon, google_business, telegram"New value: +"Platform identifier, e.g. instagram, tiktok, linkedin, linkedin_page, x, facebook, youtube, pinterest, threads, bluesky, mastodon, google_business, telegram, discord"
- Changed
list_automations2 fields changed- added
Input schema / properties / platformAdded value: +{ + "description": "Only the automations of this platform.", + "enum": [ + "instagram", + "facebook" + ], + "type": "string" +} - changed
Input schema / properties / post_id / descriptionPrevious value: -"Only the automation bound to this OmniSocials post."New value: +"Only the automations bound to this OmniSocials post (one per platform at most)."
- Changed
update_automation7 fields changed- changed
Input schema / properties / dm_text / descriptionPrevious value: -"The DM sent to the person (max 1000 characters), once per person. Required on create. Confirm the text with the user before creating the automation: it goes out in the account's name."New value: +"The DM sent to the person (max 1000 characters), once per person. On Facebook it lands in Messenger. Required on create. Confirm the text with the user before creating the automation: it goes out in the account's name." - added
Input schema / properties / facebook_post_idAdded value: +{ + "description": "For scope 'post' on Facebook: the id of a Facebook Page post that was NOT published through OmniSocials ({page-id}_{post-id}, or the post id alone). OmniSocials reads it from Facebook to check it belongs to the connected Page. Implies platform 'facebook'. Pass only one of post_id, instagram_media_id or facebook_post_id.", + "type": "string" +} - changed
Input schema / properties / instagram_media_id / descriptionPrevious value: -"For scope 'post': the numeric Instagram media id of a post or reel that was NOT published through OmniSocials. OmniSocials reads it from Instagram to check it belongs to the connected account. Pass post_id OR instagram_media_id."New value: +"For scope 'post' on Instagram: the numeric Instagram media id of a post or reel that was NOT published through OmniSocials. OmniSocials reads it from Instagram to check it belongs to the connected account. Pass only one of post_id, instagram_media_id or facebook_post_id." - added
Input schema / properties / platformAdded value: +{ + "description": "Where the automation runs: 'instagram' (default) = the connected Instagram account, 'facebook' = the connected Facebook Page (the DM lands in Messenger). instagram_media_id implies 'instagram', facebook_post_id implies 'facebook'. It cannot change after create.", + "enum": [ + "instagram", + "facebook" + ], + "type": "string" +} - changed
Input schema / properties / post_id / descriptionPrevious value: -"For scope 'post': the OmniSocials post id (from list_posts) that goes to Instagram. A scheduled post starts listening once it is live. One automation per post."New value: +"For scope 'post': the OmniSocials post id (from list_posts) that goes to the automation's platform. A scheduled post starts listening once it is live. One automation per post and platform: a post that goes to Instagram and Facebook can have one of each." - changed
Input schema / properties / scope / descriptionPrevious value: -"For the comment trigger: 'post' (default) = one post (pass post_id or instagram_media_id), 'next_post' = the next Instagram post the workspace publishes, 'any' = every post of the account."New value: +"For the comment trigger: 'post' (default) = one post (pass post_id, instagram_media_id or facebook_post_id), 'next_post' = the next post the workspace publishes on this platform, 'any' = every post of the account or Page." - changed
Input schema / properties / triggers / descriptionPrevious value: -"What starts the automation. 'comment' (default) = a comment on an Instagram post or reel; 'dm' = a keyword in a DM to the account; 'story_reply' = a keyword in a reply to a story. One automation can listen to several."New value: +"What starts the automation. 'comment' (default) = a comment on an Instagram post or reel, or on a Facebook Page post; 'dm' = a keyword in a DM to the Instagram account, or in a Messenger message to the Facebook Page; 'story_reply' = a keyword in a reply to an Instagram story (Instagram only: Facebook has no story replies). One automation can listen to several."
- Changed
update_post3 fields changed- changed
Input schema / properties / comment_dm_automation / anyOfPrevious value: -[ - { - "description": "Comment-to-DM automation on this post: when somebody comments one of trigger.keywords on the post once it is live on Instagram, the account DMs them actions.dm.text once, and optionally posts one of actions.public_reply.variations under the comment. Instagram must be in channels. Show the user the keywords and the exact DM text before creating it. The created automation comes back as comment_dm_automation on the post; manage it later with update_automation / get_automation_activity.", - "properties": { - "actions": { - "properties": { - "dm": { - "properties": { - "text": { - "description": "The DM the person receives, once (max 1000 characters). Confirm the text with the user: it goes out in their name.", - "maxLength": 1000, - "type": "string" - } - }, - "required": [ - "text" - ], - "type": "object" - }, - "public_reply": { - "properties": { - "enabled": { - "type": "boolean" - }, - "variations": { - "description": "Public replies posted under the comment, one picked at random per comment.", - "items": { - "maxLength": 300, - "type": "string" - }, - "maxItems": 10, - "type": "array" - } - }, - "type": "object" - } - }, - "required": [ - "dm" - ], - "type": "object" - }, - "limits": { - "properties": { - "max_sends": { - "anyOf": [ - { - "exclusiveMinimum": 0, - "maximum": 9007199254740991, - "type": "integer" - }, - { - "type": "null" - } - ], - "description": "Stop after this many DMs." - }, - "stop_at": { - "anyOf": [ - { - "type": "string" - }, - { - "type": "null" - } - ], - "description": "Stop at this time (ISO 8601)." - } - }, - "type": "object" - }, - "trigger": { - "properties": { - "keywords": { - "description": "Keywords that start the automation, matched case-insensitively (up to 20). Required unless match is 'any'.", - "items": { - "type": "string" - }, - "maxItems": 20, - "type": "array" - }, - "match": { - "description": "word (default): the keyword stands on its own. contains: anywhere in the comment. any: every comment (ask the user first).", - "enum": [ - "word", - "contains", - "any" - ], - "type": "string" - } - }, - "type": "object" - } - }, - "required": [ - "actions" - ], - "type": "object" - }, - { - "type": "null" - } -]New value: +[ + { + "description": "Comment-to-DM automation on this post: when somebody comments one of trigger.keywords on the post once it is live on Instagram or the Facebook Page, the account DMs them actions.dm.text once (on Facebook the DM lands in Messenger), and optionally posts one of actions.public_reply.variations under the comment. Instagram or Facebook must be in channels; platforms picks which ones get it. Show the user the keywords and the exact DM text before creating it. The created automations come back as comment_dm_automation on the post (automations lists the id of each channel); manage them later with update_automation / get_automation_activity.", + "properties": { + "actions": { + "properties": { + "dm": { + "properties": { + "text": { + "description": "The DM the person receives, once (max 1000 characters). Confirm the text with the user: it goes out in their name.", + "maxLength": 1000, + "type": "string" + } + }, + "required": [ + "text" + ], + "type": "object" + }, + "public_reply": { + "properties": { + "enabled": { + "type": "boolean" + }, + "variations": { + "description": "Public replies posted under the comment, one picked at random per comment.", + "items": { + "maxLength": 300, + "type": "string" + }, + "maxItems": 10, + "type": "array" + } + }, + "type": "object" + } + }, + "required": [ + "dm" + ], + "type": "object" + }, + "limits": { + "properties": { + "max_sends": { + "anyOf": [ + { + "exclusiveMinimum": 0, + "maximum": 9007199254740991, + "type": "integer" + }, + { + "type": "null" + } + ], + "description": "Stop after this many DMs." + }, + "stop_at": { + "anyOf": [ + { + "type": "string" + }, + { + "type": "null" + } + ], + "description": "Stop at this time (ISO 8601)." + } + }, + "type": "object" + }, + "platforms": { + "description": "The channels that get the automation: 'instagram', 'facebook' (the Facebook Page; the DM lands in Messenger) or both. One automation per channel, each with the same keywords, DM, public reply and limits. Each one must be in channels. Omit it for one automation: Instagram when the post goes there, else Facebook.", + "items": { + "enum": [ + "instagram", + "facebook" + ], + "type": "string" + }, + "minItems": 1, + "type": "array" + }, + "trigger": { + "properties": { + "keywords": { + "description": "Keywords that start the automation, matched case-insensitively (up to 20). Required unless match is 'any'.", + "items": { + "type": "string" + }, + "maxItems": 20, + "type": "array" + }, + "match": { + "description": "word (default): the keyword stands on its own. contains: anywhere in the comment. any: every comment (ask the user first).", + "enum": [ + "word", + "contains", + "any" + ], + "type": "string" + } + }, + "type": "object" + } + }, + "required": [ + "actions" + ], + "type": "object" + }, + { + "type": "null" + } +] - changed
Input schema / properties / comment_dm_automation / descriptionPrevious value: -"Replaces the post's comment-to-DM automation (keywords, DM text, public replies, limits); pass null to remove it; omit to leave it untouched."New value: +"Replaces the post's comment-to-DM setup (keywords, DM text, public replies, limits, platforms); a channel no longer listed in platforms loses its automation; pass null to remove them all; omit to leave them untouched." - added
Input schema / properties / discordAdded value: +{ + "anyOf": [ + { + "properties": { + "allow_mentions": { + "anyOf": [ + { + "type": "boolean" + }, + { + "type": "null" + } + ], + "description": "true lets @everyone, @here, role and user mentions in the text notify people. Off by default: mentions show as text and ping nobody. Only turn it on when the user asks to ping." + }, + "buttons": { + "anyOf": [ + { + "items": { + "properties": { + "text": { + "description": "Button label (1 to 80 chars).", + "maxLength": 80, + "type": "string" + }, + "url": { + "description": "Link the button opens: https:// or http://.", + "type": "string" + } + }, + "required": [ + "text", + "url" + ], + "type": "object" + }, + "maxItems": 5, + "type": "array" + }, + { + "type": "null" + } + ], + "description": "Up to 5 link buttons in one row under the message. Not with a poll." + }, + "link_preview": { + "anyOf": [ + { + "type": "boolean" + }, + { + "type": "null" + } + ], + "description": "false hides the previews of the links in the text (shown by default)." + }, + "poll": { + "anyOf": [ + { + "properties": { + "duration_hours": { + "description": "Hours the poll stays open (1 to 768, 32 days). Default 24.", + "maximum": 768, + "minimum": 1, + "type": "integer" + }, + "multiple": { + "description": "Allow several answers per person.", + "type": "boolean" + }, + "options": { + "description": "2 to 10 answer options of up to 55 chars, all different.", + "items": { + "maxLength": 55, + "type": "string" + }, + "maxItems": 10, + "minItems": 2, + "type": "array" + } + }, + "required": [ + "options" + ], + "type": "object" + }, + { + "type": "null" + } + ], + "description": "A native Discord poll. The post text is the question (max 300 chars). No media and no buttons with a poll. On update_post, null removes it." + }, + "silent": { + "anyOf": [ + { + "type": "boolean" + }, + { + "type": "null" + } + ], + "description": "Send without a push or desktop notification (Discord's @silent)." + }, + "spoiler": { + "anyOf": [ + { + "type": "boolean" + }, + { + "type": "null" + } + ], + "description": "Blur every image and video until someone clicks it." + }, + "thread_name": { + "anyOf": [ + { + "maxLength": 100, + "type": "string" + }, + { + "type": "null" + } + ], + "description": "The post title in a forum or media channel, where Discord requires one (max 100 chars). Only for those channels: a text channel takes none, so the post goes out there without it (warning thread_name_ignored)." + } + }, + "type": "object" + }, + { + "type": "null" + } + ], + "description": "Discord options. The post goes to the connected Discord channel through its webhook and shows the webhook's name and picture. Text up to 2,000 chars. Up to 10 images, GIFs and videos per message (they may mix); a video or GIF over Discord's 20 MB file limit is sent as a link in the text. No Stories; a 'reel' is sent as one video message." +}
1 tool update
- Added
get_post_status
3 tool updates
- Changed
create_and_publish_post1 field changed- changed
Input schema / properties / bluesky / properties / thread_parts / anyOfPrevious value: -[ - { - "items": { - "properties": { - "media_ids": { - "description": "Per-post media as Library IDs from upload_media (max 4) — bare IDs or { id, alt } objects. A part is one video OR up to 4 images.", - "items": { - "anyOf": [ - { - "type": "string" - }, - { - "properties": { - "alt": { - "description": "Accessibility description (alt text) for this media item, shown to screen-reader users (max 1500 chars). Applied on Mastodon, Bluesky, X, Pinterest, Instagram (images and carousel image slides — not Reels/Stories) and LinkedIn (images only — not video or documents). Describe what the image shows; strongly valued by the Mastodon/Bluesky communities.", - "maxLength": 1500, - "type": "string" - }, - "id": { - "description": "Library media ID from upload_media", - "type": "string" - } - }, - "required": [ - "id" - ], - "type": "object" - } - ] - }, - "maxItems": 4, - "type": "array" - }, - "media_urls": { - "description": "Per-post media as external URLs (max 4) — URL strings or { url, alt } objects. A part is one video OR up to 4 images.", - "items": { - "anyOf": [ - { - "type": "string" - }, - { - "properties": { - "alt": { - "description": "Accessibility description (alt text) for this media item, shown to screen-reader users (max 1500 chars). Applied on Mastodon, Bluesky, X, Pinterest, Instagram (images and carousel image slides — not Reels/Stories) and LinkedIn (images only — not video or documents). Describe what the image shows; strongly valued by the Mastodon/Bluesky communities.", - "maxLength": 1500, - "type": "string" - }, - "url": { - "description": "External media URL", - "type": "string" - } - }, - "required": [ - "url" - ], - "type": "object" - } - ] - }, - "maxItems": 4, - "type": "array" - }, - "text": { - "description": "Post text (≤ 300 chars, counted as graphemes — one emoji = 1)", - "type": "string" - } - }, - "required": [ - "text" - ], - "type": "object" - }, - "maxItems": 25, - "minItems": 2, - "type": "array" - }, - { - "type": "null" - } -]New value: +[ + { + "items": { + "properties": { + "media_ids": { + "description": "Per-post media as Library IDs from upload_media (max 10) — bare IDs or { id, alt } objects. A part is one video OR up to 10 images (5 or more post as a gallery).", + "items": { + "anyOf": [ + { + "type": "string" + }, + { + "properties": { + "alt": { + "description": "Accessibility description (alt text) for this media item, shown to screen-reader users (max 1500 chars). Applied on Mastodon, Bluesky, X, Pinterest, Instagram (images and carousel image slides — not Reels/Stories) and LinkedIn (images only — not video or documents). Describe what the image shows; strongly valued by the Mastodon/Bluesky communities.", + "maxLength": 1500, + "type": "string" + }, + "id": { + "description": "Library media ID from upload_media", + "type": "string" + } + }, + "required": [ + "id" + ], + "type": "object" + } + ] + }, + "maxItems": 10, + "type": "array" + }, + "media_urls": { + "description": "Per-post media as external URLs (max 10) — URL strings or { url, alt } objects. A part is one video OR up to 10 images (5 or more post as a gallery).", + "items": { + "anyOf": [ + { + "type": "string" + }, + { + "properties": { + "alt": { + "description": "Accessibility description (alt text) for this media item, shown to screen-reader users (max 1500 chars). Applied on Mastodon, Bluesky, X, Pinterest, Instagram (images and carousel image slides — not Reels/Stories) and LinkedIn (images only — not video or documents). Describe what the image shows; strongly valued by the Mastodon/Bluesky communities.", + "maxLength": 1500, + "type": "string" + }, + "url": { + "description": "External media URL", + "type": "string" + } + }, + "required": [ + "url" + ], + "type": "object" + } + ] + }, + "maxItems": 10, + "type": "array" + }, + "text": { + "description": "Post text (≤ 300 chars, counted as graphemes — one emoji = 1)", + "type": "string" + } + }, + "required": [ + "text" + ], + "type": "object" + }, + "maxItems": 25, + "minItems": 2, + "type": "array" + }, + { + "type": "null" + } +]
- Changed
create_post1 field changed- changed
Input schema / properties / bluesky / properties / thread_parts / anyOfPrevious value: -[ - { - "items": { - "properties": { - "media_ids": { - "description": "Per-post media as Library IDs from upload_media (max 4) — bare IDs or { id, alt } objects. A part is one video OR up to 4 images.", - "items": { - "anyOf": [ - { - "type": "string" - }, - { - "properties": { - "alt": { - "description": "Accessibility description (alt text) for this media item, shown to screen-reader users (max 1500 chars). Applied on Mastodon, Bluesky, X, Pinterest, Instagram (images and carousel image slides — not Reels/Stories) and LinkedIn (images only — not video or documents). Describe what the image shows; strongly valued by the Mastodon/Bluesky communities.", - "maxLength": 1500, - "type": "string" - }, - "id": { - "description": "Library media ID from upload_media", - "type": "string" - } - }, - "required": [ - "id" - ], - "type": "object" - } - ] - }, - "maxItems": 4, - "type": "array" - }, - "media_urls": { - "description": "Per-post media as external URLs (max 4) — URL strings or { url, alt } objects. A part is one video OR up to 4 images.", - "items": { - "anyOf": [ - { - "type": "string" - }, - { - "properties": { - "alt": { - "description": "Accessibility description (alt text) for this media item, shown to screen-reader users (max 1500 chars). Applied on Mastodon, Bluesky, X, Pinterest, Instagram (images and carousel image slides — not Reels/Stories) and LinkedIn (images only — not video or documents). Describe what the image shows; strongly valued by the Mastodon/Bluesky communities.", - "maxLength": 1500, - "type": "string" - }, - "url": { - "description": "External media URL", - "type": "string" - } - }, - "required": [ - "url" - ], - "type": "object" - } - ] - }, - "maxItems": 4, - "type": "array" - }, - "text": { - "description": "Post text (≤ 300 chars, counted as graphemes — one emoji = 1)", - "type": "string" - } - }, - "required": [ - "text" - ], - "type": "object" - }, - "maxItems": 25, - "minItems": 2, - "type": "array" - }, - { - "type": "null" - } -]New value: +[ + { + "items": { + "properties": { + "media_ids": { + "description": "Per-post media as Library IDs from upload_media (max 10) — bare IDs or { id, alt } objects. A part is one video OR up to 10 images (5 or more post as a gallery).", + "items": { + "anyOf": [ + { + "type": "string" + }, + { + "properties": { + "alt": { + "description": "Accessibility description (alt text) for this media item, shown to screen-reader users (max 1500 chars). Applied on Mastodon, Bluesky, X, Pinterest, Instagram (images and carousel image slides — not Reels/Stories) and LinkedIn (images only — not video or documents). Describe what the image shows; strongly valued by the Mastodon/Bluesky communities.", + "maxLength": 1500, + "type": "string" + }, + "id": { + "description": "Library media ID from upload_media", + "type": "string" + } + }, + "required": [ + "id" + ], + "type": "object" + } + ] + }, + "maxItems": 10, + "type": "array" + }, + "media_urls": { + "description": "Per-post media as external URLs (max 10) — URL strings or { url, alt } objects. A part is one video OR up to 10 images (5 or more post as a gallery).", + "items": { + "anyOf": [ + { + "type": "string" + }, + { + "properties": { + "alt": { + "description": "Accessibility description (alt text) for this media item, shown to screen-reader users (max 1500 chars). Applied on Mastodon, Bluesky, X, Pinterest, Instagram (images and carousel image slides — not Reels/Stories) and LinkedIn (images only — not video or documents). Describe what the image shows; strongly valued by the Mastodon/Bluesky communities.", + "maxLength": 1500, + "type": "string" + }, + "url": { + "description": "External media URL", + "type": "string" + } + }, + "required": [ + "url" + ], + "type": "object" + } + ] + }, + "maxItems": 10, + "type": "array" + }, + "text": { + "description": "Post text (≤ 300 chars, counted as graphemes — one emoji = 1)", + "type": "string" + } + }, + "required": [ + "text" + ], + "type": "object" + }, + "maxItems": 25, + "minItems": 2, + "type": "array" + }, + { + "type": "null" + } +]
- Changed
update_post1 field changed- changed
Input schema / properties / bluesky / properties / thread_parts / anyOfPrevious value: -[ - { - "items": { - "properties": { - "media_ids": { - "description": "Per-post media as Library IDs from upload_media (max 4) — bare IDs or { id, alt } objects. A part is one video OR up to 4 images.", - "items": { - "anyOf": [ - { - "type": "string" - }, - { - "properties": { - "alt": { - "description": "Accessibility description (alt text) for this media item, shown to screen-reader users (max 1500 chars). Applied on Mastodon, Bluesky, X, Pinterest, Instagram (images and carousel image slides — not Reels/Stories) and LinkedIn (images only — not video or documents). Describe what the image shows; strongly valued by the Mastodon/Bluesky communities.", - "maxLength": 1500, - "type": "string" - }, - "id": { - "description": "Library media ID from upload_media", - "type": "string" - } - }, - "required": [ - "id" - ], - "type": "object" - } - ] - }, - "maxItems": 4, - "type": "array" - }, - "media_urls": { - "description": "Per-post media as external URLs (max 4) — URL strings or { url, alt } objects. A part is one video OR up to 4 images.", - "items": { - "anyOf": [ - { - "type": "string" - }, - { - "properties": { - "alt": { - "description": "Accessibility description (alt text) for this media item, shown to screen-reader users (max 1500 chars). Applied on Mastodon, Bluesky, X, Pinterest, Instagram (images and carousel image slides — not Reels/Stories) and LinkedIn (images only — not video or documents). Describe what the image shows; strongly valued by the Mastodon/Bluesky communities.", - "maxLength": 1500, - "type": "string" - }, - "url": { - "description": "External media URL", - "type": "string" - } - }, - "required": [ - "url" - ], - "type": "object" - } - ] - }, - "maxItems": 4, - "type": "array" - }, - "text": { - "description": "Post text (≤ 300 chars, counted as graphemes — one emoji = 1)", - "type": "string" - } - }, - "required": [ - "text" - ], - "type": "object" - }, - "maxItems": 25, - "minItems": 2, - "type": "array" - }, - { - "type": "null" - } -]New value: +[ + { + "items": { + "properties": { + "media_ids": { + "description": "Per-post media as Library IDs from upload_media (max 10) — bare IDs or { id, alt } objects. A part is one video OR up to 10 images (5 or more post as a gallery).", + "items": { + "anyOf": [ + { + "type": "string" + }, + { + "properties": { + "alt": { + "description": "Accessibility description (alt text) for this media item, shown to screen-reader users (max 1500 chars). Applied on Mastodon, Bluesky, X, Pinterest, Instagram (images and carousel image slides — not Reels/Stories) and LinkedIn (images only — not video or documents). Describe what the image shows; strongly valued by the Mastodon/Bluesky communities.", + "maxLength": 1500, + "type": "string" + }, + "id": { + "description": "Library media ID from upload_media", + "type": "string" + } + }, + "required": [ + "id" + ], + "type": "object" + } + ] + }, + "maxItems": 10, + "type": "array" + }, + "media_urls": { + "description": "Per-post media as external URLs (max 10) — URL strings or { url, alt } objects. A part is one video OR up to 10 images (5 or more post as a gallery).", + "items": { + "anyOf": [ + { + "type": "string" + }, + { + "properties": { + "alt": { + "description": "Accessibility description (alt text) for this media item, shown to screen-reader users (max 1500 chars). Applied on Mastodon, Bluesky, X, Pinterest, Instagram (images and carousel image slides — not Reels/Stories) and LinkedIn (images only — not video or documents). Describe what the image shows; strongly valued by the Mastodon/Bluesky communities.", + "maxLength": 1500, + "type": "string" + }, + "url": { + "description": "External media URL", + "type": "string" + } + }, + "required": [ + "url" + ], + "type": "object" + } + ] + }, + "maxItems": 10, + "type": "array" + }, + "text": { + "description": "Post text (≤ 300 chars, counted as graphemes — one emoji = 1)", + "type": "string" + } + }, + "required": [ + "text" + ], + "type": "object" + }, + "maxItems": 25, + "minItems": 2, + "type": "array" + }, + { + "type": "null" + } +]
4 tool updates
- Changed
create_and_publish_post2 fields changed- changed
Input schema / properties / hashtag_set / descriptionPrevious value: -"Name of a saved hashtag set (from list_hashtag_sets, matched case-insensitively) to apply to this post. The set's tags are merged in once at create time; tags already present in a caption are skipped. When the user says something like 'add my usual hashtags', check list_hashtag_sets first. Instagram's 30-hashtag cap is enforced with a clear error (hashtag_limit_exceeded)."New value: +"Name of a saved hashtag set (from list_hashtag_sets, matched case-insensitively) to apply to this post. The set's tags are merged in once at create time; tags already present in a caption are skipped. When the user says something like 'add my usual hashtags', check list_hashtag_sets first. Instagram's 5-hashtag cap is enforced with a clear error (hashtag_limit_exceeded)." - added
Input schema / properties / telegramAdded value: +{ + "anyOf": [ + { + "properties": { + "buttons": { + "anyOf": [ + { + "items": { + "properties": { + "text": { + "description": "Button label (max 64 chars).", + "maxLength": 64, + "type": "string" + }, + "url": { + "description": "Link the button opens: https://, http:// or tg://.", + "type": "string" + } + }, + "required": [ + "text", + "url" + ], + "type": "object" + }, + "maxItems": 3, + "type": "array" + }, + { + "type": "null" + } + ], + "description": "Up to 3 link buttons under the post, one per row. Not on an album (2+ media) or a poll." + }, + "caption_above_media": { + "anyOf": [ + { + "type": "boolean" + }, + { + "type": "null" + } + ], + "description": "Show the text above the media instead of below." + }, + "first_comment": { + "description": "A reply the bot sends under the post right after it is published.", + "maxLength": 4096, + "type": "string" + }, + "link_preview": { + "anyOf": [ + { + "type": "boolean" + }, + { + "type": "null" + } + ], + "description": "false hides the link preview of a text-only post (shown by default)." + }, + "pin": { + "anyOf": [ + { + "type": "boolean" + }, + { + "type": "null" + } + ], + "description": "Pin the post in the chat after it is sent. Needs the bot's Edit messages right in a channel (Pin messages in a group); without it the post is sent unpinned." + }, + "poll": { + "anyOf": [ + { + "properties": { + "multiple": { + "description": "Allow several answers per person.", + "type": "boolean" + }, + "open_period": { + "description": "Seconds the poll stays open (5 s to about 30 days). Omit to keep it open.", + "maximum": 2628000, + "minimum": 5, + "type": "integer" + }, + "options": { + "description": "2 to 12 answer options of up to 100 chars, all different.", + "items": { + "maxLength": 100, + "type": "string" + }, + "maxItems": 12, + "minItems": 2, + "type": "array" + } + }, + "required": [ + "options" + ], + "type": "object" + }, + { + "type": "null" + } + ], + "description": "A native Telegram poll. The post text is the question (max 300 chars). No media with a poll. On update_post, null removes it." + }, + "protect_content": { + "anyOf": [ + { + "type": "boolean" + }, + { + "type": "null" + } + ], + "description": "Stop forwarding and saving of the post in Telegram apps." + }, + "silent": { + "anyOf": [ + { + "type": "boolean" + }, + { + "type": "null" + } + ], + "description": "Send without a notification sound." + }, + "spoiler": { + "anyOf": [ + { + "type": "boolean" + }, + { + "type": "null" + } + ], + "description": "Blur the photos and videos until someone taps them." + } + }, + "type": "object" + }, + { + "type": "null" + } + ], + "description": "Telegram options. Text up to 4,096 chars; with media, text over 1,024 chars is sent as a reply under the media. Up to 10 photos and videos per album, videos up to 50 MB, no Stories. A 'reel' is sent as a video message." +}
- Changed
create_post2 fields changed- changed
Input schema / properties / hashtag_set / descriptionPrevious value: -"Name of a saved hashtag set (from list_hashtag_sets, matched case-insensitively) to apply to this post. The set's tags are merged in once at create time; tags already present in a caption are skipped. When the user says something like 'add my usual hashtags', check list_hashtag_sets first. Instagram's 30-hashtag cap is enforced with a clear error (hashtag_limit_exceeded)."New value: +"Name of a saved hashtag set (from list_hashtag_sets, matched case-insensitively) to apply to this post. The set's tags are merged in once at create time; tags already present in a caption are skipped. When the user says something like 'add my usual hashtags', check list_hashtag_sets first. Instagram's 5-hashtag cap is enforced with a clear error (hashtag_limit_exceeded)." - added
Input schema / properties / telegramAdded value: +{ + "anyOf": [ + { + "properties": { + "buttons": { + "anyOf": [ + { + "items": { + "properties": { + "text": { + "description": "Button label (max 64 chars).", + "maxLength": 64, + "type": "string" + }, + "url": { + "description": "Link the button opens: https://, http:// or tg://.", + "type": "string" + } + }, + "required": [ + "text", + "url" + ], + "type": "object" + }, + "maxItems": 3, + "type": "array" + }, + { + "type": "null" + } + ], + "description": "Up to 3 link buttons under the post, one per row. Not on an album (2+ media) or a poll." + }, + "caption_above_media": { + "anyOf": [ + { + "type": "boolean" + }, + { + "type": "null" + } + ], + "description": "Show the text above the media instead of below." + }, + "first_comment": { + "description": "A reply the bot sends under the post right after it is published.", + "maxLength": 4096, + "type": "string" + }, + "link_preview": { + "anyOf": [ + { + "type": "boolean" + }, + { + "type": "null" + } + ], + "description": "false hides the link preview of a text-only post (shown by default)." + }, + "pin": { + "anyOf": [ + { + "type": "boolean" + }, + { + "type": "null" + } + ], + "description": "Pin the post in the chat after it is sent. Needs the bot's Edit messages right in a channel (Pin messages in a group); without it the post is sent unpinned." + }, + "poll": { + "anyOf": [ + { + "properties": { + "multiple": { + "description": "Allow several answers per person.", + "type": "boolean" + }, + "open_period": { + "description": "Seconds the poll stays open (5 s to about 30 days). Omit to keep it open.", + "maximum": 2628000, + "minimum": 5, + "type": "integer" + }, + "options": { + "description": "2 to 12 answer options of up to 100 chars, all different.", + "items": { + "maxLength": 100, + "type": "string" + }, + "maxItems": 12, + "minItems": 2, + "type": "array" + } + }, + "required": [ + "options" + ], + "type": "object" + }, + { + "type": "null" + } + ], + "description": "A native Telegram poll. The post text is the question (max 300 chars). No media with a poll. On update_post, null removes it." + }, + "protect_content": { + "anyOf": [ + { + "type": "boolean" + }, + { + "type": "null" + } + ], + "description": "Stop forwarding and saving of the post in Telegram apps." + }, + "silent": { + "anyOf": [ + { + "type": "boolean" + }, + { + "type": "null" + } + ], + "description": "Send without a notification sound." + }, + "spoiler": { + "anyOf": [ + { + "type": "boolean" + }, + { + "type": "null" + } + ], + "description": "Blur the photos and videos until someone taps them." + } + }, + "type": "object" + }, + { + "type": "null" + } + ], + "description": "Telegram options. Text up to 4,096 chars; with media, text over 1,024 chars is sent as a reply under the media. Up to 10 photos and videos per album, videos up to 50 MB, no Stories. A 'reel' is sent as a video message." +}
- Changed
get_best_times1 field changed- changed
Input schema / properties / platform / descriptionPrevious value: -"Platform identifier, e.g. instagram, tiktok, linkedin, linkedin_page, x, facebook, youtube, pinterest, threads, bluesky, mastodon, google_business"New value: +"Platform identifier, e.g. instagram, tiktok, linkedin, linkedin_page, x, facebook, youtube, pinterest, threads, bluesky, mastodon, google_business, telegram"
- Changed
update_post1 field changed- added
Input schema / properties / telegramAdded value: +{ + "anyOf": [ + { + "properties": { + "buttons": { + "anyOf": [ + { + "items": { + "properties": { + "text": { + "description": "Button label (max 64 chars).", + "maxLength": 64, + "type": "string" + }, + "url": { + "description": "Link the button opens: https://, http:// or tg://.", + "type": "string" + } + }, + "required": [ + "text", + "url" + ], + "type": "object" + }, + "maxItems": 3, + "type": "array" + }, + { + "type": "null" + } + ], + "description": "Up to 3 link buttons under the post, one per row. Not on an album (2+ media) or a poll." + }, + "caption_above_media": { + "anyOf": [ + { + "type": "boolean" + }, + { + "type": "null" + } + ], + "description": "Show the text above the media instead of below." + }, + "first_comment": { + "description": "A reply the bot sends under the post right after it is published.", + "maxLength": 4096, + "type": "string" + }, + "link_preview": { + "anyOf": [ + { + "type": "boolean" + }, + { + "type": "null" + } + ], + "description": "false hides the link preview of a text-only post (shown by default)." + }, + "pin": { + "anyOf": [ + { + "type": "boolean" + }, + { + "type": "null" + } + ], + "description": "Pin the post in the chat after it is sent. Needs the bot's Edit messages right in a channel (Pin messages in a group); without it the post is sent unpinned." + }, + "poll": { + "anyOf": [ + { + "properties": { + "multiple": { + "description": "Allow several answers per person.", + "type": "boolean" + }, + "open_period": { + "description": "Seconds the poll stays open (5 s to about 30 days). Omit to keep it open.", + "maximum": 2628000, + "minimum": 5, + "type": "integer" + }, + "options": { + "description": "2 to 12 answer options of up to 100 chars, all different.", + "items": { + "maxLength": 100, + "type": "string" + }, + "maxItems": 12, + "minItems": 2, + "type": "array" + } + }, + "required": [ + "options" + ], + "type": "object" + }, + { + "type": "null" + } + ], + "description": "A native Telegram poll. The post text is the question (max 300 chars). No media with a poll. On update_post, null removes it." + }, + "protect_content": { + "anyOf": [ + { + "type": "boolean" + }, + { + "type": "null" + } + ], + "description": "Stop forwarding and saving of the post in Telegram apps." + }, + "silent": { + "anyOf": [ + { + "type": "boolean" + }, + { + "type": "null" + } + ], + "description": "Send without a notification sound." + }, + "spoiler": { + "anyOf": [ + { + "type": "boolean" + }, + { + "type": "null" + } + ], + "description": "Blur the photos and videos until someone taps them." + } + }, + "type": "object" + }, + { + "type": "null" + } + ], + "description": "Telegram options. Text up to 4,096 chars; with media, text over 1,024 chars is sent as a reply under the media. Up to 10 photos and videos per album, videos up to 50 MB, no Stories. A 'reel' is sent as a video message." +}
3 tool updates
- Changed
create_and_publish_post1 field changed- changed
Input schema / properties / pinterest / properties / product_tags / descriptionPrevious value: -"Products to tag on the Pin, so people can shop the items in the image. Up to 24 product Pins of the connected Pinterest account, each as a Pin ID string or a Pin link (https://www.pinterest.com/pin/<id>/). Get the IDs with list_pinterest_products. Only the account's own product Pins can be tagged (public, with a link on a website the account claimed on Pinterest); products of other merchants cannot. The tags are added right after the Pin is published; a product Pinterest refuses never fails the post, and get_post shows the outcome (product_tags_result). On update_post the pinterest object replaces the stored one, so leave product_tags out to remove the tags."New value: +"Product Pins to tag on the Pin (Pinterest shows the tagged items on the image). Up to 24 product Pins of the connected Pinterest account, each as a Pin ID string or a Pin link (https://www.pinterest.com/pin/<id>/). Get the IDs with list_pinterest_products. Only the account's own product Pins can be tagged (public, with a link on a website the account claimed on Pinterest); products of other merchants cannot. The tags are added right after the Pin is published; a product Pinterest refuses never fails the post, and get_post shows the outcome (product_tags_result). On update_post the pinterest object replaces the stored one, so leave product_tags out to remove the tags."
- Changed
create_post1 field changed- changed
Input schema / properties / pinterest / properties / product_tags / descriptionPrevious value: -"Products to tag on the Pin, so people can shop the items in the image. Up to 24 product Pins of the connected Pinterest account, each as a Pin ID string or a Pin link (https://www.pinterest.com/pin/<id>/). Get the IDs with list_pinterest_products. Only the account's own product Pins can be tagged (public, with a link on a website the account claimed on Pinterest); products of other merchants cannot. The tags are added right after the Pin is published; a product Pinterest refuses never fails the post, and get_post shows the outcome (product_tags_result). On update_post the pinterest object replaces the stored one, so leave product_tags out to remove the tags."New value: +"Product Pins to tag on the Pin (Pinterest shows the tagged items on the image). Up to 24 product Pins of the connected Pinterest account, each as a Pin ID string or a Pin link (https://www.pinterest.com/pin/<id>/). Get the IDs with list_pinterest_products. Only the account's own product Pins can be tagged (public, with a link on a website the account claimed on Pinterest); products of other merchants cannot. The tags are added right after the Pin is published; a product Pinterest refuses never fails the post, and get_post shows the outcome (product_tags_result). On update_post the pinterest object replaces the stored one, so leave product_tags out to remove the tags."
- Changed
update_post1 field changed- changed
Input schema / properties / pinterest / properties / product_tags / descriptionPrevious value: -"Products to tag on the Pin, so people can shop the items in the image. Up to 24 product Pins of the connected Pinterest account, each as a Pin ID string or a Pin link (https://www.pinterest.com/pin/<id>/). Get the IDs with list_pinterest_products. Only the account's own product Pins can be tagged (public, with a link on a website the account claimed on Pinterest); products of other merchants cannot. The tags are added right after the Pin is published; a product Pinterest refuses never fails the post, and get_post shows the outcome (product_tags_result). On update_post the pinterest object replaces the stored one, so leave product_tags out to remove the tags."New value: +"Product Pins to tag on the Pin (Pinterest shows the tagged items on the image). Up to 24 product Pins of the connected Pinterest account, each as a Pin ID string or a Pin link (https://www.pinterest.com/pin/<id>/). Get the IDs with list_pinterest_products. Only the account's own product Pins can be tagged (public, with a link on a website the account claimed on Pinterest); products of other merchants cannot. The tags are added right after the Pin is published; a product Pinterest refuses never fails the post, and get_post shows the outcome (product_tags_result). On update_post the pinterest object replaces the stored one, so leave product_tags out to remove the tags."
9 tool updates
- Changed
create_and_publish_post4 fields changed- added
Input schema / properties / comment_dm_automationAdded value: +{ + "description": "Comment-to-DM automation on this post: when somebody comments one of trigger.keywords on the post once it is live on Instagram, the account DMs them actions.dm.text once, and optionally posts one of actions.public_reply.variations under the comment. Instagram must be in channels. Show the user the keywords and the exact DM text before creating it. The created automation comes back as comment_dm_automation on the post; manage it later with update_automation / get_automation_activity.", + "properties": { + "actions": { + "properties": { + "dm": { + "properties": { + "text": { + "description": "The DM the person receives, once (max 1000 characters). Confirm the text with the user: it goes out in their name.", + "maxLength": 1000, + "type": "string" + } + }, + "required": [ + "text" + ], + "type": "object" + }, + "public_reply": { + "properties": { + "enabled": { + "type": "boolean" + }, + "variations": { + "description": "Public replies posted under the comment, one picked at random per comment.", + "items": { + "maxLength": 300, + "type": "string" + }, + "maxItems": 10, + "type": "array" + } + }, + "type": "object" + } + }, + "required": [ + "dm" + ], + "type": "object" + }, + "limits": { + "properties": { + "max_sends": { + "anyOf": [ + { + "exclusiveMinimum": 0, + "maximum": 9007199254740991, + "type": "integer" + }, + { + "type": "null" + } + ], + "description": "Stop after this many DMs." + }, + "stop_at": { + "anyOf": [ + { + "type": "string" + }, + { + "type": "null" + } + ], + "description": "Stop at this time (ISO 8601)." + } + }, + "type": "object" + }, + "trigger": { + "properties": { + "keywords": { + "description": "Keywords that start the automation, matched case-insensitively (up to 20). Required unless match is 'any'.", + "items": { + "type": "string" + }, + "maxItems": 20, + "type": "array" + }, + "match": { + "description": "word (default): the keyword stands on its own. contains: anywhere in the comment. any: every comment (ask the user first).", + "enum": [ + "word", + "contains", + "any" + ], + "type": "string" + } + }, + "type": "object" + } + }, + "required": [ + "actions" + ], + "type": "object" +} - changed
Input schema / properties / google_business / properties / event / descriptionPrevious value: -"Required when topic_type is EVENT."New value: +"Required when topic_type is EVENT or OFFER. For an OFFER, the title is the offer's name and the schedule its validity period (Google rejects an offer without it)." - added
Input schema / properties / media_fitAdded value: +{ + "additionalProperties": { + "enum": [ + "auto", + "crop", + "keep" + ], + "type": "string" + }, + "description": "Image fit per channel, for feed images (type 'post') whose ratio is outside what a channel shows uncropped: { instagram: 'auto' | 'crop' | 'keep', pinterest: ... }. 'auto' (the default when omitted) takes the channel's rule: Instagram crops a tall (9:16) or wide image to 4:5 / 1.91:1 around the subject (Instagram cuts it to that window anyway, and Meta cannot boost a feed post outside it); Pinterest keeps a Pin taller than 2:3 and only reports it. 'crop' / 'keep' force it for that channel. Every decision comes back in the response `warnings` with code `image_fit` (relay it). The crop is a separate file for that channel only; 'default' and the other channels keep the original. On update_post, media_fit alone (no media) re-decides the stored images: 'keep' gives the original back, 'crop' crops an image that was kept.", + "propertyNames": { + "type": "string" + }, + "type": "object" +} - changed
Input schema / properties / youtube / properties / title / descriptionPrevious value: -"Short title shown on YouTube. Falls back to \"YouTube Short\" when omitted."New value: +"Short title shown on YouTube (max 100 characters). When omitted, the first line of the caption is used; \"YouTube Short\" only when there is no caption either."
- Added
create_automation - Changed
create_post4 fields changed- added
Input schema / properties / comment_dm_automationAdded value: +{ + "description": "Comment-to-DM automation on this post: when somebody comments one of trigger.keywords on the post once it is live on Instagram, the account DMs them actions.dm.text once, and optionally posts one of actions.public_reply.variations under the comment. Instagram must be in channels. Show the user the keywords and the exact DM text before creating it. The created automation comes back as comment_dm_automation on the post; manage it later with update_automation / get_automation_activity.", + "properties": { + "actions": { + "properties": { + "dm": { + "properties": { + "text": { + "description": "The DM the person receives, once (max 1000 characters). Confirm the text with the user: it goes out in their name.", + "maxLength": 1000, + "type": "string" + } + }, + "required": [ + "text" + ], + "type": "object" + }, + "public_reply": { + "properties": { + "enabled": { + "type": "boolean" + }, + "variations": { + "description": "Public replies posted under the comment, one picked at random per comment.", + "items": { + "maxLength": 300, + "type": "string" + }, + "maxItems": 10, + "type": "array" + } + }, + "type": "object" + } + }, + "required": [ + "dm" + ], + "type": "object" + }, + "limits": { + "properties": { + "max_sends": { + "anyOf": [ + { + "exclusiveMinimum": 0, + "maximum": 9007199254740991, + "type": "integer" + }, + { + "type": "null" + } + ], + "description": "Stop after this many DMs." + }, + "stop_at": { + "anyOf": [ + { + "type": "string" + }, + { + "type": "null" + } + ], + "description": "Stop at this time (ISO 8601)." + } + }, + "type": "object" + }, + "trigger": { + "properties": { + "keywords": { + "description": "Keywords that start the automation, matched case-insensitively (up to 20). Required unless match is 'any'.", + "items": { + "type": "string" + }, + "maxItems": 20, + "type": "array" + }, + "match": { + "description": "word (default): the keyword stands on its own. contains: anywhere in the comment. any: every comment (ask the user first).", + "enum": [ + "word", + "contains", + "any" + ], + "type": "string" + } + }, + "type": "object" + } + }, + "required": [ + "actions" + ], + "type": "object" +} - changed
Input schema / properties / google_business / properties / event / descriptionPrevious value: -"Required when topic_type is EVENT."New value: +"Required when topic_type is EVENT or OFFER. For an OFFER, the title is the offer's name and the schedule its validity period (Google rejects an offer without it)." - added
Input schema / properties / media_fitAdded value: +{ + "additionalProperties": { + "enum": [ + "auto", + "crop", + "keep" + ], + "type": "string" + }, + "description": "Image fit per channel, for feed images (type 'post') whose ratio is outside what a channel shows uncropped: { instagram: 'auto' | 'crop' | 'keep', pinterest: ... }. 'auto' (the default when omitted) takes the channel's rule: Instagram crops a tall (9:16) or wide image to 4:5 / 1.91:1 around the subject (Instagram cuts it to that window anyway, and Meta cannot boost a feed post outside it); Pinterest keeps a Pin taller than 2:3 and only reports it. 'crop' / 'keep' force it for that channel. Every decision comes back in the response `warnings` with code `image_fit` (relay it). The crop is a separate file for that channel only; 'default' and the other channels keep the original. On update_post, media_fit alone (no media) re-decides the stored images: 'keep' gives the original back, 'crop' crops an image that was kept.", + "propertyNames": { + "type": "string" + }, + "type": "object" +} - changed
Input schema / properties / youtube / properties / title / descriptionPrevious value: -"Short title shown on YouTube. Falls back to \"YouTube Short\" when omitted."New value: +"Short title shown on YouTube (max 100 characters). When omitted, the first line of the caption is used; \"YouTube Short\" only when there is no caption either."
- Added
delete_automation - Added
get_automation - Added
get_automation_activity - Added
list_automations - Added
update_automation - Changed
update_post4 fields changed- added
Input schema / properties / comment_dm_automationAdded value: +{ + "anyOf": [ + { + "description": "Comment-to-DM automation on this post: when somebody comments one of trigger.keywords on the post once it is live on Instagram, the account DMs them actions.dm.text once, and optionally posts one of actions.public_reply.variations under the comment. Instagram must be in channels. Show the user the keywords and the exact DM text before creating it. The created automation comes back as comment_dm_automation on the post; manage it later with update_automation / get_automation_activity.", + "properties": { + "actions": { + "properties": { + "dm": { + "properties": { + "text": { + "description": "The DM the person receives, once (max 1000 characters). Confirm the text with the user: it goes out in their name.", + "maxLength": 1000, + "type": "string" + } + }, + "required": [ + "text" + ], + "type": "object" + }, + "public_reply": { + "properties": { + "enabled": { + "type": "boolean" + }, + "variations": { + "description": "Public replies posted under the comment, one picked at random per comment.", + "items": { + "maxLength": 300, + "type": "string" + }, + "maxItems": 10, + "type": "array" + } + }, + "type": "object" + } + }, + "required": [ + "dm" + ], + "type": "object" + }, + "limits": { + "properties": { + "max_sends": { + "anyOf": [ + { + "exclusiveMinimum": 0, + "maximum": 9007199254740991, + "type": "integer" + }, + { + "type": "null" + } + ], + "description": "Stop after this many DMs." + }, + "stop_at": { + "anyOf": [ + { + "type": "string" + }, + { + "type": "null" + } + ], + "description": "Stop at this time (ISO 8601)." + } + }, + "type": "object" + }, + "trigger": { + "properties": { + "keywords": { + "description": "Keywords that start the automation, matched case-insensitively (up to 20). Required unless match is 'any'.", + "items": { + "type": "string" + }, + "maxItems": 20, + "type": "array" + }, + "match": { + "description": "word (default): the keyword stands on its own. contains: anywhere in the comment. any: every comment (ask the user first).", + "enum": [ + "word", + "contains", + "any" + ], + "type": "string" + } + }, + "type": "object" + } + }, + "required": [ + "actions" + ], + "type": "object" + }, + { + "type": "null" + } + ], + "description": "Replaces the post's comment-to-DM automation (keywords, DM text, public replies, limits); pass null to remove it; omit to leave it untouched." +} - changed
Input schema / properties / google_business / properties / event / descriptionPrevious value: -"Required when topic_type is EVENT."New value: +"Required when topic_type is EVENT or OFFER. For an OFFER, the title is the offer's name and the schedule its validity period (Google rejects an offer without it)." - added
Input schema / properties / media_fitAdded value: +{ + "additionalProperties": { + "enum": [ + "auto", + "crop", + "keep" + ], + "type": "string" + }, + "description": "Image fit per channel, for feed images (type 'post') whose ratio is outside what a channel shows uncropped: { instagram: 'auto' | 'crop' | 'keep', pinterest: ... }. 'auto' (the default when omitted) takes the channel's rule: Instagram crops a tall (9:16) or wide image to 4:5 / 1.91:1 around the subject (Instagram cuts it to that window anyway, and Meta cannot boost a feed post outside it); Pinterest keeps a Pin taller than 2:3 and only reports it. 'crop' / 'keep' force it for that channel. Every decision comes back in the response `warnings` with code `image_fit` (relay it). The crop is a separate file for that channel only; 'default' and the other channels keep the original. On update_post, media_fit alone (no media) re-decides the stored images: 'keep' gives the original back, 'crop' crops an image that was kept.", + "propertyNames": { + "type": "string" + }, + "type": "object" +} - changed
Input schema / properties / youtube / properties / title / descriptionPrevious value: -"Short title shown on YouTube. Falls back to \"YouTube Short\" when omitted."New value: +"Short title shown on YouTube (max 100 characters). When omitted, the first line of the caption is used; \"YouTube Short\" only when there is no caption either."
4 tool updates
- Changed
create_and_publish_post1 field changed- added
Input schema / properties / pinterest / properties / product_tagsAdded value: +{ + "description": "Products to tag on the Pin, so people can shop the items in the image. Up to 24 product Pins of the connected Pinterest account, each as a Pin ID string or a Pin link (https://www.pinterest.com/pin/<id>/). Get the IDs with list_pinterest_products. Only the account's own product Pins can be tagged (public, with a link on a website the account claimed on Pinterest); products of other merchants cannot. The tags are added right after the Pin is published; a product Pinterest refuses never fails the post, and get_post shows the outcome (product_tags_result). On update_post the pinterest object replaces the stored one, so leave product_tags out to remove the tags.", + "items": { + "type": "string" + }, + "maxItems": 24, + "type": "array" +}
- Changed
create_post1 field changed- added
Input schema / properties / pinterest / properties / product_tagsAdded value: +{ + "description": "Products to tag on the Pin, so people can shop the items in the image. Up to 24 product Pins of the connected Pinterest account, each as a Pin ID string or a Pin link (https://www.pinterest.com/pin/<id>/). Get the IDs with list_pinterest_products. Only the account's own product Pins can be tagged (public, with a link on a website the account claimed on Pinterest); products of other merchants cannot. The tags are added right after the Pin is published; a product Pinterest refuses never fails the post, and get_post shows the outcome (product_tags_result). On update_post the pinterest object replaces the stored one, so leave product_tags out to remove the tags.", + "items": { + "type": "string" + }, + "maxItems": 24, + "type": "array" +}
- Added
list_pinterest_products - Changed
update_post1 field changed- added
Input schema / properties / pinterest / properties / product_tagsAdded value: +{ + "description": "Products to tag on the Pin, so people can shop the items in the image. Up to 24 product Pins of the connected Pinterest account, each as a Pin ID string or a Pin link (https://www.pinterest.com/pin/<id>/). Get the IDs with list_pinterest_products. Only the account's own product Pins can be tagged (public, with a link on a website the account claimed on Pinterest); products of other merchants cannot. The tags are added right after the Pin is published; a product Pinterest refuses never fails the post, and get_post shows the outcome (product_tags_result). On update_post the pinterest object replaces the stored one, so leave product_tags out to remove the tags.", + "items": { + "type": "string" + }, + "maxItems": 24, + "type": "array" +}
1 tool update
- Added
get_post_approval
3 tool updates
- Changed
create_and_publish_post5 fields changed- added
Input schema / properties / facebook / properties / cover_urlAdded value: +{ + "description": "Custom thumbnail image URL (JPEG/PNG, max 10 MB). Used with thumbnail_type 'from-library'.", + "type": "string" +} - added
Input schema / properties / facebook / properties / thumb_offsetAdded value: +{ + "description": "Frame timestamp in MILLISECONDS from the start of the video (e.g. 3000 = 0:03). Used with thumbnail_type 'from-video'.", + "type": "number" +} - added
Input schema / properties / facebook / properties / thumbnail_typeAdded value: +{ + "anyOf": [ + { + "enum": [ + "from-video", + "from-library" + ], + "type": "string" + }, + { + "type": "null" + } + ], + "description": "Video thumbnail for Facebook feed videos and reels: 'from-video' uses the frame at thumb_offset, 'from-library' uploads the image at cover_url. Applied after the video is live; a thumbnail failure never fails the post. On update_post, null removes the Facebook override." +} - added
Input schema / properties / video_coverAdded value: +{ + "description": "Video thumbnail for a post whose media is ONE video. Applied on Instagram (feed videos and reels), Facebook (feed videos and reels), LinkedIn Profile and Page, TikTok, Pinterest and YouTube Shorts. YouTube Shorts: the cover shows on Shorts only on channels where YouTube has enabled custom Shorts thumbnails (rolling out since July 2026, Partner Program channels first); on other channels YouTube stores it as the default thumbnail but shows a frame from the video on Shorts. Say that it depends on the channel; do not promise it. TikTok only takes a frame: a 'custom' cover is skipped there, so add a tiktok override with type 'frame' when the user wants a specific TikTok frame. The per-platform reel fields (instagram.thumb_offset / cover_url, tiktok.video_cover_timestamp_ms, pinterest.video_cover) keep working and win over the base cover for their platform. get_post reads it back as `video_cover`.", + "properties": { + "cover_url": { + "description": "Public image URL, JPEG or PNG (type 'custom').", + "type": "string" + }, + "overrides": { + "additionalProperties": { + "anyOf": [ + { + "properties": { + "cover_url": { + "description": "Public image URL, JPEG or PNG (type 'custom').", + "type": "string" + }, + "thumb_offset": { + "description": "Milliseconds into the video (type 'frame'). 3000 = 0:03.", + "maximum": 9007199254740991, + "minimum": 0, + "type": "integer" + }, + "type": { + "description": "'frame' uses the video frame at thumb_offset; 'custom' uploads the image at cover_url.", + "enum": [ + "frame", + "custom" + ], + "type": "string" + } + }, + "required": [ + "type" + ], + "type": "object" + }, + { + "type": "null" + } + ] + }, + "description": "Per-platform overrides keyed by platform id (instagram, facebook, linkedin, linkedin_page, tiktok, pinterest, youtube). An override wins over the base cover for that platform.", + "propertyNames": { + "type": "string" + }, + "type": "object" + }, + "thumb_offset": { + "description": "Milliseconds into the video (type 'frame'). 3000 = 0:03.", + "maximum": 9007199254740991, + "minimum": 0, + "type": "integer" + }, + "type": { + "description": "'frame' uses the video frame at thumb_offset; 'custom' uploads the image at cover_url.", + "enum": [ + "frame", + "custom" + ], + "type": "string" + } + }, + "required": [ + "type" + ], + "type": "object" +} - changed
Input schema / properties / youtube / descriptionPrevious value: -"YouTube Shorts options. Only applies when type is 'reel' and youtube is among the selected channels."New value: +"YouTube Shorts options. Only applies when type is 'reel' and youtube is among the selected channels. A custom Shorts thumbnail is set with the top-level `video_cover` (a `youtube` override for a YouTube-only image); it shows on Shorts only on channels where YouTube has enabled custom Shorts thumbnails (Partner Program channels first, since July 2026), other channels show a frame from the video."
- Changed
create_post5 fields changed- added
Input schema / properties / facebook / properties / cover_urlAdded value: +{ + "description": "Custom thumbnail image URL (JPEG/PNG, max 10 MB). Used with thumbnail_type 'from-library'.", + "type": "string" +} - added
Input schema / properties / facebook / properties / thumb_offsetAdded value: +{ + "description": "Frame timestamp in MILLISECONDS from the start of the video (e.g. 3000 = 0:03). Used with thumbnail_type 'from-video'.", + "type": "number" +} - added
Input schema / properties / facebook / properties / thumbnail_typeAdded value: +{ + "anyOf": [ + { + "enum": [ + "from-video", + "from-library" + ], + "type": "string" + }, + { + "type": "null" + } + ], + "description": "Video thumbnail for Facebook feed videos and reels: 'from-video' uses the frame at thumb_offset, 'from-library' uploads the image at cover_url. Applied after the video is live; a thumbnail failure never fails the post. On update_post, null removes the Facebook override." +} - added
Input schema / properties / video_coverAdded value: +{ + "description": "Video thumbnail for a post whose media is ONE video. Applied on Instagram (feed videos and reels), Facebook (feed videos and reels), LinkedIn Profile and Page, TikTok, Pinterest and YouTube Shorts. YouTube Shorts: the cover shows on Shorts only on channels where YouTube has enabled custom Shorts thumbnails (rolling out since July 2026, Partner Program channels first); on other channels YouTube stores it as the default thumbnail but shows a frame from the video on Shorts. Say that it depends on the channel; do not promise it. TikTok only takes a frame: a 'custom' cover is skipped there, so add a tiktok override with type 'frame' when the user wants a specific TikTok frame. The per-platform reel fields (instagram.thumb_offset / cover_url, tiktok.video_cover_timestamp_ms, pinterest.video_cover) keep working and win over the base cover for their platform. get_post reads it back as `video_cover`.", + "properties": { + "cover_url": { + "description": "Public image URL, JPEG or PNG (type 'custom').", + "type": "string" + }, + "overrides": { + "additionalProperties": { + "anyOf": [ + { + "properties": { + "cover_url": { + "description": "Public image URL, JPEG or PNG (type 'custom').", + "type": "string" + }, + "thumb_offset": { + "description": "Milliseconds into the video (type 'frame'). 3000 = 0:03.", + "maximum": 9007199254740991, + "minimum": 0, + "type": "integer" + }, + "type": { + "description": "'frame' uses the video frame at thumb_offset; 'custom' uploads the image at cover_url.", + "enum": [ + "frame", + "custom" + ], + "type": "string" + } + }, + "required": [ + "type" + ], + "type": "object" + }, + { + "type": "null" + } + ] + }, + "description": "Per-platform overrides keyed by platform id (instagram, facebook, linkedin, linkedin_page, tiktok, pinterest, youtube). An override wins over the base cover for that platform.", + "propertyNames": { + "type": "string" + }, + "type": "object" + }, + "thumb_offset": { + "description": "Milliseconds into the video (type 'frame'). 3000 = 0:03.", + "maximum": 9007199254740991, + "minimum": 0, + "type": "integer" + }, + "type": { + "description": "'frame' uses the video frame at thumb_offset; 'custom' uploads the image at cover_url.", + "enum": [ + "frame", + "custom" + ], + "type": "string" + } + }, + "required": [ + "type" + ], + "type": "object" +} - changed
Input schema / properties / youtube / descriptionPrevious value: -"YouTube Shorts options. Only applies when type is 'reel' and youtube is among the selected channels."New value: +"YouTube Shorts options. Only applies when type is 'reel' and youtube is among the selected channels. A custom Shorts thumbnail is set with the top-level `video_cover` (a `youtube` override for a YouTube-only image); it shows on Shorts only on channels where YouTube has enabled custom Shorts thumbnails (Partner Program channels first, since July 2026), other channels show a frame from the video."
- Changed
update_post5 fields changed- added
Input schema / properties / facebook / properties / cover_urlAdded value: +{ + "description": "Custom thumbnail image URL (JPEG/PNG, max 10 MB). Used with thumbnail_type 'from-library'.", + "type": "string" +} - added
Input schema / properties / facebook / properties / thumb_offsetAdded value: +{ + "description": "Frame timestamp in MILLISECONDS from the start of the video (e.g. 3000 = 0:03). Used with thumbnail_type 'from-video'.", + "type": "number" +} - added
Input schema / properties / facebook / properties / thumbnail_typeAdded value: +{ + "anyOf": [ + { + "enum": [ + "from-video", + "from-library" + ], + "type": "string" + }, + { + "type": "null" + } + ], + "description": "Video thumbnail for Facebook feed videos and reels: 'from-video' uses the frame at thumb_offset, 'from-library' uploads the image at cover_url. Applied after the video is live; a thumbnail failure never fails the post. On update_post, null removes the Facebook override." +} - added
Input schema / properties / video_coverAdded value: +{ + "anyOf": [ + { + "description": "Video thumbnail for a post whose media is ONE video. Applied on Instagram (feed videos and reels), Facebook (feed videos and reels), LinkedIn Profile and Page, TikTok, Pinterest and YouTube Shorts. YouTube Shorts: the cover shows on Shorts only on channels where YouTube has enabled custom Shorts thumbnails (rolling out since July 2026, Partner Program channels first); on other channels YouTube stores it as the default thumbnail but shows a frame from the video on Shorts. Say that it depends on the channel; do not promise it. TikTok only takes a frame: a 'custom' cover is skipped there, so add a tiktok override with type 'frame' when the user wants a specific TikTok frame. The per-platform reel fields (instagram.thumb_offset / cover_url, tiktok.video_cover_timestamp_ms, pinterest.video_cover) keep working and win over the base cover for their platform. get_post reads it back as `video_cover`.", + "properties": { + "cover_url": { + "description": "Public image URL, JPEG or PNG (type 'custom').", + "type": "string" + }, + "overrides": { + "additionalProperties": { + "anyOf": [ + { + "properties": { + "cover_url": { + "description": "Public image URL, JPEG or PNG (type 'custom').", + "type": "string" + }, + "thumb_offset": { + "description": "Milliseconds into the video (type 'frame'). 3000 = 0:03.", + "maximum": 9007199254740991, + "minimum": 0, + "type": "integer" + }, + "type": { + "description": "'frame' uses the video frame at thumb_offset; 'custom' uploads the image at cover_url.", + "enum": [ + "frame", + "custom" + ], + "type": "string" + } + }, + "required": [ + "type" + ], + "type": "object" + }, + { + "type": "null" + } + ] + }, + "description": "Per-platform overrides keyed by platform id (instagram, facebook, linkedin, linkedin_page, tiktok, pinterest, youtube). An override wins over the base cover for that platform.", + "propertyNames": { + "type": "string" + }, + "type": "object" + }, + "thumb_offset": { + "description": "Milliseconds into the video (type 'frame'). 3000 = 0:03.", + "maximum": 9007199254740991, + "minimum": 0, + "type": "integer" + }, + "type": { + "description": "'frame' uses the video frame at thumb_offset; 'custom' uploads the image at cover_url.", + "enum": [ + "frame", + "custom" + ], + "type": "string" + } + }, + "required": [ + "type" + ], + "type": "object" + }, + { + "type": "null" + } + ], + "description": "Replaces the stored video cover wholesale; pass null to remove it; omit to leave it untouched. facebook.thumbnail_type / thumb_offset / cover_url merge into overrides.facebook on their own." +} - changed
Input schema / properties / youtube / descriptionPrevious value: -"YouTube Shorts options. Only applies when type is 'reel' and youtube is among the selected channels."New value: +"YouTube Shorts options. Only applies when type is 'reel' and youtube is among the selected channels. A custom Shorts thumbnail is set with the top-level `video_cover` (a `youtube` override for a YouTube-only image); it shows on Shorts only on channels where YouTube has enabled custom Shorts thumbnails (Partner Program channels first, since July 2026), other channels show a frame from the video."
48 tool updates
- First observed
approve_post - First observed
check_media_compatibility - First observed
create_and_publish_post - First observed
create_folder - First observed
create_hashtag_set - First observed
create_post - First observed
create_webhook - First observed
delete_hashtag_set - First observed
delete_inbox_comment - First observed
delete_media - First observed
delete_post - First observed
delete_webhook - First observed
get_account - First observed
get_account_analytics - First observed
get_analytics_overview - First observed
get_best_times - First observed
get_calendar - First observed
get_inbox_conversation - First observed
get_next_unanswered - First observed
get_post - First observed
get_post_analytics - First observed
get_posts_analytics - First observed
get_recent_platform_posts - First observed
get_webhook - First observed
hide_inbox_comment - First observed
list_accounts - First observed
list_approval_workflows - First observed
list_folders - First observed
list_hashtag_sets - First observed
list_inbox_conversations - First observed
list_media - First observed
list_posts - First observed
list_webhooks - First observed
list_workspaces - First observed
mark_inbox_read - First observed
publish_post - First observed
reject_post - First observed
reply_to_inbox - First observed
retry_post - First observed
rotate_webhook_secret - First observed
search_instagram_audio - First observed
search_locations - First observed
switch_workspace - First observed
update_hashtag_set - First observed
update_media - First observed
update_post - First observed
update_webhook - First observed
upload_media
Related MCP Servers
- AlicenseNot gradedqualityCmaintenancePerplexity for social: ask what competitors are running across social and get answers grounded in real ad and creative data, not guesses.2Apache 2.0
- AlicenseCqualityBmaintenanceCompetitor Monitor AI - MCP server providing AI-powered tools and automation by MEOK AI Labs113 npm54 PyPIMIT
- AlicenseAqualityCmaintenanceEnables brand visibility monitoring across major AI platforms like ChatGPT, Claude, Gemini, and Perplexity. It allows users to track visibility scores, analyze competitor data, and receive actionable insights to improve AI-generated brand recommendations.1618 npm1MIT

industrylens-mcpofficial
AlicenseNot gradedqualityBmaintenanceBrowse IndustryLens's published competitive-intelligence reports and head-to-head competitor comparisons from any AI agent — real, source-backed data.MIT
Glama MCP Gateway
Add one secure layer between your agents and this server.