Crosspost Routes
Define a route once and every publish fans out to up to 12 destinations across platforms, accounts, and workspaces.
What crosspost routes are for
A route is a persistent fanout rule. You define a source — typically a primary account, like your main LinkedIn — and up to 12 destinations across any platform, account, or workspace. When a post publishes on the source, Aidelly automatically schedules matching copies on every destination.
Useful when you have parallel audiences (personal + company LinkedIn, multiple X accounts), or when an agency needs every internal piece to land on multiple client workspaces.
Where it lives
Open Automation → Routes in the sidebar (/automation/routes). Routes are workspace-scoped.
Plan availability
| Plan | Routes | Destinations per route |
|---|---|---|
| Launch | — | — |
| Scale | 3 | Up to 12 |
| Agency | Unlimited | Up to 12 |
The 12-destination cap is enforced at the DB CHECK, the Zod schema, and the UI, so a runaway route can never blow up your AI credit consumption.
Step 1 — Create a route
- Open
/automation/routes. - Click New route.
- Source — pick a primary account, or "any publish in this workspace" to capture every publish from any account.
- Destinations — add up to 12. Each destination is an account + optional caption override.
- Click Save.
The route is now live for every future publish from the source.
Step 2 — Edit a destination's caption
Per-destination caption tweaks let each platform read native. From the route detail:
- Click on a destination row.
- Edit the caption override — supports the same
{{variables}}as post signatures. - Save.
If no override is set, the destination uses the source caption verbatim.
Step 3 — Dry-run before flipping on
Routes have a dry-run endpoint so you can preview the fanout before it runs:
- On the route detail, click Dry-run with sample post.
- Aidelly evaluates which of the 12 destinations the sample would publish to, with the resolved caption per destination.
- Skipped destinations show the skip reason inline.
Useful to verify a video-only post won't try to publish to a text-only destination.
What gets skipped (and why)
Incompatible destinations are skipped, not failed. The skip is recorded as a scheduled_post_events row and surfaced on:
- The post detail drawer — under "fanout history"
- The activity log — every skip is a separate event
- The calendar event card — a small badge appears when a route was applied
Skip reasons include: video-only platform with text post, photo platform with video post, missing media on platform that requires it, destination account disconnected.
Cross-workspace fanout (Agency only)
Agency workspaces can route a publish in one workspace to destinations in other workspaces:
- Add a destination — the workspace picker shows every workspace you have access to.
- Pick an account from that workspace.
- Save.
When the source publishes, the destination workspace gets a scheduled post created on its behalf. Member-scope permissions are honored — a member can only target workspaces they have access to.
How routes interact with other Aidelly features
- Queues — if a destination has a per-account queue, the fanned-out post enters the queue tail.
- Posting Sets — sets can pre-fill a route as a default; loading the set picks the route automatically.
- Campaigns — a campaign can have a default route, applied to every post added to the campaign.
- Auto-Post — RSS, podcast, newsletter, and YouTube auto-publishes respect routes the same way composer publishes do.
- Cooldowns — fanned-out posts respect per-account cooldown rules. A blocked destination is skipped, not retried.
Plan limits + cap rationale
The 12-destination cap matches the realistic ceiling: 11 supported platforms + 1 backup workspace. Anything beyond that is usually a sign of a misconfigured rule (e.g. a "post to every account" anti-pattern that floods feeds).
Troubleshooting
- A destination isn't receiving publishes — check the account is connected, and the source is producing publishes Aidelly can see (publishes from disconnected platforms aren't routed).
- Caption variables aren't substituting — variables are resolved at publish time per workspace. If a destination workspace is missing the variable, the literal
{{name}}text stays in place. - Member can't add a destination — they need write access to the destination workspace. Check
workspace_membershipsfor that user.