import { authenticate } from '../../plugins/auth.js'
import { getCustomerById } from '../../services/customer.service.js'
import { createPairingRequest, cancelPairingRequest } from '../../services/pairing.service.js'
import { getActiveSessionByCustomer, getActiveSessionByCustomerWithUnread, endSession, getCustomerHistory } from '../../services/session.service.js'
import { getPricingForCustomer, isValidTier, isCustomerEligibleForFreeTrial, getFreeTrial } from '../../services/pricing.service.js'
import { requestExtension } from '../../services/extension.service.js'
import { EndedBy, TopicSensitivity, UserType } from '../../constants.js'

const resolveCustomer = async (request, reply) => {
  if (request.auth?.userType !== UserType.CUSTOMER) {
    return reply.code(403).send({
      success: false,
      error: { code: 'FORBIDDEN', message: 'Customer account required' },
    })
  }
  const customer = await getCustomerById(request.auth.userId)
  if (!customer) {
    return reply.code(404).send({
      success: false,
      error: { code: 'ACCOUNT_NOT_FOUND', message: 'Customer account not found' },
    })
  }
  request.customer = customer
}

export const clientChatRoutes = async (app) => {
  // Get pricing tiers + free trial eligibility
  app.get('/pricing', { preHandler: [authenticate, resolveCustomer] }, async (request, reply) => {
    const pricing = await getPricingForCustomer(request.customer.id)
    return reply.send({ success: true, data: pricing })
  })

  app.post('/request', { preHandler: [authenticate, resolveCustomer] }, async (request, reply) => {
    const { duration_minutes, price, is_free_trial, topic_sensitivity } = request.body || {}

    if (topic_sensitivity !== TopicSensitivity.REGULAR && topic_sensitivity !== TopicSensitivity.SENSITIVE) {
      return reply.code(400).send({
        success: false,
        error: { code: 'BAD_REQUEST', message: 'topic_sensitivity must be regular or sensitive' },
      })
    }

    // Validate selection
    if (is_free_trial) {
      const eligible = await isCustomerEligibleForFreeTrial(request.customer.id)
      if (!eligible) {
        return reply.code(403).send({
          success: false,
          error: { code: 'FREE_TRIAL_INELIGIBLE', message: 'Not eligible for free trial' },
        })
      }
      const freeTrial = await getFreeTrial()
      const session = await createPairingRequest(request.customer.id, {
        duration_minutes: freeTrial.duration_minutes,
        price: 0,
        is_free_trial: true,
        topic_sensitivity,
      })
      return reply.code(201).send({ success: true, data: session })
    }

    if (!duration_minutes || price === undefined) {
      return reply.code(400).send({
        success: false,
        error: { code: 'BAD_REQUEST', message: 'duration_minutes and price are required' },
      })
    }

    if (!(await isValidTier(duration_minutes, price))) {
      return reply.code(400).send({
        success: false,
        error: { code: 'INVALID_TIER', message: 'Invalid price tier selection' },
      })
    }

    const session = await createPairingRequest(request.customer.id, { duration_minutes, price, is_free_trial: false, topic_sensitivity })
    return reply.code(201).send({ success: true, data: session })
  })

  app.post('/request/:sessionId/cancel', { preHandler: [authenticate, resolveCustomer] }, async (request, reply) => {
    const session = await cancelPairingRequest(request.params.sessionId, request.customer.id)
    return reply.send({ success: true, data: session })
  })

  app.get('/session/active', { preHandler: [authenticate, resolveCustomer] }, async (request, reply) => {
    const session = await getActiveSessionByCustomer(request.customer.id)
    return reply.send({ success: true, data: session ?? null })
  })

  app.get('/session/active-with-unread', { preHandler: [authenticate, resolveCustomer] }, async (request, reply) => {
    const session = await getActiveSessionByCustomerWithUnread(request.customer.id)
    return reply.send({ success: true, data: session ?? null })
  })

  app.post('/session/:sessionId/end', { preHandler: [authenticate, resolveCustomer] }, async (request, reply) => {
    const session = await endSession(request.params.sessionId, EndedBy.CUSTOMER, request.customer.id)
    return reply.send({ success: true, data: session })
  })

  // Request session extension
  app.post('/session/:sessionId/extend', { preHandler: [authenticate, resolveCustomer] }, async (request, reply) => {
    const { duration_minutes, price } = request.body || {}
    if (!duration_minutes || price === undefined) {
      return reply.code(400).send({
        success: false,
        error: { code: 'BAD_REQUEST', message: 'duration_minutes and price are required' },
      })
    }
    const extension = await requestExtension(request.params.sessionId, request.customer.id, { duration_minutes, price })
    return reply.send({ success: true, data: extension })
  })

  // Chat history
  app.get('/history', { preHandler: [authenticate, resolveCustomer] }, async (request, reply) => {
    const { page, limit } = request.query
    const history = await getCustomerHistory(request.customer.id, {
      page: page ? parseInt(page) : 1,
      limit: limit ? parseInt(limit) : 20,
    })
    return reply.send({ success: true, data: history })
  })
}
