<?php
/**
 * DBJ Webhook Upload Endpoint for iotools.w8jae.com
 *
 * Supports 3 upload modes:
 * 1. Multipart form-data upload: sending file in `file`, `fileToUpload`, or `upload` parameter.
 * 2. URL upload: sending JSON payload `{"url": "https://example.com/file.jpg", "filename": "optional.jpg"}` or form parameter `url`.
 * 3. Raw binary payload: sending file content directly in request body with header `X-Filename: example.jpg` or `filename` parameter.
 *
 * Authentication:
 * Header: `X-Api-Key: <SECRET_KEY>` OR Query Parameter: `?key=<SECRET_KEY>` OR JSON payload `{"key": "<SECRET_KEY>"}`
 */

// Secret API Key for Webhook authentication
$API_KEY = "wh_iotools_9f8a7c6b5e4d3c2b1a0e9d8c7b6a5f4e";

$uploadDir = 'uploads/';
$host = $_SERVER['HTTP_HOST'] ?? 'iotools.w8jae.com';
$publicUrlPrefix = "https://" . $host . "/uploads/";

// Read raw body input early (for JSON parsing or binary body)
$rawInput = file_get_contents('php://input');
$jsonData = json_decode($rawInput, true);

// 1. Authenticate Request
$providedKey = $_SERVER['HTTP_X_API_KEY'] ?? ($_REQUEST['key'] ?? ($jsonData['key'] ?? ''));

if (empty($providedKey) || !hash_equals($API_KEY, $providedKey)) {
    header('HTTP/1.1 401 Unauthorized');
    header('Content-Type: application/json');
    echo json_encode([
        'success' => false,
        'error' => 'Unauthorized: Invalid or missing API Key/Token.'
    ]);
    exit;
}

if (!is_dir($uploadDir)) {
    mkdir($uploadDir, 0755, true);
}

$targetFileName = '';
$uploadedFilePath = '';

// Helper to sanitize filename while preserving spaces, dots, dashes, underscores, and brackets
function sanitize_filename($name) {
    $name = basename(trim($name));
    $name = preg_replace('/[^a-zA-Z0-9\-_\., ()\[\]]/', '', $name);
    return trim($name, " .");
}

// 2. Check for Multipart Form-Data File Upload
$fileField = null;
foreach (['file', 'fileToUpload', 'upload'] as $field) {
    if (isset($_FILES[$field]) && $_FILES[$field]['error'] === UPLOAD_ERR_OK) {
        $fileField = $field;
        break;
    }
}

if ($fileField) {
    $origName = $_FILES[$fileField]['name'];
    $customName = $_REQUEST['filename'] ?? ($_REQUEST['customFileName'] ?? ($jsonData['filename'] ?? ''));
    
    if (!empty($customName)) {
        $sanitized = sanitize_filename($customName);
        $origExt = pathinfo($origName, PATHINFO_EXTENSION);
        if (pathinfo($sanitized, PATHINFO_EXTENSION) === '' && $origExt !== '') {
            $sanitized .= '.' . $origExt;
        }
        $targetFileName = $sanitized;
    } else {
        $targetFileName = sanitize_filename($origName);
    }

    if (empty($targetFileName)) {
        $targetFileName = 'upload_' . bin2hex(random_bytes(4)) . '.' . pathinfo($origName, PATHINFO_EXTENSION);
    }

    $targetFile = $uploadDir . $targetFileName;
    
    // Prevent overwrite by appending unique suffix if file already exists
    if (file_exists($targetFile)) {
        $ext = pathinfo($targetFileName, PATHINFO_EXTENSION);
        $base = pathinfo($targetFileName, PATHINFO_FILENAME);
        $targetFileName = $base . '_' . time() . ($ext ? '.' . $ext : '');
        $targetFile = $uploadDir . $targetFileName;
    }

    if (move_uploaded_file($_FILES[$fileField]['tmp_name'], $targetFile)) {
        $uploadedFilePath = $targetFile;
    } else {
        header('HTTP/1.1 500 Internal Server Error');
        header('Content-Type: application/json');
        echo json_encode(['success' => false, 'error' => 'Failed to save uploaded file.']);
        exit;
    }
} else {
    // 3. Check JSON Payload or Form URL Upload
    $fileUrl = $jsonData['url'] ?? ($_REQUEST['url'] ?? '');
    $customName = $jsonData['filename'] ?? ($_REQUEST['filename'] ?? ($_SERVER['HTTP_X_FILENAME'] ?? ''));

    if (!empty($fileUrl) && filter_var($fileUrl, FILTER_VALIDATE_URL)) {
        $urlPath = parse_url($fileUrl, PHP_URL_PATH);
        $urlFileName = basename($urlPath);
        
        if (!empty($customName)) {
            $targetFileName = sanitize_filename($customName);
        } else {
            $targetFileName = sanitize_filename($urlFileName);
        }

        if (empty($targetFileName)) {
            $targetFileName = 'file_' . bin2hex(random_bytes(4));
        }

        $targetFile = $uploadDir . $targetFileName;
        if (file_exists($targetFile)) {
            $ext = pathinfo($targetFileName, PATHINFO_EXTENSION);
            $base = pathinfo($targetFileName, PATHINFO_FILENAME);
            $targetFileName = $base . '_' . time() . ($ext ? '.' . $ext : '');
            $targetFile = $uploadDir . $targetFileName;
        }

        // Fetch remote file via cURL
        $ch = curl_init($fileUrl);
        $fp = fopen($targetFile, 'wb');
        curl_setopt($ch, CURLOPT_FILE, $fp);
        curl_setopt($ch, CURLOPT_HEADER, 0);
        curl_setopt($ch, CURLOPT_FOLLOWLOCATION, true);
        curl_setopt($ch, CURLOPT_TIMEOUT, 120);
        curl_setopt($ch, CURLOPT_USERAGENT, 'DBJ-Webhook-Uploader/1.0');
        $success = curl_exec($ch);
        $httpCode = curl_getinfo($ch, CURLINFO_HTTP_CODE);
        curl_close($ch);
        fclose($fp);

        if ($success && $httpCode >= 200 && $httpCode < 300 && filesize($targetFile) > 0) {
            $uploadedFilePath = $targetFile;
        } else {
            if (file_exists($targetFile)) unlink($targetFile);
            header('HTTP/1.1 400 Bad Request');
            header('Content-Type: application/json');
            echo json_encode(['success' => false, 'error' => 'Failed to download file from provided URL (HTTP Code: ' . $httpCode . ').']);
            exit;
        }
    } elseif (!empty($rawInput) && is_null($jsonData)) {
        // 4. Raw Binary Upload Body (non-JSON)
        if (!empty($customName)) {
            $targetFileName = sanitize_filename($customName);
        } else {
            $targetFileName = 'raw_' . bin2hex(random_bytes(4)) . '.bin';
        }

        $targetFile = $uploadDir . $targetFileName;
        if (file_exists($targetFile)) {
            $ext = pathinfo($targetFileName, PATHINFO_EXTENSION);
            $base = pathinfo($targetFileName, PATHINFO_FILENAME);
            $targetFileName = $base . '_' . time() . ($ext ? '.' . $ext : '');
            $targetFile = $uploadDir . $targetFileName;
        }

        if (file_put_contents($targetFile, $rawInput) !== false) {
            $uploadedFilePath = $targetFile;
        } else {
            header('HTTP/1.1 500 Internal Server Error');
            header('Content-Type: application/json');
            echo json_encode(['success' => false, 'error' => 'Failed to save raw binary body.']);
            exit;
        }
    } else {
        header('HTTP/1.1 400 Bad Request');
        header('Content-Type: application/json');
        echo json_encode(['success' => false, 'error' => 'No file, URL, or valid data payload received.']);
        exit;
    }
}

$fileSize = filesize($uploadedFilePath);
$publicUrl = $publicUrlPrefix . $targetFileName;

// Helper function to trigger transcription on api_whisper.php
function trigger_whisper_transcription($fileUrl, $fileName) {
    // Check pattern (e.g. DEV-xxxx_... or any .mp3 file)
    $ext = strtolower(pathinfo($fileName, PATHINFO_EXTENSION));
    if ($ext === 'mp3' || strpos($fileName, 'DEV-') === 0 || preg_match('/^[A-Z0-9]+-[A-Z0-9]+_\d+_\d+.*\.mp3$/i', $fileName)) {
        $secretKey = "wh_iotools_9f8a7c6b5e4d3c2b1a0e9d8c7b6a5f4e";
        $whisperApiUrl = "https://iotools.w8jae.com/api_whisper.php";

        $payload = json_encode([
            "url" => $fileUrl,
            "model" => "small",
            "language" => "en",
            "callback_url" => "https://my-server.com/receive_transcript.php"
        ]);

        $ch = curl_init($whisperApiUrl);
        curl_setopt($ch, CURLOPT_RETURNTRANSFER, true);
        curl_setopt($ch, CURLOPT_POST, true);
        curl_setopt($ch, CURLOPT_POSTFIELDS, $payload);
        curl_setopt($ch, CURLOPT_TIMEOUT, 3); // Non-blocking fast async timeout
        curl_setopt($ch, CURLOPT_HTTPHEADER, [
            'Content-Type: application/json',
            'X-Api-Key: ' . $secretKey
        ]);
        curl_exec($ch);
        curl_close($ch);
    }
}

// Trigger Whisper transcription if audio file matches pattern
trigger_whisper_transcription($publicUrl, $targetFileName);

header('Content-Type: application/json');
echo json_encode([
    'success' => true,
    'message' => 'File uploaded successfully via webhook.',
    'filename' => $targetFileName,
    'url' => $publicUrl,
    'size' => $fileSize,
    'fullPath' => '/var/www/iotools.w8jae.com/' . $uploadedFilePath
]);
exit;
