summaryrefslogtreecommitdiff
path: root/src/main
diff options
context:
space:
mode:
authorhaoyuren <13851610112@163.com>2026-03-15 20:52:13 -0500
committerhaoyuren <13851610112@163.com>2026-03-15 20:52:13 -0500
commit66a403488f3a7bc32a02bc9933c396dc4c4e031d (patch)
treeaf52777ac10a1b31487203c4281178e9188c27ba /src/main
parent6d4ee5ccd5529d6d2764da73e73fac57d7bfb216 (diff)
Add API key management UI and wire S2 key to MCP
- Settings modal on project list page for OpenAI, Anthropic, OpenRouter, Gemini, Semantic Scholar keys - Keys stored in userData/api-keys.json, masked by default with show/hide toggle - S2 API key passed to MCP server via .lattex-mcp.json to avoid rate limits Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>
Diffstat (limited to 'src/main')
-rw-r--r--src/main/index.ts25
1 files changed, 24 insertions, 1 deletions
diff --git a/src/main/index.ts b/src/main/index.ts
index 4239be5..2b7cc08 100644
--- a/src/main/index.ts
+++ b/src/main/index.ts
@@ -29,13 +29,20 @@ let mcpOnlineUsersWriteTimer: ReturnType<typeof setTimeout> | null = null
async function writeMcpState(): Promise<void> {
if (!mcpStateDir || !mcpProjectId) return
try {
- const state = {
+ // Read S2 API key if available
+ let s2Key: string | undefined
+ try {
+ const keys = JSON.parse(await readFile(apiKeysPath, 'utf-8'))
+ if (keys.semanticScholar) s2Key = keys.semanticScholar
+ } catch { /* ignore */ }
+ const state: Record<string, unknown> = {
projectId: mcpProjectId,
cookie: overleafSessionCookie,
csrf: overleafCsrfToken,
commentContexts: mcpCommentContexts,
pathDocMap: mcpPathDocMap
}
+ if (s2Key) state.semanticScholarApiKey = s2Key
await writeFile(join(mcpStateDir, '.lattex-mcp.json'), JSON.stringify(state, null, 2))
} catch { /* ignore */ }
}
@@ -91,6 +98,22 @@ ipcMain.handle('fs:readBinary', async (_e, filePath: string) => {
return buffer.buffer.slice(buffer.byteOffset, buffer.byteOffset + buffer.byteLength)
})
+// ── API Key Storage ─────────────────────────────────────────────
+
+const apiKeysPath = join(app.getPath('userData'), 'api-keys.json')
+
+ipcMain.handle('settings:getApiKeys', async () => {
+ try {
+ return JSON.parse(await readFile(apiKeysPath, 'utf-8'))
+ } catch {
+ return {}
+ }
+})
+
+ipcMain.handle('settings:setApiKeys', async (_e, keys: Record<string, string>) => {
+ await writeFile(apiKeysPath, JSON.stringify(keys, null, 2))
+})
+
// ── LaTeX Compilation ────────────────────────────────────────────
// Ensure TeX binaries are in PATH (Electron launched from Finder may miss them)