@xfxstudio/claworld 2026.4.16-testing.1 → 2026.4.16-testing.2
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/README.md +3 -3
- package/index.js +50 -0
- package/openclaw.plugin.json +1 -1
- package/package.json +4 -1
- package/setup-entry.js +6 -0
- package/skills/claworld-a2a-channel-agent/SKILL.md +218 -0
- package/skills/claworld-help/SKILL.md +304 -0
- package/skills/claworld-join-and-chat/SKILL.md +526 -0
- package/skills/claworld-manage-worlds/SKILL.md +292 -0
- package/skills/claworld-manage-worlds/references/world-context-templates.md +145 -0
- package/src/lib/chat-request.js +366 -0
- package/src/lib/public-identity.js +175 -0
- package/src/lib/relay/agent-readable-markdown.js +385 -0
- package/src/lib/relay/kickoff-progress.js +162 -0
- package/src/lib/relay/kickoff-text.js +191 -0
- package/src/lib/relay/shared.js +30 -0
- package/src/lib/runtime-errors.js +149 -0
- package/src/openclaw/index.js +51 -0
- package/src/openclaw/plugin/account-identity.js +73 -0
- package/src/openclaw/plugin/claworld-channel-plugin.js +3499 -0
- package/src/openclaw/plugin/config-schema.js +392 -0
- package/src/openclaw/plugin/lifecycle.js +114 -0
- package/src/openclaw/plugin/managed-config.js +1054 -0
- package/src/openclaw/plugin/onboarding.js +312 -0
- package/src/openclaw/plugin/register-tooling.js +728 -0
- package/src/openclaw/plugin/register.js +1616 -0
- package/src/openclaw/plugin/relay-client-shared.js +146 -0
- package/src/openclaw/plugin/relay-client.js +1469 -0
- package/src/openclaw/plugin/runtime-backup.js +105 -0
- package/src/openclaw/plugin/runtime.js +12 -0
- package/src/openclaw/plugin-version.js +67 -0
- package/src/openclaw/protocol/relay-event-protocol.js +43 -0
- package/src/openclaw/runtime/backend-error-context.js +91 -0
- package/src/openclaw/runtime/canonical-result-builder.js +126 -0
- package/src/openclaw/runtime/demo-session-bootstrap.js +32 -0
- package/src/openclaw/runtime/feedback-helper.js +145 -0
- package/src/openclaw/runtime/inbound-session-router.js +44 -0
- package/src/openclaw/runtime/outbound-session-bridge.js +29 -0
- package/src/openclaw/runtime/product-shell-helper.js +931 -0
- package/src/openclaw/runtime/runtime-path.js +19 -0
- package/src/openclaw/runtime/system-message-orchestrator.js +1 -0
- package/src/openclaw/runtime/tool-contracts.js +939 -0
- package/src/openclaw/runtime/tool-inventory.js +83 -0
- package/src/openclaw/runtime/world-membership-helper.js +320 -0
- package/src/openclaw/runtime/world-moderation-helper.js +508 -0
- package/src/product-shell/contracts/chat-request-approval-policy.js +93 -0
- package/src/product-shell/contracts/world-orchestration.js +734 -0
- package/src/product-shell/orchestration/world-conversation-text.js +229 -0
|
@@ -0,0 +1,312 @@
|
|
|
1
|
+
import {
|
|
2
|
+
DEFAULT_CLAWORLD_ACCOUNT_ID,
|
|
3
|
+
applyClaworldManagedRuntimeConfig,
|
|
4
|
+
ensureObject,
|
|
5
|
+
normalizeText,
|
|
6
|
+
resolveClaworldManagedRuntimeOptions,
|
|
7
|
+
} from './managed-config.js';
|
|
8
|
+
import {
|
|
9
|
+
defaultClaworldAccountId,
|
|
10
|
+
inspectClaworldChannelAccount,
|
|
11
|
+
listClaworldAccountIds,
|
|
12
|
+
} from './config-schema.js';
|
|
13
|
+
|
|
14
|
+
function collectUnsupportedSetupFlags(input = {}) {
|
|
15
|
+
const unsupported = [];
|
|
16
|
+
const flagMap = [
|
|
17
|
+
['appToken', '--app-token'],
|
|
18
|
+
['token', '--token'],
|
|
19
|
+
['tokenFile', '--token-file'],
|
|
20
|
+
['botToken', '--bot-token'],
|
|
21
|
+
['signalNumber', '--signal-number'],
|
|
22
|
+
['cliPath', '--cli-path'],
|
|
23
|
+
['dbPath', '--db-path'],
|
|
24
|
+
['service', '--service'],
|
|
25
|
+
['region', '--region'],
|
|
26
|
+
['authDir', '--auth-dir'],
|
|
27
|
+
['httpHost', '--http-host'],
|
|
28
|
+
['httpPort', '--http-port'],
|
|
29
|
+
['webhookPath', '--webhook-path'],
|
|
30
|
+
['webhookUrl', '--webhook-url'],
|
|
31
|
+
['audienceType', '--audience-type'],
|
|
32
|
+
['audience', '--audience'],
|
|
33
|
+
['homeserver', '--homeserver'],
|
|
34
|
+
['userId', '--user-id'],
|
|
35
|
+
['accessToken', '--access-token'],
|
|
36
|
+
['password', '--password'],
|
|
37
|
+
['deviceName', '--device-name'],
|
|
38
|
+
['initialSyncLimit', '--initial-sync-limit'],
|
|
39
|
+
['ship', '--ship'],
|
|
40
|
+
];
|
|
41
|
+
|
|
42
|
+
for (const [field, flag] of flagMap) {
|
|
43
|
+
if (normalizeText(input[field], null)) unsupported.push(flag);
|
|
44
|
+
}
|
|
45
|
+
if (Array.isArray(input.groupChannels) && input.groupChannels.length > 0) unsupported.push('--group-channels');
|
|
46
|
+
if (Array.isArray(input.dmAllowlist) && input.dmAllowlist.length > 0) unsupported.push('--dm-allowlist');
|
|
47
|
+
if (input.autoDiscoverChannels === true) unsupported.push('--auto-discover-channels');
|
|
48
|
+
if (input.useEnv === true) unsupported.push('--use-env');
|
|
49
|
+
return unsupported;
|
|
50
|
+
}
|
|
51
|
+
|
|
52
|
+
export function validateClaworldSetupInput({ input = {} } = {}) {
|
|
53
|
+
const unsupportedFlags = collectUnsupportedSetupFlags(input);
|
|
54
|
+
if (unsupportedFlags.length > 0) {
|
|
55
|
+
return (
|
|
56
|
+
'Claworld host-native setup only supports an optional local account label and --http-url/--url overrides. '
|
|
57
|
+
+ `Unsupported flag(s): ${unsupportedFlags.join(', ')}.`
|
|
58
|
+
);
|
|
59
|
+
}
|
|
60
|
+
|
|
61
|
+
const serverUrl = normalizeText(input.httpUrl, normalizeText(input.url, null));
|
|
62
|
+
if (!serverUrl) {
|
|
63
|
+
return null;
|
|
64
|
+
}
|
|
65
|
+
|
|
66
|
+
try {
|
|
67
|
+
const parsed = new URL(serverUrl);
|
|
68
|
+
if (!['http:', 'https:', 'ws:', 'wss:'].includes(parsed.protocol)) {
|
|
69
|
+
return `Unsupported Claworld server URL protocol: ${parsed.protocol}`;
|
|
70
|
+
}
|
|
71
|
+
} catch {
|
|
72
|
+
return `Invalid Claworld server URL: ${serverUrl}`;
|
|
73
|
+
}
|
|
74
|
+
|
|
75
|
+
return null;
|
|
76
|
+
}
|
|
77
|
+
|
|
78
|
+
function findAgentEntry(config = {}, agentId) {
|
|
79
|
+
const normalizedAgentId = normalizeText(agentId, null);
|
|
80
|
+
if (!normalizedAgentId) return null;
|
|
81
|
+
const list = Array.isArray(config?.agents?.list) ? config.agents.list : [];
|
|
82
|
+
return list
|
|
83
|
+
.map((entry) => ensureObject(entry))
|
|
84
|
+
.find((entry) => entry.id === normalizedAgentId) || null;
|
|
85
|
+
}
|
|
86
|
+
|
|
87
|
+
function hasClaworldBinding(config = {}, { agentId, accountId } = {}) {
|
|
88
|
+
const normalizedAgentId = normalizeText(agentId, null);
|
|
89
|
+
const normalizedAccountId = normalizeText(accountId, DEFAULT_CLAWORLD_ACCOUNT_ID);
|
|
90
|
+
const resolvedDefaultAccountId = defaultClaworldAccountId(config) || DEFAULT_CLAWORLD_ACCOUNT_ID;
|
|
91
|
+
const bindings = Array.isArray(config?.bindings) ? config.bindings : [];
|
|
92
|
+
return bindings.some((binding) => {
|
|
93
|
+
const candidate = ensureObject(binding);
|
|
94
|
+
const match = ensureObject(candidate.match);
|
|
95
|
+
const bindingChannel = normalizeText(match.channel, null);
|
|
96
|
+
const bindingAccountId = normalizeText(match.accountId, null);
|
|
97
|
+
const bindingAgentId = normalizeText(candidate.agentId, null);
|
|
98
|
+
if (bindingChannel !== 'claworld') return false;
|
|
99
|
+
if (normalizedAgentId && bindingAgentId !== normalizedAgentId) return false;
|
|
100
|
+
if (bindingAccountId === normalizedAccountId) return true;
|
|
101
|
+
return !bindingAccountId && resolvedDefaultAccountId === normalizedAccountId;
|
|
102
|
+
});
|
|
103
|
+
}
|
|
104
|
+
|
|
105
|
+
function isRelayBootstrapReady(account = {}) {
|
|
106
|
+
return Boolean(
|
|
107
|
+
account?.configured
|
|
108
|
+
&& normalizeText(account?.appToken, null),
|
|
109
|
+
);
|
|
110
|
+
}
|
|
111
|
+
|
|
112
|
+
export function inspectManagedClaworldInstall({
|
|
113
|
+
cfg = {},
|
|
114
|
+
accountId = DEFAULT_CLAWORLD_ACCOUNT_ID,
|
|
115
|
+
input = {},
|
|
116
|
+
overrides = {},
|
|
117
|
+
} = {}) {
|
|
118
|
+
const configuredAccountIds = listClaworldAccountIds(cfg);
|
|
119
|
+
const hasAnyConfig = configuredAccountIds.length > 0 || cfg?.channels?.claworld != null;
|
|
120
|
+
const managedOptions = resolveClaworldManagedRuntimeOptions({
|
|
121
|
+
cfg,
|
|
122
|
+
accountId,
|
|
123
|
+
input,
|
|
124
|
+
overrides,
|
|
125
|
+
});
|
|
126
|
+
const managedAgentPresent = Boolean(findAgentEntry(cfg, managedOptions.agentId));
|
|
127
|
+
const managedBindingPresent = hasClaworldBinding(cfg, managedOptions);
|
|
128
|
+
const managedAccountPresent = configuredAccountIds.includes(managedOptions.accountId);
|
|
129
|
+
const accountStatus = managedAccountPresent
|
|
130
|
+
? inspectClaworldChannelAccount(cfg, managedOptions.accountId)
|
|
131
|
+
: inspectClaworldChannelAccount({}, managedOptions.accountId);
|
|
132
|
+
const activationReady = isRelayBootstrapReady(accountStatus);
|
|
133
|
+
const setupReady = Boolean(
|
|
134
|
+
managedAccountPresent
|
|
135
|
+
&& managedBindingPresent
|
|
136
|
+
&& (managedOptions.manageAgentEntry !== true || managedAgentPresent)
|
|
137
|
+
);
|
|
138
|
+
|
|
139
|
+
let statusLabel = 'needs setup';
|
|
140
|
+
let selectionHint = 'remote relay world channel';
|
|
141
|
+
let quickstartScore = 5;
|
|
142
|
+
|
|
143
|
+
if (setupReady && activationReady) {
|
|
144
|
+
statusLabel = 'configured';
|
|
145
|
+
selectionHint = 'configured · ready';
|
|
146
|
+
quickstartScore = 2;
|
|
147
|
+
} else if (setupReady) {
|
|
148
|
+
statusLabel = 'configured (activation pending)';
|
|
149
|
+
selectionHint = 'configured · activation pending';
|
|
150
|
+
quickstartScore = 3;
|
|
151
|
+
} else if (managedAccountPresent && !managedBindingPresent) {
|
|
152
|
+
statusLabel = 'configured (binding pending)';
|
|
153
|
+
selectionHint = 'configured · binding pending';
|
|
154
|
+
quickstartScore = 4;
|
|
155
|
+
} else if (hasAnyConfig) {
|
|
156
|
+
statusLabel = 'configured (refresh recommended)';
|
|
157
|
+
selectionHint = 'configured · refresh recommended';
|
|
158
|
+
quickstartScore = 4;
|
|
159
|
+
}
|
|
160
|
+
|
|
161
|
+
return {
|
|
162
|
+
hasAnyConfig,
|
|
163
|
+
configuredAccountIds,
|
|
164
|
+
defaultAccountId: defaultClaworldAccountId(cfg) || null,
|
|
165
|
+
managedOptions,
|
|
166
|
+
managedAccountPresent,
|
|
167
|
+
managedAgentPresent,
|
|
168
|
+
managedBindingPresent,
|
|
169
|
+
accountStatus,
|
|
170
|
+
activationReady,
|
|
171
|
+
setupReady,
|
|
172
|
+
statusLabel,
|
|
173
|
+
selectionHint,
|
|
174
|
+
quickstartScore,
|
|
175
|
+
};
|
|
176
|
+
}
|
|
177
|
+
|
|
178
|
+
export function buildClaworldOnboardingStatus({
|
|
179
|
+
cfg = {},
|
|
180
|
+
accountId = DEFAULT_CLAWORLD_ACCOUNT_ID,
|
|
181
|
+
} = {}) {
|
|
182
|
+
const inspection = inspectManagedClaworldInstall({ cfg, accountId });
|
|
183
|
+
return {
|
|
184
|
+
configured: inspection.setupReady,
|
|
185
|
+
statusLines: [`Claworld: ${inspection.statusLabel}`],
|
|
186
|
+
selectionHint: inspection.selectionHint,
|
|
187
|
+
quickstartScore: inspection.quickstartScore,
|
|
188
|
+
activationReady: inspection.activationReady,
|
|
189
|
+
};
|
|
190
|
+
}
|
|
191
|
+
|
|
192
|
+
function applyManagedAccountName({ cfg = {}, accountId, name } = {}) {
|
|
193
|
+
const normalizedName = normalizeText(name, null);
|
|
194
|
+
if (!normalizedName) return cfg;
|
|
195
|
+
|
|
196
|
+
const next = JSON.parse(JSON.stringify(ensureObject(cfg)));
|
|
197
|
+
next.channels = ensureObject(next.channels);
|
|
198
|
+
const claworldRoot = ensureObject(next.channels.claworld);
|
|
199
|
+
const accounts = ensureObject(claworldRoot.accounts);
|
|
200
|
+
const existingAccount = ensureObject(accounts[accountId]);
|
|
201
|
+
accounts[accountId] = {
|
|
202
|
+
...existingAccount,
|
|
203
|
+
name: normalizedName,
|
|
204
|
+
...(existingAccount.registration
|
|
205
|
+
? {
|
|
206
|
+
registration: {
|
|
207
|
+
...ensureObject(existingAccount.registration),
|
|
208
|
+
displayName: normalizedName,
|
|
209
|
+
},
|
|
210
|
+
}
|
|
211
|
+
: {}),
|
|
212
|
+
};
|
|
213
|
+
next.channels.claworld = {
|
|
214
|
+
...claworldRoot,
|
|
215
|
+
accounts,
|
|
216
|
+
};
|
|
217
|
+
return next;
|
|
218
|
+
}
|
|
219
|
+
|
|
220
|
+
function resolveManagedOptionsFromContext({ cfg = {}, accountId = null, input = {}, overrides = {} } = {}) {
|
|
221
|
+
const normalizedInput = ensureObject(input);
|
|
222
|
+
const resolvedInput = { ...normalizedInput };
|
|
223
|
+
delete resolvedInput.name;
|
|
224
|
+
return resolveClaworldManagedRuntimeOptions({
|
|
225
|
+
cfg,
|
|
226
|
+
accountId: normalizeText(accountId, DEFAULT_CLAWORLD_ACCOUNT_ID),
|
|
227
|
+
input: resolvedInput,
|
|
228
|
+
overrides: {
|
|
229
|
+
...overrides,
|
|
230
|
+
...(normalizeText(normalizedInput.name, null) ? { name: normalizedInput.name } : {}),
|
|
231
|
+
},
|
|
232
|
+
});
|
|
233
|
+
}
|
|
234
|
+
|
|
235
|
+
async function applyManagedOnboardingConfig({
|
|
236
|
+
cfg = {},
|
|
237
|
+
prompter,
|
|
238
|
+
accountId = null,
|
|
239
|
+
phase = 'setup',
|
|
240
|
+
input = {},
|
|
241
|
+
} = {}) {
|
|
242
|
+
const managedOptions = resolveManagedOptionsFromContext({ cfg, accountId, input });
|
|
243
|
+
const next = applyClaworldManagedRuntimeConfig(cfg, managedOptions);
|
|
244
|
+
|
|
245
|
+
const noteLines = [
|
|
246
|
+
`Bound local agent/account: ${managedOptions.agentId}`,
|
|
247
|
+
`Remote backend: ${managedOptions.serverUrl}`,
|
|
248
|
+
managedOptions.appToken
|
|
249
|
+
? 'Activation state: ready via configured appToken'
|
|
250
|
+
: 'Activation state: pending until claworld_account(action=update_identity) runs',
|
|
251
|
+
'This flow refreshes plugin-side config and binds claworld onto the selected local agent. It does not run installer commands or start a backend service.',
|
|
252
|
+
];
|
|
253
|
+
await prompter.note(
|
|
254
|
+
noteLines.join('\n'),
|
|
255
|
+
phase === 'refresh' ? 'Claworld refresh' : 'Claworld setup',
|
|
256
|
+
);
|
|
257
|
+
|
|
258
|
+
return {
|
|
259
|
+
cfg: next.config,
|
|
260
|
+
accountId: managedOptions.accountId,
|
|
261
|
+
};
|
|
262
|
+
}
|
|
263
|
+
|
|
264
|
+
export const claworldSetupAdapter = {
|
|
265
|
+
resolveAccountId: ({ accountId }) => normalizeText(accountId, DEFAULT_CLAWORLD_ACCOUNT_ID),
|
|
266
|
+
resolveBindingAccountId: ({ cfg, agentId, accountId }) => {
|
|
267
|
+
const explicit = normalizeText(accountId, null);
|
|
268
|
+
if (explicit) return explicit;
|
|
269
|
+
const normalizedAgentId = normalizeText(agentId, null);
|
|
270
|
+
const accountIds = listClaworldAccountIds(cfg);
|
|
271
|
+
if (normalizedAgentId && accountIds.includes(normalizedAgentId)) {
|
|
272
|
+
return normalizedAgentId;
|
|
273
|
+
}
|
|
274
|
+
return accountIds.length > 0 ? defaultClaworldAccountId(cfg) : DEFAULT_CLAWORLD_ACCOUNT_ID;
|
|
275
|
+
},
|
|
276
|
+
applyAccountName: ({ cfg, accountId, name }) => applyManagedAccountName({ cfg, accountId, name }),
|
|
277
|
+
validateInput: ({ input }) => validateClaworldSetupInput({ input }),
|
|
278
|
+
applyAccountConfig: ({ cfg, accountId, input }) => {
|
|
279
|
+
const managedOptions = resolveManagedOptionsFromContext({ cfg, accountId, input });
|
|
280
|
+
return applyClaworldManagedRuntimeConfig(cfg, managedOptions).config;
|
|
281
|
+
},
|
|
282
|
+
};
|
|
283
|
+
|
|
284
|
+
export const claworldOnboardingAdapter = {
|
|
285
|
+
channel: 'claworld',
|
|
286
|
+
getStatus: async ({ cfg, accountOverrides }) => {
|
|
287
|
+
const managedAccountId = normalizeText(accountOverrides?.claworld, DEFAULT_CLAWORLD_ACCOUNT_ID);
|
|
288
|
+
return {
|
|
289
|
+
channel: 'claworld',
|
|
290
|
+
...buildClaworldOnboardingStatus({
|
|
291
|
+
cfg,
|
|
292
|
+
accountId: managedAccountId,
|
|
293
|
+
}),
|
|
294
|
+
};
|
|
295
|
+
},
|
|
296
|
+
configure: async ({ cfg, prompter, accountOverrides }) =>
|
|
297
|
+
applyManagedOnboardingConfig({
|
|
298
|
+
cfg,
|
|
299
|
+
prompter,
|
|
300
|
+
accountId: accountOverrides?.claworld,
|
|
301
|
+
phase: 'setup',
|
|
302
|
+
input: {},
|
|
303
|
+
}),
|
|
304
|
+
configureWhenConfigured: async ({ cfg, prompter, accountOverrides }) =>
|
|
305
|
+
applyManagedOnboardingConfig({
|
|
306
|
+
cfg,
|
|
307
|
+
prompter,
|
|
308
|
+
accountId: accountOverrides?.claworld,
|
|
309
|
+
phase: 'refresh',
|
|
310
|
+
input: {},
|
|
311
|
+
}),
|
|
312
|
+
};
|