// One discovery cycle: scan → upsert → mark-absent → prune. Deps injected for // tests. Prune only runs after a successful, non-empty scan, so a failed scan // can never reap rows. import { runScan } from './scan.js'; import * as devices from '../db/repos/lan_devices.js'; import { log } from '../log.js'; export async function runDeviceScanCycle({ scan = runScan, repo = devices } = {}) { const rows = await scan(); if (!rows.length) { log.warn('device scan returned no hosts; skipping upsert/prune'); return { seen: 0 }; } await repo.upsertScan(rows); await repo.markAbsent(rows.map(r => r.mac)); const pruned = await repo.prune(); log.info({ seen: rows.length, pruned }, 'device scan cycle complete'); return { seen: rows.length, pruned }; }