Log warning for unrecognised keys in Default Setup config

This commit is contained in:
Michael B. Gale
2026-07-10 00:11:17 +01:00
parent 9573f05654
commit 847e7af699
3 changed files with 405 additions and 308 deletions

650
lib/entry-points.js generated

File diff suppressed because it is too large Load Diff

View File

@@ -561,3 +561,24 @@ test("mergeDefaultSetupAndUserConfigs - keeps other properties from user-supplie
t.deepEqual(result, configFile); t.deepEqual(result, configFile);
}); });
test("mergeDefaultSetupAndUserConfigs - ignores, but warns about, unknown keys from Default Setup", async (t) => {
const logger = new RecordingLogger();
const configFile: dbConfig.UserConfig = {
"query-filters": [{ exclude: { a: "b" } }],
"paths-ignore": ["path"],
};
const result = dbConfig.mergeDefaultSetupAndUserConfigs(
logger,
{
"paths-ignore": ["other-path"],
},
configFile,
);
t.deepEqual(result, configFile);
checkExpectedLogMessages(t, logger.messages, [
"Unrecognised keys in Default Setup configuration: paths-ignore",
]);
});

View File

@@ -9,6 +9,7 @@ import {
RepositoryProperties, RepositoryProperties,
RepositoryPropertyName, RepositoryPropertyName,
} from "../feature-flags/properties"; } from "../feature-flags/properties";
import * as json from "../json";
import { Language } from "../languages"; import { Language } from "../languages";
import { Logger } from "../logging"; import { Logger } from "../logging";
import { cloneObject, ConfigurationError, prettyPrintPack } from "../util"; import { cloneObject, ConfigurationError, prettyPrintPack } from "../util";
@@ -28,13 +29,20 @@ export interface QuerySpec {
uses: string; uses: string;
} }
const ORG_SCHEMA = {
/** An array of model pack names. */
"model-packs": json.optional(json.array(json.string)),
} as const satisfies json.Schema;
/** Not intended to be provided directly by a user. */ /** Not intended to be provided directly by a user. */
export interface DefaultSetupConfig { export type OrgType = json.FromSchema<typeof ORG_SCHEMA>;
org?: {
/** An array of model pack names. */ const DEFAULT_SETUP_SCHEMA = {
"model-packs"?: string[]; org: json.optional<OrgType>(json.object(ORG_SCHEMA)),
}; } as const satisfies json.Schema;
}
/** Not intended to be provided directly by a user. */
export type DefaultSetupConfig = json.FromSchema<typeof DEFAULT_SETUP_SCHEMA>;
/** /**
* Format of the config file supplied by the user. * Format of the config file supplied by the user.
@@ -65,6 +73,14 @@ export interface UserConfig {
"default-setup"?: DefaultSetupConfig; "default-setup"?: DefaultSetupConfig;
} }
/** A subset of the `UserConfig` schema that is used by Default Setup. */
const DEFAULT_SETUP_CONFIG_SCHEMA = {
"threat-models": json.optional(json.array(json.string)),
"default-setup": json.optional<DefaultSetupConfig>(
json.object(DEFAULT_SETUP_SCHEMA),
),
} as const satisfies json.Schema;
/** /**
* Merges supported properties from two configuration files. This is intended only for * Merges supported properties from two configuration files. This is intended only for
* use with merging the `config` input provided by Default Setup with a potentially * use with merging the `config` input provided by Default Setup with a potentially
@@ -84,6 +100,20 @@ export function mergeDefaultSetupAndUserConfigs(
"Combining configuration files from 'config' and 'config-file' inputs", "Combining configuration files from 'config' and 'config-file' inputs",
); );
// Check for unexpected keys in the configuration from the `config` input
// that was provided by Default Setup. This should only contain the keys
// we would expect to receive from Default Setup.
const schemaCheckResult = json.checkSchema(
DEFAULT_SETUP_CONFIG_SCHEMA,
fromConfigInput as json.UnvalidatedObject<any>,
);
if (schemaCheckResult.unknownKeys.length > 0) {
logger.warning(
`Unrecognised keys in Default Setup configuration: ${schemaCheckResult.unknownKeys.join(", ")}`,
);
}
// Combine all specified threat models from both sources. // Combine all specified threat models from both sources.
const threatModels = new Set(fromConfigInput["threat-models"] || []); const threatModels = new Set(fromConfigInput["threat-models"] || []);
for (const configFileThreatModel of fromConfigFile["threat-models"] || []) { for (const configFileThreatModel of fromConfigFile["threat-models"] || []) {