Files
inkreach-agent/packages/plugin-template/renderer.mjs

178 lines
7.6 KiB
JavaScript

// shims/react.js
var R = window.__ASO_PLUGIN_HOST__.react;
var {
useState,
useEffect,
useRef,
useMemo,
useCallback,
createContext,
useContext,
Fragment,
memo,
forwardRef,
createElement
} = R;
// ../plugin-sdk/src/async.ts
var TimeoutError = class extends Error {
constructor(message) {
super(message);
this.name = "TimeoutError";
}
};
function withTimeout(promise, ms, label) {
let timer;
const timeout = new Promise((_, reject) => {
timer = setTimeout(() => {
reject(new TimeoutError(`${label ?? "\u64CD\u4F5C"} \u8D85\u65F6\uFF08${ms}ms\uFF09`));
}, ms);
});
return Promise.race([promise, timeout]).finally(() => clearTimeout(timer));
}
// shims/jsx-runtime.js
var { jsx, jsxs, Fragment: Fragment2 } = window.__ASO_PLUGIN_HOST__.jsxRuntime;
// ../plugin-sdk/src/ui.tsx
function cn(...classes) {
return classes.filter(Boolean).join(" ");
}
function Spinner({ size = 14, className }) {
return /* @__PURE__ */ jsx(
"span",
{
role: "status",
"aria-label": "\u52A0\u8F7D\u4E2D",
className: cn("inline-block shrink-0 animate-spin rounded-full border-line-strong", className),
style: { width: size, height: size, borderWidth: 2, borderTopColor: "var(--accent)" }
}
);
}
function LoadingState({ label = "\u52A0\u8F7D\u4E2D\u2026", className }) {
return /* @__PURE__ */ jsxs("div", { className: cn("flex flex-col items-center justify-center gap-2 py-10 text-center", className), children: [
/* @__PURE__ */ jsx(Spinner, {}),
/* @__PURE__ */ jsx("div", { className: "text-[11.5px] text-ink-3", children: label })
] });
}
function ErrorState({ title = "\u51FA\u9519\u4E86", description, onRetry, retryLabel = "\u91CD\u8BD5", className }) {
return /* @__PURE__ */ jsxs(
"div",
{
className: cn("flex flex-col items-center justify-center gap-1.5 rounded-card border border-line bg-red/10 px-6 py-10 text-center", className),
role: "alert",
children: [
/* @__PURE__ */ jsx("div", { className: "text-[12.5px] font-medium text-ink", children: title }),
description !== void 0 && description !== null && description !== "" && /* @__PURE__ */ jsx("div", { className: "max-w-full whitespace-pre-wrap break-words text-[11.5px] leading-4 text-ink-3", children: description }),
onRetry && /* @__PURE__ */ jsx(Button, { variant: "ghost", size: "sm", className: "mt-2", onClick: onRetry, children: retryLabel })
]
}
);
}
function EmptyState({ title, description, action, className }) {
return /* @__PURE__ */ jsxs("div", { className: cn("flex flex-col items-center justify-center gap-1 rounded-card border border-dashed border-line py-12 text-center", className), children: [
/* @__PURE__ */ jsx("div", { className: "text-[13px] font-medium text-ink-2", children: title }),
description !== void 0 && description !== null && description !== "" && /* @__PURE__ */ jsx("div", { className: "max-w-full break-words text-[11.5px] text-ink-3", children: description }),
action && /* @__PURE__ */ jsx("div", { className: "mt-2", children: action })
] });
}
function Button({ variant = "ghost", size = "md", loading = false, disabled, className, children, ...rest }) {
const variantCls = variant === "primary" ? "bg-accent text-white hover:opacity-90" : variant === "danger" ? "border border-line-strong text-red hover:bg-red/10" : "border border-line-strong text-ink hover:bg-hover";
const sizeCls = size === "sm" ? "px-2 py-1 text-[11px]" : "px-3 py-1.5 text-[11.5px]";
return /* @__PURE__ */ jsxs(
"button",
{
type: "button",
disabled: disabled || loading,
className: cn(
"inline-flex items-center justify-center gap-1.5 rounded-control font-medium transition-colors disabled:pointer-events-none disabled:opacity-50",
variantCls,
sizeCls,
className
),
...rest,
children: [
loading && /* @__PURE__ */ jsx(Spinner, { size: size === "sm" ? 10 : 12 }),
children
]
}
);
}
function Switch({ checked, defaultChecked, onCheckedChange, disabled, "aria-label": ariaLabel }) {
const [inner, setInner] = useState(defaultChecked ?? false);
const isControlled = checked !== void 0;
const value = isControlled ? checked : inner;
return /* @__PURE__ */ jsx(
"button",
{
type: "button",
role: "switch",
"aria-checked": value,
"aria-label": ariaLabel,
disabled,
onClick: () => {
const next = !value;
if (!isControlled) setInner(next);
onCheckedChange?.(next);
},
className: cn(
"relative h-5 w-9 shrink-0 rounded-full transition-colors disabled:pointer-events-none disabled:opacity-50",
value ? "bg-accent" : "bg-line-strong"
),
children: /* @__PURE__ */ jsx(
"span",
{
className: "absolute top-0.5 size-4 rounded-full bg-white shadow transition-transform",
style: { transform: `translateX(${value ? 16 : 2}px)` }
}
)
}
);
}
function SettingRow({ label, description, children, className }) {
return /* @__PURE__ */ jsxs("div", { className: cn("flex items-center justify-between gap-3 rounded-card border border-line px-3 py-2.5", className), children: [
/* @__PURE__ */ jsxs("div", { className: "min-w-0", children: [
/* @__PURE__ */ jsx("div", { className: "text-[12.5px] text-ink", children: label }),
description !== void 0 && description !== null && description !== "" && /* @__PURE__ */ jsx("div", { className: "mt-0.5 break-words text-[11px] leading-4 text-ink-3", children: description })
] }),
children
] });
}
// src/renderer.tsx
function fetchItems() {
return withTimeout(Promise.resolve(["\u6761\u76EE\u4E00", "\u6761\u76EE\u4E8C", "\u6761\u76EE\u4E09"]), 3e3, "\u62C9\u53D6\u6570\u636E");
}
function mount(ctx) {
function Panel() {
const [items, setItems] = useState(null);
const [error, setError] = useState(null);
const [verbose, setVerbose] = useState(false);
const [tick, setTick] = useState(0);
useEffect(() => {
let alive = true;
setItems(null);
setError(null);
fetchItems().then((data) => {
if (alive) setItems(data);
}).catch((err) => {
if (alive) setError(err instanceof Error ? err.message : String(err));
});
return () => {
alive = false;
};
}, [tick]);
return /* @__PURE__ */ jsxs("div", { className: "flex h-full flex-col gap-2 overflow-y-auto p-3", children: [
/* @__PURE__ */ jsx("div", { className: "text-[12.5px] text-ink", children: "\u6211\u7684\u63D2\u4EF6\u9762\u677F" }),
error !== null ? /* @__PURE__ */ jsx(ErrorState, { title: "\u6570\u636E\u52A0\u8F7D\u5931\u8D25", description: error, onRetry: () => setTick((t) => t + 1) }) : items === null ? /* @__PURE__ */ jsx(LoadingState, { label: "\u6B63\u5728\u62C9\u53D6\u6570\u636E\u2026" }) : items.length === 0 ? /* @__PURE__ */ jsx(EmptyState, { title: "\u6682\u65E0\u6570\u636E", description: "\u68C0\u67E5\u6570\u636E\u6E90\u540E\u70B9\u51FB\u91CD\u65B0\u52A0\u8F7D" }) : items.map((it) => /* @__PURE__ */ jsx(SettingRow, { label: it, description: "\u793A\u4F8B\u6761\u76EE" }, it)),
/* @__PURE__ */ jsx(SettingRow, { label: "\u8BE6\u7EC6\u6A21\u5F0F", description: "\u5F00\u542F\u540E main \u4FA7\u8F93\u51FA\u66F4\u8BE6\u7EC6\u7684\u65E5\u5FD7", children: /* @__PURE__ */ jsx(Switch, { checked: verbose, onCheckedChange: setVerbose, "aria-label": "\u8BE6\u7EC6\u6A21\u5F0F" }) }),
/* @__PURE__ */ jsx(Button, { variant: "ghost", size: "sm", className: "self-start", onClick: () => setTick((t) => t + 1), children: "\u91CD\u65B0\u52A0\u8F7D" })
] });
}
ctx.registerPanel(Panel);
ctx.registerView(Panel);
}
export {
mount as default
};