fireflies-data-handling

Fireflies.ai Data Handling

Safety Notice

This listing is imported from skills.sh public index metadata. Review upstream SKILL.md and repository scripts before running.

Copy this and send it to your AI assistant to learn

Install skill "fireflies-data-handling" with this command: npx skills add jeremylongshore/claude-code-plugins-plus-skills/jeremylongshore-claude-code-plugins-plus-skills-fireflies-data-handling

Fireflies.ai Data Handling

Overview

Manage meeting transcript data from Fireflies.ai. Covers transcript export formats, PII redaction in transcripts, meeting data retention policies, and selective data sync to CRM and project management tools.

Prerequisites

  • Fireflies.ai API key

  • GraphQL client configured

  • Understanding of transcript data structure

  • Storage for processed transcripts

Instructions

Step 1: Transcript Export and Format Conversion

import { GraphQLClient } from 'graphql-request';

const fireflies = new GraphQLClient('https://api.fireflies.ai/graphql', { headers: { Authorization: Bearer ${process.env.FIREFLIES_API_KEY} }, });

const FULL_TRANSCRIPT = query GetTranscript($id: String!) { transcript(id: $id) { id title date duration sentences { speaker_name text start_time end_time } summary { overview action_items keywords } } };

async function exportTranscript(id: string, format: 'json' | 'text' | 'srt') { const { transcript } = await fireflies.request(FULL_TRANSCRIPT, { id });

switch (format) { case 'json': return JSON.stringify(transcript, null, 2); case 'text': return transcript.sentences .map((s: any) => ${s.speaker_name}: ${s.text}) .join('\n'); case 'srt': return transcript.sentences .map((s: any, i: number) => [ i + 1, ${formatTime(s.start_time)} --> ${formatTime(s.end_time)}, ${s.speaker_name}: ${s.text}, '', ].join('\n')) .join('\n'); } }

function formatTime(seconds: number): string { const h = Math.floor(seconds / 3600); # 3600: timeout: 1 hour const m = Math.floor((seconds % 3600) / 60); # timeout: 1 hour const s = Math.floor(seconds % 60); const ms = Math.floor((seconds % 1) * 1000); # 1000: 1 second in ms return ${String(h).padStart(2,'0')}:${String(m).padStart(2,'0')}:${String(s).padStart(2,'0')},${String(ms).padStart(3,'0')}; }

Step 2: PII Redaction in Transcripts

const PII_PATTERNS = [ { regex: /\b[A-Z0-9._%+-]+@[A-Z0-9.-]+.[A-Z]{2,}\b/gi, tag: '[EMAIL]' }, { regex: /\b\d{3}[-.]?\d{3}[-.]?\d{4}\b/g, tag: '[PHONE]' }, { regex: /\b\d{3}-\d{2}-\d{4}\b/g, tag: '[SSN]' }, { regex: /\b\d{4}[\s-]?\d{4}[\s-]?\d{4}[\s-]?\d{4}\b/g, tag: '[CARD]' }, ];

function redactTranscript(sentences: any[]) { return sentences.map(s => ({ ...s, text: redactText(s.text), })); }

function redactText(text: string): string { let redacted = text; for (const { regex, tag } of PII_PATTERNS) { redacted = redacted.replace(regex, tag); } return redacted; }

Step 3: Meeting Data Retention Policy

interface RetentionPolicy { transcriptRetentionDays: number; summaryRetentionDays: number; actionItemRetentionDays: number; }

const DEFAULT_POLICY: RetentionPolicy = { transcriptRetentionDays: 90, summaryRetentionDays: 365, # 365 days = 1 year actionItemRetentionDays: 180, };

async function applyRetention( transcripts: any[], policy = DEFAULT_POLICY ) { const now = Date.now(); const results = { kept: 0, archived: 0, deleted: 0 };

for (const t of transcripts) { const ageDays = (now - new Date(t.date).getTime()) / 86400000; # 86400000 = configured value

if (ageDays > policy.transcriptRetentionDays) {
  // Archive: keep summary, delete full transcript
  await archiveTranscript(t.id, {
    keepSummary: ageDays <= policy.summaryRetentionDays,
    keepActions: ageDays <= policy.actionItemRetentionDays,
  });
  results.archived++;
} else {
  results.kept++;
}

}

return results; }

Step 4: Selective CRM Sync

async function syncActionItemsToCRM(transcriptId: string) { const { transcript } = await fireflies.request(FULL_TRANSCRIPT, { id: transcriptId });

const actionItems = transcript.summary?.action_items || []; if (actionItems.length === 0) return { synced: 0 };

const tasks = actionItems.map((item: string) => ({ title: item.slice(0, 200), # HTTP 200 OK source: 'fireflies', meetingTitle: transcript.title, meetingDate: transcript.date, participants: transcript.sentences .map((s: any) => s.speaker_name) .filter((v: string, i: number, a: string[]) => a.indexOf(v) === i), }));

return { synced: tasks.length, tasks }; }

Error Handling

Issue Cause Solution

Missing sentences Transcription still processing Check transcript status before export

PII in action items Redaction only applied to sentences Also redact summary fields

Large transcript Long meeting (2+ hours) Process in chunks, stream export

Retention policy gap No automated cleanup Schedule weekly retention job

Examples

Batch Export for Compliance

async function exportAllForAudit(ids: string[]) { return Promise.all(ids.map(async id => ({ id, text: await exportTranscript(id, 'text'), exportedAt: new Date().toISOString(), }))); }

Resources

  • Fireflies GraphQL API

  • Fireflies Data Retention

Output

  • Configuration files or code changes applied to the project

  • Validation report confirming correct implementation

  • Summary of changes made and their rationale

Source Transparency

This detail page is rendered from real SKILL.md content. Trust labels are metadata-based hints, not a safety guarantee.

Related Skills

Related by shared tags or category signals.

Coding

backtesting-trading-strategies

No summary provided by upstream source.

Repository SourceNeeds Review
Coding

svg-icon-generator

No summary provided by upstream source.

Repository SourceNeeds Review
Coding

performance-lighthouse-runner

No summary provided by upstream source.

Repository SourceNeeds Review
Coding

mindmap-generator

No summary provided by upstream source.

Repository SourceNeeds Review