mirror of https://github.com/openclaw/openclaw.git
Discord: share component registry across module instances
This commit is contained in:
parent
1fdff248f3
commit
aaa70cd185
|
|
@ -1,9 +1,23 @@
|
|||
import type { DiscordComponentEntry, DiscordModalEntry } from "./components.js";
|
||||
|
||||
const DEFAULT_COMPONENT_TTL_MS = 30 * 60 * 1000;
|
||||
const DISCORD_COMPONENT_ENTRIES_KEY = Symbol.for("openclaw.discord.componentEntries");
|
||||
const DISCORD_MODAL_ENTRIES_KEY = Symbol.for("openclaw.discord.modalEntries");
|
||||
|
||||
const componentEntries = new Map<string, DiscordComponentEntry>();
|
||||
const modalEntries = new Map<string, DiscordModalEntry>();
|
||||
function resolveGlobalMap<TKey, TValue>(key: symbol): Map<TKey, TValue> {
|
||||
const globalStore = globalThis as Record<PropertyKey, unknown>;
|
||||
if (globalStore[key] instanceof Map) {
|
||||
return globalStore[key] as Map<TKey, TValue>;
|
||||
}
|
||||
const created = new Map<TKey, TValue>();
|
||||
globalStore[key] = created;
|
||||
return created;
|
||||
}
|
||||
|
||||
const componentEntries = resolveGlobalMap<string, DiscordComponentEntry>(
|
||||
DISCORD_COMPONENT_ENTRIES_KEY,
|
||||
);
|
||||
const modalEntries = resolveGlobalMap<string, DiscordModalEntry>(DISCORD_MODAL_ENTRIES_KEY);
|
||||
|
||||
function isExpired(entry: { expiresAt?: number }, now: number) {
|
||||
return typeof entry.expiresAt === "number" && entry.expiresAt <= now;
|
||||
|
|
|
|||
|
|
@ -1,5 +1,5 @@
|
|||
import { MessageFlags } from "discord-api-types/v10";
|
||||
import { describe, expect, it, beforeEach } from "vitest";
|
||||
import { beforeEach, describe, expect, it } from "vitest";
|
||||
import {
|
||||
clearDiscordComponentEntries,
|
||||
registerDiscordComponentEntries,
|
||||
|
|
@ -78,6 +78,8 @@ describe("discord component registry", () => {
|
|||
clearDiscordComponentEntries();
|
||||
});
|
||||
|
||||
const componentsRegistryModuleUrl = new URL("./components-registry.ts", import.meta.url).href;
|
||||
|
||||
it("registers and consumes component entries", () => {
|
||||
registerDiscordComponentEntries({
|
||||
entries: [{ id: "btn_1", kind: "button", label: "Confirm" }],
|
||||
|
|
@ -102,4 +104,28 @@ describe("discord component registry", () => {
|
|||
expect(consumed?.id).toBe("btn_1");
|
||||
expect(resolveDiscordComponentEntry({ id: "btn_1" })).toBeNull();
|
||||
});
|
||||
|
||||
it("shares registry state across duplicate module instances", async () => {
|
||||
const first = (await import(
|
||||
`${componentsRegistryModuleUrl}?t=first-${Date.now()}`
|
||||
)) as typeof import("./components-registry.js");
|
||||
const second = (await import(
|
||||
`${componentsRegistryModuleUrl}?t=second-${Date.now()}`
|
||||
)) as typeof import("./components-registry.js");
|
||||
|
||||
first.clearDiscordComponentEntries();
|
||||
first.registerDiscordComponentEntries({
|
||||
entries: [{ id: "btn_shared", kind: "button", label: "Shared" }],
|
||||
modals: [],
|
||||
});
|
||||
|
||||
expect(second.resolveDiscordComponentEntry({ id: "btn_shared", consume: false })).toMatchObject(
|
||||
{
|
||||
id: "btn_shared",
|
||||
label: "Shared",
|
||||
},
|
||||
);
|
||||
|
||||
second.clearDiscordComponentEntries();
|
||||
});
|
||||
});
|
||||
|
|
|
|||
Loading…
Reference in New Issue