feat(web): open the local settings file

This commit is contained in:
Yichen Jiang
2026-08-04 16:33:35 +08:00
parent 828cb2ae20
commit e31b7221e7
61 changed files with 939 additions and 98 deletions

View File

@@ -10,7 +10,7 @@
import { Context, Service } from 'cordis'
import z from 'schemastery'
import { watch as chokidarWatch } from 'chokidar'
import { mkdir, readFile } from 'node:fs/promises'
import { mkdir, readFile, writeFile } from 'node:fs/promises'
import { dirname, extname, join, resolve } from 'node:path'
import { Document, parseDocument } from 'yaml'
import { withFileLock, writeFileAtomic } from '@deepseek-ai/dsh-atomic-write'
@@ -96,6 +96,11 @@ function isENOENT(error: unknown): boolean {
return (error as NodeJS.ErrnoException | null)?.code === 'ENOENT'
}
/** Whether an exclusive file create found an existing document. */
function isEEXIST(error: unknown): boolean {
return (error as NodeJS.ErrnoException | null)?.code === 'EEXIST'
}
/** File-backed settings provider (`settings.yaml`/`.json`). */
export class SettingsLocal extends Settings {
static Config: z<Config> = z.object({
@@ -139,6 +144,29 @@ export class SettingsLocal extends Settings {
return true
}
/** The resolved YAML/JSON document path exposed to local configuration surfaces. */
override get documentPath(): string {
return this.spec.filename
}
/** Materialize an absent owner-only document, then return its resolved path. */
override prepareDocument(): Promise<string> {
return this.enqueue(async () => {
await mkdir(dirname(this.spec.filename), { recursive: true, mode: 0o700 })
await withFileLock(this.spec.filename, async () => {
try {
await writeFile(this.spec.filename, '', { flag: 'wx', mode: 0o600 })
} catch (error) {
if (isEEXIST(error)) return
throw error
}
this.text = ''
if (!this.isClosed()) this.publish({})
})
return this.spec.filename
})
}
protected async load(): Promise<Record<string, unknown>> {
let text: string
try {