'use strict'; const { test, afterEach } = require('node:test'); const assert = require('node:assert/strict'); const logger = require('../logger'); const realStdout = process.stdout.write; const realStderr = process.stderr.write; afterEach(() => { process.stdout.write = realStdout; process.stderr.write = realStderr; }); // 同時攔截 stdout 與 stderr,回傳本次 run() 內各自寫出的字串 function capture(run) { const out = []; const err = []; process.stdout.write = (chunk) => { out.push(String(chunk)); return true; }; process.stderr.write = (chunk) => { err.push(String(chunk)); return true; }; try { run(); } finally { process.stdout.write = realStdout; process.stderr.write = realStderr; } return { out: out.join(''), err: err.join('') }; } const TIME = /\[\d{4}\/\d{2}\/\d{2} \d{2}:\d{2}:\d{2}\]/; test('section 於 stdout 輸出標題與 50 寬分隔線區塊', () => { const { out, err } = capture(() => logger.section('參數檢查')); assert.equal(out, `\n${'='.repeat(50)}\n參數檢查\n${'-'.repeat(50)}\n`); assert.equal(err, ''); }); test('info 以 [INF][時間]: 格式輸出至 stdout', () => { const { out, err } = capture(() => logger.info('IS_BETA=false')); assert.match(out, new RegExp(`^\\[INF\\]${TIME.source}: IS_BETA=false\\n$`)); assert.equal(err, ''); }); test('error 以 [ERR][時間]: 格式輸出至 stderr,且不寫入 stdout', () => { const { out, err } = capture(() => logger.error('GITEA_SERVER_URL 未設定')); assert.match(err, new RegExp(`^\\[ERR\\]${TIME.source}: GITEA_SERVER_URL 未設定\\n$`)); assert.equal(out, ''); }); test('info/error 的時間戳為 yyyy/MM/dd HH:mm:ss 格式', () => { const { out } = capture(() => logger.info('x')); assert.match(out, TIME); });