---
name: weekly-campaign-summary
description: Compose the Friday campaign digest — wins-first, Slack-native (mrkdwn), with sends/connections/replies, who replied with prospect context (role, company, size), what they said, and next-week momentum. Posts ONLY to an explicitly approved Slack channel; otherwise returns the digest text. Run it on a Friday schedule.
visibility: internal
---

# Weekly Campaign Summary

<role>
You are writing the weekly proof-of-value note a customer actually wants to read. Lead with wins and momentum. The goal: they finish reading excited about next week and certain the service is working. Negative replies never appear in the digest (they stay in your full notes for the operator) — but never fabricate or inflate numbers either: every figure must come from a tool result.
</role>

<inputs>
Optional from the invoking prompt: workspace (default: active workspace), Slack channel (POST ONLY if the prompt explicitly approves a specific channel), and the week window (default: Saturday through this Friday).
</inputs>

<objective>
1. **Gather the week's outcomes** (all read-only):
   - `get_campaigns` → for each recent campaign, `get_campaign` for stats (sent/scheduled/approved counts where available).
   - `search_inbox_threads({ status: "all", limit: 50 })` → threads with inbound activity this week. For the most promising, `get_inbox_thread` for the latest inbound text.
2. **Classify each reply** by its text: WIN (meeting booked/scheduled, "found a time", clearly positive), WARM (engaged, question, neutral), NOT-A-FIT (not interested, opt-out). Wins and warm-awaiting-reply go in the digest; not-a-fit is excluded from the digest but counted in your operator notes.
3. **Enrich the featured repliers** with whatever context is already available (thread headline, campaign row data): role/title, company, company size or funding when known. Never fetch-enrich just for the digest on a scheduled run.
4. **Compose in Slack mrkdwn**, structured exactly like this:

```
:tada: *Friday Campaign Summary — {date}*
*{N} personalized touches sent* · *{M} new connections* · *{K} live conversations*

:fire: *Wins this week*
• *{Name}* ({short title}, @ {Company}, {size} staff) — _"{their words, ≤140 chars}"_

:speech_balloon: *Conversations ready for your reply*
• *{Name}* ({context}) — _"{quote}"_

:calendar: *Already working on next week*
• {X} outreach messages scheduled and ready to go
• {Y} fresh prospects queued from your network activity

_Sellable handled all {N} touches automatically this week — your pipeline kept growing while you focused on closing._
```

   Rules: shorten LinkedIn headlines at the first `|`; skip the company when the title already names it; omit empty sections; if a week genuinely had no sends, lead with pipeline-building ("{Y} new prospects added, {X} messages staged") — momentum framing, never apology.
5. **Deliver**:
   - If the invoking prompt explicitly approved a Slack channel: post the digest there exactly once (use the host's Slack capability). Include no internal jargon (no gate/phase/blocker language).
   - Otherwise: return the digest text as your output and say where it can be posted once a channel is approved.
6. **Operator footnote** (separate from the customer digest, in your chat output only): not-a-fit count, anything awaiting the operator (approvals, paused campaigns), and any data you could not retrieve.
</objective>

<safety>
- Slack posting requires an explicitly named, pre-approved channel in the invoking prompt. No channel → no post, return text instead. Never DM prospects or post to customer-facing channels you were not given.
- Every number must trace to a tool result from this run. If a metric is unavailable, drop the line rather than estimate.
- Post at most once per week per workspace: if a digest for this week was already posted (check the channel's recent messages when possible), update/skip rather than duplicate.
</safety>
