/** * 子进程环境净化单源测试(v0.7.3 P3-2) * * buildSafeChildEnv 是 run_command 与 MCP stdio 启动的唯一净化实现: * E1 敏感后缀剔除;E2 敏感精确名单剔除;E3 非敏感变量保留(黑名单不误伤); * E4 runtime 注入覆盖;E5 空值剔除。 */ import { describe, it, expect } from 'vitest'; import { buildSafeChildEnv } from '../safe-env'; const SAMPLE_ENV: Record = { PATH: '/usr/bin', LANG: 'zh_CN.UTF-8', DEEPSEEK_API_KEY: 'sk-secret', MY_SERVICE_TOKEN: 't', APP_PASSWORD: 'p', GITEA_PASSWORD: 'g', GITHUB_TOKEN: 'gh', HOME: '/home/u', }; describe('buildSafeChildEnv', () => { it('E1: 敏感后缀变量全部剔除(_API_KEY/_TOKEN/_PASSWORD/_SECRET/...)', () => { const env = buildSafeChildEnv({ source: SAMPLE_ENV }); expect(env['DEEPSEEK_API_KEY']).toBeUndefined(); expect(env['MY_SERVICE_TOKEN']).toBeUndefined(); expect(env['APP_PASSWORD']).toBeUndefined(); expect(env['GITHUB_TOKEN']).toBeUndefined(); }); it('E2: 精确名单剔除(大小写不敏感后缀 + 精确 key)', () => { const env = buildSafeChildEnv({ source: { GITEA_PASSWORD: 'g', DATABASE_PASSWORD: 'd' } }); expect(env['GITEA_PASSWORD']).toBeUndefined(); expect(env['DATABASE_PASSWORD']).toBeUndefined(); }); it('E3: 非敏感变量保留(黑名单不误伤 GIT_*/代理/路径类变量)', () => { const env = buildSafeChildEnv({ source: { ...SAMPLE_ENV, GIT_AUTHOR_NAME: 'metona', HTTPS_PROXY: 'http://p:7890' }, }); expect(env['PATH']).toBe('/usr/bin'); expect(env['LANG']).toBe('zh_CN.UTF-8'); expect(env['HOME']).toBe('/home/u'); expect(env['GIT_AUTHOR_NAME']).toBe('metona'); expect(env['HTTPS_PROXY']).toBe('http://p:7890'); }); it('E4: runtime 注入覆盖净化结果(调用方运行时差异显式可控)', () => { const env = buildSafeChildEnv({ source: SAMPLE_ENV, runtime: { NODE_ENV: 'production', LANG: 'C.utf8' }, }); expect(env['NODE_ENV']).toBe('production'); // runtime 覆盖同名的净化保留值 expect(env['LANG']).toBe('C.utf8'); }); it('E5: 空值/undefined 变量剔除', () => { const env = buildSafeChildEnv({ source: { EMPTY: '', UNSET: undefined, KEEP: 'x' } }); expect('EMPTY' in env).toBe(false); expect('UNSET' in env).toBe(false); expect(env['KEEP']).toBe('x'); }); it('E6: 无 source 时回退 process.env(运行路径契约;至少保留 PATH 类基本变量)', () => { const env = buildSafeChildEnv({ runtime: { NODE_ENV: 'production' } }); expect(env['NODE_ENV']).toBe('production'); }); });