/**
 * Reusable Store Helper Functions
 * Common utilities that can be used across all Pinia stores
 */

import { toast } from '@/plugins/toast'

/**
 * Show toast notification helper
 * Uses vue3-toastify with progress bar and modern design
 * Shows only the message, ignores title parameter
 * 
 * @param {string} type - 'success', 'error', 'info', or 'warning'
 * @param {string} title - Toast title (ignored, kept for compatibility)
 * @param {string} message - Toast message to display
 */
export function showToast(type, title, message) {
  try {
    // Use only the message, ignore the title
    const displayMessage = message
    
    switch (type) {
      case 'success':
        toast.success(displayMessage, {
          autoClose: 3500,
          position: 'top-right',
          hideProgressBar: false,
        })
        break
      case 'error':
        toast.error(displayMessage, {
          autoClose: 5000,
          position: 'top-right',
          hideProgressBar: false,
        })
        break
      case 'info':
        toast.info(displayMessage, {
          autoClose: 3500,
          position: 'top-right',
          hideProgressBar: false,
        })
        break
      case 'warning':
        toast.warning(displayMessage, {
          autoClose: 4000,
          position: 'top-right',
          hideProgressBar: false,
        })
        break
      default:
        toast.info(displayMessage, {
          autoClose: 3500,
          position: 'top-right',
          hideProgressBar: false,
        })
    }
  } catch (error) {
    console[type === 'error' ? 'error' : 'log'](`${type === 'error' ? '✗' : '✓'} ${message}`)
  }
}

/**
 * Transform data for API submission
 * Removes file objects and cleans empty strings
 * @param {Object} data - Data object to transform
 * @param {Array} fileFields - Array of field names that are files (e.g., ['profile_image', 'header_image'])
 * @returns {Object} - Cleaned data object
 */
export function transformDataForAPI(data, fileFields = []) {
  const cleaned = {}
  
  Object.entries(data).forEach(([key, value]) => {
    // Skip file field objects that end with '_file'
    if (key.endsWith('_file')) {
      return
    }
    
    // Only include non-empty values for file fields
    if (fileFields.includes(key)) {
      if (value && value.trim() !== '') {
        cleaned[key] = value
      }
    } else {
      // Include all other fields
      cleaned[key] = value
    }
  })
  
  return cleaned
}

/**
 * Handle API response structure consistently
 * @param {Object} response - API response object
 * @returns {Object} - Extracted data object
 */
export function extractResponseData(response) {
  // Handle nested data structure: response.data.data
  if (response.data && response.data.status && response.data.data) {
    return response.data.data
  }
  
  // Handle direct data: response.data
  if (response.data) {
    return response.data
  }
  
  // Fallback to entire response
  return response
}

/**
 * Handle paginated response structure
 * @param {Object} response - API response object
 * @returns {Object} - { items: [], total: 0 }
 */
export function extractPaginatedData(response) {
  const result = { items: [], total: 0 }
  
  // Laravel pagination: response.data.data.data
  if (response.data?.data?.data && Array.isArray(response.data.data.data)) {
    result.items = response.data.data.data
    result.total = response.data.data.total || 0
    return result
  }
  
  // Direct array in data: response.data.data
  if (response.data?.data && Array.isArray(response.data.data)) {
    result.items = response.data.data
    result.total = response.data.total || response.data.data.length
    return result
  }
  
  // Direct array: response.data
  if (Array.isArray(response.data)) {
    result.items = response.data
    result.total = response.data.length
    return result
  }
  
  return result
}

/**
 * Recursively append a value to FormData using PHP/Laravel bracket notation so
 * nested objects/arrays (e.g. program_details.bottom_sliders) are reconstructed
 * as arrays on the backend instead of being serialized to "[object Object]".
 */
function appendFormDataValue(formData, key, value) {
  if (value === undefined || value === null) {
    // Skip nulls/undefined so they don't arrive as the strings "null"/"undefined".
    return
  }
  if (value instanceof File || value instanceof Blob || value instanceof Date) {
    formData.append(key, value)
    return
  }
  if (Array.isArray(value)) {
    value.forEach((item, index) => {
      appendFormDataValue(formData, `${key}[${index}]`, item)
    })
    return
  }
  if (typeof value === 'object') {
    Object.entries(value).forEach(([childKey, childValue]) => {
      appendFormDataValue(formData, `${key}[${childKey}]`, childValue)
    })
    return
  }
  if (typeof value === 'boolean') {
    // Laravel's `boolean` rule accepts 1/0 but not the strings "true"/"false".
    formData.append(key, value ? '1' : '0')
    return
  }
  formData.append(key, value)
}

/**
 * Create FormData for file uploads
 * @param {Object} data - Data object
 * @param {string} fileFieldName - Name of the file field (e.g., 'profile_image')
 * @param {File} fileObject - File object to upload
 * @returns {FormData}
 */
export function createFormDataWithFile(data, fileFieldName, fileObject) {
  const formData = new FormData()

  // Append all non-file fields (nested objects/arrays use bracket notation so the
  // backend reconstructs them as arrays instead of "[object Object]").
  Object.entries(data).forEach(([key, value]) => {
    if (key !== `${fileFieldName}_file` && key !== fileFieldName) {
      appendFormDataValue(formData, key, value)
    }
  })

  // Append the file
  formData.append(fileFieldName, fileObject)

  return formData
}

/**
 * Handle API errors consistently
 * @param {Error} error - Error object
 * @returns {string} - Error message
 */
export function extractErrorMessage(error) {
  const responseData = error?.response?.data || {}
  const fallback = responseData?.message || error.message || 'An error occurred'

  const validationErrors = responseData?.errors
  if (validationErrors && typeof validationErrors === 'object') {
    const firstFieldErrors = Object.values(validationErrors)[0]
    if (Array.isArray(firstFieldErrors) && firstFieldErrors.length > 0) {
      return firstFieldErrors[0]
    }
    if (typeof firstFieldErrors === 'string' && firstFieldErrors.trim()) {
      return firstFieldErrors
    }
  }

  return fallback
}

/**
 * @param {Error} error
 * @returns {{ code: string, message: string, conflict: object, requires_confirmation: boolean } | null}
 */
export function getSlugConflictPayload(error) {
  const data = error?.response?.data || {}
  if (!data?.code || !data?.conflict) {
    return null
  }

  if (!['slug_restorable', 'slug_conflict_live'].includes(data.code)) {
    return null
  }

  return {
    code: data.code,
    message: data.message || extractErrorMessage(error),
    conflict: data.conflict,
    requires_confirmation: !!data.requires_confirmation,
  }
}

/**
 * Update item in array by ID
 * @param {Array} array - Array of items
 * @param {number|string} id - Item ID
 * @param {Object} newData - New data for the item
 * @returns {Array} - Updated array
 */
export function updateItemInArray(array, id, newData) {
  const index = array.findIndex(item => item.id == id)
  if (index !== -1) {
    array[index] = newData
  }
  return array
}

/**
 * Remove item from array by ID
 * @param {Array} array - Array of items
 * @param {number|string} id - Item ID
 * @returns {Array} - Filtered array
 */
export function removeItemFromArray(array, id) {
  return array.filter(item => item.id != id)
}
