/**
 * Periodic flush of the marketplace-listing outbox (server/utils/listings/outbox.ts).
 * No Nitro cron infra exists here, so this mirrors chatDb's setInterval pattern.
 *
 * Env: LISTING_FLUSH_ENABLED=0 disables it; LISTING_FLUSH_INTERVAL_MS (default 60 000);
 *      LISTING_FLUSH_DEBOUNCE_MS (default 20 000, read by outbox.ts).
 * Only PM2 instance 0 runs it (NODE_APP_INSTANCE) so a cluster never double-sends;
 * the outbox additionally claims rows (queued → sending) before pushing.
 */
import { flushOutbox } from '../utils/listings/outbox'

export default defineNitroPlugin(() => {
  // `nuxt generate` / `build:app` boots Nitro in-process for prerendering: never arm the timer
  // there (it would hold the build process open and flush the prod outbox from a dev machine).
  if (import.meta.prerender) return
  if (process.env.LISTING_FLUSH_ENABLED === '0' || process.env.LISTING_FLUSH_ENABLED === 'false') {
    console.log('[listing-outbox] timer disabled (LISTING_FLUSH_ENABLED=0)')
    return
  }
  const inst = process.env.NODE_APP_INSTANCE
  if (inst !== undefined && inst !== '0') return
  const config: any = useRuntimeConfig()
  if (!config.api?.idempieretoken) {
    console.warn('[listing-outbox] no iDempiere service token (api.idempieretoken) — timer flush disabled, "Send now" still works')
    return
  }
  const every = Math.max(15_000, Number(process.env.LISTING_FLUSH_INTERVAL_MS) || 60_000)
  const run = () => flushOutbox({ trigger: 'timer' }).then(s => {
    const moved = s.sources.reduce((n, x) => n + x.sent + x.errors + x.requeued, 0)
    if (moved || s.confirmed || s.error) console.log(`[listing-outbox] run ${s.runId}: ${moved} change(s) processed, ${s.confirmed} confirmed, ${s.durationMs} ms${s.error ? ' ERROR ' + s.error : ''}`)
  }).catch((e: any) => console.error('[listing-outbox] timer run failed:', e?.message || e))
  // Short first delay: every Nitro reload (dev) or PM2 restart re-arms the timer, a long
  // initial wait would leave queued changes sitting while files are being edited.
  // unref: the timers must never be the only thing keeping the event loop alive.
  setTimeout(run, 10_000).unref()
  setInterval(run, every).unref()
  console.log(`[listing-outbox] timer armed every ${Math.round(every / 1000)} s`)
})
