mirror of
https://github.com/openclaw/openclaw.git
synced 2026-04-23 15:11:42 +00:00
refactor: share account id selection helpers
This commit is contained in:
@@ -3,6 +3,12 @@ import {
|
||||
normalizeAccountId,
|
||||
normalizeOptionalAccountId,
|
||||
} from "openclaw/plugin-sdk/account-id";
|
||||
import {
|
||||
listCombinedAccountIds,
|
||||
listConfiguredAccountIds,
|
||||
resolveListedDefaultAccountId,
|
||||
resolveNormalizedAccountEntry,
|
||||
} from "openclaw/plugin-sdk/account-resolution";
|
||||
import type { OpenClawConfig } from "openclaw/plugin-sdk/config-runtime";
|
||||
import { listMatrixEnvAccountIds } from "./env-vars.js";
|
||||
|
||||
@@ -27,15 +33,8 @@ export function findMatrixAccountEntry(
|
||||
if (!accounts) {
|
||||
return null;
|
||||
}
|
||||
|
||||
const normalizedAccountId = normalizeAccountId(accountId);
|
||||
for (const [rawAccountId, value] of Object.entries(accounts)) {
|
||||
if (normalizeAccountId(rawAccountId) === normalizedAccountId && isRecord(value)) {
|
||||
return value;
|
||||
}
|
||||
}
|
||||
|
||||
return null;
|
||||
const entry = resolveNormalizedAccountEntry(accounts, accountId, normalizeAccountId);
|
||||
return isRecord(entry) ? entry : null;
|
||||
}
|
||||
|
||||
export function resolveConfiguredMatrixAccountIds(
|
||||
@@ -43,22 +42,14 @@ export function resolveConfiguredMatrixAccountIds(
|
||||
env: NodeJS.ProcessEnv = process.env,
|
||||
): string[] {
|
||||
const channel = resolveMatrixChannelConfig(cfg);
|
||||
const ids = new Set<string>(listMatrixEnvAccountIds(env));
|
||||
|
||||
const accounts = channel && isRecord(channel.accounts) ? channel.accounts : null;
|
||||
if (accounts) {
|
||||
for (const [accountId, value] of Object.entries(accounts)) {
|
||||
if (isRecord(value)) {
|
||||
ids.add(normalizeAccountId(accountId));
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
if (ids.size === 0 && channel) {
|
||||
ids.add(DEFAULT_ACCOUNT_ID);
|
||||
}
|
||||
|
||||
return Array.from(ids).toSorted((a, b) => a.localeCompare(b));
|
||||
return listCombinedAccountIds({
|
||||
configuredAccountIds: listConfiguredAccountIds({
|
||||
accounts: channel && isRecord(channel.accounts) ? channel.accounts : undefined,
|
||||
normalizeAccountId,
|
||||
}),
|
||||
additionalAccountIds: listMatrixEnvAccountIds(env),
|
||||
fallbackAccountIdWhenEmpty: channel ? DEFAULT_ACCOUNT_ID : undefined,
|
||||
});
|
||||
}
|
||||
|
||||
export function resolveMatrixDefaultOrOnlyAccountId(
|
||||
@@ -74,17 +65,11 @@ export function resolveMatrixDefaultOrOnlyAccountId(
|
||||
typeof channel.defaultAccount === "string" ? channel.defaultAccount : undefined,
|
||||
);
|
||||
const configuredAccountIds = resolveConfiguredMatrixAccountIds(cfg, env);
|
||||
if (configuredDefault && configuredAccountIds.includes(configuredDefault)) {
|
||||
return configuredDefault;
|
||||
}
|
||||
if (configuredAccountIds.includes(DEFAULT_ACCOUNT_ID)) {
|
||||
return DEFAULT_ACCOUNT_ID;
|
||||
}
|
||||
|
||||
if (configuredAccountIds.length === 1) {
|
||||
return configuredAccountIds[0] ?? DEFAULT_ACCOUNT_ID;
|
||||
}
|
||||
return DEFAULT_ACCOUNT_ID;
|
||||
return resolveListedDefaultAccountId({
|
||||
accountIds: configuredAccountIds,
|
||||
configuredDefaultAccountId: configuredDefault,
|
||||
ambiguousFallbackAccountId: DEFAULT_ACCOUNT_ID,
|
||||
});
|
||||
}
|
||||
|
||||
export function requiresExplicitMatrixDefaultAccount(
|
||||
|
||||
@@ -1,4 +1,8 @@
|
||||
import { normalizeAccountId } from "openclaw/plugin-sdk/account-id";
|
||||
import {
|
||||
listConfiguredAccountIds,
|
||||
resolveNormalizedAccountEntry,
|
||||
} from "openclaw/plugin-sdk/account-resolution";
|
||||
import { DEFAULT_ACCOUNT_ID } from "../runtime-api.js";
|
||||
import type { CoreConfig, MatrixAccountConfig, MatrixConfig } from "../types.js";
|
||||
|
||||
@@ -15,34 +19,21 @@ function resolveMatrixAccountsMap(cfg: CoreConfig): Readonly<Record<string, Matr
|
||||
}
|
||||
|
||||
export function listNormalizedMatrixAccountIds(cfg: CoreConfig): string[] {
|
||||
return [
|
||||
...new Set(
|
||||
Object.keys(resolveMatrixAccountsMap(cfg))
|
||||
.filter(Boolean)
|
||||
.map((accountId) => normalizeAccountId(accountId)),
|
||||
),
|
||||
];
|
||||
return listConfiguredAccountIds({
|
||||
accounts: resolveMatrixAccountsMap(cfg),
|
||||
normalizeAccountId,
|
||||
});
|
||||
}
|
||||
|
||||
export function findMatrixAccountConfig(
|
||||
cfg: CoreConfig,
|
||||
accountId: string,
|
||||
): MatrixAccountConfig | undefined {
|
||||
const accounts = resolveMatrixAccountsMap(cfg);
|
||||
if (accounts[accountId] && typeof accounts[accountId] === "object") {
|
||||
return accounts[accountId];
|
||||
}
|
||||
const normalized = normalizeAccountId(accountId);
|
||||
for (const key of Object.keys(accounts)) {
|
||||
if (normalizeAccountId(key) === normalized) {
|
||||
const candidate = accounts[key];
|
||||
if (candidate && typeof candidate === "object") {
|
||||
return candidate;
|
||||
}
|
||||
return undefined;
|
||||
}
|
||||
}
|
||||
return undefined;
|
||||
return resolveNormalizedAccountEntry(
|
||||
resolveMatrixAccountsMap(cfg),
|
||||
accountId,
|
||||
normalizeAccountId,
|
||||
);
|
||||
}
|
||||
|
||||
export function hasExplicitMatrixAccountConfig(cfg: CoreConfig, accountId: string): boolean {
|
||||
|
||||
@@ -3,6 +3,10 @@ import {
|
||||
normalizeAccountId,
|
||||
normalizeOptionalAccountId,
|
||||
} from "openclaw/plugin-sdk/account-id";
|
||||
import {
|
||||
listCombinedAccountIds,
|
||||
resolveListedDefaultAccountId,
|
||||
} from "openclaw/plugin-sdk/account-resolution";
|
||||
import type { OpenClawConfig } from "../api.js";
|
||||
import type { NostrProfile } from "./config-schema.js";
|
||||
import { DEFAULT_RELAYS } from "./default-relays.js";
|
||||
@@ -45,28 +49,22 @@ export function listNostrAccountIds(cfg: OpenClawConfig): string[] {
|
||||
const nostrCfg = (cfg.channels as Record<string, unknown> | undefined)?.nostr as
|
||||
| NostrAccountConfig
|
||||
| undefined;
|
||||
|
||||
// If privateKey is configured at top level, we have a default account
|
||||
if (nostrCfg?.privateKey) {
|
||||
return [resolveConfiguredDefaultNostrAccountId(cfg) ?? DEFAULT_ACCOUNT_ID];
|
||||
}
|
||||
|
||||
return [];
|
||||
return listCombinedAccountIds({
|
||||
configuredAccountIds: [],
|
||||
implicitAccountId: nostrCfg?.privateKey
|
||||
? (resolveConfiguredDefaultNostrAccountId(cfg) ?? DEFAULT_ACCOUNT_ID)
|
||||
: undefined,
|
||||
});
|
||||
}
|
||||
|
||||
/**
|
||||
* Get the default account ID
|
||||
*/
|
||||
export function resolveDefaultNostrAccountId(cfg: OpenClawConfig): string {
|
||||
const preferred = resolveConfiguredDefaultNostrAccountId(cfg);
|
||||
if (preferred) {
|
||||
return preferred;
|
||||
}
|
||||
const ids = listNostrAccountIds(cfg);
|
||||
if (ids.includes(DEFAULT_ACCOUNT_ID)) {
|
||||
return DEFAULT_ACCOUNT_ID;
|
||||
}
|
||||
return ids[0] ?? DEFAULT_ACCOUNT_ID;
|
||||
return resolveListedDefaultAccountId({
|
||||
accountIds: listNostrAccountIds(cfg),
|
||||
configuredDefaultAccountId: resolveConfiguredDefaultNostrAccountId(cfg),
|
||||
});
|
||||
}
|
||||
|
||||
/**
|
||||
|
||||
@@ -2,10 +2,11 @@ import util from "node:util";
|
||||
import {
|
||||
createAccountActionGate,
|
||||
DEFAULT_ACCOUNT_ID,
|
||||
listConfiguredAccountIds as listConfiguredAccountIdsFromSection,
|
||||
listCombinedAccountIds,
|
||||
normalizeAccountId,
|
||||
normalizeOptionalAccountId,
|
||||
resolveAccountEntry,
|
||||
resolveListedDefaultAccountId,
|
||||
resolveAccountWithDefaultFallback,
|
||||
type OpenClawConfig,
|
||||
} from "openclaw/plugin-sdk/account-resolution";
|
||||
@@ -55,21 +56,23 @@ export type ResolvedTelegramAccount = {
|
||||
};
|
||||
|
||||
function listConfiguredAccountIds(cfg: OpenClawConfig): string[] {
|
||||
return listConfiguredAccountIdsFromSection({
|
||||
accounts: cfg.channels?.telegram?.accounts,
|
||||
normalizeAccountId,
|
||||
});
|
||||
const ids = new Set<string>();
|
||||
for (const key of Object.keys(cfg.channels?.telegram?.accounts ?? {})) {
|
||||
if (key) {
|
||||
ids.add(normalizeAccountId(key));
|
||||
}
|
||||
}
|
||||
return [...ids];
|
||||
}
|
||||
|
||||
export function listTelegramAccountIds(cfg: OpenClawConfig): string[] {
|
||||
const ids = Array.from(
|
||||
new Set([...listConfiguredAccountIds(cfg), ...listBoundAccountIds(cfg, "telegram")]),
|
||||
);
|
||||
const ids = listCombinedAccountIds({
|
||||
configuredAccountIds: listConfiguredAccountIds(cfg),
|
||||
additionalAccountIds: listBoundAccountIds(cfg, "telegram"),
|
||||
fallbackAccountIdWhenEmpty: DEFAULT_ACCOUNT_ID,
|
||||
});
|
||||
debugAccounts("listTelegramAccountIds", ids);
|
||||
if (ids.length === 0) {
|
||||
return [DEFAULT_ACCOUNT_ID];
|
||||
}
|
||||
return ids.toSorted((a, b) => a.localeCompare(b));
|
||||
return ids;
|
||||
}
|
||||
|
||||
let emittedMissingDefaultWarn = false;
|
||||
@@ -84,16 +87,13 @@ export function resolveDefaultTelegramAccountId(cfg: OpenClawConfig): string {
|
||||
if (boundDefault) {
|
||||
return boundDefault;
|
||||
}
|
||||
const preferred = normalizeOptionalAccountId(cfg.channels?.telegram?.defaultAccount);
|
||||
if (
|
||||
preferred &&
|
||||
listTelegramAccountIds(cfg).some((accountId) => normalizeAccountId(accountId) === preferred)
|
||||
) {
|
||||
return preferred;
|
||||
}
|
||||
const ids = listTelegramAccountIds(cfg);
|
||||
if (ids.includes(DEFAULT_ACCOUNT_ID)) {
|
||||
return DEFAULT_ACCOUNT_ID;
|
||||
const resolved = resolveListedDefaultAccountId({
|
||||
accountIds: ids,
|
||||
configuredDefaultAccountId: normalizeOptionalAccountId(cfg.channels?.telegram?.defaultAccount),
|
||||
});
|
||||
if (resolved !== ids[0] || ids.includes(DEFAULT_ACCOUNT_ID) || ids.length <= 1) {
|
||||
return resolved;
|
||||
}
|
||||
if (ids.length > 1 && !emittedMissingDefaultWarn) {
|
||||
emittedMissingDefaultWarn = true;
|
||||
@@ -102,7 +102,7 @@ export function resolveDefaultTelegramAccountId(cfg: OpenClawConfig): string {
|
||||
`${formatSetExplicitDefaultInstruction("telegram")} to avoid routing surprises in multi-account setups.`,
|
||||
);
|
||||
}
|
||||
return ids[0] ?? DEFAULT_ACCOUNT_ID;
|
||||
return resolved;
|
||||
}
|
||||
|
||||
export function resolveTelegramAccountConfig(
|
||||
|
||||
@@ -1,5 +1,5 @@
|
||||
import { describe, expect, it } from "vitest";
|
||||
import { getAccountConfig } from "./config.js";
|
||||
import { getAccountConfig, listAccountIds } from "./config.js";
|
||||
|
||||
describe("getAccountConfig", () => {
|
||||
const mockMultiAccountConfig = {
|
||||
@@ -85,3 +85,34 @@ describe("getAccountConfig", () => {
|
||||
expect(result).toBeNull();
|
||||
});
|
||||
});
|
||||
|
||||
describe("listAccountIds", () => {
|
||||
it("includes the implicit default account from simplified config", () => {
|
||||
expect(
|
||||
listAccountIds({
|
||||
channels: {
|
||||
twitch: {
|
||||
username: "testbot",
|
||||
accessToken: "oauth:test123",
|
||||
},
|
||||
},
|
||||
} as Parameters<typeof listAccountIds>[0]),
|
||||
).toEqual(["default"]);
|
||||
});
|
||||
|
||||
it("combines explicit accounts with the implicit default account once", () => {
|
||||
expect(
|
||||
listAccountIds({
|
||||
channels: {
|
||||
twitch: {
|
||||
username: "testbot",
|
||||
accounts: {
|
||||
default: { username: "testbot" },
|
||||
secondary: { username: "secondbot" },
|
||||
},
|
||||
},
|
||||
},
|
||||
} as Parameters<typeof listAccountIds>[0]),
|
||||
).toEqual(["default", "secondary"]);
|
||||
});
|
||||
});
|
||||
|
||||
@@ -1,3 +1,4 @@
|
||||
import { listCombinedAccountIds } from "openclaw/plugin-sdk/account-resolution";
|
||||
import type { OpenClawConfig } from "../runtime-api.js";
|
||||
import type { TwitchAccountConfig } from "./types.js";
|
||||
|
||||
@@ -94,13 +95,6 @@ export function listAccountIds(cfg: OpenClawConfig): string[] {
|
||||
const twitchRaw = twitch as Record<string, unknown> | undefined;
|
||||
const accountMap = twitchRaw?.accounts as Record<string, unknown> | undefined;
|
||||
|
||||
const ids: string[] = [];
|
||||
|
||||
// Add explicit accounts
|
||||
if (accountMap) {
|
||||
ids.push(...Object.keys(accountMap));
|
||||
}
|
||||
|
||||
// Add implicit "default" if base-level config exists and "default" not already present
|
||||
const hasBaseLevelConfig =
|
||||
twitchRaw &&
|
||||
@@ -108,9 +102,8 @@ export function listAccountIds(cfg: OpenClawConfig): string[] {
|
||||
typeof twitchRaw.accessToken === "string" ||
|
||||
typeof twitchRaw.channel === "string");
|
||||
|
||||
if (hasBaseLevelConfig && !ids.includes(DEFAULT_ACCOUNT_ID)) {
|
||||
ids.push(DEFAULT_ACCOUNT_ID);
|
||||
}
|
||||
|
||||
return ids;
|
||||
return listCombinedAccountIds({
|
||||
configuredAccountIds: Object.keys(accountMap ?? {}),
|
||||
implicitAccountId: hasBaseLevelConfig ? DEFAULT_ACCOUNT_ID : undefined,
|
||||
});
|
||||
}
|
||||
|
||||
@@ -3,7 +3,9 @@ import type { OpenClawConfig } from "../../config/config.js";
|
||||
import { normalizeAccountId } from "../../routing/session-key.js";
|
||||
import {
|
||||
createAccountListHelpers,
|
||||
listCombinedAccountIds,
|
||||
mergeAccountConfig,
|
||||
resolveListedDefaultAccountId,
|
||||
resolveMergedAccountConfig,
|
||||
} from "./account-helpers.js";
|
||||
|
||||
@@ -124,6 +126,74 @@ describe("createAccountListHelpers", () => {
|
||||
});
|
||||
});
|
||||
|
||||
describe("listCombinedAccountIds", () => {
|
||||
it("combines configured, additional, and implicit ids once", () => {
|
||||
expect(
|
||||
listCombinedAccountIds({
|
||||
configuredAccountIds: ["work", "alerts"],
|
||||
additionalAccountIds: ["default", "alerts"],
|
||||
implicitAccountId: "ops",
|
||||
}),
|
||||
).toEqual(["alerts", "default", "ops", "work"]);
|
||||
});
|
||||
|
||||
it("uses the fallback id when no accounts are present", () => {
|
||||
expect(
|
||||
listCombinedAccountIds({
|
||||
configuredAccountIds: [],
|
||||
fallbackAccountIdWhenEmpty: "default",
|
||||
}),
|
||||
).toEqual(["default"]);
|
||||
});
|
||||
});
|
||||
|
||||
describe("resolveListedDefaultAccountId", () => {
|
||||
it("prefers the configured default when present in the listed ids", () => {
|
||||
expect(
|
||||
resolveListedDefaultAccountId({
|
||||
accountIds: ["alerts", "work"],
|
||||
configuredDefaultAccountId: "work",
|
||||
}),
|
||||
).toBe("work");
|
||||
});
|
||||
|
||||
it("matches configured defaults against normalized listed ids", () => {
|
||||
expect(
|
||||
resolveListedDefaultAccountId({
|
||||
accountIds: ["Router D"],
|
||||
configuredDefaultAccountId: "router-d",
|
||||
}),
|
||||
).toBe("router-d");
|
||||
});
|
||||
|
||||
it("prefers the default account id when listed", () => {
|
||||
expect(
|
||||
resolveListedDefaultAccountId({
|
||||
accountIds: ["default", "work"],
|
||||
}),
|
||||
).toBe("default");
|
||||
});
|
||||
|
||||
it("can preserve an unlisted configured default", () => {
|
||||
expect(
|
||||
resolveListedDefaultAccountId({
|
||||
accountIds: ["default", "work"],
|
||||
configuredDefaultAccountId: "ops",
|
||||
allowUnlistedDefaultAccount: true,
|
||||
}),
|
||||
).toBe("ops");
|
||||
});
|
||||
|
||||
it("supports an explicit fallback id for ambiguous multi-account setups", () => {
|
||||
expect(
|
||||
resolveListedDefaultAccountId({
|
||||
accountIds: ["alerts", "work"],
|
||||
ambiguousFallbackAccountId: "default",
|
||||
}),
|
||||
).toBe("default");
|
||||
});
|
||||
});
|
||||
|
||||
describe("mergeAccountConfig", () => {
|
||||
it("drops accounts from the base config before merging", () => {
|
||||
const merged = mergeAccountConfig<{
|
||||
|
||||
@@ -49,28 +49,76 @@ export function createAccountListHelpers(
|
||||
}
|
||||
|
||||
function listAccountIds(cfg: OpenClawConfig): string[] {
|
||||
const ids = listConfiguredAccountIds(cfg);
|
||||
if (ids.length === 0) {
|
||||
return [DEFAULT_ACCOUNT_ID];
|
||||
}
|
||||
return ids.toSorted((a, b) => a.localeCompare(b));
|
||||
return listCombinedAccountIds({
|
||||
configuredAccountIds: listConfiguredAccountIds(cfg),
|
||||
fallbackAccountIdWhenEmpty: DEFAULT_ACCOUNT_ID,
|
||||
});
|
||||
}
|
||||
|
||||
function resolveDefaultAccountId(cfg: OpenClawConfig): string {
|
||||
const preferred = resolveConfiguredDefaultAccountId(cfg);
|
||||
if (preferred) {
|
||||
return preferred;
|
||||
}
|
||||
const ids = listAccountIds(cfg);
|
||||
if (ids.includes(DEFAULT_ACCOUNT_ID)) {
|
||||
return DEFAULT_ACCOUNT_ID;
|
||||
}
|
||||
return ids[0] ?? DEFAULT_ACCOUNT_ID;
|
||||
return resolveListedDefaultAccountId({
|
||||
accountIds: listAccountIds(cfg),
|
||||
configuredDefaultAccountId: resolveConfiguredDefaultAccountId(cfg),
|
||||
allowUnlistedDefaultAccount: options?.allowUnlistedDefaultAccount,
|
||||
});
|
||||
}
|
||||
|
||||
return { listConfiguredAccountIds, listAccountIds, resolveDefaultAccountId };
|
||||
}
|
||||
|
||||
export function listCombinedAccountIds(params: {
|
||||
configuredAccountIds: Iterable<string>;
|
||||
additionalAccountIds?: Iterable<string>;
|
||||
implicitAccountId?: string | undefined;
|
||||
fallbackAccountIdWhenEmpty?: string | undefined;
|
||||
}): string[] {
|
||||
const ids = new Set<string>();
|
||||
|
||||
for (const id of params.configuredAccountIds) {
|
||||
if (id) {
|
||||
ids.add(id);
|
||||
}
|
||||
}
|
||||
for (const id of params.additionalAccountIds ?? []) {
|
||||
if (id) {
|
||||
ids.add(id);
|
||||
}
|
||||
}
|
||||
if (params.implicitAccountId) {
|
||||
ids.add(params.implicitAccountId);
|
||||
}
|
||||
|
||||
if (ids.size === 0 && params.fallbackAccountIdWhenEmpty) {
|
||||
return [params.fallbackAccountIdWhenEmpty];
|
||||
}
|
||||
return [...ids].toSorted((a, b) => a.localeCompare(b));
|
||||
}
|
||||
|
||||
export function resolveListedDefaultAccountId(params: {
|
||||
accountIds: readonly string[];
|
||||
configuredDefaultAccountId?: string | undefined;
|
||||
allowUnlistedDefaultAccount?: boolean;
|
||||
ambiguousFallbackAccountId?: string | undefined;
|
||||
normalizeListedAccountId?: ((accountId: string) => string) | undefined;
|
||||
}): string {
|
||||
const preferred = params.configuredDefaultAccountId;
|
||||
const normalizeListedAccountId = params.normalizeListedAccountId ?? normalizeAccountId;
|
||||
if (
|
||||
preferred &&
|
||||
(params.allowUnlistedDefaultAccount ||
|
||||
params.accountIds.some((accountId) => normalizeListedAccountId(accountId) === preferred))
|
||||
) {
|
||||
return preferred;
|
||||
}
|
||||
if (params.accountIds.includes(DEFAULT_ACCOUNT_ID)) {
|
||||
return DEFAULT_ACCOUNT_ID;
|
||||
}
|
||||
if (params.ambiguousFallbackAccountId && params.accountIds.length > 1) {
|
||||
return params.ambiguousFallbackAccountId;
|
||||
}
|
||||
return params.accountIds[0] ?? DEFAULT_ACCOUNT_ID;
|
||||
}
|
||||
|
||||
export function mergeAccountConfig<TConfig extends Record<string, unknown>>(params: {
|
||||
channelConfig: TConfig | undefined;
|
||||
accountConfig: Partial<TConfig> | undefined;
|
||||
|
||||
@@ -1,3 +1,7 @@
|
||||
import {
|
||||
listCombinedAccountIds,
|
||||
resolveListedDefaultAccountId,
|
||||
} from "../channels/plugins/account-helpers.js";
|
||||
import type { OpenClawConfig } from "../config/config.js";
|
||||
import { tryReadSecretFileSync } from "../infra/secret-file.js";
|
||||
import {
|
||||
@@ -151,43 +155,32 @@ export function resolveLineAccount(params: {
|
||||
|
||||
export function listLineAccountIds(cfg: OpenClawConfig): string[] {
|
||||
const lineConfig = cfg.channels?.line as LineConfig | undefined;
|
||||
const accounts = lineConfig?.accounts;
|
||||
const ids = new Set<string>();
|
||||
|
||||
// Add default account if configured at base level
|
||||
if (
|
||||
const hasBaseCredentials = Boolean(
|
||||
lineConfig?.channelAccessToken?.trim() ||
|
||||
lineConfig?.tokenFile ||
|
||||
process.env.LINE_CHANNEL_ACCESS_TOKEN?.trim()
|
||||
) {
|
||||
ids.add(DEFAULT_ACCOUNT_ID);
|
||||
}
|
||||
|
||||
// Add named accounts
|
||||
if (accounts) {
|
||||
for (const id of Object.keys(accounts)) {
|
||||
ids.add(id);
|
||||
}
|
||||
}
|
||||
|
||||
return Array.from(ids);
|
||||
process.env.LINE_CHANNEL_ACCESS_TOKEN?.trim(),
|
||||
);
|
||||
const preferred = normalizeOptionalAccountId(lineConfig?.defaultAccount);
|
||||
const configuredAccountIds = [
|
||||
...new Set(
|
||||
Object.keys(lineConfig?.accounts ?? {})
|
||||
.filter(Boolean)
|
||||
.map(normalizeSharedAccountId),
|
||||
),
|
||||
];
|
||||
return listCombinedAccountIds({
|
||||
configuredAccountIds,
|
||||
implicitAccountId: hasBaseCredentials ? (preferred ?? DEFAULT_ACCOUNT_ID) : undefined,
|
||||
});
|
||||
}
|
||||
|
||||
export function resolveDefaultLineAccountId(cfg: OpenClawConfig): string {
|
||||
const preferred = normalizeOptionalAccountId(
|
||||
(cfg.channels?.line as LineConfig | undefined)?.defaultAccount,
|
||||
);
|
||||
if (
|
||||
preferred &&
|
||||
listLineAccountIds(cfg).some((accountId) => normalizeSharedAccountId(accountId) === preferred)
|
||||
) {
|
||||
return preferred;
|
||||
}
|
||||
const ids = listLineAccountIds(cfg);
|
||||
if (ids.includes(DEFAULT_ACCOUNT_ID)) {
|
||||
return DEFAULT_ACCOUNT_ID;
|
||||
}
|
||||
return ids[0] ?? DEFAULT_ACCOUNT_ID;
|
||||
return resolveListedDefaultAccountId({
|
||||
accountIds: listLineAccountIds(cfg),
|
||||
configuredDefaultAccountId: normalizeOptionalAccountId(
|
||||
(cfg.channels?.line as LineConfig | undefined)?.defaultAccount,
|
||||
),
|
||||
});
|
||||
}
|
||||
|
||||
export function normalizeAccountId(accountId: string | undefined): string {
|
||||
|
||||
@@ -3,7 +3,9 @@ export type { OpenClawConfig } from "../config/config.js";
|
||||
export { createAccountActionGate } from "../channels/plugins/account-action-gate.js";
|
||||
export {
|
||||
createAccountListHelpers,
|
||||
listCombinedAccountIds,
|
||||
mergeAccountConfig,
|
||||
resolveListedDefaultAccountId,
|
||||
resolveMergedAccountConfig,
|
||||
} from "../channels/plugins/account-helpers.js";
|
||||
export { normalizeChatType } from "../channels/chat-type.js";
|
||||
|
||||
Reference in New Issue
Block a user