Briefing Room

ClawSkills 作者 clawskills

Daily news briefing generator — produces a conversational radio-host-style audio briefing + DOCX document covering weather, X/Twitter trends, web trends, world news, politics, tech, local news, sports, markets, and crypto. macOS only (uses Apple TTS and afplay). Use when user asks for a news briefing, morning briefing, daily update, or similar.

安装 / 下载方式

TotalClaw CLI推荐
totalclaw install clawskills:clawskills~matusvojtek-briefing-room
cURL直接下载,无需登录
curl -fsSL https://skills.taituai.com/api/skills/clawskills%3Aclawskills~matusvojtek-briefing-room/file -o matusvojtek-briefing-room.md
# Briefing Room 📻

**Your personal daily news briefing — audio + document.**

On demand, research and compose a comprehensive ~10 minute news briefing in a conversational radio-host style. Output: audio file (MP3) + formatted document (DOCX).

### 💸 100% Free

- **No subscriptions, API keys, or paid services**
- Uses free public APIs (Open-Meteo weather, Coinbase prices, Google Trends RSS), web search, and local TTS
- TTS is fully local, no keys needed: MLX-Audio Kokoro (English) or Apple `say` (any language)
- Reads/writes: `~/.briefing-room/config.json` (settings) and `~/Documents/Briefing Room/` (output)

## First-Run Setup

On first use, check if `~/.briefing-room/config.json` exists. If not, run:

```bash
python3 SKILL_DIR/scripts/config.py init
```

This creates default config. The user can customize:
- **Location** — city, latitude, longitude, timezone (for weather)
- **Language** — `en`, `sk`, `de`, etc.
- **Voices** — per-language TTS engine and voice selection
- **Sections** — which news sections to include
- **Output folder** — where briefings are saved

Show setup status:
```bash
python3 SKILL_DIR/scripts/config.py status
```

## Quick Start

When user asks for a briefing (e.g. "give me a briefing", "morning update", "what's happening today"):

1. Check config exists (run setup if not)
2. Play notification sound: `afplay /System/Library/Sounds/Blow.aiff &`
3. Spawn a sub-agent with the full pipeline task **immediately**
4. Reply: "📻 Briefing Room is firing up — gathering today's news. I'll ping you when it's ready!"
5. **DO NOT BLOCK** — spawn and move on instantly

**Language override:** If user says "po slovensky", "v slovenčine", "auf deutsch", "en français", etc. → pass that to the sub-agent. Otherwise use the configured default language. Any language macOS supports will work — the agent writes the script in that language and TTS auto-detects a matching voice.

### Spawn Command

```
sessions_spawn(
  task="<full pipeline instructions — see below>",
  label="briefing-room",
  runTimeoutSeconds=600,
  cleanup="delete"
)
```

The task message should include ALL the pipeline steps below so the sub-agent is fully self-contained. **Replace all `SKILL_DIR` references with the actual absolute path to this skill's directory.**

**Host name:** Read `host.name` from config. If empty, use your own agent name (from your identity). Pass it to the sub-agent as the radio host name (e.g. "Good morning, I'm Jackie, and this is your Briefing Room...").

## Configuration

Config file: `~/.briefing-room/config.json`

Read values:
```bash
python3 SKILL_DIR/scripts/config.py get location.city
python3 SKILL_DIR/scripts/config.py get language
python3 SKILL_DIR/scripts/config.py get voices.en.mlx_voice
```

Set values:
```bash
python3 SKILL_DIR/scripts/config.py set location.city "Vienna"
python3 SKILL_DIR/scripts/config.py set location.latitude 48.21
python3 SKILL_DIR/scripts/config.py set location.longitude 16.37
python3 SKILL_DIR/scripts/config.py set language "de"
```

### Key Config Options

| Key | Default | Description |
|-----|---------|-------------|
| `location.city` | Bratislava | City name for weather + local news |
| `location.latitude` | 48.15 | Weather API latitude |
| `location.longitude` | 17.11 | Weather API longitude |
| `location.timezone` | Europe/Bratislava | Timezone for weather API |
| `language` | en | Default briefing language |
| `output.folder` | ~/Documents/Briefing Room | Output directory |
| `audio.enabled` | true | Generate audio |
| `audio.format` | mp3 | Audio format (mp3, wav, aiff) |
| `audio.tts_engine` | auto | TTS engine (auto, mlx, kokoro, builtin) |
| `sections` | all 11 (see below) | Which sections to include |
| `host.name` | (empty = agent name) | Radio host name for the briefing |
| `trends.regions` | united-states,united-kingdom, | X/Twitter trend regions (comma-separated, trailing comma = worldwide) |
| `webtrends.regions` | US,GB, | Google Trends regions (ISO codes, trailing comma = worldwide) |

### Voice Configuration Per Language

Each language can have its own TTS engine and voice:

```json
{
  "voices": {
    "en": {
      "engine": "mlx",
      "mlx_voice": "af_heart",
      "mlx_voice_blend": {"af_heart": 0.6, "af_sky": 0.4},
      "builtin_voice": "Samantha",
      "speed": 1.05
    },
    "sk": {
      "engine": "builtin",
      "builtin_voice": "Laura (Enhanced)",
      "builtin_rate": 220
    },
    "de": {
      "engine": "builtin",
      "builtin_voice": "Petra (Premium)",
      "builtin_rate": 200
    }
  }
}
```

**Engine priority (when `auto`):**
- English: mlx → kokoro → builtin
- Other languages: builtin (Apple TTS has good multilingual voices)

Users can add any language by adding a voices entry + a matching `builtin_voice` from `say -v '?'`.

## Output Structure

```
~/Documents/Briefing Room/YYYY-MM-DD/
├── briefing-YYYY-MM-DD-HHMM.docx    # Formatted document
└── briefing-YYYY-MM-DD-HHMM.mp3     # Audio briefing (~10 min)
```

**Do NOT save the .md working file in the output folder.** Use `/tmp/` for working files, delete after.

## Full Pipeline

### Step 0: Setup

```bash
# Read config
CITY=$(python3 SKILL_DIR/scripts/config.py get location.city)
LAT=$(python3 SKILL_DIR/scripts/config.py get location.latitude)
LON=$(python3 SKILL_DIR/scripts/config.py get location.longitude)
TZ=$(python3 SKILL_DIR/scripts/config.py get location.timezone)
LANG=$(python3 SKILL_DIR/scripts/config.py get language)
OUTPUT_FOLDER=$(python3 SKILL_DIR/scripts/config.py get output.folder)

DATE=$(date +%Y-%m-%d)
TIMESTAMP=$(date +%Y-%m-%d-%H%M)
OUTPUT_DIR="$OUTPUT_FOLDER/$DATE"
mkdir -p "$OUTPUT_DIR"
```

### Step 1: Gather Data — Weather

Use the configured location coordinates:

```bash
# Current weather
TZ_ENC="${TZ/\//%2F}"
BASE="https://api.open-meteo.com/v1/forecast"
CURRENT="temperature_2m,relative_humidity_2m"
CURRENT="$CURRENT,apparent_temperature,precipitation"
CURRENT="$CURRENT,weather_code,wind_speed_10m"
curl -s "$BASE?latitude=$LAT&longitude=$LON\
&current=$CURRENT&timezone=$TZ_ENC"

# 7-day forecast
DAILY="temperature_2m_max,temperature_2m_min"
DAILY="$DAILY,precipitation_sum,weather_code"
curl -s "$BASE?latitude=$LAT&longitude=$LON\
&daily=$DAILY&timezone=$TZ_ENC"
```

Or use the helper: `bash SKILL_DIR/scripts/briefing.sh weather`

Map `weather_code` to descriptions:
- 0: Clear sky ☀️
- 1-3: Partly cloudy ⛅
- 45-48: Fog 🌫️
- 51-55: Drizzle 🌦️
- 61-65: Rain 🌧️
- 71-75: Snow ❄️
- 80-82: Rain showers 🌦️
- 95-99: Thunderstorm ⛈️

### Step 2: Gather Data — News (Web Search)

Use `web_search` tool for each section. Add current date to queries for freshness. Use the configured `$CITY` for local news.

**X/Twitter Trends (from getdaytrends.com — real-time, no API key):**
```bash
bash SKILL_DIR/scripts/briefing.sh trends
```
This fetches top 25 trends from US, UK, and Worldwide. Use the output to:
- Identify the most interesting/newsworthy trends (skip generic ones like "Good Tuesday", "Taco Tuesday")
- Filter out non-Latin script trends unless they're globally significant
- Pick ~5-10 trends that overlap across regions or seem newsworthy
- Use `web_search` to get context on the top trends you selected

**Web Trends (from Google Trends RSS — what people are searching):**
```bash
bash SKILL_DIR/scripts/briefing.sh webtrends
```
This fetches trending Google searches from US, UK, and Worldwide with:
- Search term and approximate traffic volume
- Top news headline explaining why it's trending
Use this data for the Web Trends section. The headlines already provide context — no extra searching needed for most items.

**World News:**
```
web_search("top world news today {date}", count=8)
web_search("breaking news today", count=5)
```

**Politics:**
```
web_search("US politics news today {date}", count=5)
web_search("EU politics news today {date}", count=5)
web_search("geopolitics news today", count=5)
```

**⚠️ Source diversity:** All sources have bias. For balanced reporting:
- Search the same story wit