MCP App Store
by KeenEthics

Overview

Scripe is the content system for teams that post on LinkedIn. Connect your Scripe account to plan a period of posts for every profile you manage, turn ideas into drafts written in each person's own voice, schedule them on the calendar and read how they performed. What you can ask for: - A content plan for one or several profiles, built from their goals, open calendar slots, what performs in their niche and their own results. Nothing is saved until you approve the plan. - Posts drafted in the profile's own voice, using its tone of voice, past posts and knowledge base. - Ideas saved to the idea board, and Scripe's suggested ideas for each profile. - The calendar, scheduled posts and posting times. - Analytics: impressions, engagement and which posts and formats performed best. Limits: you need a Scripe account, and the plugin only reaches the workspaces and profiles your account can open. Publishing a post to LinkedIn right away, deleting a post and sending a review request or question to a colleague each ask for your confirmation first; a post you schedule goes out on its own at the time you set. Scripe never likes, comments on or reposts other people's LinkedIn posts for you.

Tools

add_post_media

ChatGPT
add_post_media — put a visual on Scripe posts, many at once (up to 20). Per item source: "recommended" (the visual the data picks — get_post_media_options explains it: a fitting media-library photo, else a Scripe template visual, else none); "library" (mediaIds from the media library — search_media, get_post_media_options — or an image YOU made and uploaded with create_media_asset); or "scripe" (Scripe makes format — QUOTE_CARD, CAROUSEL, INFOGRAPHIC, BILLBOARD, MEME — from its own templates in the workspace's brand; pass direction, what it shows; an INFOGRAPHIC needs it). TWO-PHASE: the first call attaches and makes NOTHING — it returns a PREVIEW of the visual each post would get (the library picture, or what Scripe would make: format and direction), whether it uses Scripe AI credits, and confirmItems (exactly that plan), plus a confirmationToken. Show the user the preview and wait for their explicit yes; only then call again with items: confirmItems (or the same arguments) plus the token. Never confirm for the user, not even on autopilot. Library pictures attach in the confirmed call; anything Scripe makes runs in the background (about a minute, in parallel) — poll get_draft_run with the returned runId. A post that already has media keeps it unless replace: true. Scripe never generates a photo of a person: a post that wants one and has none gets a template visual, and the preview says a real photo would do better. Nothing is scheduled.

add_profile_to_list

ChatGPT
add_profile_to_list adds one LinkedIn person to a Scripe community profile list, so Scripe starts collecting their posts for the customer to read and engage with under Community → Profiles. Use it for "add this lead to my Prospects list". profile MUST be the person's LinkedIn profile address — a full URL, a country-subdomain URL, a URL with tracking parameters, or a bare handle all work (company pages do not). NEVER PASS A NAME: Scripe cannot look a person up by name, so a name is refused or, as a single word, read as somebody's handle; ask the user for the linkedin.com/in/… URL or read it off the CRM record you already have. Optionally pass note (≤500 characters) — why they are on the list, e.g. "Hot lead from Acme, demo 20 Sep". Get the plist_… id from list_profile_lists. Adding somebody who is already on the list is reported, not duplicated. This tool does NOT like, comment on or repost anything — every engagement in Scripe is an explicit human click in the dashboard. Requires community:write.

add_profiles_to_list

ChatGPT
add_profiles_to_list adds SEVERAL LinkedIn people to one Scripe community profile list in a single call (up to 25 per call), so Scripe starts collecting their posts under Community → Profiles. PREFER THIS over calling add_profile_to_list once per person whenever you are adding more than one person, building or filling a list, or importing leads from a CRM: one call fills a list. Each entry's profile MUST be the person's LinkedIn profile address — a full URL, a country-subdomain URL, a URL with tracking parameters, or a bare handle (company pages do not work). NEVER PASS A NAME: Scripe cannot look a person up by name. The call never fails as a whole for one bad profile: every entry comes back with its own status — added, already_member (they were on the list already; that is a success, nothing was duplicated), refused (with the reason), duplicate (the same person appears earlier in the call) or not_attempted (the call ran out of time, or a daily or list limit stopped it). If notAttempted is not empty and stoppedBy is null, call again with exactly those profiles. Get the plist_… id from list_profile_lists. Re-sending a profile is safe: it comes back already_member. This tool does NOT like, comment on or repost anything. Requires community:write.

add_to_knowledge_base

ChatGPT
add_to_knowledge_base — asynchronous ingest into the Scripe knowledge base. The indexed document becomes available to RAG-aware tools (e.g. generate_post). Pick the type that matches the source: - text — plain text the host already extracted; pass text + name. - file — file content. Small files (≤ ~3 MB decoded): inline content_base64 + mimeType + filename (+ sha256 when you can compute it; server uploads to S3 for you). Anything larger MUST go two-step — uploadId from create_upload_url — because over-cap inline payloads die at the platform edge as a bare HTTP 413. - url — webpage URL; pass url. - youtube — YouTube URL; pass url. Project scoping: omit projectId to use the workspace default; pass null explicitly for a workspace-wide entry (e.g. "my org's KB"). Returns a Job envelope; get_knowledge_ingest(jobId) says processing, ready (with the document id) or failed (with the reason). Scripe stores and indexes a text within seconds. LONG TEXT IS SLOW ON YOUR SIDE, not ours: every character of text is written out as this call's argument before Scripe receives it — roughly a minute per 20,000 characters (a 15–20 minute call transcript is ~50,000 characters, about 2.5 minutes). Before sending anything that long, tell the user how long it will take and offer the faster ways in: they paste it themselves under Knowledge → Add knowledge in the Scripe dashboard, or connect their meeting tool (Granola) there so transcripts arrive on their own. Never re-send a long text because the call seemed slow — the same text sent to the same place again within minutes returns the first ingest rather than a second copy (marked deduplicated when only the name or other arguments differ).

answer_content_question

ChatGPT
answer_content_question — answer a Scripe content question that was sent to the signed-in user THEMSELF (only the respondent can answer; nobody answers on someone else's behalf). Answering again replaces the earlier answer. recipientId is optional — omitted, the user's own recipient row on the question is used.

assign_content_topic

ChatGPT
assign_content_topic assigns an existing Scripe content topic (the dashboard's TOPIC GROUP / Thema, Settings → Organization → Positioning) to one or more people/brands, so Scripe builds their post ideas around it. ADDS to the current assignment — people the topic already has keep it, and naming someone who already has it is a no-op reported under alreadyAssigned. Identify the topic by wct_… id or exact title and each person by proj_… id or exact display name; an unknown or ambiguous name is refused with the candidates. Call list_content_topics first to see topics and current assignments; to create a new topic use create_content_topic. Requires settings:write and a workspace ADMIN acting user.

attach_media_to_idea

ChatGPT
attach_media_to_idea — set a Scripe board idea's media in one FULL-STATE write: it replaces whatever the idea carried, so to add an image read media from get_idea first and send the existing img_… ids alongside the new one. Takes image-library assets only, as { kind: "images", images: [{ assetId: "img_…" }] } (ids from search_media, a finished generate_image job, or create_media_asset), or kind: "none" to clear the media decision — which clears the idea's visual format with it, and changes nothing at all on an idea that carries no media (the visual format alone is just a brief label; clear that with update_idea). An idea's media is what its eventual LinkedIn post will carry: plain images (max 20, first = cover) or ONE carousel that carries a cover image (attached alone; that cover becomes the media image and the visual format becomes CAROUSEL) — including a carousel built by the generate_carousel job, whose rendered deck now stores a durable cover (one generated before covers existed has none and is refused permanently rather than temporarily). It cannot carry video files, PDFs, or raw URLs — unlike attach_media_to_post there is no key branch. A just-created asset is refused until Scripe has re-hosted it on its CDN (usually seconds — retry shortly); unlike attach_media_to_post, status: "READY" is not the signal here, because an idea stores the image URL and only the durable one may be stored. Finally, reference-only style picks (shown by get_idea as mode: "reference") are chosen in the Scripe app, not writable here. Because the write is full-state, it also DISCARDS a style pick the idea was carrying — with either kind — and a discarded pick cannot be recreated through this API; check get_idea for mode: "reference" first and confirm with the user before replacing it. projectId is optional — omitted, it targets the connection's default project and the response names it. Returns the idea's resulting media.

attach_media_to_post

ChatGPT
attach_media_to_post — set a Scripe post's media in one FULL-STATE write: it replaces whatever the post carried, so to add a second image read media from get_post first and send the existing entries alongside the new one. Attach library images with { source: "library", assetId: "img_…" } (ids from search_media, a finished generate_image job, or create_media_asset — which is how the user's own image file gets an id); { source: "key", key } is for a key the post already carries — an img_… id, an upl_… upload handle or a displayUrl is refused there. Also takes a video, a PDF document, or kind: "none" to clear. LinkedIn's structural rules are encoded in the shape: images cannot mix with video, max 20 images. Returns the post's resulting media.

cancel_job

ChatGPT
cancel_job — cancel a queued Scripe job. Returns the updated job. Only QUEUED jobs are cancellable in v1; RUNNING returns a not_cancellable error.

check_plan_ideas

ChatGPT
check_plan_ideas — Scripe's plan-quality check on a DRAFT plan, before preview_plan: send every idea of the plan at once (up to 200: projectId, title, angle, hook, an optional label) and get the warnings the preview would give — one angle twice within a profile or across profiles, an item that is only a title. Use it for a plan longer than one preview (60 items, e.g. several weeks for many profiles), which you then preview in parts: no single preview sees two parts side by side. Fix what you agree with, then preview. Reads and writes nothing; costs no AI.

check_post_readiness

ChatGPT
check_post_readiness — is each Scripe post finished enough to send for review? Up to 20 posts (post_…). Per post the checks with pass / warn / fail and what to do: text within LinkedIn's limit, an opening line LinkedIn would not cut before "…more", leftover placeholders ([Name], TODO) or markup (bold, headings, HTML) that LinkedIn shows as plain characters, styled bold/italic letters the brand has not turned on (screen readers cannot read them), @Name text that would publish as plain text instead of a tag, hashtags against the profile's own habit, a visual where the post type reads best with one, images without alt text — plus the review state and whether the workspace requires an approval. ready means no check FAILED (warnings are the reviewer's call). Fix fails before request_review: rewrite text with your post tools, tag people and pages with tag_post_mentions, add a visual with add_post_media.

commit_plan

ChatGPT
commit_plan — step 2 of Scripe planning: write a plan preview_plan returned, in ONE call, once the user has seen the plan and said yes (unless they asked you to plan without asking). Every ready item (or only the itemKeys you pass) becomes a board idea — created from your text, saved from For You, or the existing one — planned INTO its slot, so the slot reads planned (reserved) in the user's calendar, goal card and every planning read. Each slot is re-checked first: one taken since the preview is reported as conflict, never overwritten. Idempotent — calling it again returns the first commit's results, and retries only items that failed. Creates ideas only: no post, nothing scheduled. Next: write the posts with draft_planned_posts, or leave the ideas planned for the team.

create_campaign

ChatGPT
create_campaign — create a campaign in the Scripe workspace: a title, start and end date, and optionally an emoji, a one-line summary, the brief (description — what the posts should say), a status (default draft), the profiles it is for (profileIds; omitted = workspace-wide) and labels. Put posts into it with set_post_campaign.

create_content_question

ChatGPT
create_content_question — add a content question to a Scripe idea: something the post needs from a person (a detail, a number, a story). By default it is saved as a DRAFT assigned to whoever answers for profileIds (or the people in respondentUserIds). With addToCheckIn: true it goes straight into the next content check-in for respondentUserIds (the idea page's "Add"), which needs at least one person and the check-in switched on. Send a draft later with send_content_question.

create_content_topic

ChatGPT
create_content_topic adds a content topic (the Scripe dashboard calls it a TOPIC GROUP) to a Scripe workspace — one of the themes the workspace wants to be known for on LinkedIn, which Scripe mines the LinkedIn corpus around and builds post ideas from. This is the list under Settings → Organization → Positioning, NOT the positioning documents (update_positioning), NOT a brand's tone of voice (update_tone_of_voice), NOT the topics a recording was cut into (get_source), and NOT a single post idea (create_idea). Optionally assign the topic to brands with profileIds — a topic assigned to no brand is created and listed but influences no generation until it is assigned. Requires settings:write and a workspace ADMIN acting user.

create_idea

ChatGPT
create_idea / createIdea — add an idea to a Scripe project's idea board, at the top of its column — exactly like creating a card on the board. The tool for capturing ideas still to be written — topics, angles, briefs ("send these post ideas to my project in Scripe"). NOT for finished post text: a ready-to-post LinkedIn text is a post draft (create_post_draft on the Scripe API), and any "post draft" ask means that tool, not this one. When the user hands over written-out post text without saying idea or post draft, do not guess — ask which they want first. Takes the creative brief (title, body, pillar, post format, visual format, hook, topic) and an optional campaignId (from list_campaigns) to file it under a campaign — a post later written from it joins the same campaign. projectId is optional: omit it and the idea lands in the connection's default project, which the response names back — say that name to the user. Board placement on a calendar day is a separate step (scheduleIdea / schedule_idea); this tool never creates a post or a LinkedIn schedule. Statuses: only 'inbox' (default) or 'in_production' can be set — review/done are derived from the linked post.

create_label

ChatGPT
create_label — create a new label in the Scripe workspace, the same label the dashboard's Settings → Labels page creates. Check list_labels first so you do not create a duplicate. color is optional (the next colour of the dashboard's palette when omitted). Apply it to posts with update_post_labels.

create_media_asset

ChatGPT
create_media_asset — add the user's OWN image to a Scripe project's media library — send the bytes inline as content_base64 (small files only, ~3 MB decoded max — larger requests die at the platform edge as a bare 413), or pass an uploadId from create_upload_url once you have PUT the bytes to its signed URL (preferred for anything larger). This is the step between having an image file and putting it on a post: the returned img_… id goes straight into attach_media_to_post({ media: { kind: "images", images: [{ source: "library", assetId }] } }), and it is attachable immediately even though status is "PROCESSING" (Cloudflare re-hosting and auto-tagging finish in the background; search_media lists it once they do). Images only — PDFs and documents belong in add_to_knowledge_base, audio and video in create_source_file. Re-sending the same bytes returns the asset already created.

create_note

ChatGPT
create_note — add a note to a Scripe project. Notes are short-form thoughts that can later seed a generated LinkedIn post. Returns the created note shape.

create_post_draft

ChatGPT
create_post_draft — save the user's own text as a real LinkedIn post in a Scripe project: it lands with the project's posts (NOT on the idea board), ready to edit, schedule and publish. Any "post draft" ask means this tool — never create_idea, which captures an idea to write later. When an ask like "send this to my Scripe project" carries finished post text but names neither, ask whether they want a post draft or an idea card before writing. Stores the text verbatim — generate_post is the one that AI-writes a draft. Pass scheduledFor (ISO timestamp) to schedule it; omit or null for a draft. Returns the created post.

create_source_file

ChatGPT
create_source_file — asynchronous ingest of an audio / video / pdf / image / docx file into Scripe as a source for LinkedIn drafting. Two paths: - Two-step (preferred for anything but small files): pass uploadId returned by create_upload_url after you PUT bytes to the signed URL yourself. A real audio/video recording only fits this path. - Inline (small files, ≤ ~3 MB decoded): pass content_base64 + mimeType + filename (+ sha256 of the decoded bytes when you can compute it). The server uploads to S3 on your behalf. Payloads over the cap are rejected at the platform edge as a bare HTTP 413 with no error envelope — pre-check the file size instead of retrying. Returns a Job envelope; if the host passes _meta.progressToken, the tool also streams notifications/progress until the job reaches a terminal state (or 25s elapse). When the job reports status: DONE, call get_source(result.sourceId): it returns a transcript preview and the topics the file was cut into, best-first. Pick a topic with the user, then call generate_post({ source: { type: 'topic', topicId } }) — the server reads that topic's transcript chunk itself. You do not need a hook; the generator writes its own.

create_source_text

ChatGPT
create_source_text — create a Scripe source (long-form input for LinkedIn drafting) directly from caller-supplied text. Synchronous; the text becomes the transcription verbatim. Use this for raw writeups, transcripts, or notes you want to feed into post generation.

create_upload_url

ChatGPT
create_upload_url — mint a presigned PUT URL for uploading bytes into Scripe directly. Returns { id, uploadUrl, method, contentType, maxSizeBytes, expiresAt }. After PUT, hand the returned id to the tool that consumes it as uploadId: create_media_asset for an image destined for a post, create_source_file for a recording or document to make posts from, add_to_knowledge_base (type=file) for reference material. The handle is not itself a media key — nothing accepts it in place of one. This is the PREFERRED path for anything but small files: the inline content_base64 alternative on all three consumers caps at ~3 MB decoded (larger inline payloads are rejected at the platform edge as a bare HTTP 413), while a signed PUT takes the full per-type caps (image 25 MB, PDF/docx 100 MB, audio/video 500 MB) and keeps the bytes out of model output entirely.

delete_campaign

ChatGPT
delete_campaign — PERMANENTLY delete a Scripe campaign with its attachments and comments. Its posts and ideas are KEPT and simply lose the campaign. TWO-PHASE by design: the first call WITHOUT confirmationToken returns a PREVIEW (how many posts and ideas lose it, what is deleted) plus a token — nothing is deleted yet. Show it to the user; after they explicitly confirm, call again with the SAME arguments plus the token. To end a campaign without deleting it, set its status to completed or archived with update_campaign.

delete_content_question

ChatGPT
delete_content_question — delete a content question from a Scripe idea. A scheduled question is taken out of the check-in it was waiting for. TWO-PHASE by design: the first call WITHOUT confirmationToken returns a PREVIEW plus a token — nothing is deleted yet. Show it to the user; after they explicitly confirm, call again with the SAME arguments plus the token. Requires the ideas:destroy scope.

delete_idea

ChatGPT
delete_idea — PERMANENTLY delete an idea from a Scripe idea board, and everything attached to it (assignments, sources, activity, labels, post links, input requests — recipients' public answer links stop working). Linked posts are NOT deleted. TWO-PHASE by design: first call WITHOUT confirmationToken returns a cascade PREVIEW plus a token — nothing is deleted yet. Show the preview to the user; after they explicitly confirm, call again with the SAME arguments plus the token. Requires the ideas:destroy scope, which is never implied by any other scope. projectId is optional — omitted, it targets the connection's default project, which the PREVIEW names: read that name back to the user before they confirm. This cannot be undone.

delete_knowledge_doc

ChatGPT
delete_knowledge_doc — PERMANENTLY delete a Scripe knowledge-base document. TWO-PHASE by design. First call WITHOUT confirmationToken: you get a PROPOSAL naming everything the delete removes (the document, every text chunk and its embedding, the project-visibility assignments, and any stored file object) — nothing is deleted yet. Show it to the user; after they explicitly confirm, call again with the SAME arguments plus the token. Irreversible. Requires the knowledge:destroy scope (never implied by knowledge:write or any alias). Workspace-wide documents additionally require workspace-admin authority. Anything add_to_knowledge_base created is deletable here, including a page ingested with type: "url"; only a document that is one page of a dashboard website/Notion SYNC refuses — the next sync run would restore it, so that sync is managed in the dashboard.

delete_label

ChatGPT
delete_label — PERMANENTLY delete a Scripe label. It is removed from every post, LinkedIn post, idea, calendar slot, media asset and campaign it is on; the posts and ideas themselves are kept. TWO-PHASE by design: the first call WITHOUT confirmationToken returns a PREVIEW of everything the label is applied to plus a token — nothing is deleted yet. Show the preview to the user; after they explicitly confirm, call again with the SAME arguments plus the token. To take a label off some posts only, use update_post_labels instead. Cannot be undone.

delete_media_asset

ChatGPT
delete_media_asset — remove an image from a Scripe project's media library — TWO-PHASE by design, and the undo for a create_media_asset or generate_image the user did not want. The image disappears from search_media, the dashboard's pickers, and every future attach_media_to_post or generation reference. What SURVIVES, and for how long: posts, carousels and saved templates the image is already attached to keep it for 30 DAYS (they carry their own copy of the stored file), after which the retention sweeps erase the stored file, every earlier version of it and the CDN copy, and those embedded references return 404 — so a post scheduled to publish more than 30 days out WILL lose this image, and you must say so when the user has one. Every version is erased, a re-rendered carousel or card included. An already-published LinkedIn post is untouched (LinkedIn hosts its own copy), and a LinkedIn-synced photo will not be re-imported by the sync. First call WITHOUT confirmationToken returns the proposal; replay with the token to execute. Requires the media:destroy scope, which media:write and the write alias never imply — a connection without it must be re-authorized. Find ids with search_media — but deleting an image needs access to the project that OWNS it, and search_media also lists images merely SHARED into a project (assignment is enough to attach one to a post, never to delete it). Deleting one of those answers not_found like a nonexistent id does; report it as owned by a different project — do NOT tell the user the image does not exist.

delete_note

ChatGPT
delete_note — remove a Scripe note. DEFAULT: soft ARCHIVE — the note moves into the project's Archive folder, stays restorable from the dashboard, and no confirmation is needed (rides notes:write). With permanent: true the note AND its paired calendar slot are removed forever — that path is TWO-PHASE (first call returns a proposal + confirmationToken; replay with the token after the user confirms) and requires the notes:destroy scope, which notes:write never implies.

delete_post

ChatGPT
delete_post — PERMANENTLY delete a Scripe post — TWO-PHASE by design, and the only way to remove a post the user did not want. Posts have NO archive: this deletes the row, its calendar slot, its version history and variations, its carousel, its comments and labels, and any armed team engagement, and it clears the idea-board card's link to it. Nothing restores it. If the post is already PUBLISHED, deleting it here does NOT remove it from LinkedIn — the LinkedIn post stays live and its analytics history is kept but stops linking back; say so before the user confirms, because "delete my post" usually means LinkedIn. First call WITHOUT confirmationToken returns the proposal (title, status, excerpt, what goes with it, whether the LinkedIn copy survives); replay with the token to execute. Requires the posts:destroy scope, which posts:write and the write alias never imply — a connection without it must be re-authorized. To take a post out of the schedule instead, use update_post with scheduledFor: null (reversible).

delete_source

ChatGPT
delete_source — PERMANENTLY delete a Scripe source (a transcribed long-form input) — TWO-PHASE by design. This deletes the source row, its full transcript (paragraphs and sentences), its topics and their hooks, its knowledge-base copy with the embeddings, and the stored audio/video/file object. Nothing restores it. It is NOT total erasure: posts generated from the source are the user's content and are KEPT, and the usage accounting ledger survives — the proposal names both, say so before the user confirms. First call WITHOUT confirmationToken returns the proposal (name, status, what goes, what is kept); replay with the token to execute. Requires the sources:destroy scope, which sources:write and the write alias never imply — a connection without it must be re-authorized. Find ids with list_sources. To delete a knowledge document instead, use delete_knowledge_doc.

dismiss_for_you_idea

ChatGPT
dismiss_for_you_idea — "Not interested" on a Scripe "For you" card: hides the idea for EVERY profile it suits and teaches Scripe to stop suggesting similar ideas. Reversible: restore: true brings it back (the card's Undo). Needs access to the profile that generated the idea. Idempotent. Only dismiss when the user said so — an idea you simply did not pick stays.

draft_planned_posts

ChatGPT
draft_planned_posts — step 3 of Scripe planning: turn ideas planned into slots into DRAFT posts in those same slots, up to 20 per call. By default SCRIPE writes them (mode "scripe"): the app's own pipeline — hook options generated in each post's lane, the post written in the profile's voice with its positioning, knowledge and own posts, then Scripe's voice pass that removes AI phrasing. Per item pass the ideaId and, whenever you researched, research: everything you learned for THAT post — the angle and why, the slot's intent in the plan, the exact facts, numbers and quotes (as the source states them) and their sources (search_knowledge passages, planning signals, posts, pages). Scripe's writer uses it with the profile's voice, positioning and LinkedIn data, so the post carries your specifics. Optional hook: an opening line the user chose, used verbatim; notes: short direction. Do NOT write the posts yourself first: Scripe's writer is the better writer for this profile and runs on Scripe's AI budget, not your tokens. Writing runs in the background (about a minute per post, in parallel): the call answers at once with a runId — poll get_draft_run until every item is done, then show the user the links. mode: "agent_text" (with your own content per item) is only for when the user explicitly asked YOU to write the text. Any item may instead pass an existing unscheduled postId to place. teamEngagement: true also sets up the workspace's standard team engagement on each post (teammates' likes and comments in their own voice, as the post editor's "Generate engagements"; Advanced+). Each draft lands at its idea's slot instant, linked to the idea, and is never scheduled on LinkedIn. Idempotent per idea. This call adds no visual and sends nothing for review: once the drafts exist, add_post_media and request_review each show the user a preview and act only after their yes. Scheduling stays the separate schedule_post, which schedules live on the first call.

draft_positioning_from_website

ChatGPT
draft_positioning_from_website is Scripe's website sync: it reads a company's own website and DRAFTS the workspace's positioning from it — company description, mission, vision, core statements, audience line, promised results, and the target-audience document. This WRITES NOTHING. Show the draft to the user, then call update_positioning with the parts they accept. wouldFill names the fields that are still EMPTY (a direct write) and wouldReplace the ones that already hold text (allowed, but only through the overwrite confirmation — show the user what is there first). Both use update_positioning's own field names. Use it for "pull our positioning from acme.dev".

fill_calendar_slot

ChatGPT
fill_calendar_slot — put a post into one planned Scripe posting slot as a DRAFT (never scheduled to LinkedIn). Either write it: content (the finished post text you wrote, plain text) plus, optionally, the idea it came from — forYouIdeaId (a For You idea, saved to the board first) or ideaId (a board idea) — or move an existing unscheduled post there with postId. slotAt is a slot's at from list_calendar_slots; the slot must be EMPTY. Use an idea of the slot's lane, or the slot stays empty in the goal's reading (laneMatchesSlot). Optional campaignId files the post under a campaign. Idempotent: the same source into the same slot returns the first draft (created: false). To actually publish at the slot time, call schedule_post with the returned post id and scheduledFor = slotAt — only after the user approved; it runs the review gate and the LinkedIn check.

generate_image

ChatGPT
generate_image — AI-generate a raster image into a Scripe project's media library. Returns a Job envelope; on completion the result carries the new img_… media id (usable with search_media / attach_media_to_post). A picture that shows the user themselves is never made from words alone: ask the user for a photo of themselves, then pass kind PHOTO_EDIT with its id in subjectMediaIds — a PHOTO of them is refused. Spend-capped per workspace per day — a 402 means the daily AI budget is exhausted, not that the request was malformed. Set wait_for_completion: true to block up to 18 seconds; that is under the request deadline, so a slower generation comes back RUNNING and you poll get_job(jobId) from there.

generate_post

ChatGPT
generate_post — AI-write a LinkedIn post draft in Scripe from inline text, an existing note, an idea on the board (source.type='idea' with an idea_* id from list_ideas — that is how an idea becomes a post; the post is linked to the idea, whose status becomes in_production if no post was linked yet, and its board column is left as it is), or a topic detected on an uploaded source (source.type='topic' with a tpc_* id from get_source — that is how a recording or document becomes a post). Returns a Job envelope: generation takes ~35 seconds, so the post does NOT exist yet when this returns. Poll get_job(jobId) until status is DONE, then read result.postId — that is the id of the generated post, for get_post / update_post. wait_for_completion: true blocks for up to 18 seconds first, which usually still comes back RUNNING; it saves a poll, it does not remove the need to poll.

generate_post_ideas

ChatGPT
generate_post_ideas turns material into LinkedIn post ideas in Scripe — the same suggested ideas the Scripe dashboard shows: each is saved to the brand's idea pool ("Suggested ideas for you" → "Your files") with a title, a hook, an angle and a brief that cites the passages of the material it was built on. Build on text the user pasted (an article, notes, a transcript), on a knowledge document by knowledgeDocumentId (kb_… from list_knowledge), or on nothing but the request. It does NOT write to the idea board — call create_idea with an idea's title and hook to put it there — and it is NOT generate_post (which writes a post) or search_viral_posts (a read). One premium model call per invocation, capped per brand per hour; requires ideas:write.

get_analytics_overview

ChatGPT
get_analytics_overview — current vs previous-period LinkedIn analytics rollup for one or more Scripe projects: post count, impressions, engagement rate, follower growth, and posting activity. Mirrors the in-app dashboard.

get_analytics_report

ChatGPT
get_analytics_report — the full LinkedIn analytics report for one or more Scripe projects over a date range: executive summary (posts, impressions, likes/comments/shares, engagement rate, follower growth, earned media value), per-author performance, the top posts, the daily engagement series, and the follower-count timeline. This is the JSON twin of REST's GET /v1/analytics/report (which renders it as PDF/CSV). Use get_analytics_overview for a lightweight rollup; use this when you need day-by-day series or the follower timeline. In daily[] every figure is that day's own — including engagementRate, which is 0 on a day with no impressions; cumulativeEngagementRate is the separate running rate from the start of the range, so read that one for a trend and engagementRate to compare days. posts[] holds the genuine top 20 of the whole period by impressions; postsTotal counts every post in the period, and list_post_analytics pages through all of them. posts[].content is a ~100-character excerpt (contentTruncated says so); to act on one, use its postId with get_post, which is null when the post was not published through Scripe. summary carries THREE click figures and the dashboard never adds them up: totalLinkClicks is LinkedIn's count of clicks on links inside the period's posts (the dashboard's "Link clicks (LinkedIn)" KPI card); totalTrackedLinkClicks is clicks on the workspace's Scripe tracked links by click date, workspace-wide (the "clicks tracked by Scripe" line under the conversion funnel and the Click tracking section — a different source, never added to the LinkedIn figures); totalPremiumCtaClicks is LinkedIn's Premium button clicks, not a link click. Report each under its own name.

get_campaign

ChatGPT
get_campaign — one Scripe campaign in full: its brief (summary + description), dates, status, labels, the profiles it is narrowed to with each profile's progress as the home page's campaign tile shows it (posted / scheduled / in progress / no post yet), and the campaign's posts with their state.

get_content_question

ChatGPT
get_content_question — one content question of a Scripe idea in full: text, why it is asked, status, assignment, every recipient with their status (pending / answered …, and when they were last reminded) and every answer. Recipient ids here are what nudge_content_question and answer_content_question take.

get_cross_workspace_analytics_overview

ChatGPT
get_cross_workspace_analytics_overview — the Scripe LinkedIn analytics rollup (posts, impressions, engagement rate, follower growth, posting activity) for EVERY workspace this connection can reach, in ONE call. This is the tool for "how are all my clients doing" — do NOT loop switch_workspace + get_analytics_overview per workspace, and do not switch workspaces at all to use it. Each row in data.workspaces carries the workspace it belongs to (workspace.id, workspace.name, and workspace.reach: member or agency_owner), so name the workspace beside every figure you report. data.totals is the same figures over all of them together, computed by one query rather than summed — read it instead of adding the rows up, and report no total at all when it is null (meta says why). meta.skipped names each reachable workspace with no projects you can read: that is not zero engagement, it is no visibility. meta.projects_truncated names any workspace measured on only its newest projects — say so rather than presenting its figures as complete. When meta.truncated is true you are reading the first meta.max_workspaces reachable workspaces — say so, and name the rest explicitly in workspaceId to cover them. meta.workspaces_reachable is the caller's FULL reach on either selector, not the number named and not a truncation signal. Use get_analytics_overview for one workspace or specific projects.

get_cross_workspace_analytics_report

ChatGPT
get_cross_workspace_analytics_report — the full Scripe LinkedIn analytics report (executive summary, earned media value, per-author performance, top posts, daily engagement series, follower timeline) for every workspace this connection can reach, one report per workspace under data.workspaces[].report beside the workspace it belongs to. The cross-workspace twin of get_analytics_report; use that one for a single workspace, and get_cross_workspace_analytics_overview when a rollup is enough — this returns a whole document per workspace and is much larger. It visits fewer workspaces per call than the overview (meta.max_workspaces) for that reason, so name the workspaces you care about in workspaceId when you have more than that. Each report.posts[] holds only the top meta.posts_per_workspace posts of the period by impressions while report.postsTotal counts them all — page the rest with list_post_analytics one workspace at a time. meta.projects_truncated names any workspace whose report covers only its newest projects; meta.workspaces_reachable is the caller's full reach on either selector, not the number named.

get_draft_run

ChatGPT
get_draft_run — the progress of a Scripe DRAFT RUN, the background work draft_planned_posts (Scripe's default writing mode), a confirmed add_post_media (Scripe-made visuals) and set_up_team_engagement start. Per item: queued → writing → polishing (Scripe's voice pass) → engaging (team engagement, when asked) → done; a visual is queued → adding_media → done; or failed with the reason. A done item carries the post id and its link in Scripe, the opening line the post went out with and the other hook options Scripe generated, the visual on the post (media: attached, or why not) and what team engagement was added (likes, comments). Each post takes about a minute and the items run in parallel; pass waitSeconds (up to 15) to wait for progress before answering instead of polling in a tight loop. Runs are kept 24 hours and are readable only by the user who started them.

get_engagement_policy

ChatGPT
get_engagement_policy — a Scripe project's engagement-policy defaults (auto-like / comment / reshare: OFF | REQUEST | ON), per-requester overrides, whether engagement CAN be enabled (stored LinkedIn-connection state — no live probe), and the plan-lock state. Engagement actions execute under this project's LinkedIn identity. Answer "is anything engaging as me?" from effective, never from policy: policy: null is the normal state of most projects and means NO policy governs the project, so every engagement naming it is declined — effective reports that as all-OFF with source: "no_policy", versus source: "policy" for stored defaults. The plan lock rides the output: locked workspaces can still read what would unlock.

get_for_you_idea

ChatGPT
get_for_you_idea — one Scripe "For you" idea in full: title, hook, angle, lane and format, the ARGUMENT for it with numbered markers, and every SOURCE it was built on — the origin item (article, video, followed profile, knowledge document) and each cited reference (LinkedIn posts with their numbers, the client's own posts and positioning, knowledge-base passages) with its URL or id and the words of the argument it backs (citedFor) — plus why it was picked. Read it before writing a post from the idea: ground the post in these sources and the client's own material, never invent figures.

get_goals

ChatGPT
get_goals — Scripe's posting GOALS and progress, as the dashboard's goal tile shows them: per profile the goal period (the workspace's planning cycle, 1–12 weeks), the weekly post goal, the lane mix, and per lane (REACH / TRUST / CONVERT) the target, how many are done (published + scheduled), still to do, drafts waiting and over target. Omit projectId for the workspace view: every profile you can access plus per-lane totals. Use it to decide how many posts of which lane a period still needs before filling calendar slots. Lanes: REACH = posts that need no prior relationship and ask nothing of the reader (stories, opinions, relatable takes); TRUST = posts that SHOW first-hand work and expertise (how-tos, lessons, results, behind the scenes); CONVERT = posts that invite the ask from the client's own material (offers, case studies, customer results). A lane is a ration of the posting goal, never a sequence a reader travels through.

get_icp

ChatGPT
get_icp reads a Scripe workspace's Ideal customer (ICP): who it sells to as buyer personas (titles, functions, seniority, buying role), company criteria (industries, company size, countries, languages, company types), good- and bad-fit keywords, never-a-fit titles and industries, named target accounts, customers and competitors, and how strict a fit is. The people who engage with a profile's posts are scored for fit against it. It is workspace-wide; pass projectId to also see what ONE profile is scored against (its own override, the workspace's, or none). Read it before update_icp.

get_idea

ChatGPT
get_idea — one idea from a Scripe idea board, in full: the creative brief (pillar, format, hook, topic), the campaign it is filed under, the capture evidence (angle, proven-idea stats, reference posts, origin), the idea's media (attached images / a carousel cover with img_… asset ids, or a reference-only style pick — edit it with attach_media_to_idea), AI readiness with open clarifying questions, attached source material, and the linked post. The media URL fields (media.images[].imageUrl, media.styleImageUrl) are null unless this connection ALSO holds the media:read scope: images listed with a null imageUrl means the link is withheld, not that the idea has no media — media: null is what no media means. projectId is optional — omitted, it reads the connection's default project and the response names it.

get_job

ChatGPT
get_job — one async Scripe job by id, including a live progress snapshot (percent + stage label) when the worker has reported one.

get_knowledge_doc

ChatGPT
get_knowledge_doc — one Scripe knowledge document: metadata, processing status, tags, the chunk count, and a text preview capped at 2,000 characters — the full body is never returned over the API.

get_knowledge_ingest

ChatGPT
get_knowledge_ingest — whether something sent to the Scripe knowledge base with add_to_knowledge_base is in yet. Pass the jobId that call returned. Answers processing (still being indexed — a text takes seconds; ask again, never re-send it), ready with the documentId of the stored document, failed with the reason nothing was stored, or cancelled.

get_linkedin_performance_insights

ChatGPT
get_linkedin_performance_insights / getLinkedInPerformanceInsights — look up Scripe's LinkedIn Trend Report 2026 (what measurably performs on LinkedIn). Call it BEFORE advising or rewriting whenever the user wants a post to "go viral", get more reach or engagement, or asks what works best: hooks/first line, length, story vs lesson, format (image, photo set, video, carousel), which picture, calls to action, links, hashtags, posting frequency or time, topics, industry or German-language specifics. Returns only the relevant sections with their figures and how to apply them. Pass the user's ask as question, or pick topics.

get_next_free_slot

ChatGPT
get_next_free_slot — the next free LinkedIn posting slot for a Scripe project, from its posting-time template (falls back to 09:00 on the first open day when no template is configured). Free means: no post already scheduled at that minute and nothing else on the calendar that day — so after you schedule something into the slot, calling this again returns the NEXT one, which is how you spread several posts out. Say localTime to the user; do NOT convert iso yourself.

get_note

ChatGPT
get_note — one Scripe note by id (the short-form thoughts that seed LinkedIn posts).

get_personal_dna

ChatGPT
get_personal_dna reads a Scripe profile's positioning — the PERSON document of the content strategy (dashboard: knowledge base → profile folder → Positioning; "You" on the Strategy card): who the author is (intro), their credibility points, their opinions & hot takes, and their tellable stories. PER-PROFILE, unlike the workspace-wide company positioning and target audience (get_positioning). The list-like sections hold one entry per line. Use it before writing anything, so you can tell the user what is already there.

get_planning_overview

ChatGPT
get_planning_overview — START HERE to plan Scripe content: the whole workspace calendar in ONE call. For every profile you can reach (or the profileIds you name — "our", "we" and "everyone" mean every profile you can reach unless the user names people), over ONE range — the current goal period by default, or period: next|previous, weeksAhead: N ("the next 7 weeks"), or explicit from/to — it returns the posting goal per lane (target / done / to do), the planned slots (open ones with their at instant and lane, ones an idea already reserves, drafts, scheduled, published), the idea stock per lane (For You and board), LinkedIn health, and gaps (no schedule, goal bigger than the slots left, a lane with no ideas). Plus the themes the range's calendar already repeats (repeatedThemes: give new ideas other angles), the workspace's goal-period length, whether posts need approval, the campaigns running in the range, and how many reviews and content questions wait for you. The range is echoed with planFrom, the first day that can still take a post. Use the open slots' at values directly in preview_plan; then, in one turn, read the profiles you plan for with get_profile_planning_context (who they are) and get_planning_signals (what works in their niche, what their sources published, their performance, For You with reasons). Lanes: REACH = posts that need no prior relationship and ask nothing of the reader (stories, opinions, relatable takes); TRUST = posts that SHOW first-hand work and expertise (how-tos, lessons, results, behind the scenes); CONVERT = posts that invite the ask from the client's own material (offers, case studies, customer results). A lane is a ration of the posting goal, never a sequence a reader travels through.

get_planning_signals

ChatGPT
get_planning_signals — what is HAPPENING around Scripe profiles, for planning from evidence, in ONE bounded call (up to 10 profiles; omit profileIds for every profile you can reach). Returns: (1) niche — what works on LinkedIn right now among people like each profile: recent posts by OTHER people that beat their own author's usual engagement (outlierMultiple), with opening, format, lane, author and link, each listed once with the profileIds it is relevant to; (2) sourceItems — what the profiles' followed sources published since sourcesSince (default 7 days ago), with each profile's match score and the For You idea it already became; (3) per profile performance — THE source of performance numbers: its own posts of the last 90 days by post format (with lane), lane, media format and content topic, each with a lift against that profile's own median, headed by summary — what performed for that profile, in words: plan more of it and say what you learned; quote a lift from the profile it sits under; (4) per profile idea stock — forYou (the strongest unsaved For You ideas per lane, WHY Scripe picked each and its source) and board (unplaced board ideas); raise ideasPerLane for a long plan instead of paging list_for_you_ideas per profile; (5) knowledge — knowledge-base documents added in the last knowledgeDays (default 30: meetings, interviews, files, synced docs), each with its opening (a recording's chapters) and the profiles that can use it; (6) knowledgeSummaries — per profile the most relevant document Scripe already summarised (its own first, then the one matching its content topics; last 180 days): every chapter with its summary, or a meeting's own summary — cite it by name in an idea's notes; read one whole with read_knowledge_document. Nothing is ranked or chosen for you: weigh it yourself, then write ideas in preview_plan. include narrows the sections; detail: "full" widens every list. Every answer stays under a host's inline limit: trimmed: true says list tails were cut — ask again for fewer profileIds or a narrower include.

get_positioning

ChatGPT
get_positioning reads a Scripe workspace's Positioning: the COMPANY document (what the company does and for whom, mission, vision, core statements, promised results, and the website it was synced from), the TARGET-AUDIENCE document, and the GLOBAL (organization) tone of voice with its plan-lock state. All of it is workspace-wide — every brand in the workspace shares it, including the LinkedIn brands that post from it. Use it before writing anything, so you can tell the user what is already there. Per-brand tone of voice is a different thing (get_settings).

get_post

ChatGPT
get_post — one Scripe post (a LinkedIn post or draft) by id — the full content, which list_posts only excerpts — including the media it will publish with — read that before attach_media_to_post, which is a full-state write — and the workspace status it sits in (statusId / statusTitle / statusCategory, the ids update_post accepts back). When the user asks why a post did not go out, read delivery: state says whether anything will still try, retryUntil when the publisher stops, and detail the reason plus the repair. lastPublishError beside it is the raw message from the last attempt. review says where the post stands in the approval workflow: state (pending means somebody still has to sign it off), reviewerUserId (resolve with list_team), deadline / overdue, and notes — the reviewer's own words when they sent it back, which is the whole substance of a rejection. requiredByWorkspace says whether this workspace expects every post to pass review before it is scheduled.

get_post_engagements

ChatGPT
get_post_engagements — a Scripe post's team engagement timeline: the likes, comments and reposts queued to fire under OTHER brands' LinkedIn identities after the post goes live, plus availableActors — the workspace brands and company pages this post could engage from, each with its LinkedIn-connection state and its per-action engagement policy (OFF | REQUEST | ON) resolved for THIS post's project. Call it before update_post_engagements: the actor ids and each row's eng_… id come from here. Also reports the plan lock (team engagement is an Advanced+ feature — locked workspaces can read but not change). Needs projects:read ON TOP of posts:read, because availableActors is workspace brand and company-page data — their ids, display names, LinkedIn connection state and engagement-policy states — not this one post's content.

get_post_media_options

ChatGPT
get_post_media_options — which visual fits each Scripe post, decided from DATA, and what could be it. Per post (up to 20, post_…): the RECOMMENDED visual — a real photo from the media library, a Scripe template visual (QUOTE_CARD, CAROUSEL, INFOGRAPHIC, BILLBOARD) or none — with the reason in words (the post type's visual, Scripe's 2026 LinkedIn trend report, this profile's own posts by media); up to 5 media-library pictures ranked by MEANING for that post (what they show, whether people are in them, whether another recent post already wears them); and the media the post carries now. Then call add_post_media, which previews the visuals for the user's yes before anything changes. A post that wants a real photo of the person and finds none says so (needsPersonPhoto) — ask the user for one, or upload an image you made with create_media_asset.

get_posting_times

ChatGPT
get_posting_times / getPostingTimes — when this Scripe project's LinkedIn posts perform best: the user's OWN posting-time buckets (per hour of day and per weekday×hour) with post counts, impressions, and engagement, aggregated over a lookback window. Use it for "when should I post", "what time works best", "best day to post". Hours are on the PROJECT's calendar clock by default — the same zone list_calendar and get_next_free_slot answer in — and the response says which zone in timeZone; quote it when you name an hour. Only slots the project has actually posted in are returned: a missing hour means it was never tried, NOT that it performs badly. Needs real posting history — a handful of posts is not a signal, say so.

get_profile_list

ChatGPT
get_profile_list returns one Scripe community profile list with the LinkedIn people on it — name, headline, profile URL, the note whoever added them left, and whether Scripe has collected any of their posts yet. Call it before add_profile_to_list to check whether somebody is already on the list, and after one to report what changed. Get the plist_… id from list_profile_lists. Requires community:read.

get_profile_planning_context

ChatGPT
get_profile_planning_context — everything you need to write good ideas and posts for Scripe profiles, in ONE bounded call: pass profileIds (up to 10 per call — every profile you are planning for, e.g. all with open slots from get_planning_overview) or one projectId. Per profile: its positioning ("You": intro, credibility, opinions, stories), target audience, tone of voice, content topics, post history (recent openings to avoid repeating, its best posts and its lane mix — Reach / Trust / Convert — over 90 days; performance numbers are get_planning_signals'), its knowledge base (folders incl. Granola, Drive and Post history with their last sync, newest documents, meetings in the planning range first), the campaigns running in the range with their brief, and its idea stock (strongest For You ideas per lane, unplaced board ideas). Once for all: the company positioning and the post format keys preview_plan accepts, per lane. Several profiles default to detail: "concise"; one to full. Read a knowledge document's full text with read_knowledge_document. Every answer stays under a host's inline limit: trimmed: true says list tails (idea stock first) or long texts were cut — ask again with fewer profileIds (about 3 per call at detail: "full"). What is happening around the profiles (niche outliers, source items, performance by format and topic, For You reasons) is get_planning_signals.

get_project

ChatGPT
get_project — one Scripe project (a LinkedIn account, company page or amplifier) by id. Same enriched shape as list_projects — includes name, typeLabel, username, avatarUrl and linkedIn. This is the tool for "is my LinkedIn still connected?" and for "why did my post not go out?": linkedIn.canPublish says whether publishing is possible right now, linkedIn.state says which of the five conditions the account is in, and linkedIn.detail names the cause and the repair. Only a human can reconnect LinkedIn — linkedIn.reconnectUrl is where. Stored health, not a live probe.

get_settings

ChatGPT
get_settings — a Scripe project's curated settings: generation-context knobs (language — one of Scripe's supported content languages, the value update_tone_of_voice takes —, formality, post length / formatting / emoji preferences), the project tone-of-voice fields (custom instructions, CTAs, footer, emoji + bullet symbols), the workspace-level custom-instruction state, calendar settings (timezone, week start), and the content pillars. Structured fields only — never the rendered prompt context.

get_source

ChatGPT
get_source — one Scripe source (a transcribed long-form input for LinkedIn drafting) by id. The response includes the source status and a 2 KB transcript preview. Once status: "Success" it also includes a topics array, best-first by score (0–100, how well the topic would work as a post); each topic has id (tpc_*), title, summary and keyTakeaways. fromSeconds gives the topic's position in the source, so an earlier chapter is not a better one. To turn a topic into a post, pass its id straight to generate_post({ source: { type: 'topic', topicId } }) — the full transcript is never served here, and the generator writes its own hook. hooks[] is only populated for sources a human worked on in the Scripe dashboard; it is empty for API-created sources and you do not need it.

get_usage

ChatGPT
get_usage — what this Scripe workspace has used of its limits, and whether the next AI job would be accepted. Answers "can I still generate posts this week?", "how much of my budget is left?" and "why did that generation fail — when can I retry?" in one call. Read canGenerate first: false means the next generate_post / generate_image / knowledge ingest WILL be refused, and blockedBy says which limit (weekly_ai_budget — wait until ai.resetsAt or upgrade; daily_api_spend_cap — resets 00:00 UTC). AI budgets are reported as a percentage of the allowance, never as money; storage is reported in bytes. Call this BEFORE a batch of generations rather than discovering the limit through a failure.

get_workspace

ChatGPT
get_workspace — the Scripe workspace this connection is currently acting against, including plan and the principal envelope (OAuth client + acting user, or API key). Useful as a smoke test to confirm the connection is healthy. The active workspace is the default (consent-pinned) workspace unless this connection sends a Scripe-Workspace-Id header.

get_workspace_context

ChatGPT
get_workspace_context — one-call overview of the active Scripe workspace: plan + feature flags, whether the review workflow is required, and up to 25 projects with display name, type and stored LinkedIn connection health. Each project's streak is always null (retired). The LinkedIn health is the stored status as of its lastValidatedAt timestamp — this read never probes LinkedIn live, so treat it as "last known", not current. projectsTruncated: true means the workspace has more than 25 projects; use list_projects to page through the rest.

list_calendar

ChatGPT
list_calendar / listCalendar — a Scripe project's LinkedIn content calendar for a date range: scheduled and planned posts (with workflow status and any last publish error), note slots, idea placements, and the recurring posting-time template. Use it for "what's on my calendar", "what goes out next week", "which days are free". Dates are calendar days in the project's timezone.

list_calendar_slots

ChatGPT
list_calendar_slots — a Scripe profile's PLANNED posting slots ahead, by day: every posting time of its schedule with the content lane the posting goal gives it (REACH / TRUST / CONVERT), the time in the profile's zone, a pillar hint, and its state — empty, draft (a post is planned there, not yet scheduled), scheduled or published — with the post (status, campaign, source idea). Default range: the next 14 days; at most 31 days per call — or name a goal period (current / next / previous) or weeksAhead and it reads that whole range from its first plannable day (up to 13 weeks). For every profile at once, get_planning_overview is one call. onlyEmpty: true returns just the slots still needing a post — the list to fill with fill_calendar_slot. Fill a slot with an idea of the SAME lane. A profile with no posting schedule has no slots (update_posting_schedule sets one). Lanes: REACH = posts that need no prior relationship and ask nothing of the reader (stories, opinions, relatable takes); TRUST = posts that SHOW first-hand work and expertise (how-tos, lessons, results, behind the scenes); CONVERT = posts that invite the ask from the client's own material (offers, case studies, customer results). A lane is a ration of the posting goal, never a sequence a reader travels through.

list_campaigns

ChatGPT
list_campaigns — list the Scripe workspace's campaigns (the Campaigns page): title, emoji, status, start and end dates, the profiles each is narrowed to (none = workspace-wide), labels and post count. Filter with status. Use get_campaign for one campaign's brief, per-profile progress and posts.

list_company_pages

ChatGPT
list_company_pages — every LinkedIn company page discovered or activated in the active Scripe workspace; the delta over list_projects: activation status, stored admin token health (as of last validation, never a live probe), follower count, and the activated project's engagement-policy defaults. Use the activated project's proj_… id with other tools to operate on an activated page.

list_content_questions

ChatGPT
list_content_questions — the content questions of one Scripe idea (the idea page's Questions rail): each question's text, status (draft / scheduled / sent / answered) and who it is for. Use get_content_question for recipients and answers.

list_content_topics

ChatGPT
list_content_topics lists a Scripe workspace's content topics (the dashboard calls them TOPIC GROUPS / Themen — the list under Settings → Organization → Positioning) and, for each, the people/brands it is assigned to. An assigned topic is one Scripe builds that person's post ideas around; an unassigned one influences nothing. Pass profileId to see only the topics of one person. Use it before assign_content_topic / unassign_content_topic to see what is already assigned, and to get the wct_… ids those tools accept. NOT the positioning documents (get_positioning) and NOT the topics a recording was cut into (get_source). Requires workspace:read.

list_for_you_ideas

ChatGPT
list_for_you_ideas — the Scripe "For you" suggested post ideas (Explore → For you): ideas Scripe generated for a profile from trending LinkedIn topics, followed sources, the client's own results and knowledge base. Omit projectId for the whole workspace's pool, or pass one profile. Each idea carries its lane (REACH / TRUST / CONVERT), format, a one-line whyPicked, its origin and whether it is already saved to a board. Use it to pick ideas for empty calendar slots: match an idea's lane to the slot's lane (list_calendar_slots). Then get_for_you_idea for the full argument and every source, save_for_you_idea to keep it, dismiss_for_you_idea to hide it, or fill_calendar_slot with its forYouIdeaId to write it into a slot. Lanes: REACH = posts that need no prior relationship and ask nothing of the reader (stories, opinions, relatable takes); TRUST = posts that SHOW first-hand work and expertise (how-tos, lessons, results, behind the scenes); CONVERT = posts that invite the ask from the client's own material (offers, case studies, customer results). A lane is a ration of the posting goal, never a sequence a reader travels through.

list_ideas

ChatGPT
list_ideas / listIdeas — a Scripe project's idea board, newest first: title, brief fields (pillar, post format, hook), the DERIVED workflow status (inbox | in_production | review | done), calendar placement, and whether the idea is waiting on someone's input, and the campaign it is filed under. Use it for "what's on my idea board", "which ideas are ready to produce", "what am I waiting on", "which ideas are in campaign X" (campaignId). Paginated (default 25). projectId is optional — omitted, it reads the connection's default project and the response names it.

list_jobs

ChatGPT
list_jobs — async Scripe jobs (generation, ingest, indexing) in the workspace, newest first. Filter by type, status, and creation date. List entries do NOT include live progress — call get_job for a single job's progress snapshot.

list_knowledge

ChatGPT
list_knowledge — the Scripe knowledge-base documents visible to a project, newest first: the project's own documents plus workspace-wide documents (0 assignments = visible to all projects). Hidden ephemeral chat uploads never appear. Optional folder filter. Default page size 25, max 100.

list_labels

ChatGPT
list_labels — list every label of the Scripe workspace (the post labels managed under Settings → Labels), with each label's colour, description and label group. Call it to find a label id before update_post_labels, list_posts_with_label, update_label or delete_label, or before create_label to avoid a duplicate.

list_notes

ChatGPT
list_notes — the notes in a Scripe project, newest first. Notes are short-form thoughts that can seed a LinkedIn post. Optional filters by folder and slot date, plus q to search the note bodies for what a note is about ("the note where I wrote about churn"). Default page size 50, max 200. pagination.total counts everything the filter matches, not just this page — use limit: 1 for "how many …" instead of paging.

list_post_analytics

ChatGPT
list_post_analytics — per-post LinkedIn analytics (views, likes, comments, shares, engagement rate) for posts already LIVE on LinkedIn, for one or more Scripe projects. For ONE post the user is asking about, pass its postId — never fetch a date window and scan it. Otherwise it defaults to newest first; pass sort: "impressions" or "engagement" for the top performers in a period. Offset-paginated; default page size 50, max 200. Each row carries THREE ids and only one of them is actionable: post_id is the Scripe post (post_…) for get_post / update_post, and it is null for posts not published through Scripe; id identifies the analytics record itself and no tool accepts it; linkedin_post_id / permalink locate the post on LinkedIn. content is an excerpt by default — see the content argument. metrics.views is null (views_available: false, rate null) for a company page post LinkedIn no longer reports lifetime impressions for (older than its 12-month window when last read) — say it is unknown, never zero.

list_post_comments

ChatGPT
list_post_comments — the comments under one of the user's OWN LinkedIn posts in Scripe, with every reply nested under its comment, so you can analyse what the audience said: recurring questions, objections, the angles people pick up on, ideas for the next post or infographic. Use it whenever the user asks to read, summarise or analyse "the comments under my post". Name the post with postId (post_…, from list_posts or a list_post_analytics row's post_id) or linkedInPost (the post's LinkedIn URL, or a list_post_analytics row's linkedin_post_id for a post not published through Scripe); to find the post the user means, list their posts first (list_posts with q, or list_post_analytics sorted by engagement). Comments are ANONYMISED by design: each carries its text, createdAt and replies, plus byPostAuthor (written from the user's workspace: their own profile or page, or a reply a teammate sent from Scripe), and NEVER who wrote it — no name, headline, profile link or id, and a person tagged inside a comment reads @[someone]. Do not ask for or guess the commenters; analyse the content. Reactions on individual comments are not available; post.reactionCount and post.commentCount are LinkedIn's totals for the whole post. Every page re-reads the post on LinkedIn live (freshness.state: "fresh"); a comment that read did not return is left out and counted in notAvailable, and so are replies the bounded live read did not fetch on a busy post. Any other freshness state means LinkedIn could not be read right now and NO comments come back (every one counted in notAvailable) — an empty list then is not an empty thread. Whenever notAvailable is above 0, tell the user the set is partial rather than presenting it as complete. Pages are offsets into each call's live list, so a comment arriving between pages can repeat or skip one. Only posts of the user's own profiles are reachable; anyone else's post answers not_found. Requires a paid plan (the comments inbox).

list_post_statuses

ChatGPT
list_post_statuses — a Scripe project's content pipeline: every kanban column (draft / inProgress / review / scheduled / published categories) with postCount, how many posts sit in it right now. This is the one call that answers "what's in my pipeline?", "what am I working on?" or "how much is waiting for review?" — read counts.byCategory for the per-category totals and counts.total for the project, and never call list_posts once per column to add them up. Each row's id is the statusId update_post moves a post to, and the one list_posts filters by — so go from a count straight to the posts behind it with list_posts({ statusId }).

list_posts

ChatGPT
list_posts — the LinkedIn posts and drafts in a Scripe project, newest first. Every row reports the post's lifecycle status plus the workspace status it sits in (statusId, statusTitle, statusCategory) — a published post reads status: "published", a scheduled one "scheduled". Filter by status (lifecycle), statusCategory (kanban category, the vocabulary list_post_statuses returns) or statusId (one named column), plus a date window — dateFrom/dateTo filter the day the DRAFT was written, and publishedFrom/publishedTo the day it went LIVE, which is what "what did I publish last week" asks (the two differ by six days on average). Every row reports publishedAt, the only field that dates a publish — scheduledAt is an intention and stays set on posts that never went out. Every row also reports delivery, which is what answers "did my post go out?": delivery.state: "missed" means the publisher has given up and the post will never send even though status still reads "scheduled", and delivery.detail says why and what to do about it. Filter by it (delivery: "missed") to find them — never infer a failure from scheduledAt being in the past. Every row also reports review, which answers "what needs approval?": review.awaitingDecision: true (state pending) is the only thing that means somebody has to sign it off, and review.reviewerUserId says who (resolve it with list_team). Filter with review: "pending" — a post sitting in a "review" board column is NOT the same question: that column also holds already-approved posts, rejected ones, and posts nobody was asked to look at. To find a post by what it is ABOUT ("my post on pricing", "the one where I mentioned the webinar") pass q — never page the whole project looking for it. Each row's content is an EXCERPT by default (contentTruncated: true says so) — never quote it back to the user as the post; call get_post for the one they meant, or pass content: "full" with a small limit. Default page size 50, max 200. To answer "how many …" read pagination.total — it counts everything the filter matches, not just this page, so limit: 1 answers a counting question in one cheap call. Never add up pages to get a count, and never report the page size as the total.

list_posts_with_label

ChatGPT
list_posts_with_label — list the Scripe posts that carry one label, newest first, across every profile the user can access (or one profile with projectId). Each post comes with its state (draft / scheduled / published) and dates. Paginate with nextCursor. Label ids come from list_labels.

list_profile_lists

ChatGPT
list_profile_lists returns the Scripe community profile lists of one brand — the named watchlists of LinkedIn people whose posts Scripe collects, shown under Community → Profiles in the Scripe dashboard. Call it first to get the plist_… id that get_profile_list and add_profile_to_list take; there is no other way to name a list. projectId is optional: omit it and Scripe uses the connection's DEFAULT project, and the response echoes which one it landed on. This is NOT the customer's own brands (list_projects) and NOT their own posts' team engagement (get_post_engagements). Requires community:read.

list_projects

ChatGPT
list_projects — the Scripe projects (LinkedIn accounts, company pages and amplifiers) in the connected workspace, newest first. This is how you find a projectId for any other Scripe tool. Each row carries the dashboard display fields: name (rendered display name), typeLabel (one of "LinkedIn Account", "Company Page", "Amplifier Account"), username (LinkedIn vanity slug), and avatarUrl (CDN-cached profile picture). Use the raw enum type for filtering and pagination.next_cursor to walk older pages. Every row also carries linkedIn — whether Scripe can publish as that project right now. Read linkedIn.canPublish and linkedIn.state; never linkedIn.connectionStatus, which is a stored cache that reads CONNECTED for accounts holding no token at all.

list_sources

ChatGPT
list_sources — a Scripe project's sources (transcribed long-form inputs for LinkedIn drafting), newest first: name, status, duration, and a 2 KB transcript preview per row. Fetch a single source for its topics. Default page size 25, max 100. These are the recordings and files a user UPLOADED — what the profiles' FOLLOWED sources (feeds, sites, LinkedIn creators) published lately is get_planning_signals.

list_team

ChatGPT
list_team — the active Scripe workspace's team members: display name, email, role (the label the dashboard shows: "Admin", "Member" or "Client"), avatar, join date, and the projects each member is individually assigned to. Reads at most 100 members — truncated: true with a higher totalCount means the workspace has more. Project references are limited to the ones you can reach yourself and to 25 distinct projects — projectsTruncated: true means some were omitted; use list_projects for the full set. Never returns credentials or tokens.

list_waiting_for_me

ChatGPT
list_waiting_for_me — what waits on YOU in this Scripe workspace: posts you are the assigned reviewer of (still in review, not yet on LinkedIn) and content questions sent to you that nobody has answered yet. Each comes with a url that opens it in the Scripe web app — the post editor where you approve or request changes, or the idea page where you answer. kind narrows to reviews or questions. Read-only: approving stays in Scripe; answer a question with answer_content_question when the user dictates the answer.

list_workspaces

ChatGPT
list_workspaces — every Scripe workspace this connection can reach; for an OAuth connection, every workspace the consenting user belongs to plus every client workspace billed to an agency they own. Each entry has an id, a name, reach (member or agency_owner, which is why it is reachable) and isDefault (the connection default, active until you switch). An agency_owner entry can have an empty name when its LinkedIn workspace identity could not be resolved — the id still works. To work in a different workspace, pass its id to switch_workspace; every subsequent tool call then runs against it until you switch again.

nudge_content_question

ChatGPT
nudge_content_question — remind a person who has not answered a Scripe sent content question; the reminder re-sends their open check-in. At most once per person every 24 hours (a second nudge inside that window is refused with when it opens again). recipientId comes from get_content_question's recipients (status pending).

preview_plan

ChatGPT
preview_plan — step 1 of planning Scripe content into calendar slots, for one or many profiles in ONE call. Send every item of the plan: projectId, slotAt (an open slot's at from get_planning_overview), and the idea for that slot — one YOU wrote (idea: title, optional hook / angle / notes / postType or lane), an existing board idea (ideaId), or a For You idea (forYouIdeaId) — plus an optional campaignId. A For You idea is a starting point, not a finished idea: give it overrides (YOUR hook / angle / notes from this person's own material), which commit_plan writes onto the board idea it saves. Scripe checks each item against the live calendar (the slot exists, is ahead and is free; the idea is this profile's and used once; you may plan for this profile) and returns a planId with a verdict per item (ready / conflict / invalid) and warnings: a lane that is not the slot's, two posts on one day, and the ideas' quality — one angle twice (within a profile or across profiles), an idea close to a post or idea the calendar already holds, or an item that is only a title. Quality warnings are advice: fix the ones you agree with in ONE corrected preview, or name them to the user. A plan longer than one preview (60 items) is checked as a whole first with check_plan_ideas. A For You item carries its angle (edited when yours). Nothing is written. Show the user the plan, then call commit_plan with the planId. Write the idea texts yourself from the profile's context (get_profile_planning_context); never invent figures, names or quotes. At most 60 items. Lanes: REACH = posts that need no prior relationship and ask nothing of the reader (stories, opinions, relatable takes); TRUST = posts that SHOW first-hand work and expertise (how-tos, lessons, results, behind the scenes); CONVERT = posts that invite the ask from the client's own material (offers, case studies, customer results). A lane is a ration of the posting goal, never a sequence a reader travels through.

publish_post

ChatGPT
publish_post — publish a Scripe post to LinkedIn immediately. TWO-PHASE: call it WITHOUT confirmationToken to get phase: "proposal" back — the rendered commentary, the publishing identity, the connection pre-flight, and a token. SHOW that proposal to the user and get explicit approval. Then call again with identical arguments PLUS confirmationToken to publish. Requires the posts:publish scope, which posts:write never implies. Irreversible — there is no unpublish.

read_knowledge_document

ChatGPT
read_knowledge_document — read ONE Scripe knowledge-base document in full (a Granola meeting, an uploaded file, a synced Drive or GitHub file), in order, up to maxCharacters (default 12,000, at most 24,000). The id comes from list_knowledge, search_knowledge or get_profile_planning_context. Use it before writing an idea or a post that rests on the document, so you quote what it says and never invent.

request_review

ChatGPT
request_review — send Scripe posts for REVIEW and assign the reviewer, many at once (up to 50): each post moves into the workspace's review stage with a pending review for that person, and the reviewer gets ONE notification for the whole batch. TWO-PHASE: the first call sends NOTHING — it returns a PREVIEW (which posts go to whom, what happens to each, how the reviewer is notified) plus a confirmationToken. Show the user the preview and wait for their explicit yes; only then call again with the SAME arguments plus the token. Never confirm for the user, not even on autopilot. reviewer is a workspace member's user id (list_team), email or exact name; ask the user who should review when it is not obvious. It never approves or rejects — the reviewer decides in Scripe. Per post the result says requested, already with that reviewer, or why it was refused, with a link to the post in Scripe. Needs a plan with content approvals.

save_for_you_idea

ChatGPT
save_for_you_idea — the "Save" on a Scripe "For you" card: puts the idea on a profile's idea board with its brief, sources and template, exactly as the dashboard does. FOR ME (default): saves it to one profile — projectId, or, omitted, the profile that generated it. FOR EVERYONE: forAllSuitedProfiles: true also assigns the board idea to every other profile the idea suits that you can access (the workspace page's Add). Idempotent: saving an idea the profile already holds returns that board idea (created: false). The board idea's idea_… id then works with the idea-board tools (schedule_idea, update_idea).

schedule_idea

ChatGPT
schedule_idea / scheduleIdea — place an idea on a DAY of a Scripe idea board's content calendar (or remove it with null) — planning only, fully reversible, no confirmation. This does NOT create a post and does NOT schedule anything to LinkedIn: to actually publish, a draft is written (postGenerator) and scheduled (schedulePost / schedule_post) separately. projectId is optional — omitted, it plans in the connection's default project and the response names it.

schedule_post

ChatGPT
schedule_post — put an existing Scripe post on the calendar to go live on LinkedIn. ONE call schedules it for real: there is no proposal and no confirmation step, so call it once the user has asked for the post to be scheduled at that time. The post is then published to LinkedIn AUTOMATICALLY at scheduledFor (within ~2 minutes) with no further action from anyone. Tell the user plainly that it is scheduled and will go live on LinkedIn at scheduledForLocal (the time in the project's timezone) — the result's notice says exactly that. To undo, call update_post with scheduledFor: null (back to a draft); to move it, call schedule_post again with the new time. Refused, with nothing scheduled, when the post needs an approved review, the workspace has no plan that can publish, or the LinkedIn connection cannot post — a 409 conflict carries details.reason and details.reconnectUrl to relay, since only the user can reconnect.

search_knowledge

ChatGPT
search_knowledge — search a Scripe profile's knowledge base by MEANING: the passages most relevant to a topic, from uploaded documents, synced Drive / GitHub files, Granola meeting notes and the profile's own post history. Use it to ground an idea or a post in the customer's own material ("what did the last customer calls say about pricing?"). Narrow it with folderId (a folder id from get_profile_planning_context) or documentIds (from list_knowledge) so one folder is not outranked by the rest. Each result names its document — read it whole with read_knowledge_document. NOT for listing what exists: that is list_knowledge, because a folder's name appears in no passage.

search_media

ChatGPT
search_media — search a Scripe project's reachable media-library images (owned or profile-assigned), READY only, newest first. Optional free-text query over title/filename/AI caption and a source filter (UPLOAD | LINKEDIN_SYNC | GENERATED). Returns display URLs, tags, and provenance attribution. Use the returned img_… ids with attach_media_to_post. An image the user has just given you is not in here — add it with create_media_asset first.

search_viral_posts

ChatGPT
search_viral_posts — semantic search over Scripe's inspiration feed for high-performing LinkedIn posts relevant to a topic. Returns posts from other authors (the project's own posts are excluded) with their engagement metrics — useful for finding proven angles, hooks, and formats before drafting. By DEFAULT it returns only OUTLIERS: posts that beat their own author's median engagement by at least 2x (outlier_multiplier, capped at 10), so a big account's ordinary post does not count as viral. Raise minOutlierMultiplier for a stronger breakout, and pass mediaFormats for a shape — 'carousel' is a swipeable deck, 'multi_image' several photos. Only posts in the project's language, above minEngagement total engagement and inside publishedWithinDays (90 by default) are searched, so a short or empty result may be those filters at work rather than a topic nobody writes about. meta.narrowed_to is present when you narrowed beyond the default and the answer is short: one of those filters MAY be why, so offer to widen — language:'all', a lower minOutlierMultiplier, a wider publishedWithinDays or no mediaFormats — rather than concluding that nobody writes about the topic. Open a result with permalink and its writer with author.profile_url; id is a feed row id that no other tool accepts. metrics.views is null whenever LinkedIn withheld impressions (usual for someone else's post) — report it as unknown, never as zero. An outlier_multiplier of null means NOT SCORED, never average, and only outlier_baseline: 'AUTHOR' supports a sentence about that author's own usual performance. meta.returned is how many posts came back, not how many exist.

send_content_question

ChatGPT
send_content_question — send a Scripe content question to the people it is assigned to: when: "next_check_in" adds it to the next content check-in, "at" schedules it (sendAt + timezone), "now" sends it immediately by the people's channels (app, email …). ALWAYS TWO-PHASE, whichever when: the first call sends and schedules NOTHING — it returns a PREVIEW of who receives it, when and through which channels, plus a token. Show the user the preview and wait for their explicit yes; only then call again with the SAME arguments plus the token. Never confirm for the user, not even on autopilot. One question per call; several go out with send_content_questions.

send_content_questions

ChatGPT
send_content_questions — send several Scripe content questions, from one idea or many, in ONE go: each person they reach gets ONE notification (one inbox entry, one push, one email) holding all of their questions, with one answer page grouped by idea. Use it INSTEAD of calling send_content_question repeatedly whenever more than one question goes out — six questions across four ideas are one notification per person, not six. questions lists { ideaId, questionId, projectId? } (up to 30). when: "next_check_in" adds them to the next content check-in, "at" schedules them (sendAt + timezone), "now" sends them immediately. ALWAYS TWO-PHASE, whichever when: the first call sends and schedules NOTHING — it returns a PREVIEW of who receives how many questions, when and through which channels, plus a token. Show the user the preview and wait for their explicit yes; only then call again with the SAME arguments plus the token. Never confirm for the user, not even on autopilot. A batch sends whole or not at all: one question that cannot be sent (already sent, blank, nobody assigned) refuses it, naming the question.

set_post_campaign

ChatGPT
set_post_campaign — put one or many Scripe posts (up to 50) into a campaign, or take them out with campaignId: null. A post belongs to at most one campaign, so this replaces any campaign it had. Post ids come from list_posts / get_post; campaign ids from list_campaigns. Every post must be one the user can access, or nothing is changed.

set_up_team_engagement

ChatGPT
set_up_team_engagement — set up the workspace's STANDARD team engagement on one or more Scripe posts, exactly what the post editor's "Generate engagements" does: every teammate whose engagement policy allows it likes the post when it goes live, and every teammate who allows comments gets one comment Scripe writes in THAT teammate's own voice — each comment knowing the others, so no two say the same thing — staggered over the first hour after publication. Teammates already engaging on a post are skipped, so calling it twice adds nothing. Use it once the posts exist (after draft_planned_posts finished, or on any post); draft_planned_posts also takes teamEngagement: true to do this as each post is written. It runs in the background — poll get_draft_run with the returned runId. Composing is NOT consent: when a post is scheduled each teammate's policy is resolved fail-closed (REQUEST queues an approval in Scripe, OFF never fires). To pick actors or write the comments yourself, use update_post_engagements instead. Requires an Advanced or Business plan. Up to 20 posts per call.

switch_workspace

ChatGPT
switch_workspace — change the active Scripe workspace for this connection. Every subsequent tool call (reads and writes) runs against the workspace you switch to, until you switch again. Call list_workspaces first to get valid ids. Switching to a different workspace clears the default project, so call list_projects and pass an explicit projectId to write tools afterwards. The switch is CONNECTION state, not conversation state: it outlives this conversation (up to 12h) and later conversations on the same connection inherit it — while it is active every tool result carries an Active workspace: line naming it. Switch back with defaultWorkspaceId from this response as soon as the user's work in the other workspace is done, and tell them which workspace you acted in.

tag_post_mentions

ChatGPT
tag_post_mentions — turn the names a Scripe post writes into real LinkedIn tags (a colleague, a client, a company). Per mention pass text exactly as the post writes it (with or without the @), kind (person / company) when you know, and a hint when the person is not one of the workspace's own (their company or role, from the post or the user — "CEO at Acme"). Scripe resolves who each name is itself and tags only when it is SURE: one of the workspace's own profiles or pages, a tag its posts already made under that name, or your hint matching exactly one candidate's LinkedIn headline. Otherwise the name stays untagged and the answer says how many candidates there were (never who — member data stays in Scripe): tell the user to pick in Scripe's editor. A name is tagged ONCE, at its first mention outside an existing tag (later mentions keep the plain name, a typed @ dropped), and not again when the post already tags them; the previous text stays in the post's version history. The tag shows the post's own words, because LinkedIn links a person on one of their names (first, last or full) and a company page only on its FULL name: a first name stays a first name, a name the post continues is taken whole, and a company the post names only in part stays untagged with the full name to write. Only for posts not yet on LinkedIn.

unassign_content_topic

ChatGPT
unassign_content_topic removes a Scripe content topic (the dashboard's TOPIC GROUP / Thema) from one or more people/brands, so it no longer steers their post ideas. The topic itself stays in the workspace and keeps its other assignments; only the named people lose it — including any sub-topics added under it for that person, which are deleted. Naming someone who does not have the topic is a no-op reported under notAssigned. Identify the topic by wct_… id or exact title and each person by proj_… id or exact display name. Call list_content_topics first to see current assignments. Requires settings:write and a workspace ADMIN acting user.

update_campaign

ChatGPT
update_campaign — change a Scripe campaign: title, emoji, summary, brief (description), status, dates, the profiles it is narrowed to (profileIds REPLACES the set; [] = workspace-wide) or its labels (labelIds REPLACES the set). Send only what changes. Narrowing the profiles detaches the campaign from ideas of profiles that drop out (they are kept). Moving the status to active notifies the people assigned to its profiles, once.

update_content_question

ChatGPT
update_content_question — edit a Scripe content question's text, why, placeholder, or who it is for (profileIds / respondentUserIds REPLACE the assignment). Only a draft or scheduled question can change; editing a scheduled one takes it back to draft (send it again with send_content_question). A sent or answered question is fixed — create a new one instead.

update_engagement_policy

ChatGPT
update_engagement_policy — set a Scripe project's engagement-policy defaults (auto-like / comment / reshare) - TWO-PHASE by design, and DIRECTION-RESTRICTED: this surface can set OFF or REQUEST only; turning a policy fully ON (autonomous engagement under this project's LinkedIn identity) must be done by the user in the Scripe dashboard. First call WITHOUT confirmationToken: you get a PROPOSAL back (current vs new defaults) - nothing is written yet. Show it to the user; after they explicitly confirm, call again with the SAME arguments plus the token to execute. All three defaults are required (the write is full-state). Setting everything to OFF (disarm) is always allowed; non-OFF values require an eligible plan. A LinkedIn connection is needed to publish, not to store the policy. Disarming a project that has no policy row (effective.source: "no_policy" on get_engagement_policy) creates none — nothing engages as that project today, and an all-OFF row would block the defaults Scripe seeds on a plan upgrade or LinkedIn reconnect; the proposal says so before the user confirms. Requires a workspace ADMIN acting user.

update_global_tone_of_voice

ChatGPT
update_global_tone_of_voice writes a Scripe workspace's organization-wide tone of voice (custom instructions, footer, per-brand instruction policy). TWO-PHASE: call WITHOUT confirmationToken to get a PROPOSAL rendering the full new text next to the current values — nothing is written yet. After the user explicitly confirms, call again with the SAME arguments plus the token. Fills EMPTY text fields only unless overwrite: true. Requires settings:write, a workspace ADMIN acting user, and a Business plan.

update_icp

ChatGPT
update_icp writes a Scripe workspace's Ideal customer (ICP), the targeting the fit of the people who engage is scored against. Sparse; every list is one string with one entry per line and REPLACES that list (read get_icp first); personas is a JSON array. Empty fields are written directly. Replacing what is already there is allowed but TWO-PHASE: send the new values with overwrite: true and WITHOUT confirmationToken to get a PROPOSAL naming each field with its current and new value — nothing is written yet. Show it to the user; after they explicitly confirm, call again with the SAME arguments plus the token. Requires the settings:write scope and a workspace ADMIN acting user.

update_idea

ChatGPT
update_idea — edit an idea's brief on a Scripe idea board: title, body, pillar, post format, visual format, hook, topic, campaign (campaignId from list_campaigns, null to take it out of its campaign) and/or its workflow status. Only provided fields change; pass null to clear a brief field. status is the idea's API workflow status, not its board column: writing it never moves the card, and board columns are customised per workspace and not exposed. Only 'inbox' or 'in_production' can be written; review/done are derived from the linked post and cannot be written. projectId is optional — omitted, it edits in the connection's default project and the response names it. Calendar placement is schedule_idea; deletion is delete_idea.

update_label

ChatGPT
update_label — rename, recolour or re-describe a Scripe label, or move it into (or out of, with labelGroupId: null) a label group. Send only the fields that change. Every post carrying the label shows the change. Ids come from list_labels.

update_note

ChatGPT
update_note — edit an existing Scripe note's body and/or folder. The note's calendar placement is not writable here. Returns the updated note. To remove a note, use delete_note instead (archives by default).

update_personal_dna

ChatGPT
update_personal_dna writes a Scripe profile's positioning (the person document: intro, credibility, opinions, stories — list sections one entry per line). Empty fields are written directly. Replacing text that already exists is allowed but TWO-PHASE: send the new values with overwrite: true and WITHOUT confirmationToken to get a PROPOSAL naming each field with its current and new text — nothing is written yet. Show it to the user; after they explicitly confirm, call again with the SAME arguments plus the token. Requires the settings:write scope and a workspace ADMIN acting user.

update_positioning

ChatGPT
update_positioning writes a Scripe workspace's Positioning documents (company description, mission, vision, statements, audience line, results, website; and the separate target-audience document). Empty fields are written directly. Replacing text that already exists is allowed but TWO-PHASE: send the new values with overwrite: true and WITHOUT confirmationToken to get a PROPOSAL naming each field with its current and new text — nothing is written yet. Show it to the user; after they explicitly confirm, call again with the SAME arguments plus the token. Requires the settings:write scope and a workspace ADMIN acting user.

update_post

ChatGPT
update_post — edit an existing Scripe LinkedIn post's content/title/contentType, change its custom status (by statusCategory or statusId), and/or UNSCHEDULE it via scheduledFor: null. Scheduling a time is done through schedule_post (one call, goes live automatically) - passing a non-null scheduledFor here returns a teaching error. Returns the updated post.

update_post_engagements

ChatGPT
update_post_engagements — edit a Scripe post's team engagement timeline (add / modify / remove queued likes, comments and reposts), exactly what the post editor's team engagement panel does. Composing a row is NOT consent: when the post is scheduled, each acting brand's engagement policy is resolved fail-closed — REQUEST policies queue a human approval in the Scripe dashboard, brands without consent never fire, and approvals can only be granted in the dashboard, never from this surface. Limits (all also enforced server-side): requires an Advanced+ plan (the editor's gate); actors must be in the post's own workspace, LinkedIn-connected and non-OFF for the action (see availableActors on get_post_engagements); a profile can LIKE or REPOST a post only once; comments max 1250 chars; delays are the editor's fixed options; a row that has already been executed on LinkedIn can be neither edited nor removed (naming one refuses the whole call, so a batch never applies half of itself). Editing an approved row's text or actor revokes the approval and re-asks the brand — same rule as the editor. REMOVING a row is permanent and cascades: any tracked (smart) links bound to that engagement are deleted along with their click history and their redirect-cache entries, so links already shared in that comment stop resolving and their analytics are gone. Needs projects:read ON TOP of posts:write, because the response carries the same workspace brand and company-page data as get_post_engagements (ids, display names, LinkedIn connection state, engagement-policy states) and this verb acts under those brands' identities.

update_post_labels

ChatGPT
update_post_labels — apply labels to Scripe posts or take them off, on ONE or MANY posts in one call (up to 50). Pass add and/or remove to change only those labels and keep the rest, or replace to set each post's labels to exactly that list (replace: [] clears them). Post ids come from list_posts or get_post; label ids from list_labels (create_label makes a new one). Every post must be one the user can access, or nothing is changed.

update_posting_schedule

ChatGPT
update_posting_schedule — set a Scripe project's RECURRING LinkedIn posting-time template - the weekly slots get_next_free_slot suggests from and the calendar draws as open. Use this for "post me Tuesdays and Thursdays at 8"; use schedule_post to put ONE post at ONE time. FULL-STATE: the slots you send replace the whole week, so read get_settings.calendar.schedule.slots first and send it back with your edit applied (an empty array removes the schedule). TWO-PHASE: call first WITHOUT confirmationToken and you get a PROPOSAL rendering the resulting week and naming every slot that would be REMOVED - nothing is written yet. Show it to the user; after they confirm, call again with the SAME arguments plus the token. Times are wall clocks in the project's calendar timezone (pass timeZone to change it). Setting a template does not publish anything and does not move posts that are already scheduled.

update_tone_of_voice

ChatGPT
update_tone_of_voice — update a Scripe project's PROJECT-LEVEL tone-of-voice and generation settings - TWO-PHASE by design. First call WITHOUT confirmationToken: you get a PROPOSAL back rendering the FULL new text of every field you are changing next to the current values - nothing is written yet. Show it to the user; after they explicitly confirm, call again with the SAME arguments plus the token to execute. The token is bound to this exact change set and expires in ~5 minutes - changing anything invalidates it. These settings become prompt content for every future generation, so the write requires a workspace ADMIN acting user. Workspace-level (organization) tone of voice cannot be changed from this surface.

Capabilities

Writes

Example Prompts

Click any prompt to copy it.

Similar Apps