function parseJson(str) { try {
    return JSON.parse(str);
}
catch {
    return null;
} }
function isObject(v) { return !!v && typeof v === 'object' && !Array.isArray(v); }
/**
 * Whitelist tool function arguments keys after decode to match schema (e.g., keep only 'command'/'workdir').
 * Stage: response_pre. Runs after TOON decode and before stringify.
 */
export class ResponseToolArgumentsWhitelistFilter {
    name = 'response_tool_arguments_whitelist';
    stage = 'response_pre';
    getWhitelist(_ctx) {
        // For now, keep minimal keys for shell schema. Can be extended/configured later.
        const env = String(process?.env?.ROUTECODEX_SHELL_ARGS_KEYS || '').trim();
        if (env)
            return env.split(',').map(s => s.trim()).filter(Boolean);
        return ['command', 'workdir'];
    }
    apply(input, context) {
        try {
            const out = JSON.parse(JSON.stringify(input || {}));
            const choices = Array.isArray(out.choices) ? out.choices : [];
            const keys = this.getWhitelist(context);
            for (const ch of choices) {
                const msg = ch && ch.message ? ch.message : undefined;
                const tcs = msg && Array.isArray(msg.tool_calls) ? msg.tool_calls : [];
                for (const tc of tcs) {
                    const fn = tc && tc.function ? tc.function : undefined;
                    const argStr = fn && typeof fn.arguments === 'string' ? fn.arguments : undefined;
                    if (!argStr)
                        continue;
                    const parsed = parseJson(argStr);
                    if (!isObject(parsed))
                        continue;
                    const whitelisted = {};
                    for (const k of keys) {
                        if (k in parsed)
                            whitelisted[k] = parsed[k];
                    }
                    try {
                        fn.arguments = JSON.stringify(whitelisted);
                    }
                    catch { /* keep original */ }
                }
            }
            out.choices = choices;
            return { ok: true, data: out };
        }
        catch {
            return { ok: true, data: input };
        }
    }
}
