Skip to main content

Documentation Index

Fetch the complete documentation index at: https://docs.sf-voice.sh/llms.txt

Use this file to discover all available pages before exploring further.

Le SDK @sf-voice/media enveloppe l’API sf-voice media pour les applications TypeScript. Utilisez-le pour soumettre des actifs médias, attendre l’indexation et rechercher à travers les surfaces vidéo, audio et transcription avec vos propres identifiants d’actifs orientés client.

Ingérer les actifs

Soumettez des médias depuis une URL, une clé S3 ou un buffer navigateur/fichier.

Conservez vos ID

Passez votre propre asset_id afin que les résultats se rattachent à votre système.

Cadrer la recherche

Utilisez asset_class ou asset_ids pour que la recherche reste liée au bon client ou groupe.
Le SDK n’expose que les termes sf-voice. Le mappage spécifique au fournisseur a lieu dans le backend.

Nouveau sur sf-voice media ?

Commencez par la vue d’ensemble du produit avant d’utiliser la référence du SDK.

Installation

pnpm add @sf-voice/media@latest

Créer un client

import { SfVoiceMedia } from "@sf-voice/media";

const client = new SfVoiceMedia({
  baseUrl: "https://api.sf-voice.com",
  apiKey: process.env.SF_VOICE_API_KEY!,
  timeoutMs: 30_000,
});
OptionRequisDescription
baseUrlOuiURL de base pour l’API sf-voice media.
apiKeyOuiClé API envoyée comme en-tête X-API-Key.
timeoutMsNonDélai d’expiration par requête en millisecondes. Par défaut 30_000.

Champs principaux

ChampDescription
asset_idVotre identifiant unique pour l’actif média. Obligatoire à l’ingestion.
asset_classGroupe logique optionnel, tel qu’un client, un espace de travail, un projet ou un dépôt. Utilisé pour cadrer la recherche.
typesSurfaces médias optionnelles à indexer ou rechercher : "video", "audio", "transcript".
metadataMétadonnées clé/valeur plates optionnelles. Les valeurs doivent être des chaînes, des nombres ou des booléens.
thresholdScore de recherche minimal optionnel de 0.0 à 1.0. Des valeurs plus élevées renvoient moins de résultats mais plus fiables.

Choisir asset_class

Utilisez asset_class pour la frontière dans laquelle votre produit doit rechercher par défaut. Pour la plupart des produits orientés client, il s’agit du client final, de l’espace de travail, du projet, du dépôt ou de la collection. Bons exemples de asset_class :
  • customer_acme
  • workspace_123
  • project_onboarding
  • repo_mobile_app
Ne comptez pas sur la recherche globale pour les workflows orientés client, sauf si chaque utilisateur est autorisé à rechercher dans tous les actifs indexés.

Flux de bout en bout

1

Soumettre un actif

const ingest = await client.ingest({
  source: "url",
  asset_id: "video_123",
  asset_class: "customer_acme",
  url: "https://example.com/recording.mp4",
  media_type: "video",
  types: ["video", "audio", "transcript"],
  metadata: {
    title: "product demo",
    customer_id: "acme",
  },
});
2

Attendre l'indexation

const task = await client.pollTask(ingest.task_id, {
  intervalMs: 2_000,
  timeoutMs: 120_000,
});

if (task.status === "failed") {
  throw new Error(task.error ?? "ingest task failed");
}
3

Rechercher dans les médias indexés

const search = await client.search({
  query: "where does the customer mention pricing?",
  asset_class: "customer_acme",
  types: ["transcript"],
  threshold: 0.7,
  limit: 10,
});

console.log(search.results);

Utilisation côté navigateur et serveur

Le SDK fonctionne partout où le runtime fournit fetch, FormData et Blob.
RuntimeSource d’ingestion recommandée
Application navigateursource: "file" pour les téléversements directs depuis des champs de fichier.
Service backendsource: "url" ou source: "s3" lorsque le média est déjà stocké.
Runtime workersource: "url" ou source: "file" selon les API de corps de requête disponibles.
Pour les gros fichiers, préférez téléverser le média d’abord vers votre couche de stockage et l’ingérer par URL ou clé S3.

Ingestion

ingest(request) soumet un média pour indexation et renvoie immédiatement un identifiant de tâche.

Entrée

Champs communs :
ChampRequisDescription
asset_idOuiVotre identifiant unique pour l’actif.
asset_classNonGroupe logique pour l’actif. La recherche peut ensuite l’utiliser comme portée.
media_typeNon"video" ou "audio".
typesNonSurfaces à indexer : "video", "audio", "transcript".
metadataNonMétadonnées clé/valeur plates pour votre propre corrélation.
Champs spécifiques à la source :
SourceChamps requisDescription
urlurlIngérer depuis une URL publique ou accessible par le backend.
s3s3_keyIngérer depuis une clé S3 déjà connectée à sf-voice.
filefile, filenameTéléverser directement un Blob, ArrayBuffer ou Uint8Array.

Exemples

const ingest = await client.ingest({
  source: "url",
  asset_id: "video_123",
  asset_class: "customer_acme",
  url: "https://example.com/recording.mp4",
  media_type: "video",
  types: ["video", "audio", "transcript"],
});

Sortie

type IngestResponse = {
  asset_id: string;
  task_id: string;
  status: "pending";
};
{
  "asset_id": "video_123",
  "task_id": "task_abc123",
  "status": "pending"
}

Tâches et interrogation

Utilisez getTask(taskId) pour récupérer l’état d’une tâche une seule fois. Utilisez pollTask(taskId, options) pour attendre que la tâche atteigne "ready" ou "failed".
const task = await client.pollTask("task_abc123", {
  intervalMs: 2_000,
  timeoutMs: 120_000,
});
type Task = {
  task_id: string;
  asset_id: string;
  asset_class?: string;
  types: Array<"video" | "audio" | "transcript">;
  status: "pending" | "indexing" | "ready" | "failed";
  error?: string;
  created_at: string;
  completed_at?: string;
};

Recherche

search(request) recherche dans les médias indexés en langage naturel.
Préférez asset_class ou asset_ids pour la recherche orientée client. Utilisez scope: "all" uniquement lorsque vous voulez intentionnellement rechercher dans tous les actifs.
La recherche dispose de trois modes de cadrage :
ModeExempleÀ utiliser quand
asset_class{ asset_class: "customer_acme" }Recherche d’un client, espace de travail, projet ou collection.
asset_ids{ asset_ids: ["video_123"] }Recherche dans un ensemble connu d’actifs.
scope: "all"{ scope: "all" }Recherche intentionnelle dans tous les actifs indexés.

Entrée

ChampRequisDescription
queryOuiRequête de recherche en langage naturel.
typesNonSurfaces à rechercher : "video", "audio", "transcript".
asset_idsNonRestreindre la recherche à des identifiants d’actifs clients spécifiques.
asset_classNonRestreindre la recherche à un groupe logique. Recommandé pour la recherche cadrée par client.
scopeNonDéfinir sur "all" uniquement lors d’une recherche intentionnelle dans tous les actifs.
thresholdNonScore de correspondance minimal de 0.0 à 1.0. Par défaut à la valeur par défaut de l’API.
pageNonNuméro de page.
limitNonRésultats max par page.

Exemples

const search = await client.search({
  query: "refund policy",
  asset_class: "customer_acme",
  types: ["transcript"],
});

Sortie

type SearchResponse = {
  results: Array<{
    asset_id: string;
    score: number;
    start_ms: number;
    end_ms: number;
    match_type: "video" | "audio" | "transcript";
    thumbnail_url?: string;
  }>;
  page_info: {
    total: number;
    page: number;
    limit: number;
    next_page_token?: string;
  };
};
{
  "results": [
    {
      "asset_id": "video_123",
      "score": 0.84,
      "start_ms": 42000,
      "end_ms": 58000,
      "match_type": "transcript",
      "thumbnail_url": "https://api.sf-voice.com/assets/video_123/thumb.jpg"
    }
  ],
  "page_info": {
    "total": 1,
    "page": 1,
    "limit": 10
  }
}
start_ms et end_ms sont des décalages en millisecondes dans le média source. Utilisez-les pour positionner un lecteur directement au moment correspondant.

Actifs

const assets = await client.listAssets({ page: 1, limit: 20 });
const asset = await client.getAsset("video_123");
await client.deleteAsset("video_123");
type Asset = {
  asset_id: string;
  asset_class?: string;
  media_type: "video" | "audio";
  source_type: "url" | "s3" | "file";
  types: Array<"video" | "audio" | "transcript">;
  status: "pending" | "indexing" | "ready" | "failed";
  metadata?: Record<string, string | number | boolean>;
  duration_ms?: number;
  created_at: string;
  updated_at: string;
};

Erreurs

Chaque réponse API non-2xx déclenche SfVoiceMediaError.
import { SfVoiceMediaError } from "@sf-voice/media";

try {
  await client.search({
    query: "pricing",
    asset_class: "customer_acme",
  });
} catch (error) {
  if (error instanceof SfVoiceMediaError) {
    console.error(error.code);
    console.error(error.status);
    console.error(error.message);
  }
  throw error;
}
SfVoiceMediaRequestTimeoutError est levée lorsqu’une requête HTTP unique dépasse le délai d’expiration du client. SfVoiceMediaPollTimeoutError est levée lorsque pollTask dépasse son délai d’expiration avant que la tâche n’atteigne "ready" ou "failed".