fix(secrets): also normalize openclaw_gateway deviceToken

Greptile P1: execute.ts reads a top-level `deviceToken` from adapterConfig
and sends it as gateway authentication material alongside authToken and
password, so it must be normalized too. Confirmed at
packages/adapters/openclaw-gateway/src/server/execute.ts:1071,1252,1255.

Extends the regression test to cover it.

Co-Authored-By: Claude Opus 5 <noreply@anthropic.com>
This commit is contained in:
spuhaha18 2026-08-07 20:14:03 +09:00
parent 1eba85bc1c
commit 8dbec8ba8e
2 changed files with 7 additions and 2 deletions

View File

@ -266,6 +266,7 @@ describeEmbeddedPostgres("agent service secret binding sync", () => {
const companyId = await seedCompany();
const literalAuthToken = `openclaw-token-${randomUUID()}`;
const literalPassword = `openclaw-password-${randomUUID()}`;
const literalDeviceToken = `openclaw-device-token-${randomUUID()}`;
const literalPrivateKeyPem = [
"-----BEGIN PRIVATE KEY-----",
`openclaw-device-key-${randomUUID()}`,
@ -281,6 +282,7 @@ describeEmbeddedPostgres("agent service secret binding sync", () => {
url: "ws://127.0.0.1:18789",
authToken: literalAuthToken,
password: literalPassword,
deviceToken: literalDeviceToken,
devicePrivateKeyPem: literalPrivateKeyPem,
},
runtimeConfig: {},
@ -296,8 +298,9 @@ describeEmbeddedPostgres("agent service secret binding sync", () => {
const serializedConfig = JSON.stringify(persistedConfig);
expect(serializedConfig).not.toContain(literalAuthToken);
expect(serializedConfig).not.toContain(literalPassword);
expect(serializedConfig).not.toContain(literalDeviceToken);
expect(serializedConfig).not.toContain(literalPrivateKeyPem);
for (const key of ["authToken", "password", "devicePrivateKeyPem"]) {
for (const key of ["authToken", "password", "deviceToken", "devicePrivateKeyPem"]) {
expect(persistedConfig[key]).toMatchObject({
type: "secret_ref",
version: "latest",
@ -316,6 +319,7 @@ describeEmbeddedPostgres("agent service secret binding sync", () => {
expect(bindings.map((binding) => binding.configPath).sort()).toEqual([
"authToken",
"devicePrivateKeyPem",
"deviceToken",
"password",
]);
@ -330,6 +334,7 @@ describeEmbeddedPostgres("agent service secret binding sync", () => {
);
expect(resolved.config.authToken).toBe(literalAuthToken);
expect(resolved.config.password).toBe(literalPassword);
expect(resolved.config.deviceToken).toBe(literalDeviceToken);
expect(resolved.config.devicePrivateKeyPem).toBe(literalPrivateKeyPem);
});

View File

@ -77,7 +77,7 @@ const COMING_SOON_SECRET_PROVIDERS: ReadonlySet<SecretProvider> = new Set([
]);
const FALLBACK_ADAPTER_SCHEMA_SECRET_FIELDS: Readonly<Record<string, readonly string[]>> = {
hermes_gateway: ["apiKey"],
openclaw_gateway: ["authToken", "token", "password", "devicePrivateKeyPem"],
openclaw_gateway: ["authToken", "token", "deviceToken", "password", "devicePrivateKeyPem"],
};
const USER_SECRET_DEFINITION_KEY_UNIQUE_CONSTRAINT = "user_secret_definitions_company_key_uq";
const USER_SECRET_VALUE_UNIQUE_CONSTRAINT = "company_secrets_user_definition_owner_uq";