refactor(client): use type safety for option names

This commit is contained in:
Elian Doran 2025-09-23 20:24:40 +03:00
parent 23c2acaab7
commit 5a15024e59
No known key found for this signature in database
6 changed files with 23 additions and 21 deletions

View File

@ -8,6 +8,7 @@ import FAttribute, { type FAttributeRow } from "../entities/fattribute.js";
import FAttachment, { type FAttachmentRow } from "../entities/fattachment.js";
import type { default as FNote, FNoteRow } from "../entities/fnote.js";
import type { EntityChange } from "../server_types.js";
import type { OptionNames } from "@triliumnext/commons";
async function processEntityChanges(entityChanges: EntityChange[]) {
const loadResults = new LoadResults(entityChanges);
@ -30,9 +31,8 @@ async function processEntityChanges(entityChanges: EntityChange[]) {
continue; // only noise
}
options.set(attributeEntity.name, attributeEntity.value);
loadResults.addOption(attributeEntity.name);
options.set(attributeEntity.name as OptionNames, attributeEntity.value);
loadResults.addOption(attributeEntity.name as OptionNames);
} else if (ec.entityName === "attachments") {
processAttachment(loadResults, ec);
} else if (ec.entityName === "blobs") {

View File

@ -1,4 +1,4 @@
import type { AttachmentRow, EtapiTokenRow } from "@triliumnext/commons";
import type { AttachmentRow, EtapiTokenRow, OptionNames } from "@triliumnext/commons";
import type { AttributeType } from "../entities/fattribute.js";
import type { EntityChange } from "../server_types.js";
@ -67,7 +67,7 @@ export default class LoadResults {
private revisionRows: RevisionRow[];
private noteReorderings: string[];
private contentNoteIdToComponentId: ContentNoteIdToComponentIdRow[];
private optionNames: string[];
private optionNames: OptionNames[];
private attachmentRows: AttachmentRow[];
public hasEtapiTokenChanges: boolean = false;
@ -180,11 +180,11 @@ export default class LoadResults {
return this.contentNoteIdToComponentId.find((l) => l.noteId === noteId && l.componentId !== componentId);
}
addOption(name: string) {
addOption(name: OptionNames) {
this.optionNames.push(name);
}
isOptionReloaded(name: string) {
isOptionReloaded(name: OptionNames) {
return this.optionNames.includes(name);
}

View File

@ -20,7 +20,7 @@ class Options {
this.arr = arr;
}
get(key: string) {
get(key: OptionNames) {
return this.arr?.[key] as string;
}
@ -40,7 +40,7 @@ class Options {
}
}
getInt(key: string) {
getInt(key: OptionNames) {
const value = this.arr?.[key];
if (typeof value === "number") {
return value;
@ -52,7 +52,7 @@ class Options {
return null;
}
getFloat(key: string) {
getFloat(key: OptionNames) {
const value = this.arr?.[key];
if (typeof value !== "string") {
return null;
@ -60,15 +60,15 @@ class Options {
return parseFloat(value);
}
is(key: string) {
is(key: OptionNames) {
return this.arr[key] === "true";
}
set(key: string, value: OptionValue) {
set(key: OptionNames, value: OptionValue) {
this.arr[key] = value;
}
async save(key: string, value: OptionValue) {
async save(key: OptionNames, value: OptionValue) {
this.set(key, value);
const payload: Record<string, OptionValue> = {};
@ -85,7 +85,7 @@ class Options {
await server.put<void>("options", newValues);
}
async toggle(key: string) {
async toggle(key: OptionNames) {
await this.save(key, (!this.is(key)).toString());
}
}

View File

@ -34,10 +34,10 @@ export async function validateProviders(validationWarning: HTMLElement): Promise
precedenceList = [precedenceStr];
}
}
// Check for configuration issues with providers in the precedence list
const configIssues: string[] = [];
// Always add experimental warning as the first item
configIssues.push(t("ai_llm.experimental_warning"));

View File

@ -14,9 +14,9 @@ import dialog from "../../../services/dialog";
import { useTriliumEvent } from "../../react/hooks";
export default function ShortcutSettings() {
const [ keyboardShortcuts, setKeyboardShortcuts ] = useState<KeyboardShortcut[]>([]);
const [ keyboardShortcuts, setKeyboardShortcuts ] = useState<KeyboardShortcut[]>([]);
const [ filter, setFilter ] = useState<string>();
useEffect(() => {
server.get<KeyboardShortcut[]>("keyboard-actions").then(setKeyboardShortcuts);
}, [])
@ -82,7 +82,7 @@ export default function ShortcutSettings() {
</FormText>
<FormGroup name="keyboard-shortcut-filter">
<FormTextBox
<FormTextBox
placeholder={t("shortcuts.type_text_to_filter")}
currentValue={filter} onChange={(value) => setFilter(value.toLowerCase())}
/>
@ -136,7 +136,7 @@ function KeyboardShortcutTable({ filter, keyboardShortcuts }: { filter?: string,
}}>
{action.separator}
</td>
) : ( (!filter || filterKeyboardAction(action, filter)) &&
) : ( (!filter || filterKeyboardAction(action, filter)) &&
<>
<td>{action.friendlyName}</td>
<td>
@ -181,4 +181,4 @@ function getOptionName(actionName: string) {
function getActionNameFromOptionName(optionName: string) {
return optionName.at(PREFIX.length)?.toLowerCase() + optionName.substring(PREFIX.length + 1);
}
}

View File

@ -100,6 +100,7 @@ export interface OptionDefinitions extends KeyboardShortcutsOptions<KeyboardActi
codeNoteTheme: string;
initialized: boolean;
databaseReadonly: boolean;
isPasswordSet: boolean;
overrideThemeFonts: boolean;
spellCheckEnabled: boolean;
@ -138,6 +139,7 @@ export interface OptionDefinitions extends KeyboardShortcutsOptions<KeyboardActi
// AI/LLM integration options
aiEnabled: boolean;
aiProvider: string;
aiProviderPrecedence: string; // TODO: Is this still supported?
aiSystemPrompt: string;
aiTemperature: string;
openaiApiKey: string;