/** * 继电器命令行调试工具 —— 参数化触发按键/配对/原始命令,方便接线调试。 * * 用法(端口/波特率走 .env 的 SERIAL_PORT/SERIAL_BAUD): * npx ts-node scripts/relay.ts probe # 查版本(只读握手) * npx ts-node scripts/relay.ts status # 读 64 路状态 * npx ts-node scripts/relay.ts pair remote # 进配对(按 config 默认) * npx ts-node scripts/relay.ts pair meter --hold 2500 # 进配对,覆盖时长 * npx ts-node scripts/relay.ts press remote convex --hold 800 # 点按命名键 * npx ts-node scripts/relay.ts pulse 34,35 --hold 3000 # 同时脉冲指定通道 * npx ts-node scripts/relay.ts on 34 / off 34 # 单路通/断 * npx ts-node scripts/relay.ts raw 55C8210155 # 发原始 16 进制帧 */ import * as dotenv from 'dotenv'; import * as path from 'path'; dotenv.config({ path: path.resolve(__dirname, '../.env') }); import { SerialController } from '../utils/common/serial_controller'; import { triggerRelayAction, pressButton } from '../utils/common/relay.helper'; function flag(name: string): string | undefined { const i = process.argv.indexOf(`--${name}`); return i >= 0 ? process.argv[i + 1] : undefined; } /** 取位置参数(剔除 --flag 及其紧随的值)。 */ function positionals(): string[] { const argv = process.argv.slice(2); const out: string[] = []; for (let i = 0; i < argv.length; i++) { if (argv[i].startsWith('--')) { i++; // 跳过该 flag 的值 continue; } out.push(argv[i]); } return out; } async function main() { const [cmd, a, b] = positionals(); const hold = flag('hold') ? parseInt(flag('hold') as string, 10) : undefined; switch (cmd) { case 'probe': { const c = new SerialController(); await c.open(); console.log(await c.queryVersion()); await c.close(); break; } case 'status': { const c = new SerialController(); await c.open(); console.log('status:', (await c.readStatus()).toString('hex').toUpperCase()); await c.close(); break; } case 'pair': { if (!a) throw new Error('用法: pair [--hold ms]'); await triggerRelayAction(a, 'pairing', hold ? { holdMs: hold } : {}); break; } case 'press': { if (!a || !b) throw new Error('用法: press