import refreshTokenHelper from "../../../utils/refreshTokenHelper"
import errorHandlingHelper from "../../../utils/errorHandlingHelper"
import fetchHelper from "../../../utils/fetchHelper"

// POST /api/plentyone/stocks/sync
// Syncs local qty on hand to PlentyOne directly via REST API
// Body: { orderSourceId, variationId, quantity, sku?, productId?, itemId? }
//
// PlentyOne Stock Correction REST API (working endpoint):
// PUT /rest/items/{itemId}/variations/{variationId}/stock/correction
const handleFunc = async (event: any, authToken: any = null) => {
  const token = authToken ?? await getTokenHelper(event)
  const body = await readBody(event)

  const { orderSourceId, variationId, quantity, sku, productId } = body

  // variationId = SKU (numeric ID)
  const effectiveVariationId = variationId || sku

  if(!orderSourceId) {
    return { status: 400, message: 'orderSourceId is required', success: false }
  }
  if(!effectiveVariationId) {
    return { status: 400, message: 'variationId (SKU) is required', success: false }
  }
  if(quantity === undefined || quantity === null) {
    return { status: 400, message: 'quantity is required', success: false }
  }

  // Load order source to verify it's PlentyOne and get credentials
  const os: any = await fetchHelper(event, `models/c_ordersource/${orderSourceId}`, 'GET', token, null)
  if(!os) {
    return { status: 404, message: 'Order Source not found', success: false }
  }
  if(!(os?.Marketplace?.id === '6' || os?.Marketplace?.identifier === 'plentyone')) {
    return { status: 400, message: 'Selected Order Source is not PlentyOne', success: false }
  }

  // Get PlentyOne credentials from order source
  const baseUrl = os?.marketplace_url || os?.SHOPWARE_URL || ''
  const clientId = os?.marketplace_key || ''
  const clientSecret = os?.marketplace_secret || ''

  if(!baseUrl) {
    return { status: 400, message: 'No marketplace_url configured for this Order Source', success: false }
  }
  if(!clientId || !clientSecret) {
    return { status: 400, message: 'No marketplace_key or marketplace_secret configured for this Order Source', success: false }
  }

  // Get PlentyOne warehouse ID (default: 102)
  const warehouseId = os?.PlentyOne_Warehouse_ID || 102

  try {
    // Normalize base URL
    let host = baseUrl.trim()
    if(!/^https?:\/\//i.test(host)) host = `https://${host}`
    host = host.replace(/\/$/, '')
    // Remove /rest suffix if present
    const baseHost = host.replace(/\/rest\/?$/, '')
    const apiBase = `${baseHost}/rest`

    // Get OAuth access token from PlentyOne
    const tokenUrl = `${baseHost}/rest/login`
    let accessToken = ''
    try {
      const tokenRes: any = await $fetch(tokenUrl, {
        method: 'POST',
        headers: {
          'Content-Type': 'application/json',
          'Accept': 'application/json'
        },
        body: {
          username: clientId,
          password: clientSecret
        }
      })
      accessToken = tokenRes?.accessToken || tokenRes?.access_token || ''
    } catch (tokenErr: any) {
      console.error('PlentyOne OAuth error:', tokenErr?.data || tokenErr?.message)
      return { status: 401, message: 'Failed to authenticate with PlentyOne. Check marketplace_key and marketplace_secret.', success: false }
    }

    if(!accessToken) {
      return { status: 401, message: 'No access token received from PlentyOne', success: false }
    }

    const authHeaders = {
      'Authorization': `Bearer ${accessToken}`,
      'Content-Type': 'application/json',
      'Accept': 'application/json'
    }

    const numericVariationId = Number(effectiveVariationId)
    const targetQty = Number(quantity)

    // First, get the itemId for this variation from PlentyOne
    // We need itemId for the working endpoint: PUT /rest/items/{itemId}/variations/{variationId}/stock/correction
    let itemId = body.itemId ? Number(body.itemId) : null

    if(!itemId) {
      // Search for variation using PlentyOne variations endpoint with id filter
      try {
        const variationSearchUrl = `${apiBase}/items/variations?id=${numericVariationId}`
        const variationRes: any = await $fetch(variationSearchUrl, {
          method: 'GET',
          headers: authHeaders
        })
        const entry = Array.isArray(variationRes?.entries) ? variationRes.entries[0] : (Array.isArray(variationRes) ? variationRes[0] : variationRes)
        itemId = entry?.itemId || entry?.item_id || null
        console.log('PlentyOne variation search:', { variationId: numericVariationId, itemId })
      } catch (varErr: any) {
        console.error('Failed to search variation for itemId:', varErr?.message)
      }

      // Fallback: try stock endpoint
      if(!itemId) {
        try {
          const stockUrl = `${apiBase}/stockmanagement/stock?variationId=${numericVariationId}&warehouseId=${warehouseId}`
          const stockRes: any = await $fetch(stockUrl, {
            method: 'GET',
            headers: authHeaders
          })
          const entries = stockRes?.entries || stockRes
          if(Array.isArray(entries) && entries[0]?.itemId) {
            itemId = entries[0].itemId
            console.log('PlentyOne itemId from stock:', itemId)
          }
        } catch (stockErr: any) {
          console.error('Failed to fetch itemId from stock:', stockErr?.message)
        }
      }
    }

    if(!itemId) {
      return {
        status: 400,
        success: false,
        message: 'Could not determine itemId for this variation. Please provide itemId in the request.',
        variationId: numericVariationId
      }
    }

    // Stock correction endpoint (working endpoint discovered via testing)
    // PUT /rest/items/{itemId}/variations/{variationId}/stock/correction
    const correctionUrl = `${apiBase}/items/${itemId}/variations/${numericVariationId}/stock/correction`

    const correctionBody = {
      warehouseId: warehouseId,
      quantity: targetQty,
      storageLocationId: 0
    }

    console.log('PlentyOne stock correction request:', { url: correctionUrl, body: correctionBody })

    const result: any = await $fetch(correctionUrl, {
      method: 'PUT',
      headers: authHeaders,
      body: correctionBody
    })

    console.log('PlentyOne stock correction response:', JSON.stringify(result).slice(0, 800))

    // Find this variation's updated stock in the response
    let updatedStock = null
    if(Array.isArray(result)) {
      const thisVariation = result.find((r: any) =>
        Number(r.variationId) === numericVariationId && Number(r.warehouseId) === Number(warehouseId)
      )
      if(thisVariation) {
        updatedStock = thisVariation.physicalStock ?? thisVariation.stockPhysical
      }
    }

    return {
      status: 200,
      success: true,
      message: `Stock corrected to ${updatedStock ?? targetQty} for variation ${numericVariationId} in warehouse ${warehouseId}`,
      variationId: numericVariationId,
      itemId,
      quantity: targetQty,
      updatedStock,
      warehouseId,
      plentyOneResponse: result
    }

  } catch (err: any) {
    const errData = err?.data || err
    const errMsg = errData?.message || errData?.error?.message || err?.message || 'Failed to sync stock to PlentyOne'
    const errStatus = err?.status || err?.response?.status || errData?.status || 500

    // Log detailed error for debugging
    console.error('PlentyOne stock sync error:', {
      variationId: effectiveVariationId,
      quantity,
      warehouseId,
      error: errData
    })

    return {
      status: errStatus,
      success: false,
      message: errMsg,
      error: errData,
      variationId: effectiveVariationId
    }
  }
}

export default defineEventHandler(async (event) => {
  try {
    return await handleFunc(event)
  } catch (err: any) {
    try {
      const authToken = await refreshTokenHelper(event)
      return await handleFunc(event, authToken)
    } catch (error: any) {
      const data = errorHandlingHelper(err?.data ?? err, error?.data ?? error)
      if([401, 402, 403, 407].includes(Number(data.status))) {
        //@ts-ignore
        setCookie(event, 'user', null)
      }
      return { ...data, success: false }
    }
  }
})
