feat(schema): add custom tools config and runtime types
continuous-integration/drone/push Build is passing

This commit is contained in:
apairon committed 2026-10-20 20:45:19 +00:00
1 parent 21472bdc72
commit 439c8773e6
2 files changed
+217

No files matched your search

Vendored
+115
View File
@@ -593,6 +593,121 @@ declare global {
[key: string]: any
}
// ── Custom Tools (Admin) ─────────────────────────────────────────────────
/** Project config entry (`meta.tools[]`). */
export interface AdminToolConfig {
name: string
label?: string | { [lang: string]: string }
description?: string | { [lang: string]: string }
icon?: string
group?: string
module: string | { eval: string }
permissions?: string[]
capabilities?: Array<"db" | "files" | "xlsx" | "ui" | "log" | "progress" | "state">
settings?: Record<string, any>
hidden?: boolean
}
/** File handle handed to tools (data URL, no live Blob). */
export interface AdminToolFile {
src: string
name: string
type?: string
size?: number
}
/** Fail-fast batch result; no rollback. */
export interface AdminToolBatchResult {
ok: boolean
failedIndex?: number
error?: unknown
}
export interface AdminToolDb {
find(
collection: string,
opts?: Record<string, any>
): Promise<CollectionDocument[]>
count(collection: string, opts?: Record<string, any>): Promise<number>
loadAll(
collection: string,
opts?: Record<string, any>,
onProgress?: (done: number, total: number) => void
): Promise<CollectionDocument[]>
create(collection: string, data: Record<string, any>): Promise<CollectionDocument>
update(collection: string, id: string, data: Record<string, any>): Promise<Partial<CollectionDocument>>
delete(collection: string, id: string): Promise<void>
updateMany(collection: string, items: Array<{ id: string; data: Record<string, any> }>): Promise<AdminToolBatchResult>
deleteMany(collection: string, ids: string[]): Promise<AdminToolBatchResult>
}
export interface AdminToolUi {
supports(type: string): boolean
slot(el: HTMLElement, element: any): void
styles: CSSStyleSheet[]
registerWidget(type: string, factory: (...args: any[]) => any, opts?: { replace?: boolean }): () => void
render(el: HTMLElement, widget: Record<string, any>): void | (() => void)
field(opts: Record<string, any>): any
form(opts: Record<string, any>): any
[key: string]: any
}
export interface AdminToolI18n {
lang: string
languages: string[]
t(key: string, vars?: Record<string, unknown>): string
text(value: string | Record<string, string> | undefined | null, vars?: Record<string, unknown>): string
has(key: string): boolean
add(lang: string, messages: Record<string, unknown>): () => void
add(messages: Record<string, unknown>, lang?: string): () => void
extend(lang: string, messages: Record<string, unknown>): () => void
extend(messages: Record<string, unknown>, lang?: string): () => void
onChange(cb: (lang: string) => void): () => void
dispose?(): void
}
/** Browser context handed to a tool module. `context === ctx`. */
export interface AdminToolContext {
context: AdminToolContext
apiVersion: 1
uiVersion: 1
host: "tool" | "macro" | "server"
capabilities: string[]
project: ProjectInfo
tool: AdminToolConfig
auth: { id: string; username: string; role: number; permissions: string[] } | null
db: AdminToolDb
files: { get(input: File | Blob | string, name?: string): Promise<AdminToolFile> }
xlsx: any
state: Map<string, unknown>
lang: string
languages: string[]
i18n: AdminToolI18n
theme: { mode: "light" | "dark"; tokens: Record<string, string> }
log(message: string, details?: unknown): void
progress(done: number, total: number, label?: string): void
signal: AbortSignal
hostData: Record<string, any>
asset(specifier: string): string
ui: AdminToolUi
}
export interface AdminToolModule {
mount(
el: HTMLElement,
ctx: AdminToolContext
): void | (() => void) | Promise<void | (() => void)>
messages?: Record<string, Record<string, any>>
}
export interface AdminToolException {
status?: number
msg: string
json?: any
}
/** Represents a single audit log entry as received in audit.return hooks */
export interface AuditLogEntry {
id?: string