Scheduling
Most agent workflows are time-triggered. Three approaches:
| Approach | Pros | Cons |
|---|---|---|
| LaunchAgents (macOS) | Reliable, runs without Claude | No reasoning, just scripts |
| Claude Code cron commands | Can reason about edge cases | Needs active session |
| Hybrid (recommended) | Scripts collect data, agents reason | More complex but most capable |
Recommended: Hybrid Model
- Scripts run on schedule via LaunchAgents (data collection, simple routing)
- Agent reasoning triggered when classification/drafting is needed
- Results pushed via SMS/email/Telegram/other channels
LaunchAgents (macOS Scheduled Tasks)
LaunchAgents are .plist files in ~/Library/LaunchAgents/ that run scripts on schedule.
Example LaunchAgent Setup
| Agent | Schedule | Purpose |
|---|---|---|
com.yourname.nightcrew | 3:00 AM daily | Nightly data pipeline |
com.yourname.morningbrief | 6:00 AM daily | Morning digest generation |
com.yourname.todo-sync | Every 10 min | Sync todos with a note-taking app |
com.yourname.n8n | At startup | n8n workflow engine |
Example: Nightly Pipeline
An example nightly automation pipeline that collects data across sources:
| Stage | What It Does |
|---|---|
| 1 | File triage (Downloads -> PARA folders) |
| 2 | Claude Code session context extraction |
| 3 | Email digest + cleanup |
| 4 | Message extraction (WhatsApp, iMessage, etc.) |
| 5 | Voice memo transcription |
| 6 | Calendar events for today/tomorrow |
| 7 | Photo triage and classification |
| 8 | Activity summary compilation |
| 9 | Morning brief generation |
| 10 | Git push to sync repo |
The key pattern is: collect -> aggregate -> output to vault -> push.
┌─ Schedule (LaunchAgents) ───────────────────────────────────┐
│ │
│ 3 AM NightCrew ──▶ 6 AM Morning Brief ──▶ Every 10m │
│ Todo Sync │
└────────┬────────────────────────────────────────────────────┘
│
▼
┌─ Pipeline Stages ───────────────────────────────────────────┐
│ │
│ File Triage ──▶ Data Extract ──▶ Aggregate ──▶ Output │
│ │ │
│ ▼ │
│ Push to Vault │
│ │
└─────────────────────────────────────────────────────────────┘Setting Up a New LaunchAgent
<?xml version="1.0" encoding="UTF-8"?>
<!DOCTYPE plist PUBLIC "-//Apple//DTD PLIST 1.0//EN"
"http://www.apple.com/DTDs/PropertyList-1.0.dtd">
<plist version="1.0">
<dict>
<key>Label</key>
<string>com.yourname.example-task</string>
<key>ProgramArguments</key>
<array>
<string>/usr/bin/python3</string>
<string>/path/to/script.py</string>
</array>
<key>StartCalendarInterval</key>
<dict>
<key>Hour</key>
<integer>8</integer>
<key>Minute</key>
<integer>0</integer>
</dict>
<key>EnvironmentVariables</key>
<dict>
<key>OP_DISABLED</key>
<string>1</string>
<key>PATH</key>
<string>/usr/local/bin:/usr/bin:/bin</string>
</dict>
<key>StandardOutPath</key>
<string>/tmp/example-task.log</string>
<key>StandardErrorPath</key>
<string>/tmp/example-task-error.log</string>
</dict>
</plist>Important: LaunchAgents cannot use 1Password CLI (no GUI session for biometric). Set OP_DISABLED=1 and use .env files as fallback.
# Load a LaunchAgent
launchctl load ~/Library/LaunchAgents/com.yourname.example-task.plist
# Unload
launchctl unload ~/Library/LaunchAgents/com.yourname.example-task.plist
# Check status
launchctl list | grep com.yournameLast updated on