# How we turn our content calendar into social post drafts

Each day our agent checks the Notion content calendar, writes posts suited to each platform for what is coming up, and parks them in Slack with their dates until a person approves and publishes.

Canonical page: https://themachine.myapps.ai/use-cases/social-scheduler

We plan our content in Notion: what ships, what launches, what we announce and
on which day. But a calendar row is not a post. Someone still has to turn it
into a LinkedIn update, a tweet and an Instagram caption, and that job tends to
happen on the day itself, in a hurry, or slip through entirely. The calendar
knew what was due. Nobody had written the words.

So we gave that gap to an agent on Machine, and it closes it every day. It
checks the Notion calendar, writes posts suited to each platform for anything
launching or publishing soon, and leaves every draft in our marketing Slack
channel with its planned date. It never posts anything itself. A person reads,
edits and publishes.

- **Team:** Machine
- **Runs on:** A daily schedule
- **Connected systems:** Notion · Slack
- **Mode:** Clean session each run · drafts only, a person publishes

## The problem

A content calendar gives you the *what* and the *when*. It does not give you the
words each platform needs. Writing the LinkedIn version, the X version and the
Instagram caption for every launch and announcement is its own piece of work,
and someone has to remember it, usually with the clock ticking just before the
date.

The obvious fixes don't stick. A scheduling tool will queue posts, but only
after somebody has written them. A shared "posts to write" doc relies on someone
opening it every day and getting ahead of the date. And since writing keeps
getting pushed to "later", launches and announcements often go out with no
social post at all, or with one dashed off five minutes before it was needed.

## What we built

With Machine, a daily cron starts an agent. Each run gets a fresh **session**,
a clean cloud computer (a sandbox) for that day only, which reads our Notion
content calendar for anything launching, publishing or being announced in the
next few days. For each item it writes a post shaped for each platform, since
LinkedIn, X and Instagram each want a different length, tone and structure. It
then drops the whole batch into our marketing Slack channel with each draft
tagged by its planned date. Nothing gets scheduled or published automatically.
The drafts wait in Slack until someone gives the go-ahead.

## How it works

### Run daily, starting clean each time

A **cron trigger** starts the agent every day. Each run opens a new
**session** in a sandbox of its own. It carries no memory forward, so it reads
the calendar as it stands today instead of relying on whatever it wrote
yesterday.

### Teach it how each platform sounds

The rules for each platform's copy sit in a **skill**, the playbook the agent
brings to every run. LinkedIn gets a longer, more explanatory voice. X gets
one tight idea. Instagram gets a caption followed by hashtags. When our voice
changes or we add a platform, we edit the skill, and every draft from then on
follows suit.

### Link the calendar and the review channel

With a narrow **connector**, whose keys stay on our servers so the model never
sees a raw token, the agent reads entries in the Notion content calendar that
fall inside the look-ahead window. Through a **channel**, it sends the batch of
drafts to Slack. Neither link reaches any social platform.

### Set the limits

Reading the calendar and writing to a single Slack channel is all this agent
can do. It has no connector to LinkedIn, X, Instagram or any other social
account, so it has no route to a live post at all. That protection is not an
instruction it obeys. It is a permission it simply does not have.

### Hold each draft until someone approves

Every day the Slack post lists the upcoming calendar items, each with a draft
for every platform and its planned date. Someone on the team reads each draft,
tidies it up if needed, and schedules or publishes it with the tool they
already use. The agent stops at the draft.

> **The pattern**
> A daily **cron** opens a clean session that reads the **Notion** content
> calendar through a narrow connector, writes copy for each platform from a
> **skill**, and sends the batch to **Slack** for approval. The agent has no
> connector to any social account, so nothing can go live without a person.

## Guardrails

What this agent writes will one day speak for the company in public, so the
things it can do by itself are few:

- **No social connectors, period.** The agent holds no key and no connector for
  LinkedIn, X, Instagram or any other platform. Publishing is not forbidden by
  a rule. The ability is simply missing from what this agent was given.
- **Draft only.** A Slack message full of drafts is the only thing it sends out.
  Nothing gets scheduled, queued or posted anywhere.
- **Isolation.** Each run happens in a sandbox of its own, which is thrown away
  once the run finishes.
- **Scoped secrets.** The Notion connector's key stays on our servers. No raw
  token ever enters the sandbox.
- **Everything is code.** The platform playbook, the look-ahead window and the
  agent's permissions are files in the repo, and changing them takes a reviewed
  **change request** rather than a dashboard toggle.

## The outcome

- **Every day:** Upcoming calendar items written up as drafts well in advance
- **0 posts:** Go live automatically, as every draft waits for a person
- **3 platforms:** LinkedIn, X and Instagram written in a single pass

Launches and announcements that once got a hurried post on the day, or nothing
at all, now land in Slack several days early with a draft for each platform.
The agent turns calendar rows into copy. The team still chooses what goes out.
