@nextclaw/server 0.10.31 → 0.10.33
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/index.d.ts +26 -1
- package/dist/index.js +149 -3
- package/package.json +4 -4
package/dist/index.d.ts
CHANGED
|
@@ -500,6 +500,31 @@ type ProviderAuthImportResult = {
|
|
|
500
500
|
source: "cli";
|
|
501
501
|
expiresAt?: string;
|
|
502
502
|
};
|
|
503
|
+
type ChannelAuthStartRequest = {
|
|
504
|
+
accountId?: string;
|
|
505
|
+
baseUrl?: string;
|
|
506
|
+
};
|
|
507
|
+
type ChannelAuthStartResult = {
|
|
508
|
+
channel: string;
|
|
509
|
+
kind: "qr_code";
|
|
510
|
+
sessionId: string;
|
|
511
|
+
qrCode: string;
|
|
512
|
+
qrCodeUrl: string;
|
|
513
|
+
expiresAt: string;
|
|
514
|
+
intervalMs: number;
|
|
515
|
+
note?: string;
|
|
516
|
+
};
|
|
517
|
+
type ChannelAuthPollRequest = {
|
|
518
|
+
sessionId: string;
|
|
519
|
+
};
|
|
520
|
+
type ChannelAuthPollResult = {
|
|
521
|
+
channel: string;
|
|
522
|
+
status: "pending" | "scanned" | "authorized" | "expired" | "error";
|
|
523
|
+
message?: string;
|
|
524
|
+
nextPollMs?: number;
|
|
525
|
+
accountId?: string | null;
|
|
526
|
+
notes?: string[];
|
|
527
|
+
};
|
|
503
528
|
type AuthStatusView = {
|
|
504
529
|
enabled: boolean;
|
|
505
530
|
configured: boolean;
|
|
@@ -1189,4 +1214,4 @@ declare function getUiBridgeSecretPath(): string;
|
|
|
1189
1214
|
declare function readUiBridgeSecret(): string | null;
|
|
1190
1215
|
declare function ensureUiBridgeSecret(): string;
|
|
1191
1216
|
|
|
1192
|
-
export { type AgentBindingView, type AgentProfileView, type ApiError, type ApiResponse, type AppMetaView, type AuthEnabledUpdateRequest, type AuthLoginRequest, type AuthPasswordUpdateRequest, type AuthSetupRequest, type AuthStatusView, type BindingPeerView, type BochaFreshnessValue, type ChannelSpecView, type ChatCapabilitiesView, type ChatCommandOptionView, type ChatCommandView, type ChatCommandsView, type ChatRunListView, type ChatRunState, type ChatRunView, type ChatSessionTypeCtaView, type ChatSessionTypeOptionView, type ChatSessionTypesView, type ChatTurnRequest, type ChatTurnResult, type ChatTurnStopRequest, type ChatTurnStopResult, type ChatTurnStreamEvent, type ChatTurnView, type ConfigActionExecuteRequest, type ConfigActionExecuteResult, type ConfigActionManifest, type ConfigActionType, type ConfigMetaView, type ConfigSchemaResponse, type ConfigUiHint, type ConfigUiHints, type ConfigView, type CronActionResult, type CronEnableRequest, type CronJobStateView, type CronJobView, type CronListView, type CronPayloadView, type CronRunRequest, type CronScheduleView, DEFAULT_SESSION_TYPE, type MarketplaceApiConfig, type MarketplaceInstallKind, type MarketplaceInstallSkillParams, type MarketplaceInstallSpec, type MarketplaceInstalledRecord, type MarketplaceInstalledView, type MarketplaceInstaller, type MarketplaceItemSummary, type MarketplaceItemType, type MarketplaceItemView, type MarketplaceListView, type MarketplaceLocalizedTextMap, type MarketplaceMcpContentView, type MarketplaceMcpDoctorResult, type MarketplaceMcpInstallKind, type MarketplaceMcpInstallRequest, type MarketplaceMcpInstallResult, type MarketplaceMcpInstallSpec, type MarketplaceMcpManageAction, type MarketplaceMcpManageRequest, type MarketplaceMcpManageResult, type MarketplaceMcpTemplateInput, type MarketplacePluginContentView, type MarketplacePluginInstallKind, type MarketplacePluginInstallRequest, type MarketplacePluginInstallResult, type MarketplacePluginManageAction, type MarketplacePluginManageRequest, type MarketplacePluginManageResult, type MarketplaceRecommendationView, type MarketplaceSkillContentView, type MarketplaceSkillInstallKind, type MarketplaceSkillInstallRequest, type MarketplaceSkillInstallResult, type MarketplaceSkillManageAction, type MarketplaceSkillManageRequest, type MarketplaceSkillManageResult, type MarketplaceSort, type ProviderAuthImportResult, type ProviderAuthPollRequest, type ProviderAuthPollResult, type ProviderAuthStartRequest, type ProviderAuthStartResult, type ProviderConfigUpdate, type ProviderConfigView, type ProviderConnectionTestRequest, type ProviderConnectionTestResult, type ProviderCreateRequest, type ProviderCreateResult, type ProviderDeleteResult, type ProviderSpecView, type RemoteAccessView, type RemoteAccountView, type RemoteBrowserAuthPollRequest, type RemoteBrowserAuthPollResult, type RemoteBrowserAuthStartRequest, type RemoteBrowserAuthStartResult, type RemoteDoctorCheckView, type RemoteDoctorView, type RemoteLoginRequest, type RemoteRuntimeView, type RemoteServiceAction, type RemoteServiceActionResult, type RemoteServiceView, type RemoteSettingsUpdateRequest, type RemoteSettingsView, type RuntimeConfigUpdate, type SearchConfigUpdate, type SearchConfigView, type SearchProviderConfigView, type SearchProviderName, type SearchProviderSpecView, type SecretProviderEnvView, type SecretProviderExecView, type SecretProviderFileView, type SecretProviderView, type SecretRefView, type SecretSourceView, type SecretsConfigUpdate, type SecretsView, type SessionConfigView, type SessionEntryView, type SessionEventView, type SessionHistoryView, type SessionMessageView, type SessionPatchUpdate, SessionPatchValidationError, type SessionsListView, type UiChatRuntime, type UiNcpAgent, type UiNcpSessionListView, type UiNcpSessionMessagesView, type UiRemoteAccessHost, type UiServerEvent, type UiServerHandle, type UiServerOptions, buildConfigMeta, buildConfigSchemaView, buildConfigView, createCustomProvider, createUiRouter, deleteCustomProvider, deleteSession, ensureUiBridgeSecret, executeConfigAction, getSessionHistory, getUiBridgeSecretPath, listSessions, loadConfigOrDefault, patchSession, readUiBridgeSecret, startUiServer, testProviderConnection, updateChannel, updateModel, updateProvider, updateRuntime, updateSearch, updateSecrets };
|
|
1217
|
+
export { type AgentBindingView, type AgentProfileView, type ApiError, type ApiResponse, type AppMetaView, type AuthEnabledUpdateRequest, type AuthLoginRequest, type AuthPasswordUpdateRequest, type AuthSetupRequest, type AuthStatusView, type BindingPeerView, type BochaFreshnessValue, type ChannelAuthPollRequest, type ChannelAuthPollResult, type ChannelAuthStartRequest, type ChannelAuthStartResult, type ChannelSpecView, type ChatCapabilitiesView, type ChatCommandOptionView, type ChatCommandView, type ChatCommandsView, type ChatRunListView, type ChatRunState, type ChatRunView, type ChatSessionTypeCtaView, type ChatSessionTypeOptionView, type ChatSessionTypesView, type ChatTurnRequest, type ChatTurnResult, type ChatTurnStopRequest, type ChatTurnStopResult, type ChatTurnStreamEvent, type ChatTurnView, type ConfigActionExecuteRequest, type ConfigActionExecuteResult, type ConfigActionManifest, type ConfigActionType, type ConfigMetaView, type ConfigSchemaResponse, type ConfigUiHint, type ConfigUiHints, type ConfigView, type CronActionResult, type CronEnableRequest, type CronJobStateView, type CronJobView, type CronListView, type CronPayloadView, type CronRunRequest, type CronScheduleView, DEFAULT_SESSION_TYPE, type MarketplaceApiConfig, type MarketplaceInstallKind, type MarketplaceInstallSkillParams, type MarketplaceInstallSpec, type MarketplaceInstalledRecord, type MarketplaceInstalledView, type MarketplaceInstaller, type MarketplaceItemSummary, type MarketplaceItemType, type MarketplaceItemView, type MarketplaceListView, type MarketplaceLocalizedTextMap, type MarketplaceMcpContentView, type MarketplaceMcpDoctorResult, type MarketplaceMcpInstallKind, type MarketplaceMcpInstallRequest, type MarketplaceMcpInstallResult, type MarketplaceMcpInstallSpec, type MarketplaceMcpManageAction, type MarketplaceMcpManageRequest, type MarketplaceMcpManageResult, type MarketplaceMcpTemplateInput, type MarketplacePluginContentView, type MarketplacePluginInstallKind, type MarketplacePluginInstallRequest, type MarketplacePluginInstallResult, type MarketplacePluginManageAction, type MarketplacePluginManageRequest, type MarketplacePluginManageResult, type MarketplaceRecommendationView, type MarketplaceSkillContentView, type MarketplaceSkillInstallKind, type MarketplaceSkillInstallRequest, type MarketplaceSkillInstallResult, type MarketplaceSkillManageAction, type MarketplaceSkillManageRequest, type MarketplaceSkillManageResult, type MarketplaceSort, type ProviderAuthImportResult, type ProviderAuthPollRequest, type ProviderAuthPollResult, type ProviderAuthStartRequest, type ProviderAuthStartResult, type ProviderConfigUpdate, type ProviderConfigView, type ProviderConnectionTestRequest, type ProviderConnectionTestResult, type ProviderCreateRequest, type ProviderCreateResult, type ProviderDeleteResult, type ProviderSpecView, type RemoteAccessView, type RemoteAccountView, type RemoteBrowserAuthPollRequest, type RemoteBrowserAuthPollResult, type RemoteBrowserAuthStartRequest, type RemoteBrowserAuthStartResult, type RemoteDoctorCheckView, type RemoteDoctorView, type RemoteLoginRequest, type RemoteRuntimeView, type RemoteServiceAction, type RemoteServiceActionResult, type RemoteServiceView, type RemoteSettingsUpdateRequest, type RemoteSettingsView, type RuntimeConfigUpdate, type SearchConfigUpdate, type SearchConfigView, type SearchProviderConfigView, type SearchProviderName, type SearchProviderSpecView, type SecretProviderEnvView, type SecretProviderExecView, type SecretProviderFileView, type SecretProviderView, type SecretRefView, type SecretSourceView, type SecretsConfigUpdate, type SecretsView, type SessionConfigView, type SessionEntryView, type SessionEventView, type SessionHistoryView, type SessionMessageView, type SessionPatchUpdate, SessionPatchValidationError, type SessionsListView, type UiChatRuntime, type UiNcpAgent, type UiNcpSessionListView, type UiNcpSessionMessagesView, type UiRemoteAccessHost, type UiServerEvent, type UiServerHandle, type UiServerOptions, buildConfigMeta, buildConfigSchemaView, buildConfigView, createCustomProvider, createUiRouter, deleteCustomProvider, deleteSession, ensureUiBridgeSecret, executeConfigAction, getSessionHistory, getUiBridgeSecretPath, listSessions, loadConfigOrDefault, patchSession, readUiBridgeSecret, startUiServer, testProviderConnection, updateChannel, updateModel, updateProvider, updateRuntime, updateSearch, updateSecrets };
|
package/dist/index.js
CHANGED
|
@@ -2606,6 +2606,96 @@ var ChatRoutesController = class {
|
|
|
2606
2606
|
};
|
|
2607
2607
|
};
|
|
2608
2608
|
|
|
2609
|
+
// src/ui/channel-auth.ts
|
|
2610
|
+
import { saveConfig as saveConfig3 } from "@nextclaw/core";
|
|
2611
|
+
import {
|
|
2612
|
+
enablePluginInConfig
|
|
2613
|
+
} from "@nextclaw/openclaw-compat";
|
|
2614
|
+
function clonePluginConfig(value) {
|
|
2615
|
+
if (!value || typeof value !== "object" || Array.isArray(value)) {
|
|
2616
|
+
return void 0;
|
|
2617
|
+
}
|
|
2618
|
+
return JSON.parse(JSON.stringify(value));
|
|
2619
|
+
}
|
|
2620
|
+
function findPluginChannelBinding(bindings, channelId) {
|
|
2621
|
+
const normalizedChannelId = channelId.trim().toLowerCase();
|
|
2622
|
+
return bindings.find((binding) => binding.channelId.trim().toLowerCase() === normalizedChannelId) ?? null;
|
|
2623
|
+
}
|
|
2624
|
+
function toPublicChannelAuthPollResult(result) {
|
|
2625
|
+
return {
|
|
2626
|
+
channel: result.channel,
|
|
2627
|
+
status: result.status,
|
|
2628
|
+
message: result.message,
|
|
2629
|
+
nextPollMs: result.nextPollMs,
|
|
2630
|
+
accountId: result.accountId,
|
|
2631
|
+
notes: result.notes
|
|
2632
|
+
};
|
|
2633
|
+
}
|
|
2634
|
+
function applyAuthorizedChannelAuthResult(params) {
|
|
2635
|
+
if (params.result.status !== "authorized" || !params.result.pluginConfig) {
|
|
2636
|
+
return;
|
|
2637
|
+
}
|
|
2638
|
+
const currentConfig = loadConfigOrDefault(params.configPath);
|
|
2639
|
+
const nextConfig = enablePluginInConfig(
|
|
2640
|
+
{
|
|
2641
|
+
...currentConfig,
|
|
2642
|
+
plugins: {
|
|
2643
|
+
...currentConfig.plugins,
|
|
2644
|
+
entries: {
|
|
2645
|
+
...currentConfig.plugins.entries ?? {},
|
|
2646
|
+
[params.binding.pluginId]: {
|
|
2647
|
+
...currentConfig.plugins.entries?.[params.binding.pluginId] ?? {},
|
|
2648
|
+
config: params.result.pluginConfig
|
|
2649
|
+
}
|
|
2650
|
+
}
|
|
2651
|
+
}
|
|
2652
|
+
},
|
|
2653
|
+
params.binding.pluginId
|
|
2654
|
+
);
|
|
2655
|
+
saveConfig3(nextConfig, params.configPath);
|
|
2656
|
+
}
|
|
2657
|
+
async function startChannelAuth(params) {
|
|
2658
|
+
const binding = findPluginChannelBinding(params.bindings, params.channelId);
|
|
2659
|
+
const start = binding?.channel.auth?.start;
|
|
2660
|
+
if (!binding || !start) {
|
|
2661
|
+
return null;
|
|
2662
|
+
}
|
|
2663
|
+
const config = loadConfigOrDefault(params.configPath);
|
|
2664
|
+
const result = await start({
|
|
2665
|
+
cfg: config,
|
|
2666
|
+
pluginId: binding.pluginId,
|
|
2667
|
+
channelId: binding.channelId,
|
|
2668
|
+
pluginConfig: clonePluginConfig(config.plugins.entries?.[binding.pluginId]?.config),
|
|
2669
|
+
accountId: params.request.accountId?.trim() || null,
|
|
2670
|
+
baseUrl: params.request.baseUrl?.trim() || null
|
|
2671
|
+
});
|
|
2672
|
+
return result;
|
|
2673
|
+
}
|
|
2674
|
+
async function pollChannelAuth(params) {
|
|
2675
|
+
const binding = findPluginChannelBinding(params.bindings, params.channelId);
|
|
2676
|
+
const poll = binding?.channel.auth?.poll;
|
|
2677
|
+
if (!binding || !poll) {
|
|
2678
|
+
return null;
|
|
2679
|
+
}
|
|
2680
|
+
const config = loadConfigOrDefault(params.configPath);
|
|
2681
|
+
const result = await poll({
|
|
2682
|
+
cfg: config,
|
|
2683
|
+
pluginId: binding.pluginId,
|
|
2684
|
+
channelId: binding.channelId,
|
|
2685
|
+
pluginConfig: clonePluginConfig(config.plugins.entries?.[binding.pluginId]?.config),
|
|
2686
|
+
sessionId: params.sessionId
|
|
2687
|
+
});
|
|
2688
|
+
if (!result) {
|
|
2689
|
+
return null;
|
|
2690
|
+
}
|
|
2691
|
+
applyAuthorizedChannelAuthResult({
|
|
2692
|
+
configPath: params.configPath,
|
|
2693
|
+
binding,
|
|
2694
|
+
result
|
|
2695
|
+
});
|
|
2696
|
+
return toPublicChannelAuthPollResult(result);
|
|
2697
|
+
}
|
|
2698
|
+
|
|
2609
2699
|
// src/ui/provider-auth.ts
|
|
2610
2700
|
import { createHash, randomBytes as randomBytes3, randomUUID as randomUUID2 } from "crypto";
|
|
2611
2701
|
import { readFile } from "fs/promises";
|
|
@@ -2614,7 +2704,7 @@ import { isAbsolute, resolve } from "path";
|
|
|
2614
2704
|
import {
|
|
2615
2705
|
ConfigSchema as ConfigSchema3,
|
|
2616
2706
|
loadConfig as loadConfig3,
|
|
2617
|
-
saveConfig as
|
|
2707
|
+
saveConfig as saveConfig4
|
|
2618
2708
|
} from "@nextclaw/core";
|
|
2619
2709
|
var authSessions = /* @__PURE__ */ new Map();
|
|
2620
2710
|
var DEFAULT_AUTH_INTERVAL_MS = 2e3;
|
|
@@ -2819,7 +2909,7 @@ function setProviderApiKey(params) {
|
|
|
2819
2909
|
target.apiBase = params.defaultApiBase;
|
|
2820
2910
|
}
|
|
2821
2911
|
const next = ConfigSchema3.parse(config);
|
|
2822
|
-
|
|
2912
|
+
saveConfig4(next, params.configPath);
|
|
2823
2913
|
}
|
|
2824
2914
|
async function startProviderAuth(configPath, providerName, options) {
|
|
2825
2915
|
cleanupExpiredAuthSessions();
|
|
@@ -3326,6 +3416,60 @@ var ConfigRoutesController = class {
|
|
|
3326
3416
|
this.options.publish({ type: "config.updated", payload: { path: `channels.${channel}` } });
|
|
3327
3417
|
return c.json(ok(result));
|
|
3328
3418
|
};
|
|
3419
|
+
startChannelAuth = async (c) => {
|
|
3420
|
+
const channel = c.req.param("channel");
|
|
3421
|
+
let payload = {};
|
|
3422
|
+
const rawBody = await c.req.raw.text();
|
|
3423
|
+
if (rawBody.trim().length > 0) {
|
|
3424
|
+
try {
|
|
3425
|
+
payload = JSON.parse(rawBody);
|
|
3426
|
+
} catch {
|
|
3427
|
+
return c.json(err("INVALID_BODY", "invalid json body"), 400);
|
|
3428
|
+
}
|
|
3429
|
+
}
|
|
3430
|
+
try {
|
|
3431
|
+
const result = await startChannelAuth({
|
|
3432
|
+
configPath: this.options.configPath,
|
|
3433
|
+
channelId: channel,
|
|
3434
|
+
request: {
|
|
3435
|
+
accountId: typeof payload.accountId === "string" ? payload.accountId : void 0,
|
|
3436
|
+
baseUrl: typeof payload.baseUrl === "string" ? payload.baseUrl : void 0
|
|
3437
|
+
},
|
|
3438
|
+
bindings: this.options.getPluginChannelBindings?.() ?? []
|
|
3439
|
+
});
|
|
3440
|
+
if (!result) {
|
|
3441
|
+
return c.json(err("NOT_SUPPORTED", `channel auth is not supported: ${channel}`), 404);
|
|
3442
|
+
}
|
|
3443
|
+
return c.json(ok(result));
|
|
3444
|
+
} catch (error) {
|
|
3445
|
+
const message = error instanceof Error ? error.message : String(error);
|
|
3446
|
+
return c.json(err("AUTH_START_FAILED", message), 400);
|
|
3447
|
+
}
|
|
3448
|
+
};
|
|
3449
|
+
pollChannelAuth = async (c) => {
|
|
3450
|
+
const channel = c.req.param("channel");
|
|
3451
|
+
const body = await readJson(c.req.raw);
|
|
3452
|
+
if (!body.ok) {
|
|
3453
|
+
return c.json(err("INVALID_BODY", "invalid json body"), 400);
|
|
3454
|
+
}
|
|
3455
|
+
const sessionId = typeof body.data.sessionId === "string" ? body.data.sessionId.trim() : "";
|
|
3456
|
+
if (!sessionId) {
|
|
3457
|
+
return c.json(err("INVALID_BODY", "sessionId is required"), 400);
|
|
3458
|
+
}
|
|
3459
|
+
const result = await pollChannelAuth({
|
|
3460
|
+
configPath: this.options.configPath,
|
|
3461
|
+
channelId: channel,
|
|
3462
|
+
sessionId,
|
|
3463
|
+
bindings: this.options.getPluginChannelBindings?.() ?? []
|
|
3464
|
+
});
|
|
3465
|
+
if (!result) {
|
|
3466
|
+
return c.json(err("NOT_FOUND", "channel auth session not found"), 404);
|
|
3467
|
+
}
|
|
3468
|
+
if (result.status === "authorized") {
|
|
3469
|
+
this.options.publish({ type: "config.updated", payload: { path: `channels.${channel}` } });
|
|
3470
|
+
}
|
|
3471
|
+
return c.json(ok(result));
|
|
3472
|
+
};
|
|
3329
3473
|
updateSecrets = async (c) => {
|
|
3330
3474
|
const body = await readJson(c.req.raw);
|
|
3331
3475
|
if (!body.ok) {
|
|
@@ -5163,6 +5307,8 @@ function registerConfigRoutes(app, configController) {
|
|
|
5163
5307
|
app.post("/api/config/providers/:provider/auth/poll", configController.pollProviderAuth);
|
|
5164
5308
|
app.post("/api/config/providers/:provider/auth/import-cli", configController.importProviderAuthFromCli);
|
|
5165
5309
|
app.put("/api/config/channels/:channel", configController.updateChannel);
|
|
5310
|
+
app.post("/api/config/channels/:channel/auth/start", configController.startChannelAuth);
|
|
5311
|
+
app.post("/api/config/channels/:channel/auth/poll", configController.pollChannelAuth);
|
|
5166
5312
|
app.put("/api/config/secrets", configController.updateSecrets);
|
|
5167
5313
|
app.put("/api/config/runtime", configController.updateRuntime);
|
|
5168
5314
|
app.post("/api/config/actions/:actionId/execute", configController.executeAction);
|
|
@@ -5396,7 +5542,7 @@ function startUiServer(options) {
|
|
|
5396
5542
|
);
|
|
5397
5543
|
app.get("*", (c) => {
|
|
5398
5544
|
const path = c.req.path;
|
|
5399
|
-
if (path.startsWith("/api") || path.startsWith("/ws")) {
|
|
5545
|
+
if (path.startsWith("/api") || path.startsWith("/ws") || path.startsWith("/_remote")) {
|
|
5400
5546
|
return c.notFound();
|
|
5401
5547
|
}
|
|
5402
5548
|
return c.html(indexHtml);
|
package/package.json
CHANGED
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "@nextclaw/server",
|
|
3
|
-
"version": "0.10.
|
|
3
|
+
"version": "0.10.33",
|
|
4
4
|
"private": false,
|
|
5
5
|
"description": "Nextclaw UI/API server.",
|
|
6
6
|
"type": "module",
|
|
@@ -20,10 +20,10 @@
|
|
|
20
20
|
"ws": "^8.18.0",
|
|
21
21
|
"@nextclaw/mcp": "0.1.29",
|
|
22
22
|
"@nextclaw/ncp": "0.3.1",
|
|
23
|
+
"@nextclaw/openclaw-compat": "0.3.16",
|
|
23
24
|
"@nextclaw/ncp-http-agent-server": "0.3.1",
|
|
24
|
-
"@nextclaw/runtime": "0.2.
|
|
25
|
-
"@nextclaw/core": "0.9.11"
|
|
26
|
-
"@nextclaw/openclaw-compat": "0.3.15"
|
|
25
|
+
"@nextclaw/runtime": "0.2.11",
|
|
26
|
+
"@nextclaw/core": "0.9.11"
|
|
27
27
|
},
|
|
28
28
|
"devDependencies": {
|
|
29
29
|
"@types/node": "^20.17.6",
|