diff --git a/fireflies/README.md b/fireflies/README.md index ed6e7d4..04486f7 100644 --- a/fireflies/README.md +++ b/fireflies/README.md @@ -3,8 +3,8 @@ ## Why Install This Skill Turn Fireflies meetings into usable data without hand-copying notes. Search transcripts, inspect -summaries and action items, review analytics, and ask focused questions with AskFred from a single -dependency-free command line tool. +summaries and action items, review analytics, fetch audio and video recording links, and ask +focused questions with AskFred from a single dependency-free command line tool. It also makes sensitive operations deliberate: every mutation requires an explicit confirmation, and every mutation can be previewed locally before it is sent. @@ -42,6 +42,7 @@ python3 scripts/fireflies meetings rename transcript-id --title "Q3 roadmap" --d ## Triggers - Fireflies.ai transcripts, summaries, notes, contacts, channels, or analytics +- Meeting audio/video recording download links (`transcripts get` returns `video_url`/`audio_url`) - AskFred questions about meeting content - Remote audio upload to Fireflies - Fireflies Webhooks V2 signature verification diff --git a/fireflies/SKILL.md b/fireflies/SKILL.md index 31abc0e..5d317b5 100644 --- a/fireflies/SKILL.md +++ b/fireflies/SKILL.md @@ -33,7 +33,7 @@ the target, scope, and rollback path; then route the change through the CLI's li | Need | Command | |---|---| | Find transcript metadata | `scripts/fireflies transcripts list --keyword TEXT --limit 10 --json` | -| Read a meeting, summary, sentences, and analytics | `scripts/fireflies transcripts get ID --json` | +| Read a meeting, summary, sentences, analytics, and recording links | `scripts/fireflies transcripts get ID --json` | | People, channels, groups, contacts, apps | `users`, `channels`, `groups`, `contacts`, `apps` | | Meeting analytics or live meetings | `analytics --start DATE --end DATE`, `meetings active` | | Ask a transcript question | `askfred create --question TEXT --transcript-id ID --confirm` | diff --git a/fireflies/evals/evals.json b/fireflies/evals/evals.json index 671916a..feedb58 100644 --- a/fireflies/evals/evals.json +++ b/fireflies/evals/evals.json @@ -56,6 +56,17 @@ "Notes AskFred mutations require AI credits and --confirm", "Does not claim AskFred works without an API key" ] + }, + { + "id": "recording-urls", + "prompt": "I have a transcript ID for a meeting I attended and I want to download the audio and video recordings of it. How does the skill give me those files?", + "expected_output": "The agent uses the fireflies transcripts get command with the transcript ID; the returned JSON includes video_url and audio_url fields, which are the download links for the meeting's video and audio recordings. It explains the query is a read-only GraphQL query requiring FIREFLIES_API_KEY and returns JSON.", + "assertions": [ + "Uses the fireflies transcripts get command with a transcript ID", + "Identifies video_url and audio_url in the returned fields as the recording download links", + "Notes the query is read-only and requires FIREFLIES_API_KEY", + "Does not propose an upload or mutation for a read-only lookup" + ] } ] } diff --git a/fireflies/references/api-reference.md b/fireflies/references/api-reference.md index b68aceb..78ebd94 100644 --- a/fireflies/references/api-reference.md +++ b/fireflies/references/api-reference.md @@ -41,6 +41,8 @@ follows (live schema wins): - `createBite` names its argument `transcript_Id` (capital I) and `privacies` takes `[BitePrivacy!]` (enum: `public`, `team`, `participants`). - `shareMeeting` input gained `expiry_days` (7, 14, or 30). +- `transcript` selection gained `video_url` and `audio_url` (meeting recording download links), + verified by live introspection on 2026-08-10. - `updateMeetingChannel` (changelog 2.15.0), `addToLiveMeeting`, `createLiveSoundbite`, `createUploadUrl`/`confirmUpload`, `setUserRole`, and `askfred_thread` were added as ergonomic commands after the audit found them documented but uncovered. diff --git a/fireflies/references/cli-reference.md b/fireflies/references/cli-reference.md index 18163bb..3c174c2 100644 --- a/fireflies/references/cli-reference.md +++ b/fireflies/references/cli-reference.md @@ -10,7 +10,7 @@ subcommands: `--json`, `--api-key`, `--endpoint`, `--timeout`, `--dry-run`, `--q |---|---| | `query --document DOC [--variables JSON|--variables-file PATH]` | Generic read-only GraphQL | | `mutation --document DOC ... --confirm` | Generic mutation | -| `transcripts list|get|delete` | Search, inspect, or delete meetings | +| `transcripts list|get|delete` | Search, inspect, or delete meetings; `get` also returns `video_url`/`audio_url` recording download links | | `users`, `contacts`, `channels`, `groups`, `bites`, `apps` | Workspace/content reads; `users set-role --user-id ID --role admin|user` assigns roles | | `analytics`, `meetings active`, `live-action-items` | Analytics and live data | | `meetings rename|privacy|state|share|revoke-share|update-channel` | Meeting mutations; `share` accepts `--expiry-days` | diff --git a/fireflies/references/workflows.md b/fireflies/references/workflows.md index 49da7dc..83df76d 100644 --- a/fireflies/references/workflows.md +++ b/fireflies/references/workflows.md @@ -11,6 +11,16 @@ scripts/fireflies transcripts get transcript-id --json The detailed query includes summary, speakers, sentences, and analytics. +## Fetch Recording Download URLs + +Use this to grab the meeting's audio and video recordings. The response's `video_url` and +`audio_url` fields are the download links for the recording. + +```bash +scripts/fireflies transcripts get transcript-id --json +# response includes "video_url" and "audio_url" — signed download links for the recording +``` + ## Extract Actions and Summary Use this for a currently live meeting or for a completed transcript. diff --git a/fireflies/scripts/fireflies b/fireflies/scripts/fireflies index 4ffaa33..13eef33 100755 --- a/fireflies/scripts/fireflies +++ b/fireflies/scripts/fireflies @@ -16,7 +16,7 @@ EX_USAGE, EX_CONFIG, EX_TRANSPORT, EX_GRAPHQL, EX_CONFIRM = 2, 3, 4, 5, 6 DOCS = { "transcripts_list": "query Transcripts($title: String, $keyword: String, $scope: String, $fromDate: DateTime, $toDate: DateTime, $limit: Int, $skip: Int, $hostEmail: String, $userId: String, $mine: Boolean, $organizers: [String!], $participants: [String!], $channelId: String, $organizerEmail: String, $participantEmail: String) { transcripts(title: $title, keyword: $keyword, scope: $scope, fromDate: $fromDate, toDate: $toDate, limit: $limit, skip: $skip, host_email: $hostEmail, user_id: $userId, mine: $mine, organizers: $organizers, participants: $participants, channel_id: $channelId, organizer_email: $organizerEmail, participant_email: $participantEmail) { id title date duration organizer_email participants transcript_url } }", - "transcript": "query Transcript($id: String!) { transcript(id: $id) { id title date duration organizer_email participants transcript_url summary { overview } speakers { id name } sentences { index text speaker_name start_time end_time } analytics { sentiments { negative_pct neutral_pct positive_pct } } } }", + "transcript": "query Transcript($id: String!) { transcript(id: $id) { id title date duration organizer_email participants transcript_url video_url audio_url summary { overview } speakers { id name } sentences { index text speaker_name start_time end_time } analytics { sentiments { negative_pct neutral_pct positive_pct } } } }", "users": "query Users { users { user_id email name is_admin integrations } }", "me": "query User { user { user_id email name is_admin integrations } }", "user": "query User($id: String!) { user(id: $id) { user_id email name is_admin integrations } }", diff --git a/fireflies/tests/test_fireflies.py b/fireflies/tests/test_fireflies.py index 6e157cb..becbf2d 100644 --- a/fireflies/tests/test_fireflies.py +++ b/fireflies/tests/test_fireflies.py @@ -79,6 +79,7 @@ class FirefliesTests(unittest.TestCase): self.assertEqual(analytics["variables"],{"startTime":"2026-01-01","endTime":"2026-01-31"}) transcript=json.loads(self.run_cli("transcripts","get","transcript-id","--dry-run","--json").stdout)["payload"] self.assertIn("negative_pct neutral_pct positive_pct",transcript["query"]) + self.assertIn("video_url audio_url",transcript["query"]) audit=json.loads(self.run_cli("audit-events","--filter",'{"category":"MEETING_OPERATIONS"}',"--dry-run","--json").stdout)["payload"] self.assertIn("events { id time action actor { user_id } resource { type id } }",audit["query"]) def test_transcripts_list_document_is_current(self):