<?php
/**
 * Utility Functions
 */

function redirect(string $url): void
{
    if (session_status() === PHP_SESSION_ACTIVE) {
        session_write_close();
    }
    header('Location: ' . $url);
    exit;
}

function e($value): string
{
    return htmlspecialchars($value ?? '', ENT_QUOTES, 'UTF-8');
}

function format_date(?string $date, string $format = 'M j, Y'): string
{
    if (!$date) return '-';
    return date($format, strtotime($date));
}

function format_datetime(?string $datetime, string $format = 'M j, Y g:i A'): string
{
    if (!$datetime) return '-';
    return date($format, strtotime($datetime));
}

function format_number($number, int $decimals = 2): string
{
    return number_format((float) $number, $decimals);
}

function time_ago(?string $datetime): string
{
    if (!$datetime) return '-';
    $now = new DateTime();
    $past = new DateTime($datetime);
    $diff = $now->diff($past);

    if ($diff->y > 0) return $diff->y . ' year' . ($diff->y > 1 ? 's' : '') . ' ago';
    if ($diff->m > 0) return $diff->m . ' month' . ($diff->m > 1 ? 's' : '') . ' ago';
    if ($diff->d > 0) return $diff->d . ' day' . ($diff->d > 1 ? 's' : '') . ' ago';
    if ($diff->h > 0) return $diff->h . ' hour' . ($diff->h > 1 ? 's' : '') . ' ago';
    if ($diff->i > 0) return $diff->i . ' min' . ($diff->i > 1 ? 's' : '') . ' ago';
    return 'just now';
}

function status_badge(string $status): string
{
    $classes = [
        'active'     => 'badge-success',
        'inactive'   => 'badge-secondary',
        'draft'      => 'badge-secondary',
        'open'       => 'badge-info',
        'in_progress' => 'badge-warning',
        'completed'  => 'badge-success',
        'cancelled'  => 'badge-danger',
        'pending'    => 'badge-warning',
        'counted'    => 'badge-info',
        'checked'    => 'badge-info',
        'approved'   => 'badge-success',
        'rejected'   => 'badge-danger',
        'recount'    => 'badge-warning',
        'suspended'  => 'badge-danger',
        'Active'     => 'badge-success',
        'Inactive'   => 'badge-secondary',
        'admin'      => 'badge-danger',
        'controller' => 'badge-warning',
        'counter'    => 'badge-info',
        'checker'    => 'badge-success',
    ];
    $class = $classes[$status] ?? ($classes[strtolower($status)] ?? 'badge-secondary');
    $label = ucwords(str_replace('_', ' ', $status));
    return '<span class="badge ' . $class . '">' . $label . '</span>';
}

function priority_badge(string $priority): string
{
    $classes = [
        'low'    => 'badge-secondary',
        'normal' => 'badge-info',
        'high'   => 'badge-warning',
        'urgent' => 'badge-danger',
    ];
    $class = $classes[$priority] ?? 'badge-secondary';
    return '<span class="badge ' . $class . '">' . ucfirst($priority) . '</span>';
}

function truncate(string $text, int $length = 50): string
{
    if (strlen($text) <= $length) return $text;
    return substr($text, 0, $length) . '...';
}

function get_current_url(): string
{
    return (isset($_SERVER['HTTPS']) && $_SERVER['HTTPS'] === 'on' ? 'https' : 'http') . '://' . $_SERVER['HTTP_HOST'] . $_SERVER['REQUEST_URI'];
}

function get_base_url(): string
{
    $protocol = (!empty($_SERVER['HTTPS']) && $_SERVER['HTTPS'] !== 'off') ? 'https' : 'http';
    return $protocol . '://' . $_SERVER['HTTP_HOST'];
}

function generate_random_string(int $length = 16): string
{
    return bin2hex(random_bytes($length / 2));
}

function log_action(int $userId, string $action, string $entityType, int $entityId = 0, ?array $details = null): void
{
    try {
        $db = Database::getInstance();
        $db->insert('audit_log', [
            'user_id'     => $userId,
            'action'      => $action,
            'entity_type' => $entityType,
            'entity_id'   => $entityId,
            'details'     => $details ? json_encode($details) : null,
            'ip_address'  => $_SERVER['REMOTE_ADDR'] ?? null,
        ]);
    } catch (Exception $e) {
        error_log('Audit log error: ' . $e->getMessage());
    }
}

function format_location(?string $store, ?string $rack, ?string $level, ?string $bin, ?string $zone = null): string
{
    if ($zone) {
        return $zone;
    }
    
    $parts = [];
    if ($store) {
        $parts[] = $store;
    }
    if ($rack) {
        $parts[] = 'R:' . $rack;
    }
    if ($level) {
        $parts[] = 'L:' . $level;
    }
    if ($bin) {
        $parts[] = 'B:' . $bin;
    }
    
    return $parts ? implode(' / ', $parts) : '-';
}

/**
 * Upload image file and return relative path or false on failure
 * @param string $file_key $_FILES key
 * @param int $max_size_kb max file size KB
 * @param array $allowed_mimes MIME types
 * @return string|false relative path like 'uploads/item_images/filename.jpg'
 */
function upload_image(string $file_key = 'item_image', int $max_size_kb = 2048, array $allowed_mimes = ['image/jpeg', 'image/png', 'image/gif', 'image/webp', 'image/svg+xml']): string|false 
{
    if (!isset($_FILES[$file_key]) || $_FILES[$file_key]['error'] !== UPLOAD_ERR_OK) {
        return false;
    }

    $file = $_FILES[$file_key];
    $finfo = finfo_open(FILEINFO_MIME_TYPE);
    $mime = finfo_file($finfo, $file['tmp_name']);
    finfo_close($finfo);

    if (!in_array($mime, $allowed_mimes)) {
        return false;
    }

    if ($file['size'] > $max_size_kb * 1024) {
        return false;
    }

    $upload_dir = APP_ROOT . '/uploads/item_images/';
    if (!is_dir($upload_dir)) {
        mkdir($upload_dir, 0755, true);
    }

    $ext = strtolower(pathinfo($file['name'], PATHINFO_EXTENSION));
    $filename = 'item_' . SessionManager::getUserId() . '_' . time() . '_' . uniqid() . '.' . $ext;
    $target_path = $upload_dir . $filename;

    if (move_uploaded_file($file['tmp_name'], $target_path)) {
        return 'uploads/item_images/' . $filename;
    }

    return false;
}

function delete_image(?string $image_path): bool 
{
    if (!$image_path || !file_exists(APP_ROOT . '/' . $image_path)) {
        return true;
    }
    return unlink(APP_ROOT . '/' . $image_path);
}

/**
 * Display image thumbnail or placeholder
 */
function item_image_thumbnail(?string $image_path, int $width = 50, int $height = 50): string 
{
    if (!$image_path || !file_exists(APP_ROOT . '/' . $image_path)) {
        return '<div style="width:' . $width . 'px;height:' . $height . 'px;background:#f0f0f0;border:1px solid #ddd;border-radius:4px;display:flex;align-items:center;justify-content:center;color:#999;font-size:12px;">No Image</div>';
    }
    $style = 'width:' . $width . 'px;height:' . $height . 'px;object-fit:cover;border-radius:4px;border:1px solid #ddd;';
    return '<img src="' . APP_URL . '/' . $image_path . '?v=' . filemtime(APP_ROOT . '/' . $image_path) . '" style="' . $style . '" alt="Item Image" loading="lazy">';
}



