fix(plugin): remediate ML-07 R2 findings

This commit is contained in:
2026-08-27 21:16:27 +08:00
parent 29cf322f1a
commit f0ac7d70d1
10 changed files with 381 additions and 29 deletions

View File

@@ -10,7 +10,6 @@ import type {
} from '../../../shared/data-service';
import {
DATA_SERVICE_PLUGIN_ID,
DATA_SERVICE_TOOL_DEFINITIONS,
type CodingPluginToolDefinition,
} from '../../../shared/coding-plugins';
import type { DataServiceOperations } from '../../services/data-service-client';
@@ -170,10 +169,6 @@ type DataServiceResult =
| DataServiceInstanceRemoval
| null;
function toolByName(toolName: string): CodingPluginToolDefinition | undefined {
return DATA_SERVICE_TOOL_DEFINITIONS.find(({ name }) => name === toolName);
}
async function callDataService(
operations: DataServiceOperations,
toolName: string,
@@ -271,14 +266,13 @@ export class DataServicePluginAdapter implements CodingPluginAdapter {
tool: CodingPluginToolDefinition,
input: unknown,
): Promise<AdapterInvocationResult<DataServiceResult>> {
const canonicalTool = toolByName(tool.name);
if (!canonicalTool || !validateInput(canonicalTool, input)) {
if (!validateInput(tool, input)) {
return failure('plugin_input_invalid', 'Data Service tool input is invalid');
}
try {
return projectResult(await callDataService(
this.operations,
canonicalTool.name,
tool.name,
input as InputRecord,
_context.projectPath,
));

View File

@@ -113,7 +113,10 @@ export interface CodingCapabilityRegistryPort {
export type CodingCapabilityRegistry = CodingCapabilityRegistryPort;
export interface CodingCapabilityRegistryOptions {
policyClient: Pick<{ getState(): PluginPolicyClientState }, 'getState'>;
policyClient: {
getState(): PluginPolicyClientState;
refresh(): Promise<void>;
};
getEnabledPluginIds?: (projectPath: string) => Promise<readonly string[]>;
projectPlugins?: {
getEnabledPluginIds(projectPath: string): Promise<readonly string[]>;
@@ -375,6 +378,21 @@ export class CodingCapabilityRegistryImpl implements CodingCapabilityRegistryPor
tools: [],
};
}
const hasAssignedServerPlugin = this.definitions.some((definition) => (
definition.requiresBackend
&& this.adaptersByPluginId.has(definition.id)
&& definition.skills.some(({ id }) => assigned.includes(id))
));
if (!hasAssignedServerPlugin) {
return {
catalogRevision: this.options.policyClient.getState().revision,
pluginIds: [],
effectiveSkillIds: effectiveCoreSkills,
skillEntries: effectiveCoreSkills.map((id) => ({ id, entryPath: `${id}/SKILL.md` })),
tools: [],
};
}
await this.options.policyClient.refresh();
const enabled = await this.enabledPluginIds(input.projectPath);
const state = this.options.policyClient.getState();
const pluginIds: string[] = [];