@songsid/agend 2.3.0-beta.7 → 2.3.0-beta.9
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/dist/agent-cli-instructions.md +2 -1
- package/dist/agent-cli.js +3 -0
- package/dist/agent-cli.js.map +1 -1
- package/dist/agent-whats-new.js +2 -0
- package/dist/agent-whats-new.js.map +1 -1
- package/dist/channel/mcp-tools.js +3 -3
- package/dist/channel/mcp-tools.js.map +1 -1
- package/dist/daemon.d.ts +2 -0
- package/dist/daemon.js +29 -9
- package/dist/daemon.js.map +1 -1
- package/dist/decision-list.d.ts +25 -0
- package/dist/decision-list.js +30 -0
- package/dist/decision-list.js.map +1 -0
- package/dist/fleet-manager.d.ts +9 -2
- package/dist/fleet-manager.js +44 -12
- package/dist/fleet-manager.js.map +1 -1
- package/dist/fleet-traffic.d.ts +36 -0
- package/dist/fleet-traffic.js +100 -0
- package/dist/fleet-traffic.js.map +1 -1
- package/dist/general-knowledge/skills/web-appearance/SKILL.md +17 -10
- package/dist/general-knowledge/skills/web-dashboard/SKILL.md +32 -13
- package/dist/instance-config-impact.js +1 -0
- package/dist/instance-config-impact.js.map +1 -1
- package/dist/outbound-handlers.js +4 -1
- package/dist/outbound-handlers.js.map +1 -1
- package/dist/outbound-schemas.d.ts +6 -4
- package/dist/outbound-schemas.js +7 -3
- package/dist/outbound-schemas.js.map +1 -1
- package/dist/settings-api.js +4 -0
- package/dist/settings-api.js.map +1 -1
- package/dist/settings-change.js +4 -0
- package/dist/settings-change.js.map +1 -1
- package/dist/settings-effect.js +2 -0
- package/dist/settings-effect.js.map +1 -1
- package/dist/tool-permissions.js +9 -42
- package/dist/tool-permissions.js.map +1 -1
- package/dist/ui/app-effects.js +9 -5
- package/dist/ui/chat-ambient.js +8 -7
- package/dist/ui/chat-effect-posters.js +3 -2
- package/dist/ui/chat-effects.js +22 -15
- package/dist/ui/chat-render.js +5 -2
- package/dist/ui/chat-strings.js +6 -4
- package/dist/ui/chat-thread.js +134 -17
- package/dist/ui/effect-trial-controller.js +13 -8
- package/dist/ui/fleet-canvas.js +54 -18
- package/dist/ui/fleet-org.js +3 -3
- package/dist/ui/fleet-traffic.js +156 -37
- package/dist/ui/fleet-usage.js +401 -0
- package/dist/ui/panel-chat.js +101 -47
- package/dist/ui/panel-fleet.js +6 -5
- package/dist/ui/panel-settings.js +6 -1
- package/dist/ui/settings-owner-effects.js +1 -1
- package/dist/ui/settings-strings.js +2 -0
- package/dist/ui/shared/agend-auth.js +1 -1
- package/dist/ui/shared/app-route.js +1 -1
- package/dist/ui/shared/app-stream.js +3 -2
- package/dist/ui/shared/app.css +89 -9
- package/dist/ui/shared/effect-app-runtime.js +3 -3
- package/dist/ui/shared/effect-chat-runtime.js +1 -1
- package/dist/ui/shared/effect-policy.js +5 -6
- package/dist/ui/shared/effect-profiler.js +31 -9
- package/dist/ui/shared/effect-registry.js +23 -31
- package/dist/ui/shared/effect-stock-snapshot.js +9 -0
- package/dist/ui/shared/effect-stock-trust.js +37 -6
- package/dist/ui/shared/effect-trial-source.js +1 -1
- package/dist/ui/shared/effect-trial-stage.js +27 -21
- package/dist/ui/shared/effect-trial.css +1 -1
- package/dist/ui/shared/fx-motion.js +12 -3
- package/dist/ui/shared/tokens.css +9 -3
- package/dist/ui/shared/usage-dialog.js +8 -0
- package/dist/ui/shared/view-strings.js +4 -0
- package/dist/ui/web-terminal/terminal.css +4 -4
- package/dist/usage-report.d.ts +12 -1
- package/dist/usage-report.js +39 -8
- package/dist/usage-report.js.map +1 -1
- package/dist/web-ambient.js +9 -2
- package/dist/web-ambient.js.map +1 -1
- package/dist/web-api.d.ts +2 -0
- package/dist/web-api.js +8 -3
- package/dist/web-api.js.map +1 -1
- package/dist/web-settings-patch.d.ts +3 -1
- package/dist/web-settings-patch.js +4 -1
- package/dist/web-settings-patch.js.map +1 -1
- package/dist/web-shell-routes.d.ts +1 -1
- package/dist/web-shell-routes.js +1 -1
- package/dist/web-shell-routes.js.map +1 -1
- package/dist/workflow-templates/default.md +1 -1
- package/package.json +1 -1
|
@@ -0,0 +1,25 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* #2152: what `list_decisions` answers. The fleet's decisions are long (82 of them were 126 KB, ≈31k–42k tokens in one
|
|
3
|
+
* call) and every instance lists them after a restart, so by default it answers titles — id, title, scope, date, tags —
|
|
4
|
+
* and the full text is asked for: one decision by `id`, or all of them with `full: true`. One function for both entry
|
|
5
|
+
* paths (the MCP tool through the daemon, and the agent endpoint's `decision-*` ops).
|
|
6
|
+
*/
|
|
7
|
+
import type { Decision } from "./scheduler/types.js";
|
|
8
|
+
export interface DecisionTitle {
|
|
9
|
+
id: string;
|
|
10
|
+
title: string;
|
|
11
|
+
scope: Decision["scope"];
|
|
12
|
+
/** The day it was last changed (YYYY-MM-DD). */
|
|
13
|
+
date: string;
|
|
14
|
+
tags?: string[];
|
|
15
|
+
status?: Decision["status"];
|
|
16
|
+
}
|
|
17
|
+
export declare const DECISION_TITLES_HINT = "Titles only. Call list_decisions with { id } for one decision's full text, or { full: true } for every one.";
|
|
18
|
+
/**
|
|
19
|
+
* The answer: `{ decision }` for an id, the full records for `full`, else the titles. `all` is the list as the store
|
|
20
|
+
* returns it (already filtered by scope, archive and tags).
|
|
21
|
+
*/
|
|
22
|
+
export declare function decisionListAnswer(all: readonly Decision[], opts?: {
|
|
23
|
+
id?: unknown;
|
|
24
|
+
full?: unknown;
|
|
25
|
+
}): unknown;
|
|
@@ -0,0 +1,30 @@
|
|
|
1
|
+
export const DECISION_TITLES_HINT = "Titles only. Call list_decisions with { id } for one decision's full text, or { full: true } for every one.";
|
|
2
|
+
/** One decision by id (exact, or a unique prefix of at least 6 characters); null when none or more than one match. */
|
|
3
|
+
function byId(all, id) {
|
|
4
|
+
const exact = all.find(d => d.id === id);
|
|
5
|
+
if (exact)
|
|
6
|
+
return exact;
|
|
7
|
+
if (id.length < 6)
|
|
8
|
+
return null;
|
|
9
|
+
const hits = all.filter(d => d.id.startsWith(id));
|
|
10
|
+
return hits.length === 1 ? hits[0] : null;
|
|
11
|
+
}
|
|
12
|
+
/**
|
|
13
|
+
* The answer: `{ decision }` for an id, the full records for `full`, else the titles. `all` is the list as the store
|
|
14
|
+
* returns it (already filtered by scope, archive and tags).
|
|
15
|
+
*/
|
|
16
|
+
export function decisionListAnswer(all, opts = {}) {
|
|
17
|
+
if (typeof opts.id === "string" && opts.id.trim()) {
|
|
18
|
+
const d = byId(all, opts.id.trim());
|
|
19
|
+
return d ? { decision: d } : { error: `No decision '${opts.id.trim()}' among these (an id, or a unique prefix of 6 or more characters).` };
|
|
20
|
+
}
|
|
21
|
+
if (opts.full === true)
|
|
22
|
+
return all;
|
|
23
|
+
const titles = all.map(d => ({
|
|
24
|
+
id: d.id, title: d.title, scope: d.scope, date: (d.updated_at || d.created_at || "").slice(0, 10),
|
|
25
|
+
...(d.tags?.length ? { tags: d.tags } : {}),
|
|
26
|
+
...(d.status && d.status !== "active" ? { status: d.status } : {}),
|
|
27
|
+
}));
|
|
28
|
+
return { decisions: titles, hint: DECISION_TITLES_HINT };
|
|
29
|
+
}
|
|
30
|
+
//# sourceMappingURL=decision-list.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"decision-list.js","sourceRoot":"","sources":["../src/decision-list.ts"],"names":[],"mappings":"AAkBA,MAAM,CAAC,MAAM,oBAAoB,GAAG,6GAA6G,CAAC;AAElJ,sHAAsH;AACtH,SAAS,IAAI,CAAC,GAAwB,EAAE,EAAU;IAChD,MAAM,KAAK,GAAG,GAAG,CAAC,IAAI,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC,EAAE,KAAK,EAAE,CAAC,CAAC;IACzC,IAAI,KAAK;QAAE,OAAO,KAAK,CAAC;IACxB,IAAI,EAAE,CAAC,MAAM,GAAG,CAAC;QAAE,OAAO,IAAI,CAAC;IAC/B,MAAM,IAAI,GAAG,GAAG,CAAC,MAAM,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC,EAAE,CAAC,UAAU,CAAC,EAAE,CAAC,CAAC,CAAC;IAClD,OAAO,IAAI,CAAC,MAAM,KAAK,CAAC,CAAC,CAAC,CAAC,IAAI,CAAC,CAAC,CAAE,CAAC,CAAC,CAAC,IAAI,CAAC;AAC7C,CAAC;AAED;;;GAGG;AACH,MAAM,UAAU,kBAAkB,CAAC,GAAwB,EAAE,OAAyC,EAAE;IACtG,IAAI,OAAO,IAAI,CAAC,EAAE,KAAK,QAAQ,IAAI,IAAI,CAAC,EAAE,CAAC,IAAI,EAAE,EAAE,CAAC;QAClD,MAAM,CAAC,GAAG,IAAI,CAAC,GAAG,EAAE,IAAI,CAAC,EAAE,CAAC,IAAI,EAAE,CAAC,CAAC;QACpC,OAAO,CAAC,CAAC,CAAC,CAAC,EAAE,QAAQ,EAAE,CAAC,EAAE,CAAC,CAAC,CAAC,EAAE,KAAK,EAAE,gBAAgB,IAAI,CAAC,EAAE,CAAC,IAAI,EAAE,oEAAoE,EAAE,CAAC;IAC7I,CAAC;IACD,IAAI,IAAI,CAAC,IAAI,KAAK,IAAI;QAAE,OAAO,GAAG,CAAC;IACnC,MAAM,MAAM,GAAoB,GAAG,CAAC,GAAG,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC;QAC5C,EAAE,EAAE,CAAC,CAAC,EAAE,EAAE,KAAK,EAAE,CAAC,CAAC,KAAK,EAAE,KAAK,EAAE,CAAC,CAAC,KAAK,EAAE,IAAI,EAAE,CAAC,CAAC,CAAC,UAAU,IAAI,CAAC,CAAC,UAAU,IAAI,EAAE,CAAC,CAAC,KAAK,CAAC,CAAC,EAAE,EAAE,CAAC;QACjG,GAAG,CAAC,CAAC,CAAC,IAAI,EAAE,MAAM,CAAC,CAAC,CAAC,EAAE,IAAI,EAAE,CAAC,CAAC,IAAI,EAAE,CAAC,CAAC,CAAC,EAAE,CAAC;QAC3C,GAAG,CAAC,CAAC,CAAC,MAAM,IAAI,CAAC,CAAC,MAAM,KAAK,QAAQ,CAAC,CAAC,CAAC,EAAE,MAAM,EAAE,CAAC,CAAC,MAAM,EAAE,CAAC,CAAC,CAAC,EAAE,CAAC;KACnE,CAAC,CAAC,CAAC;IACJ,OAAO,EAAE,SAAS,EAAE,MAAM,EAAE,IAAI,EAAE,oBAAoB,EAAE,CAAC;AAC3D,CAAC"}
|
package/dist/fleet-manager.d.ts
CHANGED
|
@@ -75,7 +75,7 @@ import { ModStore } from "./web-mod-store.js";
|
|
|
75
75
|
import { AgentMods } from "./web-mod-agent.js";
|
|
76
76
|
import { type CachedImage } from "./web-images.js";
|
|
77
77
|
import { WebSettingsTools } from "./web-settings-tools.js";
|
|
78
|
-
import { type TrafficItem } from "./fleet-traffic.js";
|
|
78
|
+
import { type Delegation, type TrafficItem } from "./fleet-traffic.js";
|
|
79
79
|
import { type RawConfigPatch } from "./settings-api.js";
|
|
80
80
|
import { type AgentEndpointContext } from "./agent-endpoint.js";
|
|
81
81
|
import { ClassicChannelManager } from "./classic-channel-manager.js";
|
|
@@ -705,8 +705,12 @@ export declare class FleetManager implements FleetContext, LifecycleContext, Arc
|
|
|
705
705
|
private ensureDeliveryOutbox;
|
|
706
706
|
/** #1918: cross-instance traffic, as the org canvas draws it (fleet-traffic.ts). */
|
|
707
707
|
private readonly trafficLog;
|
|
708
|
+
private readonly delegations;
|
|
708
709
|
private trafficMemo;
|
|
709
|
-
/**
|
|
710
|
+
/**
|
|
711
|
+
* One delivery row's traffic item, kept for the snapshot and sent to the open pages when it is news; and the
|
|
712
|
+
* delegation it opens or closes (a task and its report), sent as "delegation".
|
|
713
|
+
*/
|
|
710
714
|
private publishTraffic;
|
|
711
715
|
/**
|
|
712
716
|
* GET /ui/traffic: what is in flight now (the outbox's pending rows) and what finished in the last two minutes, at
|
|
@@ -716,6 +720,7 @@ export declare class FleetManager implements FleetContext, LifecycleContext, Arc
|
|
|
716
720
|
trafficSnapshot(): {
|
|
717
721
|
now: string;
|
|
718
722
|
items: TrafficItem[];
|
|
723
|
+
delegations: Delegation[];
|
|
719
724
|
};
|
|
720
725
|
/** Synchronous SQLite admission; the caller may acknowledge only after this returns. */
|
|
721
726
|
admitDurableDelivery(input: {
|
|
@@ -2198,6 +2203,8 @@ export declare class FleetManager implements FleetContext, LifecycleContext, Arc
|
|
|
2198
2203
|
private guildEmojiCache;
|
|
2199
2204
|
private guildEmojiFetches;
|
|
2200
2205
|
private webImageCaches;
|
|
2206
|
+
/** Server emoji whose picture fetch failure was already logged at warn (once each; bounded). */
|
|
2207
|
+
private readonly webEmojiFailures;
|
|
2201
2208
|
private webImageCache;
|
|
2202
2209
|
/**
|
|
2203
2210
|
* The bots instances and ClassicBot rooms speak through, by connections configured now (a connection removed from
|
package/dist/fleet-manager.js
CHANGED
|
@@ -183,7 +183,7 @@ import { crossInstanceVisibility, runVisibilityCommand } from "./cross-instance-
|
|
|
183
183
|
import { WebSettingsTools } from "./web-settings-tools.js";
|
|
184
184
|
import { bindGuestRequest, guestRouteDecision } from "./web-guest-access.js";
|
|
185
185
|
import { GUEST_ROOM_TICK_MS, GuestRoomMembership, guestGroupRooms } from "./web-guest-rooms.js";
|
|
186
|
-
import { TrafficLog, trafficItem } from "./fleet-traffic.js";
|
|
186
|
+
import { Delegations, TrafficLog, trafficItem } from "./fleet-traffic.js";
|
|
187
187
|
import { installedChannel, updateNoticeKey } from "./update-check.js";
|
|
188
188
|
import { resolveInstalledAgend } from "./update-dispatch.js";
|
|
189
189
|
import { resolveUpdateLaunch, openUpdateLog, updateLogPath, watchUpdateLaunch } from "./update-launch.js";
|
|
@@ -232,6 +232,7 @@ import { AuthorityStateStore } from "./authority/authority-state.js";
|
|
|
232
232
|
import { SessionAuthorizations } from "./authority/session-authorizations.js";
|
|
233
233
|
import { SessionAuthorizationRequests } from "./web-session-authorization.js";
|
|
234
234
|
import { GuestLoginCodes, WebLoginCodes, LOGIN_CODE_TTL_MS } from "./web-login.js";
|
|
235
|
+
import { decisionListAnswer } from "./decision-list.js";
|
|
235
236
|
import { CodeRequestLimiter, ReturningDevices } from "./web-returning-device.js";
|
|
236
237
|
import { allowedHostNames, applyWebSecurityHeaders, hostnameOf, isHostAllowed, LOOPBACK_HOST_NAMES, WEB_HOST_REJECTED_MESSAGE } from "./web-host-guard.js";
|
|
237
238
|
import { createPreviewListener, normalizeOrigin, previewAvailability, previewSettings } from "./web-preview.js";
|
|
@@ -1693,16 +1694,27 @@ export class FleetManager {
|
|
|
1693
1694
|
}
|
|
1694
1695
|
/** #1918: cross-instance traffic, as the org canvas draws it (fleet-traffic.ts). */
|
|
1695
1696
|
trafficLog = new TrafficLog();
|
|
1697
|
+
delegations = new Delegations();
|
|
1696
1698
|
trafficMemo = null;
|
|
1697
|
-
/**
|
|
1699
|
+
/**
|
|
1700
|
+
* One delivery row's traffic item, kept for the snapshot and sent to the open pages when it is news; and the
|
|
1701
|
+
* delegation it opens or closes (a task and its report), sent as "delegation".
|
|
1702
|
+
*/
|
|
1698
1703
|
publishTraffic(row, state) {
|
|
1699
1704
|
try {
|
|
1700
1705
|
const item = trafficItem(row, this.fleetConfig, new Date().toISOString(), state);
|
|
1701
1706
|
const news = item ? this.trafficLog.note(item) : null;
|
|
1702
|
-
|
|
1707
|
+
const work = news ? this.delegations.note(row, news) : [];
|
|
1708
|
+
if (news || work.length)
|
|
1703
1709
|
this.trafficMemo = null;
|
|
1710
|
+
if (news)
|
|
1704
1711
|
this.emitSseEvent("traffic", news);
|
|
1705
|
-
|
|
1712
|
+
// Each delegation as its two instances are seen now: one that expires or is pushed out may be older than a change
|
|
1713
|
+
// to their visibility (the incoming row's own item was checked; these can be anyone's).
|
|
1714
|
+
const visible = (name) => crossInstanceVisibility(this.fleetConfig, name) !== "hidden";
|
|
1715
|
+
for (const d of work)
|
|
1716
|
+
if (visible(d.from) && visible(d.to))
|
|
1717
|
+
this.emitSseEvent("delegation", d);
|
|
1706
1718
|
}
|
|
1707
1719
|
catch (err) {
|
|
1708
1720
|
this.logger.debug({ err }, "traffic: an item was not published");
|
|
@@ -1722,7 +1734,8 @@ export class FleetManager {
|
|
|
1722
1734
|
.map((r) => trafficItem(r, this.fleetConfig, r.createdAt ?? now)).filter((i) => i !== null);
|
|
1723
1735
|
const visible = (name) => crossInstanceVisibility(this.fleetConfig, name) !== "hidden";
|
|
1724
1736
|
const items = this.trafficLog.snapshot(pending).filter((i) => visible(i.from) && visible(i.to));
|
|
1725
|
-
|
|
1737
|
+
const delegations = this.delegations.snapshot().filter((d) => visible(d.from) && visible(d.to));
|
|
1738
|
+
this.trafficMemo = { atMs: nowMs, value: { now, items, delegations } };
|
|
1726
1739
|
return this.trafficMemo.value;
|
|
1727
1740
|
}
|
|
1728
1741
|
/** Synchronous SQLite admission; the caller may acknowledge only after this returns. */
|
|
@@ -10163,10 +10176,11 @@ export class FleetManager {
|
|
|
10163
10176
|
}
|
|
10164
10177
|
case "fleet_decision_list":
|
|
10165
10178
|
db.pruneExpiredDecisions();
|
|
10166
|
-
|
|
10179
|
+
// #2152: titles by default; the full text by id, or all of it with full: true.
|
|
10180
|
+
result = decisionListAnswer(db.listDecisions(projectRoot, {
|
|
10167
10181
|
includeArchived: payload.include_archived,
|
|
10168
10182
|
tags: payload.tags,
|
|
10169
|
-
});
|
|
10183
|
+
}), { id: payload.id, full: payload.full });
|
|
10170
10184
|
break;
|
|
10171
10185
|
case "fleet_decision_update": {
|
|
10172
10186
|
const id = payload.id;
|
|
@@ -10359,10 +10373,16 @@ export class FleetManager {
|
|
|
10359
10373
|
created_by: instance,
|
|
10360
10374
|
});
|
|
10361
10375
|
}
|
|
10362
|
-
|
|
10363
|
-
|
|
10364
|
-
|
|
10365
|
-
|
|
10376
|
+
// #2152: titles by default (agend-agent decision-list); one decision's full text by id (decision-get <id>).
|
|
10377
|
+
// The CLI sends include_archived (snake case, as the MCP tool): both spellings are read.
|
|
10378
|
+
case "list":
|
|
10379
|
+
case "get":
|
|
10380
|
+
if (op === "get" && !asStr(args.id)?.trim())
|
|
10381
|
+
return { error: "id is required" };
|
|
10382
|
+
return decisionListAnswer(db.listDecisions(projectRoot, {
|
|
10383
|
+
includeArchived: args.includeArchived === true || args.include_archived === true,
|
|
10384
|
+
tags: asStrArr(args.tags),
|
|
10385
|
+
}), { id: op === "get" ? asStr(args.id) ?? "" : args.id, full: args.full });
|
|
10366
10386
|
case "update": {
|
|
10367
10387
|
const id = asStr(args.id);
|
|
10368
10388
|
if (!id)
|
|
@@ -11398,11 +11418,23 @@ export class FleetManager {
|
|
|
11398
11418
|
guildEmojiFetches = new Map();
|
|
11399
11419
|
// ── #1630: what stands for an instance in the web app, and Discord server emoji in web chat ──
|
|
11400
11420
|
webImageCaches = null;
|
|
11421
|
+
/** Server emoji whose picture fetch failure was already logged at warn (once each; bounded). */
|
|
11422
|
+
webEmojiFailures = new Set();
|
|
11401
11423
|
webImageCache(kind) {
|
|
11402
11424
|
const onError = (key, err) => this.logger.debug({ err: err?.message, key }, "web image fetch failed (kept what was cached)");
|
|
11425
|
+
// A server emoji's picture that cannot be fetched reads `:name:` in web chat (it used to be an empty box, the user's
|
|
11426
|
+
// "tofu"): say why once per emoji, where it can be seen, not on every render (its key is quiet for an hour anyway).
|
|
11427
|
+
const emojiError = (key, err) => {
|
|
11428
|
+
if (this.webEmojiFailures.has(key))
|
|
11429
|
+
return onError(key, err);
|
|
11430
|
+
this.webEmojiFailures.add(key);
|
|
11431
|
+
while (this.webEmojiFailures.size > 512)
|
|
11432
|
+
this.webEmojiFailures.delete(this.webEmojiFailures.values().next().value);
|
|
11433
|
+
this.logger.warn({ err: err?.message, key }, "Discord server emoji picture could not be fetched (web chat shows its :name:)");
|
|
11434
|
+
};
|
|
11403
11435
|
this.webImageCaches ??= {
|
|
11404
11436
|
avatars: new WebImageCache({ dir: join(this.dataDir, "cache", "avatars"), onError }),
|
|
11405
|
-
emoji: new WebImageCache({ dir: join(this.dataDir, "cache", "emoji"), onError }),
|
|
11437
|
+
emoji: new WebImageCache({ dir: join(this.dataDir, "cache", "emoji"), onError: emojiError }),
|
|
11406
11438
|
};
|
|
11407
11439
|
return this.webImageCaches[kind];
|
|
11408
11440
|
}
|