5.1 KiB
| phase | plan | type |
|---|---|---|
| 02-model-discovery | 2 | execute |
Purpose: Enable dynamic fetching of available models from fal.ai's API, normalized to our ProviderModel interface. Output: Working fal.ai provider that registers in the provider system and an API route for client access.
<execution_context> ~/.claude/get-shit-done/workflows/execute-phase.md ~/.claude/get-shit-done/templates/summary.md </execution_context>
@.planning/PROJECT.md @.planning/ROADMAP.md @.planning/STATE.md @.planning/phases/02-model-discovery/DISCOVERY.mdPrior plan context:
@.planning/phases/02-model-discovery/02-01-SUMMARY.md
Key files:
@src/lib/providers/types.ts @src/lib/providers/index.ts @src/lib/providers/replicate.ts @src/types/index.ts
Tech stack available:
- Provider abstraction interfaces (ProviderInterface, ProviderModel)
- Provider registry with registerProvider()
- ProviderType includes "fal"
- Replicate provider pattern established
Established patterns:
- Provider implementation in src/lib/providers/{provider}.ts
- API route at src/app/api/providers/{provider}/models/route.ts
- Self-registration via registerProvider()
Constraining decisions:
- No SDKs - use direct fetch calls
- API keys from localStorage via provider settings
- Import types from @/lib/providers and @/types
- Implement helper function to get API key from localStorage (client) or return null (server)
- Implement listModels():
- Fetch GET https://api.fal.ai/v1/models with optional Key auth header
- Filter to categories: text-to-image, image-to-image, text-to-video, image-to-video
- Map models to ProviderModel[]:
- id: endpoint_id
- name: metadata.display_name
- description: metadata.description
- provider: "fal"
- coverImage: metadata.thumbnail_url
- capabilities: [metadata.category as ModelCapability]
- Return first page only (no pagination traversal)
- Implement searchModels(query):
- Fetch GET https://api.fal.ai/v1/models?q={query}&category=text-to-image (or combined categories)
- Map and return results same as listModels
- Implement getModel(modelId):
- Fetch GET https://api.fal.ai/v1/models?endpoint_id={modelId}
- Return first result mapped to ProviderModel
- Implement generate() as stub returning { success: false, error: "Not implemented" } (Phase 3)
- Implement isConfigured() checking if API key exists (note: fal.ai works without key but with rate limits)
- Implement getApiKey() returning key from localStorage or null
- Call registerProvider(falProvider) at module level
Note: fal.ai categories map directly to our ModelCapability type. TypeScript compiles without errors: npx tsc --noEmit fal.ts exports working provider, registered in registry when imported
Task 2: Create fal.ai models API route src/app/api/providers/fal/models/route.ts Create Next.js API route for fetching fal.ai models server-side:- Export GET handler
- Get optional API key from request header (fal.ai works without but rate limited)
- Parse optional
searchquery param - Build fetch URL:
- Base: https://api.fal.ai/v1/models
- Add ?q={search} if search param provided
- Add category filter for image/video types only
- Add Authorization header if API key provided: Key {apiKey}
- Map response.models to ProviderModel[] using same logic as provider:
- Filter to relevant categories (text-to-image, image-to-image, text-to-video, image-to-video)
- Map endpoint_id, metadata.display_name, metadata.description, etc.
- Return { success: true, models: ProviderModel[] }
- Handle errors: return { success: false, error: message }
Pattern to follow from Replicate API route (02-01). curl -X GET "http://localhost:3000/api/providers/fal/models" returns JSON with models array (works without key due to fal.ai's optional auth) API route returns model list, works with or without API key, filters to image/video categories
Before declaring plan complete: - [ ] `npx tsc --noEmit` passes - [ ] `npm run build` succeeds - [ ] fal.ai provider file exists and exports provider - [ ] API route file exists at correct path - [ ] Provider registers when module is imported - [ ] Models filtered to image/video capabilities only<success_criteria>
- fal.ai provider implements ProviderInterface
- Provider self-registers via registerProvider()
- API route proxies model fetching (optional auth)
- Models normalized to ProviderModel interface
- Only image/video models returned (no audio, 3D, etc.)
- No TypeScript errors </success_criteria>