import defaults from '../defaults.mjs'
import { formatLog } from './loghelper.mjs'
import { getApp, stopSpam } from '../util.mjs'

/*
 * Event: 'core.restart'
 *
 * Restart server
 */
export async function restart(ctx, data, cb) {
  if (ctx.db.config.allowRestart) {
    ctx.core.restart()
  } else {
    ctx.log.fatal('Invalid core restart command')
    ctx.log.event.error('Invalid core restart command')
  }
}

/*
 * Event: 'core.getlastlogs'
 *
 * Returns last few log messages from log
 */
export async function getlastlogs(ctx, data, cb) {
  if (data.name === 'service-core') {
    return cb(ctx.core.log.ringbuffer.records.map(formatLog))
  }
  let app = getApp(ctx, data.name, 'getlastlogs')
  if (!app) return

  cb(app.ctx.log.ringbuffer.records.map(formatLog))
}

/*
 * Event: 'core.listenlogs'
 *
 * Start listening to new log lines
 */
export async function listenlogs(ctx, data) {
  ctx.socket.join('logger.' + (data.name || 'service-core'))
}

/*
 * Event: 'core.unlistenlogs'
 *
 * Stop listening to new log lines
 */
export async function unlistenlogs(ctx, data) {
  ctx.socket.leave('logger.' + (data.name || 'service-core'))
}

/*
 * Event: 'core.update'
 *
 * Update specific software
 */
export async function update(ctx, data, cb) {
  let app = getApp(ctx, data.name, 'update')
  if (!app) return

  if (stopSpam(ctx, 'update', data.name)) return

  ctx.log.info('Checking for updates on app ' + data.name)
  app.update().then(function(res) {
    ctx.log.info(res, 'Update completed on app ' + data.name)
  }, function(err) {
    ctx.log.error(err, 'Error checking for updates on app ' + data.name)
  })
}

/*
 * Event: 'core.start'
 *
 * Start specific software
 */
export async function start(ctx, data, cb) {
  let app = getApp(ctx, data.name, 'start')
  if (!app) return
  
  if (stopSpam(ctx, 'start', data.name)) return

  ctx.log.info('Checking for updates on app ' + data.name)
  ctx.core.runApplication(app).then(function(res) {
    ctx.log.info('Successfully started ' + data.name + ' running ' + app.running)
  }, function(err) {
    ctx.log.error(err, 'Error starting app ' + data.name)
  })
}

/*
 * Event: 'core.listentoapp'
 *
 * Start listening to changes in core application name
 */
export async function listentoapp(ctx, data) {
  if (!data.name) {
    ctx.log.warn(`listento called with missing name`)
    return
  }

  let app = getApp(ctx, data.name, 'listentoapp')
  if (!app) return

  ctx.socket.join('app.' + data.name)
  let version = ctx.db.data.core[app.name].versions[0]
  ctx.socket.emit('app.updatelog', {
    name: data.name,
    log: version?.log || ctx.db.data.core[app.name].updater
  })
}

/*
 * Event: 'core.unlistentoapp'
 *
 * Stop listening to new log lines
 */
export async function unlistentoapp(ctx, data) {
  if (!data.name) {
    ctx.log.warn(`unlistento called with missing name`)
    return
  }
  
  let app = getApp(ctx, data.name, 'unlistentoapp')
  if (!app) return

  ctx.socket.leave('app.' + data.name)
}
