メインコンテンツまでスキップ

Preload API

Elftia 通过 Electron 的 contextBridge 将后端能力安全地暴露给前端。前端通过 window.api 全局对象调用所有后端功能。

认证机制

所有 IPC 调用都自动携带认证 Token,开发者无需手动处理:

{/* packages/desktop/app/preload/index.ts — 简化示意 */}

const authToken = ipcRenderer.sendSync('auth:bootstrap');

const invoke = (channel: string, ...args: any[]) =>
ipcRenderer.invoke(channel, authToken, ...args);

命名空间索引

命名空间职责方法数
runtime运行时环境1
authSession认证会话8
account账户管理7
projects项目管理6
files文件操作12
sessions项目会话3
chat聊天核心6
chatSessions聊天会话 CRUD5
chatMessages聊天消息 CRUD7
chatAssistants聊天助手 CRUD6
completionLLM 补全10
llmConfigLLM 配置30+
settings应用设置4
appPreferences应用偏好2
config文件配置7
theme主题管理11
mcpMCP 服务器12
agentAgent 操作15+
magiMagi 服务4
elfiElfi 助手3
image图片生成3
video视频生成3
music音乐生成1
media媒体管理10
webSearch网络搜索9
windowControls窗口控制7
diagnostics系统诊断6
env环境检测5
gitGit 操作2
prompts提示词管理9
export导出功能2
channelPluginsChannel 插件6

runtime

window.api.runtime.getEnvironment(): Promise<RuntimeEnvironment>

返回运行时环境信息(平台、版本、路径等)。


authSession

window.api.authSession.getState(): Promise<AuthState>
window.api.authSession.startBrowserLogin(): Promise<void>
window.api.authSession.refresh(): Promise<void>
window.api.authSession.syncProfile(): Promise<void>
window.api.authSession.getAccessToken(): Promise<string>
window.api.authSession.logout(): Promise<void>
window.api.authSession.retrySteamLogin(): Promise<void>
window.api.authSession.subscribe(cb: (state: AuthState) => void): () => void

subscribe 返回取消订阅函数。


account

window.api.account.list(type?: string): Promise<Account[]>
window.api.account.create(payload: CreateAccountInput): Promise<Account>
window.api.account.delete(id: string): Promise<void>
window.api.account.toggle(id: string, isActive: boolean): Promise<void>
window.api.account.reveal(id: string): Promise<string>
window.api.account.export(options?: ExportOptions): Promise<ExportResult>
window.api.account.clear(type?: string): Promise<void>

projects

window.api.projects.list(): Promise<Project[]>
window.api.projects.create(input: { path: string; displayName?: string }): Promise<Project>
window.api.projects.rename(projectId: string, displayName?: string): Promise<void>
window.api.projects.delete(projectId: string): Promise<void>
window.api.projects.browse(dirPath?: string): Promise<BrowseResult>
window.api.projects.createWorkspace(payload: { path: string; workspaceType: string }): Promise<void>

files

window.api.files.snapshot(projectId: string): Promise<FileTree>
window.api.files.subscribe(projectId: string, cb: (patch: FilePatch) => void): () => void
window.api.files.watch(projectId: string): Promise<void>
window.api.files.unwatch(projectId: string): Promise<void>
window.api.files.read(projectId: string, filePath: string): Promise<string>
window.api.files.readBinary(projectId: string, filePath: string): Promise<Buffer>
window.api.files.write(projectId: string, filePath: string, content: string): Promise<void>
window.api.files.shallow(projectId: string, dirPath?: string): Promise<FileEntry[]>
window.api.files.search(projectId: string, params?: SearchParams): Promise<SearchResult[]>
window.api.files.searchMetrics(): Promise<SearchMetrics>
window.api.files.revealInFolder(filePath: string): Promise<void>
window.api.files.clearCache(projectId: string): Promise<void>

chat

window.api.chat.appendMessage(sessionId: string, msg: any): Promise<void>
window.api.chat.getMessages(sessionId: string, query?: any): Promise<Message[]>
window.api.chat.sendCommand(payload: CommandPayload): Promise<void>
window.api.chat.abortSession(payload: { sessionId: string }): Promise<void>
window.api.chat.checkSessionStatus(payload: { sessionId: string }): Promise<SessionStatus>
window.api.chat.onEvent(cb: (data: ChatEvent) => void): () => void

chatSessions

window.api.chatSessions.list(query?: ListQuery): Promise<ChatSession[]>
window.api.chatSessions.get(id: string): Promise<ChatSession>
window.api.chatSessions.create(input: CreateChatSessionInput): Promise<ChatSession>
window.api.chatSessions.update(id: string, input: UpdateInput): Promise<ChatSession>
window.api.chatSessions.delete(id: string): Promise<void>

chatMessages

window.api.chatMessages.getActivePath(sessionId: string): Promise<Message[]>
window.api.chatMessages.getPage(query: PageQuery): Promise<PageResult>
window.api.chatMessages.getBranches(sessionId: string, parentId: string | null): Promise<Message[]>
window.api.chatMessages.append(sessionId: string, message: MessageInput): Promise<Message>
window.api.chatMessages.update(messageId: string, updates: MessageUpdate): Promise<Message>
window.api.chatMessages.switchBranch(messageId: string): Promise<void>
window.api.chatMessages.delete(messageId: string): Promise<void>

chatAssistants

window.api.chatAssistants.list(): Promise<ChatAssistant[]>
window.api.chatAssistants.get(id: string): Promise<ChatAssistant>
window.api.chatAssistants.create(input: CreateAssistantInput): Promise<ChatAssistant>
window.api.chatAssistants.update(id: string, input: UpdateInput): Promise<ChatAssistant>
window.api.chatAssistants.delete(id: string): Promise<void>
window.api.chatAssistants.setDefault(id: string): Promise<void>

completion

window.api.completion.complete(payload: CompletePayload): Promise<CompleteResult>
window.api.completion.stream(payload: StreamPayload): Promise<{ streamId: string }>
window.api.completion.onStreamEvent(streamId: string, cb: (data: StreamEvent) => void): () => void
window.api.completion.getModels(providerId: string): Promise<Model[]>
window.api.completion.testModel(providerId: string, modelId: string): Promise<TestResult>
window.api.completion.chatInSession(payload: ChatInSessionPayload): Promise<void>
window.api.completion.regenerateInSession(payload: RegeneratePayload): Promise<void>
window.api.completion.onChatCompleted(cb: (data: ChatCompletedEvent) => void): () => void
window.api.completion.createRPFirstMessage(payload: { sessionId: string }): Promise<void>

llmConfig

{/* 提供商 CRUD */}
window.api.llmConfig.getProviders(): Promise<Provider[]>
window.api.llmConfig.getProvider(id: string): Promise<Provider>
window.api.llmConfig.addProvider(payload: AddProviderInput): Promise<Provider>
window.api.llmConfig.updateProvider(payload: UpdateProviderInput): Promise<Provider>
window.api.llmConfig.deleteProvider(id: string): Promise<void>
window.api.llmConfig.toggleProvider(id: string, enabled: boolean): Promise<void>
window.api.llmConfig.discoverModels(id: string, options?: { forceRefresh?: boolean }): Promise<Model[]>

{/* 预设 */}
window.api.llmConfig.getProviderPresets(): Promise<Preset[]>
window.api.llmConfig.addFromPreset(payload: { presetId: string; apiKey?: string }): Promise<Provider>

{/* 模型参数 */}
window.api.llmConfig.getAgentDefaultModels(): Promise<DefaultModels>
window.api.llmConfig.setAgentDefaultModels(payload: DefaultModels): Promise<void>
window.api.llmConfig.getGlobalModelParameters(): Promise<GlobalModelParameters>
window.api.llmConfig.setGlobalModelParameters(payload: GlobalModelParameters): Promise<void>

{/* API 密钥池 */}
window.api.llmConfig.getApiKeys(providerId: string): Promise<ApiKeyEntry[]>
window.api.llmConfig.addApiKey(input: ApiKeyInput): Promise<ApiKeyEntry>
window.api.llmConfig.updateApiKey(id: string, updates: ApiKeyUpdate): Promise<ApiKeyEntry>
window.api.llmConfig.deleteApiKey(id: string): Promise<void>
window.api.llmConfig.toggleApiKey(id: string, enabled: boolean): Promise<void>

{/* 导入/导出 */}
window.api.llmConfig.exportConfig(): Promise<ExportedConfig>
window.api.llmConfig.importConfig(payload: ExportedConfig): Promise<void>

settings

window.api.settings.get(key: string): Promise<any>
window.api.settings.set(key: string, value: any): Promise<void>
window.api.settings.getExperimentalFeatures(): Promise<ExperimentalFeatures>
window.api.settings.setExperimentalFeatures(payload: ExperimentalFeatures): Promise<void>

appPreferences

window.api.appPreferences.get(): Promise<AppPreferences>
window.api.appPreferences.update(payload: Partial<AppPreferences>): Promise<void>

config

window.api.config.get(key: string): Promise<any>
window.api.config.getAll(): Promise<Record<string, any>>
window.api.config.getPath(): Promise<string>
window.api.config.set(key: string, value: any): Promise<void>
window.api.config.merge(key: string, patch: any): Promise<void>
window.api.config.reset(key: string): Promise<void>
window.api.config.onChange(cb: (event: ConfigChangeEvent) => void): () => void

theme

window.api.theme.getState(): Promise<ThemeState>
window.api.theme.setMode(mode: 'light' | 'dark' | 'system'): Promise<void>
window.api.theme.updateUserTheme(payload: UserThemeUpdate): Promise<void>
window.api.theme.setCustomCss(css: string): Promise<void>
window.api.theme.setWallpaper(payload: WallpaperConfig): Promise<void>
window.api.theme.setWallpaperPreferences(payload: WallpaperPreferences): Promise<void>
window.api.theme.setRemoteAssetsPolicy(payload: RemoteAssetsPolicy): Promise<void>
window.api.theme.exportProfile(): Promise<ThemeProfile>
window.api.theme.importProfile(payload: ThemeProfile): Promise<void>
window.api.theme.resetProfile(): Promise<void>
window.api.theme.onUpdated(cb: (state: ThemeState) => void): () => void

mcp

window.api.mcp.list(): Promise<McpServer[]>
window.api.mcp.add(payload: AddMcpInput): Promise<McpServer>
window.api.mcp.addJson(payload: JsonMcpConfig): Promise<McpServer>
window.api.mcp.remove(payload: { id: string }): Promise<void>
window.api.mcp.test(payload: { id: string }): Promise<TestResult>
window.api.mcp.discover(payload: { id: string }): Promise<DiscoveryResult>
window.api.mcp.update(payload: { id: string; updates: McpUpdate }): Promise<void>
window.api.mcp.listServerTools(serverId: string): Promise<Tool[]>
window.api.mcp.listAllTools(): Promise<Tool[]>
window.api.mcp.callTool(payload: CallToolInput): Promise<ToolResult>
window.api.mcp.checkDependency(command: string): Promise<boolean>
window.api.mcp.installDependency(command: string): Promise<void>

agent

window.api.agent.checkAvailability(): Promise<boolean>
window.api.agent.getBackends(): Promise<BackendInfo[]>
window.api.agent.createSession(options: CreateSessionOptions): Promise<{ sessionId: string }>
window.api.agent.resumeSession(params: ResumeParams): Promise<void>
window.api.agent.interrupt(sessionId: string): Promise<void>
window.api.agent.respondPermission(params: { requestId: string; result: any }): Promise<void>
window.api.agent.respondAskUserQuestion(params: { requestId: string; result: { answers: Record<string, string>; annotations?: Record<string, { notes?: string }>; cancelled?: boolean } }): Promise<{ success: boolean }>
window.api.agent.getActiveSessions(): Promise<ActiveSession[]>
window.api.agent.isSessionActive(sessionId: string): Promise<boolean>
window.api.agent.selectFolder(): Promise<{ canceled: boolean; path: string | null }>
window.api.agent.onEvent(cb: (data: AgentEvent) => void): () => void
window.api.agent.onPermissionRequest(cb: (data: PermissionRequest) => void): () => void
window.api.agent.onAskUserQuestion(cb: (data: AskUserQuestionRequest) => void): () => void
window.api.agent.onA2UIRender(cb: (data: A2UIEvent) => void): () => void
window.api.agent.onDevPreview(cb: (data: PreviewStatus) => void): () => void

{/* 子命名空间 */}
window.api.agent.customAgents.list/get/create/update/delete/run/export/import(...)
window.api.agent.mcpRefs.list/attach/detach/toggleEnabled(...)
window.api.agent.agentSessions.create/get/list/update/delete(...)
window.api.agent.sharedComponents.create/get/list/update/delete(...)
window.api.agent.personas.list/get/create/update/delete(...)

image

window.api.image.generate(payload: ImageGeneratePayload): Promise<ImageResult>
window.api.image.generateInSession(payload: SessionImagePayload): Promise<void>
window.api.image.onGenerationCompleted(cb: (data: GenerationCompletedEvent) => void): () => void

video

window.api.video.generate(payload: VideoGeneratePayload): Promise<VideoResult>
window.api.video.generateInSession(payload: SessionVideoPayload): Promise<void>
window.api.video.onGenerationCompleted(cb: (data: GenerationCompletedEvent) => void): () => void

music

window.api.music.generateInSession(payload: SessionMusicPayload): Promise<void>

sessions

window.api.sessions.list(projectId: string, query?: any): Promise<Session[]>
window.api.sessions.delete(projectId: string, sessionId: string): Promise<void>
window.api.sessions.getTokenUsage(projectId: string, sessionId: string): Promise<TokenUsage>

magi

window.api.magi.getStatus(): Promise<MagiStatus>
window.api.magi.getConfig(): Promise<MagiConfig>
window.api.magi.updateConfig(payload: Partial<MagiConfig>): Promise<void>
window.api.magi.resetSession(): Promise<void>

elfi

window.api.elfi.ask(payload: { question: string; context?: string }): Promise<ElfiResponse>
window.api.elfi.getKnowledge(path: string): Promise<string>
window.api.elfi.searchKnowledge(query: string): Promise<KnowledgeResult[]>

media

window.api.media.migrateBase64ToFiles(): Promise<MigrationResult>
window.api.media.getMigrationStatus(): Promise<MigrationStatus>
window.api.media.onMigrationProgress(cb: (data: ProgressEvent) => void): () => void
window.api.media.generateMissingThumbnails(): Promise<MigrationResult>
window.api.media.onThumbnailProgress(cb: (data: ProgressEvent) => void): () => void
window.api.media.compressImage(payload: { base64: string; mimeType: string }): Promise<CompressResult>
window.api.media.compressDataUrl(dataUrl: string): Promise<CompressResult>
window.api.media.compressMany(payload: CompressInput[]): Promise<CompressResult[]>
window.api.media.migrateAttachmentsToFiles(): Promise<MigrationResult>
window.api.media.getAttachmentMigrationStatus(): Promise<MigrationStatus>

env

window.api.env.checkAll(options?: { force?: boolean }): Promise<EnvCheckResult>
window.api.env.installTool(name: string): Promise<void>
window.api.env.repairAll(): Promise<void>
window.api.env.getLastResult(): Promise<EnvCheckResult>
window.api.env.onProgress(cb: (data: ProgressEvent) => void): () => void

git

window.api.git.status(projectId: string): Promise<GitStatus>
window.api.git.diff(projectId: string, filePath: string, options?: { staged?: boolean; isUntracked?: boolean }): Promise<string>

prompts

window.api.prompts.list(query?: ListQuery): Promise<Prompt[]>
window.api.prompts.get(id: string): Promise<Prompt>
window.api.prompts.create(input: CreatePromptInput): Promise<Prompt>
window.api.prompts.update(id: string, input: UpdatePromptInput): Promise<Prompt>
window.api.prompts.delete(id: string): Promise<void>
window.api.prompts.reorder(ids: string[], sortOrders: number[]): Promise<void>
window.api.prompts.incrementUsage(id: string): Promise<void>
window.api.prompts.search(query: string, limit?: number): Promise<Prompt[]>
window.api.prompts.quickList(): Promise<Prompt[]>

export

window.api.export.sessions(input: ExportSessionsInput): Promise<ExportResult[]>
window.api.export.messages(input: ExportMessagesInput): Promise<ExportResult>

channelPlugins

window.api.channelPlugins.listPlugins(): Promise<ChannelPlugin[]>
window.api.channelPlugins.listInstances(): Promise<ChannelInstance[]>
window.api.channelPlugins.add(payload: AddChannelInput): Promise<ChannelInstance>
window.api.channelPlugins.remove(id: string): Promise<void>
window.api.channelPlugins.update(payload: UpdateChannelInput): Promise<void>
window.api.channelPlugins.changeStatus(payload: { id: string; status: ChannelStatus }): Promise<void>

webSearch

window.api.webSearch.search(query: string, providerId: string, options?: SearchOptions): Promise<SearchResult[]>
window.api.webSearch.configureProvider(config: ProviderConfig): Promise<void>
window.api.webSearch.configureProviders(configs: ProviderConfig[]): Promise<void>
window.api.webSearch.isProviderEnabled(providerId: string): Promise<boolean>
window.api.webSearch.getProviderConfig(providerId: string): Promise<ProviderConfig>
window.api.webSearch.getProviders(): Promise<Provider[]>
window.api.webSearch.jinaReader(url: string, options?: { timeout?: number }): Promise<string>
window.api.webSearch.isAvailable(): Promise<boolean>

windowControls

window.api.windowControls.minimize(): Promise<void>
window.api.windowControls.toggleMaximize(): Promise<void>
window.api.windowControls.close(): Promise<void>
window.api.windowControls.toggleDevTools(): Promise<void>
window.api.windowControls.getDeveloperMode(): Promise<boolean>
window.api.windowControls.enableDeveloperMode(): Promise<void>
window.api.windowControls.disableDeveloperMode(): Promise<void>

diagnostics

window.api.diagnostics.dump(): Promise<DiagnosticsData>
window.api.diagnostics.export(options: ExportOptions): Promise<string>
window.api.diagnostics.bundle(options: BundleOptions): Promise<string>
window.api.diagnostics.clearCaches(): Promise<void>
window.api.diagnostics.dbVacuum(): Promise<void>
window.api.diagnostics.dbGetSize(): Promise<number>

事件订阅模式

所有 onXxx 方法都返回一个取消订阅函数,典型用法:

useEffect(() => {
const unsubscribe = window.api.chat.onEvent((data) => {
handleChatEvent(data);
});
return unsubscribe; // 组件卸载时自动取消订阅
}, []);

主要事件通道汇总

方法推送通道事件内容
authSession.subscribeauthSession:state认证状态变更
chat.onEventchat:event聊天流式事件
completion.onStreamEventcompletion:stream:{id}补全流式事件
completion.onChatCompletedchat:completed聊天完成
image.onGenerationCompletedgeneration:completed图片生成完成
video.onGenerationCompletedvideo:generation:completed视频生成完成
agent.onEventagent:eventAgent 事件
agent.onPermissionRequestagent:permissionRequest权限请求
agent.onAskUserQuestionagent:askUserQuestionAgent 提问(ask_user_question MCP)
theme.onUpdatedtheme:updated主题变更
config.onChangeconfig:changed配置变更
files.subscribefiles:patch:{projectId}文件变更补丁
env.onProgressenv:progress环境检测进度