import { describe, it } from 'node:test'; import assert from 'node:assert/strict'; import { assessMcpDeferral, severityForForcedSchemas, FORCED_SCHEMA_TOKENS_HIGH, FORCED_SCHEMA_TOKENS_MEDIUM, } from '../../scanners/lib/mcp-deferral.mjs'; // A small helper to build server shapes the way active-config-reader exposes them. const srv = (over = {}) => ({ name: 'srv', source: '.mcp.json', enabled: true, toolCount: 10, estimatedTokens: 2500, alwaysLoad: false, ...over, }); describe('assessMcpDeferral — default (deferred) case', () => { it('no settings + a plain server → tool search NOT disabled, nothing forced upfront', () => { const a = assessMcpDeferral({ settings: {}, mcpServers: [srv()] }); assert.equal(a.toolSearchDisabled, false); assert.equal(a.reason, null); assert.equal(a.confidence, null); assert.equal(a.forcedUpfront, false); assert.deepEqual(a.affectedServers, []); assert.equal(a.aggregateTokens, 0); }); it('empty inputs are tolerated', () => { const a = assessMcpDeferral({}); assert.equal(a.toolSearchDisabled, false); assert.equal(a.forcedUpfront, false); }); }); describe('assessMcpDeferral — config-file disabling signals (HIGH confidence)', () => { it('settings.env.ENABLE_TOOL_SEARCH="false" → disabled, high, all servers affected', () => { const a = assessMcpDeferral({ settings: { env: { ENABLE_TOOL_SEARCH: 'false' } }, mcpServers: [srv({ name: 'a', estimatedTokens: 1000 }), srv({ name: 'b', estimatedTokens: 2000 })], }); assert.equal(a.toolSearchDisabled, true); assert.equal(a.reason, 'enable-tool-search-false'); assert.equal(a.confidence, 'high'); assert.equal(a.forcedUpfront, true); assert.equal(a.affectedServers.length, 2); assert.equal(a.aggregateTokens, 3000); }); it('permissions.deny including bare "ToolSearch" → disabled, high', () => { const a = assessMcpDeferral({ settings: { permissions: { deny: ['Read(./.env)', 'ToolSearch'] } }, mcpServers: [srv()], }); assert.equal(a.toolSearchDisabled, true); assert.equal(a.reason, 'deny-tool-search'); assert.equal(a.confidence, 'high'); }); it('explicit ENABLE_TOOL_SEARCH="false" wins over a haiku model for the reason label', () => { const a = assessMcpDeferral({ settings: { env: { ENABLE_TOOL_SEARCH: 'false' }, model: 'claude-haiku-4-5' }, mcpServers: [srv()], }); assert.equal(a.toolSearchDisabled, true); assert.equal(a.reason, 'enable-tool-search-false'); assert.equal(a.confidence, 'high'); }); }); describe('assessMcpDeferral — configured Haiku model (MEDIUM confidence)', () => { it('settings.model matching /haiku/ → disabled, medium, haiku-model', () => { const a = assessMcpDeferral({ settings: { model: 'claude-haiku-4-5-20251001' }, mcpServers: [srv()], }); assert.equal(a.toolSearchDisabled, true); assert.equal(a.reason, 'haiku-model'); assert.equal(a.confidence, 'medium'); assert.equal(a.forcedUpfront, true); }); it('haiku disables even when ENABLE_TOOL_SEARCH="true" (Haiku lacks tool_reference support)', () => { const a = assessMcpDeferral({ settings: { env: { ENABLE_TOOL_SEARCH: 'true' }, model: 'haiku' }, mcpServers: [srv()], }); assert.equal(a.toolSearchDisabled, true); assert.equal(a.reason, 'haiku-model'); }); }); describe('assessMcpDeferral — non-disabling values', () => { it('ENABLE_TOOL_SEARCH="true" (non-haiku) → NOT disabled', () => { const a = assessMcpDeferral({ settings: { env: { ENABLE_TOOL_SEARCH: 'true' }, model: 'claude-sonnet-4-6' }, mcpServers: [srv()], }); assert.equal(a.toolSearchDisabled, false); assert.equal(a.forcedUpfront, false); }); it('ENABLE_TOOL_SEARCH="auto" → threshold mode, NOT disabled', () => { const a = assessMcpDeferral({ settings: { env: { ENABLE_TOOL_SEARCH: 'auto' } }, mcpServers: [srv()], }); assert.equal(a.toolSearchDisabled, false); assert.equal(a.thresholdMode, true); assert.equal(a.forcedUpfront, false); }); it('ENABLE_TOOL_SEARCH="auto:5" → threshold mode', () => { const a = assessMcpDeferral({ settings: { env: { ENABLE_TOOL_SEARCH: 'auto:5' } }, mcpServers: [srv()], }); assert.equal(a.thresholdMode, true); assert.equal(a.toolSearchDisabled, false); }); }); describe('assessMcpDeferral — per-server alwaysLoad', () => { it('alwaysLoad:true server with tool search enabled → that server forced upfront only', () => { const a = assessMcpDeferral({ settings: {}, mcpServers: [ srv({ name: 'always', alwaysLoad: true, estimatedTokens: 1500 }), srv({ name: 'deferred', alwaysLoad: false, estimatedTokens: 9000 }), ], }); assert.equal(a.toolSearchDisabled, false); assert.equal(a.forcedUpfront, true); assert.equal(a.alwaysLoadServers.length, 1); assert.equal(a.affectedServers.length, 1); assert.equal(a.affectedServers[0].name, 'always'); assert.equal(a.aggregateTokens, 1500); }); it('when tool search is disabled, ALL active servers are affected (not just alwaysLoad)', () => { const a = assessMcpDeferral({ settings: { env: { ENABLE_TOOL_SEARCH: 'false' } }, mcpServers: [ srv({ name: 'always', alwaysLoad: true, estimatedTokens: 1500 }), srv({ name: 'deferred', alwaysLoad: false, estimatedTokens: 2500 }), ], }); assert.equal(a.affectedServers.length, 2); assert.equal(a.aggregateTokens, 4000); }); }); describe('assessMcpDeferral — server filtering', () => { it('disabled servers (enabled:false) are excluded from affected + aggregate', () => { const a = assessMcpDeferral({ settings: { env: { ENABLE_TOOL_SEARCH: 'false' } }, mcpServers: [ srv({ name: 'on', enabled: true, estimatedTokens: 1000 }), srv({ name: 'off', enabled: false, estimatedTokens: 5000 }), ], }); assert.equal(a.affectedServers.length, 1); assert.equal(a.affectedServers[0].name, 'on'); assert.equal(a.aggregateTokens, 1000); }); it('no active servers → not forced upfront even when tool search disabled', () => { const a = assessMcpDeferral({ settings: { env: { ENABLE_TOOL_SEARCH: 'false' } }, mcpServers: [], }); assert.equal(a.toolSearchDisabled, true); assert.equal(a.forcedUpfront, false); assert.equal(a.aggregateTokens, 0); }); }); describe('severityForForcedSchemas', () => { it('high confidence scales with aggregate tokens', () => { assert.equal(severityForForcedSchemas(FORCED_SCHEMA_TOKENS_HIGH, 'high'), 'high'); assert.equal(severityForForcedSchemas(FORCED_SCHEMA_TOKENS_MEDIUM, 'high'), 'medium'); assert.equal(severityForForcedSchemas(100, 'high'), 'low'); }); it('medium confidence is capped at medium', () => { assert.equal(severityForForcedSchemas(FORCED_SCHEMA_TOKENS_HIGH * 10, 'medium'), 'medium'); assert.equal(severityForForcedSchemas(100, 'medium'), 'low'); }); });