--- name: cf-switch-backend description: "Switch ContentForge's tracking and delivery backend between Google Sheets + Drive, Airtable, and local filesystem — guiding credential setup, verifying access, optionally migrating existing tracking records and output files (migration is additive and never deletes source data), and updating tracking.backend in the brand profile so the next run uses it immediately. Triggers on \"/contentforge:cf-switch-backend\", \"switch tracking to Airtable\", \"move tracking to Google Sheets\", \"which backend am I using\", \"migrate my tracking data\". Runs backend-migrator.py, sheets-tracker.py, airtable-tracker.py, or local-tracker.py; --status reports current backend health. Pairs with /contentforge:cf-cowork-setup for the Cowork Drive route and /contentforge:cf-style-guide, whose Step G sets the initial backend." disable-model-invocation: true argument-hint: "[local | airtable | google_sheets] [--status]" effort: high --- # Switch Tracking Backend Switch ContentForge's tracking and delivery backend between **Google Sheets + Drive**, **Airtable**, or **Local filesystem**. Optionally migrate existing tracking data and output files to the new backend. ## When to Use - Switching from local (default) to a cloud backend for collaboration - Migrating from Google to Airtable (or vice versa) for simpler auth - Downgrading to local when cloud access isn't needed - Checking current backend status before switching **Running in Cowork?** The "local" backend writes to the ephemeral sandbox filesystem — files vanish at session end. For Cowork team setups, use the Google (Drive) route and run `/contentforge:cf-cowork-setup` first to wire the Drive folder layout. ## How to Use ``` /contentforge:cf-switch-backend airtable /contentforge:cf-switch-backend google_sheets /contentforge:cf-switch-backend local /contentforge:cf-switch-backend --status ``` ## What This Command Does ### Step 1: Identify Current Backend Read the active brand profile's `tracking.backend` field. Report current state: ``` Current backend: local Records: 47 tracking records (~/.claude-marketing/{brand}/tracking/tracking.json) Output files: 42 files in ~/.claude-marketing/{brand}/outputs/{YYYY}/{MM}/ ``` ### Step 2: Validate Target Backend **If switching to Airtable:** 1. Check `AIRTABLE_TOKEN` environment variable exists 2. If missing, guide through setup: - Go to [airtable.com/create/tokens](https://airtable.com/create/tokens) - Create a Personal Access Token with `data.records:read` and `data.records:write` scopes - Select the base that will hold tracking data - Set the environment variable: `export AIRTABLE_TOKEN=patXXXXXXXX` 3. Ask for the Airtable Base ID (from the base URL: `airtable.com/appXXXXXXXXX/...`) 4. Verify access by running: ``` python {scripts_dir}/airtable-tracker.py --action init --base-id {base_id} ``` **If switching to Google Sheets + Drive:** 1. Check Google credentials at `~/.claude-marketing/google-credentials.json` 2. If missing, guide through setup: - Go to Google Cloud Console > IAM & Admin > Service Accounts - Create a project (or use existing) - Enable Google Sheets API and Google Drive API - Create a Service Account and download the JSON key - Save to `~/.claude-marketing/google-credentials.json` - Create a Google Sheet and share it with the service account email (Editor) - Create a Google Drive folder and share it with the service account email (Editor) 3. Ask for the Google Sheet ID and Drive folder ID 4. Verify access by running: ``` python {scripts_dir}/sheets-tracker.py --action init --sheet-id {sheet_id} ``` **If switching to Local:** - No setup needed — works immediately - Run init to ensure directory exists: ``` python {scripts_dir}/local-tracker.py --action init --brand "{brand}" ``` ### Step 3: Offer Migration If the current backend has existing records: ``` You have 47 tracking records and 42 output files on 'local'. Would you like to migrate this data to Airtable? 1. Yes — Copy all records and files to the new backend 2. No — Start fresh (existing data preserved but not synced) 3. Skip — Just switch, decide on migration later ``` **If yes**, run: ``` python {scripts_dir}/backend-migrator.py --action migrate --brand "{brand}" --from {current} --to {target} [backend-specific args] ``` `{current}` and `{target}` must be one of `local`, `airtable`, `google_sheets` — the migrator rejects any other value. Report migration results: ``` Migration complete: Records migrated: 47 Files migrated: 42 Files failed: 0 Source data preserved at: ~/.claude-marketing/{brand}/tracking/tracking.json and ~/.claude-marketing/{brand}/outputs/{YYYY}/{MM}/ ``` ### Step 4: Update Brand Profile Update the brand profile JSON: - Set `tracking.backend` to the new backend value - Fill in backend-specific config (base_id, sheet_id, folder_id, etc.) ### Step 5: Confirm ``` Backend switched to Airtable. New tracking records → Airtable base appXXXXXX Output files → Airtable attachment fields Previous data preserved at: ~/.claude-marketing/{brand}/tracking/tracking.json and ~/.claude-marketing/{brand}/outputs/{YYYY}/{MM}/ Run /contentforge:cf-switch-backend --status to verify anytime. ``` ## Backend Comparison | Factor | Google Sheets + Drive | Airtable | Local | |--------|----------------------|----------|-------| | Auth setup | Service account (~5 min) | Personal token (~2 min) | None | | Tracking | Google Sheets | Airtable records | JSON file | | File delivery | Google Drive | Attachment field | Local filesystem | | Collaboration | Share via Google | Share via Airtable | Single user | | Free tier | 15GB Drive | 1,000 records + 10GB | Unlimited | | Offline | No | No | Yes | ## Check Status Run with `--status` flag to check current backend health: ``` /contentforge:cf-switch-backend --status ``` This runs: ``` python {scripts_dir}/backend-migrator.py --action status --brand "{brand}" --from {current_backend} ``` ## Important Notes - **Migration is additive** — source data is never deleted - **Migration is idempotent for records that carry a `requirement_id`** — dedup is keyed on that field, so records without one are re-written on every run - **Migration is resumable on the same basis** — re-running after an interruption skips whatever already landed with a matching `requirement_id` - **Migrating *from* `google_sheets` moves records only** — downloading the linked Drive files is not implemented yet, so rows arrive without their attachments (the source Drive copies are untouched) - **You can switch back anytime** — data is preserved on all backends you've used - **The pipeline uses whichever backend is set** in `tracking.backend` — switching takes effect immediately for the next content run ## Related Skills - **[/contentforge:cf-style-guide](../cf-style-guide/SKILL.md)** — Brand setup (Step G sets initial backend) - **[/contentforge:cf-cowork-setup](../cf-cowork-setup/SKILL.md)** — Wire Cowork + Drive before choosing the Google backend in Cowork - **[/contentforge:cf-integrations](../cf-integrations/SKILL.md)** — Check all connector status - **[/contentforge:cf-connect](../cf-connect/SKILL.md)** — Set up individual connectors