@silicaclaw/cli 2026.3.20-2 → 2026.3.20-21
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/CHANGELOG.md +108 -0
- package/INSTALL.md +13 -7
- package/README.md +60 -12
- package/VERSION +1 -1
- package/apps/local-console/dist/apps/local-console/src/server.d.ts +139 -3
- package/apps/local-console/dist/apps/local-console/src/server.js +1029 -92
- package/apps/local-console/dist/packages/core/src/index.d.ts +2 -0
- package/apps/local-console/dist/packages/core/src/index.js +2 -0
- package/apps/local-console/dist/packages/core/src/privateCrypto.d.ts +17 -0
- package/apps/local-console/dist/packages/core/src/privateCrypto.js +40 -0
- package/apps/local-console/dist/packages/core/src/privateMessage.d.ts +23 -0
- package/apps/local-console/dist/packages/core/src/privateMessage.js +74 -0
- package/apps/local-console/dist/packages/core/src/profile.js +2 -0
- package/apps/local-console/dist/packages/core/src/publicProfileSummary.d.ts +4 -0
- package/apps/local-console/dist/packages/core/src/publicProfileSummary.js +3 -0
- package/apps/local-console/dist/packages/core/src/types.d.ts +40 -0
- package/apps/local-console/dist/packages/network/src/relayPreview.d.ts +12 -0
- package/apps/local-console/dist/packages/network/src/relayPreview.js +108 -8
- package/apps/local-console/dist/packages/network/src/types.d.ts +4 -0
- package/apps/local-console/dist/packages/storage/src/repos.d.ts +27 -1
- package/apps/local-console/dist/packages/storage/src/repos.js +35 -1
- package/apps/local-console/public/app/app.js +502 -11
- package/apps/local-console/public/app/events.js +21 -0
- package/apps/local-console/public/app/network.js +144 -32
- package/apps/local-console/public/app/overview.js +57 -27
- package/apps/local-console/public/app/social.js +342 -105
- package/apps/local-console/public/app/styles.css +149 -43
- package/apps/local-console/public/app/template.js +196 -100
- package/apps/local-console/public/app/translations.js +438 -316
- package/apps/local-console/src/server.ts +1177 -90
- package/apps/public-explorer/public/app/template.js +2 -2
- package/apps/public-explorer/public/app/translations.js +36 -36
- package/docs/NEW_USER_OPERATIONS.md +5 -5
- package/docs/OPENCLAW_BRIDGE.md +7 -7
- package/docs/OPENCLAW_BRIDGE_ZH.md +6 -6
- package/node_modules/@silicaclaw/core/dist/packages/core/src/index.d.ts +2 -0
- package/node_modules/@silicaclaw/core/dist/packages/core/src/index.js +2 -0
- package/node_modules/@silicaclaw/core/dist/packages/core/src/privateCrypto.d.ts +17 -0
- package/node_modules/@silicaclaw/core/dist/packages/core/src/privateCrypto.js +40 -0
- package/node_modules/@silicaclaw/core/dist/packages/core/src/privateMessage.d.ts +23 -0
- package/node_modules/@silicaclaw/core/dist/packages/core/src/privateMessage.js +74 -0
- package/node_modules/@silicaclaw/core/dist/packages/core/src/profile.js +2 -0
- package/node_modules/@silicaclaw/core/dist/packages/core/src/publicProfileSummary.d.ts +4 -0
- package/node_modules/@silicaclaw/core/dist/packages/core/src/publicProfileSummary.js +3 -0
- package/node_modules/@silicaclaw/core/dist/packages/core/src/types.d.ts +40 -0
- package/node_modules/@silicaclaw/core/package.json +2 -2
- package/node_modules/@silicaclaw/core/src/index.ts +2 -0
- package/node_modules/@silicaclaw/core/src/privateCrypto.ts +57 -0
- package/node_modules/@silicaclaw/core/src/privateMessage.ts +101 -0
- package/node_modules/@silicaclaw/core/src/profile.ts +2 -0
- package/node_modules/@silicaclaw/core/src/publicProfileSummary.ts +7 -0
- package/node_modules/@silicaclaw/core/src/types.ts +44 -0
- package/node_modules/@silicaclaw/network/dist/packages/network/src/relayPreview.d.ts +12 -0
- package/node_modules/@silicaclaw/network/dist/packages/network/src/relayPreview.js +108 -8
- package/node_modules/@silicaclaw/network/dist/packages/network/src/types.d.ts +4 -0
- package/node_modules/@silicaclaw/network/src/relayPreview.ts +120 -10
- package/node_modules/@silicaclaw/network/src/types.ts +2 -0
- package/node_modules/@silicaclaw/storage/dist/packages/core/src/index.d.ts +2 -0
- package/node_modules/@silicaclaw/storage/dist/packages/core/src/index.js +2 -0
- package/node_modules/@silicaclaw/storage/dist/packages/core/src/privateCrypto.d.ts +17 -0
- package/node_modules/@silicaclaw/storage/dist/packages/core/src/privateCrypto.js +40 -0
- package/node_modules/@silicaclaw/storage/dist/packages/core/src/privateMessage.d.ts +23 -0
- package/node_modules/@silicaclaw/storage/dist/packages/core/src/privateMessage.js +74 -0
- package/node_modules/@silicaclaw/storage/dist/packages/core/src/profile.js +2 -0
- package/node_modules/@silicaclaw/storage/dist/packages/core/src/publicProfileSummary.d.ts +4 -0
- package/node_modules/@silicaclaw/storage/dist/packages/core/src/publicProfileSummary.js +3 -0
- package/node_modules/@silicaclaw/storage/dist/packages/core/src/types.d.ts +40 -0
- package/node_modules/@silicaclaw/storage/dist/packages/storage/src/repos.d.ts +27 -1
- package/node_modules/@silicaclaw/storage/dist/packages/storage/src/repos.js +35 -1
- package/node_modules/@silicaclaw/storage/package.json +2 -2
- package/node_modules/@silicaclaw/storage/src/repos.ts +59 -1
- package/openclaw-skills/silicaclaw-bridge-setup/SKILL.md +18 -0
- package/openclaw-skills/silicaclaw-bridge-setup/VERSION +1 -1
- package/openclaw-skills/silicaclaw-bridge-setup/manifest.json +2 -2
- package/openclaw-skills/silicaclaw-broadcast/SKILL.md +18 -0
- package/openclaw-skills/silicaclaw-broadcast/VERSION +1 -1
- package/openclaw-skills/silicaclaw-broadcast/manifest.json +2 -2
- package/openclaw-skills/silicaclaw-network-config/SKILL.md +158 -0
- package/openclaw-skills/silicaclaw-network-config/VERSION +1 -0
- package/openclaw-skills/silicaclaw-network-config/agents/openai.yaml +6 -0
- package/openclaw-skills/silicaclaw-network-config/manifest.json +27 -0
- package/openclaw-skills/silicaclaw-network-config/references/network-modes.md +22 -0
- package/openclaw-skills/silicaclaw-network-config/references/owner-dialogue-cheatsheet-zh.md +47 -0
- package/openclaw-skills/silicaclaw-network-config/references/public-discovery.md +22 -0
- package/openclaw-skills/silicaclaw-owner-push/SKILL.md +18 -0
- package/openclaw-skills/silicaclaw-owner-push/VERSION +1 -1
- package/openclaw-skills/silicaclaw-owner-push/manifest.json +2 -2
- package/openclaw-skills/silicaclaw-owner-push/references/runtime-setup.md +3 -0
- package/openclaw-skills/silicaclaw-owner-push/scripts/owner-push-forwarder.mjs +151 -9
- package/package.json +1 -1
- package/packages/core/dist/packages/core/src/index.d.ts +2 -0
- package/packages/core/dist/packages/core/src/index.js +2 -0
- package/packages/core/dist/packages/core/src/privateCrypto.d.ts +17 -0
- package/packages/core/dist/packages/core/src/privateCrypto.js +40 -0
- package/packages/core/dist/packages/core/src/privateMessage.d.ts +23 -0
- package/packages/core/dist/packages/core/src/privateMessage.js +74 -0
- package/packages/core/dist/packages/core/src/profile.js +2 -0
- package/packages/core/dist/packages/core/src/publicProfileSummary.d.ts +4 -0
- package/packages/core/dist/packages/core/src/publicProfileSummary.js +3 -0
- package/packages/core/dist/packages/core/src/types.d.ts +40 -0
- package/packages/core/package.json +2 -2
- package/packages/core/src/index.ts +2 -0
- package/packages/core/src/privateCrypto.ts +57 -0
- package/packages/core/src/privateMessage.ts +101 -0
- package/packages/core/src/profile.ts +2 -0
- package/packages/core/src/publicProfileSummary.ts +7 -0
- package/packages/core/src/types.ts +44 -0
- package/packages/network/dist/packages/network/src/relayPreview.d.ts +12 -0
- package/packages/network/dist/packages/network/src/relayPreview.js +108 -8
- package/packages/network/dist/packages/network/src/types.d.ts +4 -0
- package/packages/network/src/relayPreview.ts +120 -10
- package/packages/network/src/types.ts +2 -0
- package/packages/storage/dist/packages/core/src/index.d.ts +2 -0
- package/packages/storage/dist/packages/core/src/index.js +2 -0
- package/packages/storage/dist/packages/core/src/privateCrypto.d.ts +17 -0
- package/packages/storage/dist/packages/core/src/privateCrypto.js +40 -0
- package/packages/storage/dist/packages/core/src/privateMessage.d.ts +23 -0
- package/packages/storage/dist/packages/core/src/privateMessage.js +74 -0
- package/packages/storage/dist/packages/core/src/profile.js +2 -0
- package/packages/storage/dist/packages/core/src/publicProfileSummary.d.ts +4 -0
- package/packages/storage/dist/packages/core/src/publicProfileSummary.js +3 -0
- package/packages/storage/dist/packages/core/src/types.d.ts +40 -0
- package/packages/storage/dist/packages/storage/src/repos.d.ts +27 -1
- package/packages/storage/dist/packages/storage/src/repos.js +35 -1
- package/packages/storage/package.json +2 -2
- package/packages/storage/src/repos.ts +59 -1
- package/scripts/silicaclaw-cli.mjs +4 -1
- package/scripts/silicaclaw-gateway.mjs +114 -2
- package/scripts/validate-openclaw-skill.mjs +19 -0
- package/node_modules/@silicaclaw/storage/dist/index.d.ts +0 -3
- package/node_modules/@silicaclaw/storage/dist/index.js +0 -19
- package/node_modules/@silicaclaw/storage/dist/jsonRepo.d.ts +0 -7
- package/node_modules/@silicaclaw/storage/dist/jsonRepo.js +0 -29
- package/node_modules/@silicaclaw/storage/dist/repos.d.ts +0 -61
- package/node_modules/@silicaclaw/storage/dist/repos.js +0 -67
- package/node_modules/@silicaclaw/storage/dist/socialRuntimeRepo.d.ts +0 -5
- package/node_modules/@silicaclaw/storage/dist/socialRuntimeRepo.js +0 -57
- package/packages/storage/dist/index.d.ts +0 -3
- package/packages/storage/dist/index.js +0 -19
- package/packages/storage/dist/jsonRepo.d.ts +0 -7
- package/packages/storage/dist/jsonRepo.js +0 -29
- package/packages/storage/dist/repos.d.ts +0 -61
- package/packages/storage/dist/repos.js +0 -67
- package/packages/storage/dist/socialRuntimeRepo.d.ts +0 -5
- package/packages/storage/dist/socialRuntimeRepo.js +0 -57
|
@@ -24,6 +24,139 @@ export function createSocialController({
|
|
|
24
24
|
toPrettyJson,
|
|
25
25
|
writeUiCache,
|
|
26
26
|
}) {
|
|
27
|
+
const SKILLS_SECTION_LIMIT = 4;
|
|
28
|
+
const SKILLS_DIALOGUE_LIMIT = 1;
|
|
29
|
+
let lastMessagesRenderKey = "";
|
|
30
|
+
let lastLogsRenderKey = "";
|
|
31
|
+
const sectionRenderCache = new Map();
|
|
32
|
+
let skillsQuery = "";
|
|
33
|
+
let skillsFilter = "all";
|
|
34
|
+
const skillsExpanded = {
|
|
35
|
+
bundled: false,
|
|
36
|
+
installed: false,
|
|
37
|
+
dialogue: false,
|
|
38
|
+
};
|
|
39
|
+
let lastSkillsPayload = null;
|
|
40
|
+
|
|
41
|
+
function skillModeLabel(mode) {
|
|
42
|
+
if (mode === "workspace") return t("labels.skillsModeWorkspace");
|
|
43
|
+
if (mode === "legacy") return t("labels.skillsModeLegacy");
|
|
44
|
+
if (mode === "bundled") return t("labels.skillsModeBundled");
|
|
45
|
+
if (mode === "installed") return t("labels.skillsModeInstalled");
|
|
46
|
+
return mode ? String(mode) : t("labels.skillsModeGeneric");
|
|
47
|
+
}
|
|
48
|
+
|
|
49
|
+
function normalizeSkillSearchText(value) {
|
|
50
|
+
return String(value || "").trim().toLowerCase();
|
|
51
|
+
}
|
|
52
|
+
|
|
53
|
+
function setSkillsQuery(value) {
|
|
54
|
+
skillsQuery = normalizeSkillSearchText(value);
|
|
55
|
+
}
|
|
56
|
+
|
|
57
|
+
function setSkillsFilter(value) {
|
|
58
|
+
const next = String(value || "").trim();
|
|
59
|
+
skillsFilter = ["all", "attention", "updates", "installed"].includes(next) ? next : "all";
|
|
60
|
+
}
|
|
61
|
+
|
|
62
|
+
function toggleSkillsExpanded(section) {
|
|
63
|
+
if (!(section in skillsExpanded)) return;
|
|
64
|
+
skillsExpanded[section] = !skillsExpanded[section];
|
|
65
|
+
}
|
|
66
|
+
|
|
67
|
+
function skillMatchesSearch(skill) {
|
|
68
|
+
if (!skillsQuery) return true;
|
|
69
|
+
const haystack = [
|
|
70
|
+
skill.display_name,
|
|
71
|
+
skill.name,
|
|
72
|
+
skill.description,
|
|
73
|
+
skill.version,
|
|
74
|
+
...(Array.isArray(skill.capabilities) ? skill.capabilities : []),
|
|
75
|
+
...(Array.isArray(skill.owner_dialogue_examples_zh) ? skill.owner_dialogue_examples_zh : []),
|
|
76
|
+
].map((item) => normalizeSkillSearchText(item)).join(" ");
|
|
77
|
+
return haystack.includes(skillsQuery);
|
|
78
|
+
}
|
|
79
|
+
|
|
80
|
+
function skillMatchesFilter(skill, section) {
|
|
81
|
+
if (skillsFilter === "all") return true;
|
|
82
|
+
if (skillsFilter === "updates") return Boolean(skill.update_available);
|
|
83
|
+
if (skillsFilter === "installed") {
|
|
84
|
+
return section === "installed" ? true : Boolean(skill.installed_in_openclaw);
|
|
85
|
+
}
|
|
86
|
+
if (skillsFilter === "attention") {
|
|
87
|
+
return section === "installed"
|
|
88
|
+
? Boolean(skill.update_available)
|
|
89
|
+
: Boolean(skill.update_available || !skill.installed_in_openclaw);
|
|
90
|
+
}
|
|
91
|
+
return true;
|
|
92
|
+
}
|
|
93
|
+
|
|
94
|
+
function renderSkillsSectionFooter({ footerId, section, totalCount, visibleCount, limit }) {
|
|
95
|
+
const footer = document.getElementById(footerId);
|
|
96
|
+
if (!footer) return;
|
|
97
|
+
if (totalCount <= limit) {
|
|
98
|
+
footer.innerHTML = "";
|
|
99
|
+
return;
|
|
100
|
+
}
|
|
101
|
+
const expanded = skillsExpanded[section];
|
|
102
|
+
const hiddenCount = Math.max(totalCount - visibleCount, 0);
|
|
103
|
+
footer.innerHTML = `
|
|
104
|
+
<button class="secondary skills-section__toggle" type="button" data-skills-toggle="${section}">
|
|
105
|
+
${expanded ? t("actions.showLess") : t("actions.showMoreCount", { count: String(hiddenCount) })}
|
|
106
|
+
</button>
|
|
107
|
+
`;
|
|
108
|
+
}
|
|
109
|
+
|
|
110
|
+
function renderFilteredSkillCards({ skills, section, gridId, footerId, renderer, limit, emptyText }) {
|
|
111
|
+
const filtered = skills.filter((skill) => skillMatchesSearch(skill) && skillMatchesFilter(skill, section));
|
|
112
|
+
const expanded = skillsExpanded[section];
|
|
113
|
+
const visible = expanded ? filtered : filtered.slice(0, limit);
|
|
114
|
+
document.getElementById(gridId).innerHTML = visible.length
|
|
115
|
+
? visible.map((skill) => renderer(skill)).join("")
|
|
116
|
+
: `<div class="skills-empty">${filtered.length === 0 && skills.length > 0 ? t("hints.skillsNoFilterMatch") : emptyText}</div>`;
|
|
117
|
+
renderSkillsSectionFooter({
|
|
118
|
+
footerId,
|
|
119
|
+
section,
|
|
120
|
+
totalCount: filtered.length,
|
|
121
|
+
visibleCount: visible.length,
|
|
122
|
+
limit,
|
|
123
|
+
});
|
|
124
|
+
return filtered.length;
|
|
125
|
+
}
|
|
126
|
+
|
|
127
|
+
function renderSkillsFilterMeta({ bundledCount, installedCount, dialogueCount }) {
|
|
128
|
+
const matchedTotal = bundledCount + installedCount + dialogueCount;
|
|
129
|
+
const filterLabel = t(`labels.skillsFilter${skillsFilter.charAt(0).toUpperCase()}${skillsFilter.slice(1)}`);
|
|
130
|
+
document.getElementById("skillsFilterMeta").textContent = t("hints.skillsFilterMeta", {
|
|
131
|
+
count: String(matchedTotal),
|
|
132
|
+
filter: filterLabel,
|
|
133
|
+
});
|
|
134
|
+
document.querySelectorAll("[data-skills-filter]").forEach((btn) => {
|
|
135
|
+
btn.classList.toggle("active", btn.getAttribute("data-skills-filter") === skillsFilter);
|
|
136
|
+
});
|
|
137
|
+
}
|
|
138
|
+
|
|
139
|
+
function formatSectionCount(visibleCount, totalCount) {
|
|
140
|
+
return visibleCount === totalCount ? String(totalCount) : `${visibleCount}/${totalCount}`;
|
|
141
|
+
}
|
|
142
|
+
|
|
143
|
+
function setCachedContent(id, value, mode = "html") {
|
|
144
|
+
const cacheKey = `${mode}:${id}`;
|
|
145
|
+
if (sectionRenderCache.get(cacheKey) === value) {
|
|
146
|
+
return;
|
|
147
|
+
}
|
|
148
|
+
const el = document.getElementById(id);
|
|
149
|
+
if (!el) return;
|
|
150
|
+
if (mode === "text") {
|
|
151
|
+
el.textContent = value;
|
|
152
|
+
} else if (mode === "class") {
|
|
153
|
+
el.className = value;
|
|
154
|
+
} else {
|
|
155
|
+
el.innerHTML = value;
|
|
156
|
+
}
|
|
157
|
+
sectionRenderCache.set(cacheKey, value);
|
|
158
|
+
}
|
|
159
|
+
|
|
27
160
|
function renderSocialMessages() {
|
|
28
161
|
const listEl = document.getElementById("socialMessageList");
|
|
29
162
|
const metaEl = document.getElementById("socialMessageMeta");
|
|
@@ -37,10 +170,16 @@ export function createSocialController({
|
|
|
37
170
|
seconds: String(Math.floor((governance.send_limit?.window_ms || 60000) / 1000)),
|
|
38
171
|
})}`
|
|
39
172
|
: t("overview.messageHint");
|
|
40
|
-
hintEl.textContent = governanceHint;
|
|
41
173
|
if (!socialMessagesCache.length) {
|
|
42
|
-
|
|
43
|
-
|
|
174
|
+
const nextMeta = t("overview.noMessagesMeta");
|
|
175
|
+
const nextHtml = `<div class="empty-state">${t("overview.noMessagesEmpty")}</div>`;
|
|
176
|
+
const renderKey = JSON.stringify({ hint: governanceHint, meta: nextMeta, html: nextHtml });
|
|
177
|
+
if (renderKey !== lastMessagesRenderKey) {
|
|
178
|
+
hintEl.textContent = governanceHint;
|
|
179
|
+
metaEl.textContent = nextMeta;
|
|
180
|
+
listEl.innerHTML = nextHtml;
|
|
181
|
+
lastMessagesRenderKey = renderKey;
|
|
182
|
+
}
|
|
44
183
|
return;
|
|
45
184
|
}
|
|
46
185
|
|
|
@@ -59,16 +198,28 @@ export function createSocialController({
|
|
|
59
198
|
seconds: String(Math.floor((governance.send_limit?.window_ms || 60000) / 1000)),
|
|
60
199
|
})}`
|
|
61
200
|
: "";
|
|
62
|
-
|
|
201
|
+
const nextMeta = `${baseMeta}${governanceMeta}`;
|
|
63
202
|
|
|
64
203
|
if (!filteredMessages.length) {
|
|
65
|
-
|
|
204
|
+
const nextHtml = `<div class="empty-state">${t("overview.noMessagesEmpty")}</div>`;
|
|
205
|
+
const renderKey = JSON.stringify({ hint: governanceHint, meta: nextMeta, html: nextHtml });
|
|
206
|
+
if (renderKey !== lastMessagesRenderKey) {
|
|
207
|
+
hintEl.textContent = governanceHint;
|
|
208
|
+
metaEl.textContent = nextMeta;
|
|
209
|
+
listEl.innerHTML = nextHtml;
|
|
210
|
+
lastMessagesRenderKey = renderKey;
|
|
211
|
+
}
|
|
66
212
|
return;
|
|
67
213
|
}
|
|
68
214
|
|
|
69
|
-
|
|
215
|
+
const nextHtml = filteredMessages
|
|
70
216
|
.map((item) => {
|
|
71
217
|
const visibleRemoteCount = getVisibleRemotePublicCount();
|
|
218
|
+
const avatarUrl = String(item.avatar_url || "").trim();
|
|
219
|
+
const displayName = String(item.display_name || t("overview.unnamed")).trim() || t("overview.unnamed");
|
|
220
|
+
const avatar = avatarUrl
|
|
221
|
+
? `<img class="agent-card__avatar" src="${escapeHtml(avatarUrl)}" alt="${escapeHtml(displayName)}" loading="lazy" />`
|
|
222
|
+
: `<div class="agent-card__avatar-fallback">${escapeHtml((displayName[0] || "?").toUpperCase())}</div>`;
|
|
72
223
|
const selfStatusChips = item.is_self
|
|
73
224
|
? `
|
|
74
225
|
<span class="tag-chip" style="margin-left:8px;">${t("overview.selfMessagePublished")}</span>
|
|
@@ -101,14 +252,17 @@ export function createSocialController({
|
|
|
101
252
|
return `
|
|
102
253
|
<div class="log-item">
|
|
103
254
|
<div style="display:flex; align-items:center; justify-content:space-between; gap:12px;">
|
|
104
|
-
<div>
|
|
105
|
-
|
|
106
|
-
<
|
|
107
|
-
|
|
108
|
-
|
|
109
|
-
|
|
110
|
-
|
|
111
|
-
|
|
255
|
+
<div style="display:flex; align-items:flex-start; gap:10px; min-width:0;">
|
|
256
|
+
${avatar}
|
|
257
|
+
<div style="min-width:0;">
|
|
258
|
+
<strong>${escapeHtml(displayName)}</strong>
|
|
259
|
+
<span class="mono" style="color:#90a2c3; margin-left:8px;">${escapeHtml(shortId(item.agent_id || ""))}</span>
|
|
260
|
+
<span class="tag-chip" style="margin-left:8px;">${escapeHtml(item.topic || t("labels.globalTopic"))}</span>
|
|
261
|
+
${item.is_self ? `<span class="tag-chip" style="margin-left:8px;">${t("overview.messageFilterSelf")}</span>` : ""}
|
|
262
|
+
<span class="tag-chip" style="margin-left:8px;">${item.online ? t("overview.online") : t("overview.offline")}</span>
|
|
263
|
+
${observationChip}
|
|
264
|
+
${selfStatusChips}
|
|
265
|
+
</div>
|
|
112
266
|
</div>
|
|
113
267
|
<div class="mono" style="color:#90a2c3;">${new Date(item.created_at).toLocaleString()}</div>
|
|
114
268
|
</div>
|
|
@@ -118,6 +272,25 @@ export function createSocialController({
|
|
|
118
272
|
`;
|
|
119
273
|
})
|
|
120
274
|
.join("");
|
|
275
|
+
const renderKey = JSON.stringify({
|
|
276
|
+
hint: governanceHint,
|
|
277
|
+
meta: nextMeta,
|
|
278
|
+
filter: socialMessageFilter,
|
|
279
|
+
messages: filteredMessages.map((item) => [
|
|
280
|
+
item.message_id,
|
|
281
|
+
item.updated_at || item.created_at,
|
|
282
|
+
item.remote_observation_count || 0,
|
|
283
|
+
item.online ? 1 : 0,
|
|
284
|
+
]),
|
|
285
|
+
visibleRemoteCount: getVisibleRemotePublicCount(),
|
|
286
|
+
});
|
|
287
|
+
if (renderKey === lastMessagesRenderKey) {
|
|
288
|
+
return;
|
|
289
|
+
}
|
|
290
|
+
hintEl.textContent = governanceHint;
|
|
291
|
+
metaEl.textContent = nextMeta;
|
|
292
|
+
listEl.innerHTML = nextHtml;
|
|
293
|
+
lastMessagesRenderKey = renderKey;
|
|
121
294
|
}
|
|
122
295
|
|
|
123
296
|
async function refreshMessages() {
|
|
@@ -162,19 +335,29 @@ export function createSocialController({
|
|
|
162
335
|
const publicDiscoveryText = status.public_enabled ? t("social.publicDiscoveryEnabled") : t("social.publicDiscoveryDisabled");
|
|
163
336
|
|
|
164
337
|
const namespaceText = `${status.connected_to_silicaclaw ? t("social.connectedToSilicaClaw") : t("social.notConnected")} · ${publicDiscoveryText} · ${t("social.mode")} ${mode}`;
|
|
165
|
-
|
|
166
|
-
|
|
338
|
+
setCachedContent("socialStatusLine", summaryLine, "text");
|
|
339
|
+
setCachedContent("socialStatusSubline", namespaceText, "text");
|
|
167
340
|
const bar = document.getElementById("integrationStatusBar");
|
|
168
|
-
|
|
169
|
-
|
|
341
|
+
const barClassName = `integration-strip ${status.connected_to_silicaclaw && status.public_enabled ? "ok" : "warn"}${getActiveTab() === "overview" ? "" : " hidden"}`;
|
|
342
|
+
const barText = t("social.barStatus", {
|
|
170
343
|
connected: status.connected_to_silicaclaw ? t("common.yes") : t("common.no"),
|
|
171
344
|
mode,
|
|
172
345
|
public: status.public_enabled ? t("common.on") : t("common.off"),
|
|
173
346
|
});
|
|
174
|
-
|
|
347
|
+
if (bar.className !== barClassName) {
|
|
348
|
+
bar.className = barClassName;
|
|
349
|
+
}
|
|
350
|
+
if (bar.textContent !== barText) {
|
|
351
|
+
bar.textContent = barText;
|
|
352
|
+
}
|
|
353
|
+
const brandStatusDot = document.getElementById("brandStatusDot");
|
|
354
|
+
const brandStatusClassName = `sidebar-version__status ${status.connected_to_silicaclaw ? "ok" : "warn"}`;
|
|
355
|
+
if (brandStatusDot.className !== brandStatusClassName) {
|
|
356
|
+
brandStatusDot.className = brandStatusClassName;
|
|
357
|
+
}
|
|
175
358
|
writeUiCache("silicaclaw_ui_social", {
|
|
176
|
-
integrationStatusText:
|
|
177
|
-
integrationStatusClassName:
|
|
359
|
+
integrationStatusText: barText,
|
|
360
|
+
integrationStatusClassName: barClassName,
|
|
178
361
|
socialStatusLineText: summaryLine,
|
|
179
362
|
socialStatusSublineText: namespaceText,
|
|
180
363
|
});
|
|
@@ -182,14 +365,14 @@ export function createSocialController({
|
|
|
182
365
|
if (!status.configured && status.configured_reason) reasons.push(t("social.configuredReason", { reason: status.configured_reason }));
|
|
183
366
|
if (!status.running && status.running_reason) reasons.push(t("social.runningReason", { reason: status.running_reason }));
|
|
184
367
|
if (!status.discoverable && status.discoverable_reason) reasons.push(t("social.discoverableReasonFull", { reason: status.discoverable_reason }));
|
|
185
|
-
|
|
368
|
+
setCachedContent("socialStateHint", reasons.length ? reasons.join(" · ") : t("hints.allIntegrationChecksPassed"), "text");
|
|
186
369
|
const modeSelect = document.getElementById("socialModeSelect");
|
|
187
370
|
const displayedSelectedMode = getSocialModeDirty() && getSocialModePending() ? getSocialModePending() : selectedMode;
|
|
188
371
|
if (modeSelect && displayedSelectedMode !== "-") modeSelect.value = displayedSelectedMode;
|
|
189
372
|
renderSocialModeHint(displayedSelectedMode, mode, !!social.network_requires_restart, getSocialModeDirty());
|
|
190
373
|
setSocialModePendingState(getSocialModeDirty());
|
|
191
374
|
|
|
192
|
-
|
|
375
|
+
setCachedContent("socialPrimaryCards", [
|
|
193
376
|
[t("social.configured"), status.configured ? t("common.yes") : t("common.no")],
|
|
194
377
|
[t("social.running"), status.running ? t("common.yes") : t("common.no")],
|
|
195
378
|
[t("social.discoverable"), discoverable ? t("common.yes") : t("common.no")],
|
|
@@ -197,9 +380,9 @@ export function createSocialController({
|
|
|
197
380
|
[t("social.networkMode"), mode],
|
|
198
381
|
[t("labels.adapter"), effectiveAdapter],
|
|
199
382
|
[t("social.discoverableReason"), status.discoverable_reason || "-"],
|
|
200
|
-
].map(([k, v]) => `<div class="card"><div class="label">${k}</div><div class="value" style="font-size:17px;">${v}</div></div>`).join("");
|
|
383
|
+
].map(([k, v]) => `<div class="card"><div class="label">${k}</div><div class="value" style="font-size:17px;">${v}</div></div>`).join(""));
|
|
201
384
|
|
|
202
|
-
|
|
385
|
+
setCachedContent("socialIntegrationCards", [
|
|
203
386
|
[t("social.connected"), bridge.connected_to_silicaclaw ? t("common.yes") : t("common.no")],
|
|
204
387
|
[t("social.messageBroadcast"), bridge.message_broadcast_enabled ? t("common.on") : t("common.off")],
|
|
205
388
|
[t("social.displayName"), status.display_name || t("overview.unnamed")],
|
|
@@ -207,9 +390,9 @@ export function createSocialController({
|
|
|
207
390
|
[t("social.socialFound"), summary.social_md_found ? t("common.yes") : t("common.no")],
|
|
208
391
|
[t("social.socialSource"), summary.social_md_source_path || "-"],
|
|
209
392
|
[t("social.reuseOpenClawIdentity"), summary.reused_openclaw_identity ? t("common.yes") : t("common.no")],
|
|
210
|
-
].map(([k, v]) => `<div class="card"><div class="label">${k}</div><div class="value" style="font-size:17px;">${v}</div></div>`).join("");
|
|
393
|
+
].map(([k, v]) => `<div class="card"><div class="label">${k}</div><div class="value" style="font-size:17px;">${v}</div></div>`).join(""));
|
|
211
394
|
|
|
212
|
-
|
|
395
|
+
setCachedContent("socialMessagePathCards", [
|
|
213
396
|
[t("social.messageBroadcast"), bridge.message_broadcast_enabled ? t("common.on") : t("common.off")],
|
|
214
397
|
[t("social.publicDiscovery"), status.public_enabled ? t("common.on") : t("common.off")],
|
|
215
398
|
[t("social.namespace"), effectiveNamespace],
|
|
@@ -218,7 +401,7 @@ export function createSocialController({
|
|
|
218
401
|
[t("network.lastPoll"), networkDiag.last_poll_at ? new Date(networkDiag.last_poll_at).toLocaleTimeString() : "-"],
|
|
219
402
|
[t("network.lastPublish"), networkDiag.last_publish_at ? new Date(networkDiag.last_publish_at).toLocaleTimeString() : "-"],
|
|
220
403
|
[t("network.lastError"), networkDiag.last_error || t("network.none")],
|
|
221
|
-
].map(([k, v]) => `<div class="card"><div class="label">${k}</div><div class="value" style="font-size:17px;">${escapeHtml(String(v))}</div></div>`).join("");
|
|
404
|
+
].map(([k, v]) => `<div class="card"><div class="label">${k}</div><div class="value" style="font-size:17px;">${escapeHtml(String(v))}</div></div>`).join(""));
|
|
222
405
|
|
|
223
406
|
const skillLearning = bridge.skill_learning || {};
|
|
224
407
|
const ownerDelivery = bridge.owner_delivery || {};
|
|
@@ -246,21 +429,21 @@ export function createSocialController({
|
|
|
246
429
|
ownerDeliveryHeadline = t("feedback.openclawRoleNotRunning");
|
|
247
430
|
ownerDeliveryBody = ownerDelivery.reason || "-";
|
|
248
431
|
}
|
|
249
|
-
|
|
250
|
-
|
|
251
|
-
|
|
432
|
+
setCachedContent("socialOwnerDeliveryStatus", `feedback ${ownerDeliveryTone}`, "class");
|
|
433
|
+
setCachedContent("socialOwnerDeliveryStatus", ownerDeliveryHeadline, "text");
|
|
434
|
+
setCachedContent("socialOwnerDeliverySubline", [
|
|
252
435
|
`${t("social.broadcastReadable")}: ${ownerDelivery.bridge_messages_readable ? t("common.yes") : t("common.no")}`,
|
|
253
436
|
`${t("social.ownerForwardCommand")}: ${ownerDelivery.forward_command_configured ? t("common.yes") : t("common.no")}`,
|
|
254
437
|
`${t("social.ownerForwardReady")}: ${ownerDelivery.ready ? t("common.yes") : t("common.no")}`,
|
|
255
|
-
].join(" · ");
|
|
256
|
-
|
|
257
|
-
|
|
438
|
+
].join(" · "), "text");
|
|
439
|
+
setCachedContent("socialOwnerDeliveryReason", ownerDeliveryBody, "text");
|
|
440
|
+
setCachedContent("socialCapabilityCards", [
|
|
258
441
|
[t("socialCapability.publicBroadcast"), bridge.message_broadcast_enabled ? t("common.yes") : t("common.no")],
|
|
259
442
|
[t("socialCapability.monitorBroadcasts"), ownerDelivery.bridge_messages_readable ? t("common.yes") : t("common.no")],
|
|
260
443
|
[t("socialCapability.autoPushToOwner"), ownerDelivery.ready ? t("common.yes") : t("common.no")],
|
|
261
444
|
[t("socialCapability.ownerPrivateBoundary"), t("socialCapability.ownerPrivateBoundaryValue")],
|
|
262
|
-
].map(([k, v]) => `<div class="card"><div class="label">${escapeHtml(String(k))}</div><div class="value" style="font-size:17px;">${escapeHtml(String(v))}</div></div>`).join("");
|
|
263
|
-
|
|
445
|
+
].map(([k, v]) => `<div class="card"><div class="label">${escapeHtml(String(k))}</div><div class="value" style="font-size:17px;">${escapeHtml(String(v))}</div></div>`).join(""));
|
|
446
|
+
setCachedContent("openclawSkillCards", [
|
|
264
447
|
[t("social.openclawInstalled"), openclawDetected ? t("common.yes") : t("common.no")],
|
|
265
448
|
[t("social.running"), openclawRunning ? t("common.yes") : t("common.no")],
|
|
266
449
|
[t("social.skillInstalled"), skillInstalled ? t("common.yes") : t("common.no")],
|
|
@@ -268,16 +451,17 @@ export function createSocialController({
|
|
|
268
451
|
[t("social.ownerForwardReady"), ownerDelivery.ready ? t("common.yes") : t("common.no")],
|
|
269
452
|
[t("social.ownerForwardCommand"), ownerDelivery.forward_command_configured ? t("common.yes") : t("common.no")],
|
|
270
453
|
[t("social.openclawDetectionMode"), bridge.openclaw_runtime?.detection_mode || "-"],
|
|
454
|
+
["Gateway probe", bridge.openclaw_runtime?.gateway_probe_ok ? t("common.yes") : t("common.no")],
|
|
271
455
|
[t("social.openclawGateway"), bridge.openclaw_runtime?.gateway_url || "-"],
|
|
272
456
|
[t("social.installMode"), skillLearning.install_mode || "-"],
|
|
273
457
|
[t("social.installedPath"), skillInstalled ? installedSkillPath : "-"],
|
|
274
|
-
].map(([k, v]) => `<div class="card"><div class="label">${k}</div><div class="value" style="font-size:17px;">${escapeHtml(v)}</div></div>`).join("");
|
|
275
|
-
|
|
458
|
+
].map(([k, v]) => `<div class="card"><div class="label">${k}</div><div class="value" style="font-size:17px;">${escapeHtml(v)}</div></div>`).join(""));
|
|
459
|
+
setCachedContent("openclawSkillPath", ownerDelivery.forward_command
|
|
276
460
|
? `${ownerDelivery.forward_command}${ownerDelivery.owner_channel ? ` · ${ownerDelivery.owner_channel}` : ""}${ownerDelivery.owner_target ? ` · ${ownerDelivery.owner_target}` : ""}`
|
|
277
461
|
: skillInstalled
|
|
278
462
|
? installedSkillPath
|
|
279
|
-
: `${installAction.recommended_command || "-"}${bridge.openclaw_runtime?.gateway_url ? ` · detect ${bridge.openclaw_runtime.gateway_url}` : ""}
|
|
280
|
-
|
|
463
|
+
: `${installAction.recommended_command || "-"}${bridge.openclaw_runtime?.gateway_url ? ` · detect ${bridge.openclaw_runtime.gateway_url}` : ""}`, "text");
|
|
464
|
+
setCachedContent("openclawSkillHint", !openclawDetected
|
|
281
465
|
? t("feedback.openclawRoleBroadcasterOnly")
|
|
282
466
|
: !openclawRunning
|
|
283
467
|
? t("feedback.openclawRoleNotRunning")
|
|
@@ -285,11 +469,11 @@ export function createSocialController({
|
|
|
285
469
|
? t("feedback.openclawRoleReadyToLearn")
|
|
286
470
|
: ownerDelivery.ready
|
|
287
471
|
? t("feedback.openclawRoleOwnerReady")
|
|
288
|
-
|
|
289
|
-
|
|
290
|
-
|
|
291
|
-
|
|
292
|
-
: t("feedback.openclawRoleLearned");
|
|
472
|
+
: ownerDelivery.bridge_messages_readable && !ownerDelivery.forward_command_configured
|
|
473
|
+
? t("feedback.openclawRoleLearningOnly")
|
|
474
|
+
: ownerDelivery.bridge_messages_readable
|
|
475
|
+
? t("feedback.openclawRoleNeedsOwnerRoute")
|
|
476
|
+
: t("feedback.openclawRoleLearned"), "text");
|
|
293
477
|
const skillInstallBtn = document.getElementById("openclawSkillInstallBtn");
|
|
294
478
|
skillInstallBtn.textContent = !openclawDetected
|
|
295
479
|
? t("actions.openclawNotInstalled")
|
|
@@ -310,33 +494,33 @@ export function createSocialController({
|
|
|
310
494
|
document.getElementById("governanceDuplicateWindowInput").value = String(Math.floor((policy.duplicate_window_ms ?? 180000) / 1000));
|
|
311
495
|
document.getElementById("governanceBlockedAgentsInput").value = blockedAgentIds.join(", ");
|
|
312
496
|
document.getElementById("governanceBlockedTermsInput").value = blockedTerms.join(", ");
|
|
313
|
-
|
|
497
|
+
setCachedContent("socialGovernanceCards", [
|
|
314
498
|
[t("labels.sendLimit"), `${policy.send_limit?.max ?? "-"} / ${Math.floor((policy.send_limit?.window_ms ?? 60000) / 1000)}s`],
|
|
315
499
|
[t("labels.receiveLimit"), `${policy.receive_limit?.max ?? "-"} / ${Math.floor((policy.receive_limit?.window_ms ?? 60000) / 1000)}s`],
|
|
316
500
|
[t("labels.duplicateWindowSeconds"), `${Math.floor((policy.duplicate_window_ms ?? 0) / 1000)}s`],
|
|
317
501
|
[t("labels.blockedAgentIds"), blockedAgentIds.length],
|
|
318
502
|
[t("labels.blockedTerms"), blockedTerms.length],
|
|
319
|
-
].map(([k, v]) => `<div class="card"><div class="label">${k}</div><div class="value" style="font-size:17px;">${v}</div></div>`).join("");
|
|
503
|
+
].map(([k, v]) => `<div class="card"><div class="label">${k}</div><div class="value" style="font-size:17px;">${v}</div></div>`).join(""));
|
|
320
504
|
|
|
321
505
|
const moderationEvents = Array.isArray(governance.recent_events) ? governance.recent_events : [];
|
|
322
|
-
|
|
506
|
+
setCachedContent("socialModerationList", moderationEvents.length === 0
|
|
323
507
|
? `<div class="empty-state">${t("network.noModerationEvents")}</div>`
|
|
324
508
|
: moderationEvents.map((event) => `
|
|
325
509
|
<div class="log-item">
|
|
326
510
|
<div class="log-${event.level || "warn"}">[${String(event.level || "warn").toUpperCase()}] ${escapeHtml(event.message || "-")}</div>
|
|
327
511
|
<div class="mono" style="color:#90a2c3;">${new Date(event.timestamp).toLocaleString()}</div>
|
|
328
512
|
</div>
|
|
329
|
-
`).join("");
|
|
513
|
+
`).join(""));
|
|
330
514
|
|
|
331
|
-
|
|
515
|
+
setCachedContent("socialAdvancedCards", [
|
|
332
516
|
[t("labels.adapter"), effectiveAdapter],
|
|
333
517
|
[t("social.namespace"), effectiveNamespace],
|
|
334
518
|
[t("labels.room"), effectiveRoom],
|
|
335
519
|
[t("social.bridgeStatus"), bridge.connected_to_silicaclaw ? t("common.yes") : t("common.no")],
|
|
336
520
|
[t("social.messageBroadcast"), bridge.message_broadcast_enabled ? t("common.on") : t("common.off")],
|
|
337
521
|
[t("social.restartRequired"), social.network_requires_restart ? t("common.yes") : t("common.no")],
|
|
338
|
-
].map(([k, v]) => `<div class="card"><div class="label">${k}</div><div class="value" style="font-size:17px;">${v}</div></div>`).join("");
|
|
339
|
-
|
|
522
|
+
].map(([k, v]) => `<div class="card"><div class="label">${k}</div><div class="value" style="font-size:17px;">${v}</div></div>`).join(""));
|
|
523
|
+
setCachedContent("socialAdvancedWrap", toPrettyJson({
|
|
340
524
|
effective_runtime: {
|
|
341
525
|
mode: effectiveMode,
|
|
342
526
|
adapter: effectiveAdapter,
|
|
@@ -358,17 +542,17 @@ export function createSocialController({
|
|
|
358
542
|
social_md_found: summary.social_md_found,
|
|
359
543
|
social_md_source_path: summary.social_md_source_path,
|
|
360
544
|
},
|
|
361
|
-
});
|
|
545
|
+
}), "text");
|
|
362
546
|
|
|
363
|
-
|
|
547
|
+
setCachedContent("socialSourceWrap", toPrettyJson({
|
|
364
548
|
found: social.found,
|
|
365
549
|
source_path: social.source_path,
|
|
366
550
|
parse_error: social.parse_error,
|
|
367
|
-
});
|
|
368
|
-
|
|
551
|
+
}), "text");
|
|
552
|
+
setCachedContent("socialRawWrap", toPrettyJson({
|
|
369
553
|
raw_frontmatter: social.raw_frontmatter || null,
|
|
370
|
-
});
|
|
371
|
-
|
|
554
|
+
}), "text");
|
|
555
|
+
setCachedContent("socialRuntimeWrap", toPrettyJson(runtime), "text");
|
|
372
556
|
}
|
|
373
557
|
|
|
374
558
|
async function exportSocialTemplate() {
|
|
@@ -383,23 +567,43 @@ export function createSocialController({
|
|
|
383
567
|
const logLevelFilter = getLogLevelFilter();
|
|
384
568
|
const el = document.getElementById("logList");
|
|
385
569
|
if (!logsCache.length) {
|
|
386
|
-
|
|
570
|
+
const nextHtml = `<div class="empty-state">${t("network.noLogsYet")}</div>`;
|
|
571
|
+
if (nextHtml !== lastLogsRenderKey) {
|
|
572
|
+
el.innerHTML = nextHtml;
|
|
573
|
+
lastLogsRenderKey = nextHtml;
|
|
574
|
+
}
|
|
387
575
|
return;
|
|
388
576
|
}
|
|
389
577
|
const filtered = logLevelFilter === "all" ? logsCache : logsCache.filter((item) => String(item.level || "").toLowerCase() === logLevelFilter);
|
|
390
578
|
if (!filtered.length) {
|
|
391
|
-
|
|
579
|
+
const nextHtml = `<div class="empty-state">${t("network.noLogsForLevel", { level: logLevelFilter })}</div>`;
|
|
580
|
+
if (nextHtml !== lastLogsRenderKey) {
|
|
581
|
+
el.innerHTML = nextHtml;
|
|
582
|
+
lastLogsRenderKey = nextHtml;
|
|
583
|
+
}
|
|
392
584
|
return;
|
|
393
585
|
}
|
|
394
|
-
|
|
586
|
+
const nextHtml = filtered.map((item) => `
|
|
395
587
|
<div class="log-item">
|
|
396
588
|
<div class="log-${item.level}">[${String(item.level).toUpperCase()}] ${item.message}</div>
|
|
397
589
|
<div class="mono" style="color:#90a2c3;">${new Date(item.timestamp).toLocaleString()}</div>
|
|
398
590
|
</div>
|
|
399
591
|
`).join("");
|
|
592
|
+
const renderKey = JSON.stringify({
|
|
593
|
+
level: logLevelFilter,
|
|
594
|
+
items: filtered.map((item) => [item.timestamp, item.level, item.message]),
|
|
595
|
+
});
|
|
596
|
+
if (renderKey === lastLogsRenderKey) {
|
|
597
|
+
return;
|
|
598
|
+
}
|
|
599
|
+
el.innerHTML = nextHtml;
|
|
600
|
+
lastLogsRenderKey = renderKey;
|
|
400
601
|
}
|
|
401
602
|
|
|
402
603
|
async function refreshLogs() {
|
|
604
|
+
if (getActiveTab() !== "network") {
|
|
605
|
+
return;
|
|
606
|
+
}
|
|
403
607
|
setLogsCache((await api("/api/logs")).data || []);
|
|
404
608
|
renderLogs();
|
|
405
609
|
}
|
|
@@ -425,8 +629,8 @@ export function createSocialController({
|
|
|
425
629
|
<div class="skill-card">
|
|
426
630
|
<div class="skill-card__top">
|
|
427
631
|
<div>
|
|
428
|
-
<div class="skill-card__eyebrow">${escapeHtml(options.eyebrow || skill.install_mode || "skill")}</div>
|
|
429
|
-
<div class="skill-card__title">${escapeHtml(skill.display_name || skill.name || "
|
|
632
|
+
<div class="skill-card__eyebrow">${escapeHtml(skillModeLabel(options.eyebrow || skill.install_mode || "skill"))}</div>
|
|
633
|
+
<div class="skill-card__title">${escapeHtml(skill.display_name || skill.name || t("labels.skillsModeGeneric"))}</div>
|
|
430
634
|
</div>
|
|
431
635
|
<div class="skill-card__version mono">${escapeHtml(versionText)}</div>
|
|
432
636
|
</div>
|
|
@@ -476,7 +680,7 @@ export function createSocialController({
|
|
|
476
680
|
<div class="skill-card">
|
|
477
681
|
<div class="skill-card__top">
|
|
478
682
|
<div>
|
|
479
|
-
<div class="skill-card__eyebrow">${escapeHtml(skill.display_name || skill.name || "
|
|
683
|
+
<div class="skill-card__eyebrow">${escapeHtml(skill.display_name || skill.name || t("labels.skillsModeGeneric"))}</div>
|
|
480
684
|
<div class="skill-card__title">${escapeHtml(t("labels.skillsDialogueExamples"))}</div>
|
|
481
685
|
</div>
|
|
482
686
|
<div class="skill-card__version mono">${escapeHtml(skill.version || "-")}</div>
|
|
@@ -502,8 +706,12 @@ export function createSocialController({
|
|
|
502
706
|
`;
|
|
503
707
|
}
|
|
504
708
|
|
|
505
|
-
async function refreshSkills() {
|
|
506
|
-
const
|
|
709
|
+
async function refreshSkills(options = {}) {
|
|
710
|
+
const useCached = options.useCached === true;
|
|
711
|
+
const payload = useCached && lastSkillsPayload
|
|
712
|
+
? lastSkillsPayload
|
|
713
|
+
: ((await api("/api/skills")).data || {});
|
|
714
|
+
lastSkillsPayload = payload;
|
|
507
715
|
const bundled = Array.isArray(payload.bundled_skills) ? payload.bundled_skills : [];
|
|
508
716
|
const installed = Array.isArray(payload.installed_skills) ? payload.installed_skills : [];
|
|
509
717
|
const openclaw = payload.openclaw || {};
|
|
@@ -585,13 +793,9 @@ export function createSocialController({
|
|
|
585
793
|
[t("labels.skillsAutoPush"), ownerPushSkill?.installed_in_openclaw ? t("common.yes") : t("common.no")],
|
|
586
794
|
].map(([k, v]) => `<div class="skills-summary-card"><div class="label">${k}</div><div class="value">${escapeHtml(v)}</div></div>`).join("");
|
|
587
795
|
|
|
588
|
-
|
|
589
|
-
document.getElementById("
|
|
590
|
-
|
|
591
|
-
document.getElementById("skillsDialogueCount").textContent = `${featuredSkills.length}`;
|
|
592
|
-
|
|
593
|
-
document.getElementById("skillsFeaturedSpotlights").innerHTML = featuredSkills.length
|
|
594
|
-
? featuredSkills.map((skill) => `
|
|
796
|
+
const filteredFeaturedSkills = featuredSkills.filter((skill) => skillMatchesSearch(skill) && skillMatchesFilter(skill, "bundled"));
|
|
797
|
+
document.getElementById("skillsFeaturedSpotlights").innerHTML = filteredFeaturedSkills.length
|
|
798
|
+
? filteredFeaturedSkills.map((skill) => `
|
|
595
799
|
<div class="skills-spotlight">
|
|
596
800
|
<div class="skill-card__eyebrow">${escapeHtml(skill.name === "silicaclaw-owner-push" ? t("labels.skillsAutoPush") : t("labels.skillsBroadcastLearning"))}</div>
|
|
597
801
|
<div class="skills-spotlight__title">${escapeHtml(skill.display_name || skill.name)}</div>
|
|
@@ -602,38 +806,67 @@ export function createSocialController({
|
|
|
602
806
|
</div>
|
|
603
807
|
</div>
|
|
604
808
|
`).join("")
|
|
605
|
-
: `<div class="skills-empty">${t("hints.skillsNoBundled")}</div>`;
|
|
606
|
-
|
|
607
|
-
|
|
608
|
-
|
|
609
|
-
|
|
610
|
-
|
|
611
|
-
|
|
612
|
-
|
|
613
|
-
|
|
614
|
-
|
|
615
|
-
|
|
616
|
-
|
|
617
|
-
|
|
618
|
-
|
|
619
|
-
|
|
620
|
-
|
|
621
|
-
|
|
622
|
-
|
|
623
|
-
|
|
624
|
-
|
|
625
|
-
|
|
626
|
-
|
|
627
|
-
|
|
628
|
-
|
|
629
|
-
|
|
630
|
-
|
|
631
|
-
|
|
632
|
-
:
|
|
633
|
-
|
|
634
|
-
|
|
635
|
-
|
|
636
|
-
|
|
809
|
+
: `<div class="skills-empty">${featuredSkills.length > 0 ? t("hints.skillsNoFilterMatch") : t("hints.skillsNoBundled")}</div>`;
|
|
810
|
+
|
|
811
|
+
const bundledMatchCount = renderFilteredSkillCards({
|
|
812
|
+
skills: bundledSorted,
|
|
813
|
+
section: "bundled",
|
|
814
|
+
gridId: "skillsBundledGrid",
|
|
815
|
+
footerId: "skillsBundledFooter",
|
|
816
|
+
limit: SKILLS_SECTION_LIMIT,
|
|
817
|
+
emptyText: t("hints.skillsNoBundled"),
|
|
818
|
+
renderer: (skill) => renderSkillCard(skill, {
|
|
819
|
+
eyebrow: skill.install_mode === "workspace" || skill.install_mode === "legacy" ? skill.install_mode : "bundled",
|
|
820
|
+
statusText: skill.update_available
|
|
821
|
+
? t("labels.skillsUpdateAvailable")
|
|
822
|
+
: skill.installed_in_openclaw
|
|
823
|
+
? `${t("labels.skillsStatus")}: ${t("common.yes")}`
|
|
824
|
+
: t("hints.skillsNotInstalled"),
|
|
825
|
+
installable: true,
|
|
826
|
+
updateAvailable: skill.update_available,
|
|
827
|
+
installedVersion: skill.installed_version,
|
|
828
|
+
bundledVersion: skill.version,
|
|
829
|
+
}),
|
|
830
|
+
});
|
|
831
|
+
|
|
832
|
+
const installedMatchCount = renderFilteredSkillCards({
|
|
833
|
+
skills: installedSorted,
|
|
834
|
+
section: "installed",
|
|
835
|
+
gridId: "skillsInstalledGrid",
|
|
836
|
+
footerId: "skillsInstalledFooter",
|
|
837
|
+
limit: SKILLS_SECTION_LIMIT,
|
|
838
|
+
emptyText: t("hints.skillsNoInstalled"),
|
|
839
|
+
renderer: (skill) => renderSkillCard(skill, {
|
|
840
|
+
eyebrow: skill.install_mode || "installed",
|
|
841
|
+
statusText: skill.update_available
|
|
842
|
+
? t("labels.skillsUpdateAvailable")
|
|
843
|
+
: `${t("labels.skillsStatus")}: ${escapeHtml(skillModeLabel(skill.install_mode || "installed"))}`,
|
|
844
|
+
updateAvailable: skill.update_available,
|
|
845
|
+
installedVersion: skill.version,
|
|
846
|
+
bundledVersion: skill.bundled_version,
|
|
847
|
+
}),
|
|
848
|
+
});
|
|
849
|
+
|
|
850
|
+
const dialogueMatchCount = renderFilteredSkillCards({
|
|
851
|
+
skills: featuredSkills,
|
|
852
|
+
section: "dialogue",
|
|
853
|
+
gridId: "skillsDialogueGrid",
|
|
854
|
+
footerId: "skillsDialogueFooter",
|
|
855
|
+
limit: SKILLS_DIALOGUE_LIMIT,
|
|
856
|
+
emptyText: t("hints.skillsNoDialogueExamples"),
|
|
857
|
+
renderer: (skill) => renderDialogueCard(skill),
|
|
858
|
+
});
|
|
859
|
+
|
|
860
|
+
document.getElementById("skillsFeaturedCount").textContent = formatSectionCount(filteredFeaturedSkills.length, featuredSkills.length);
|
|
861
|
+
document.getElementById("skillsBundledCount").textContent = formatSectionCount(bundledMatchCount, bundled.length);
|
|
862
|
+
document.getElementById("skillsInstalledCount").textContent = formatSectionCount(installedMatchCount, installed.length);
|
|
863
|
+
document.getElementById("skillsDialogueCount").textContent = formatSectionCount(dialogueMatchCount, featuredSkills.length);
|
|
864
|
+
|
|
865
|
+
renderSkillsFilterMeta({
|
|
866
|
+
bundledCount: bundledMatchCount,
|
|
867
|
+
installedCount: installedMatchCount,
|
|
868
|
+
dialogueCount: dialogueMatchCount,
|
|
869
|
+
});
|
|
637
870
|
|
|
638
871
|
const installBtn = document.getElementById("skillsInstallBtn");
|
|
639
872
|
installBtn.textContent = !openclawDetected
|
|
@@ -659,6 +892,10 @@ export function createSocialController({
|
|
|
659
892
|
refreshSocial,
|
|
660
893
|
renderLogs,
|
|
661
894
|
renderSocialMessages,
|
|
895
|
+
rerenderSkills: () => refreshSkills({ useCached: true }),
|
|
896
|
+
setSkillsFilter,
|
|
897
|
+
setSkillsQuery,
|
|
662
898
|
setLogLevelFilter,
|
|
899
|
+
toggleSkillsExpanded,
|
|
663
900
|
};
|
|
664
901
|
}
|