import { type Derived } from "./core/handle.ts"; export interface ResourceOptions { /** 連続した変化をまとめる(ms)。入力に追従する検索などで使う。 */ debounce?: number; /** 取得中も前回の値を保持する(既定 true。チラつき防止)。 */ keepPrevious?: boolean; /** 生成時にすぐ取得するか(既定 true)。 */ immediate?: boolean; } export interface Resource { /** 取得できた値。まだ無ければ undefined。 */ data: Derived; /** 取得中か(debounce 待ちも含む)。 */ loading: Derived; /** 失敗した理由。成功したら undefined に戻る。 */ error: Derived; /** 手動で取り直す。 */ refetch(): void; /** 進行中のリクエストを中断する。 */ abort(): void; /** 取得の完了を待つ(テスト・初期化待ち用)。 */ ready(): Promise; } type Fetcher = (value: S, signal: AbortSignal) => T | Promise; /** * 一度だけ取得する: * const rows = $$.resource(() => fetch("/js/simulation.json").then(r => r.json())); * $$("@spinner").when(rows.loading); * $$("@error").when(() => !!rows.error()); * * 入力に追従して取得し直す(前のリクエストは自動で中断される): * const q = $$("@q").val().state(""); * const hits = $$.resource(q, (keyword, signal) => * fetch(`/search?q=${keyword}`, { signal }).then(r => r.json()), { debounce: 300 }); */ export declare function resource(fetcher: Fetcher, options?: ResourceOptions): Resource; export declare function resource(source: unknown, fetcher: Fetcher, options?: ResourceOptions): Resource; export interface Action { (...args: A): Promise; /** 実行中か。 $$("@save").prop("disabled", save.running) */ running: Derived; /** 直前の失敗理由。 */ error: Derived; } /** * const save = $$.action(async () => { * await fetch("/api/save", { method: "POST", body: … }); * }); * $$("@save").click(save); * $$("@save").prop("disabled", save.running); // 押せない間は自動で無効 * $$("@save-error").when(() => !!save.error()); */ export declare function action(fn: (...args: A) => unknown | Promise): Action; export {};