<?php
/**
 * API للمزامنة الأوفلاين
 * يدعم: إنشاء/تحديث المرضى، الطلبات، النتائج
 */
$config = require __DIR__ . '/../config/config.php';
require_once __DIR__ . '/../src/Core/Database.php';
require_once __DIR__ . '/../src/Core/Auth.php';
require_once __DIR__ . '/../src/Core/Tenant.php';
require_once __DIR__ . '/../src/Core/AuditLog.php';
require_once __DIR__ . '/../src/Core/ErrorHandler.php';
require_once __DIR__ . '/../src/Core/Logger.php';
require_once __DIR__ . '/../src/Core/RateLimiter.php';
require_once __DIR__ . '/../src/Core/ApiMiddleware.php';
require_once __DIR__ . '/../src/Core/ApiResponse.php';
require_once __DIR__ . '/../src/Core/SecurityHeaders.php';

// تعريف DEBUG_MODE
define('DEBUG_MODE', $config['debug'] ?? false);

// تهيئة Logger و Error Handler
$logger = new \App\Core\Logger(__DIR__ . '/../logs/app.log');
\App\Core\ErrorHandler::register($logger);

// إضافة Security Headers للـ API
\App\Core\SecurityHeaders::setForApi();

$db = \App\Core\Database::getInstance($config['db'])->connection();
\App\Core\Tenant::resolve($db);

$middleware = new \App\Core\ApiMiddleware($db, $config);
$middleware->handleCors();

if (session_status() === PHP_SESSION_NONE) {
    $sessionConfig = $config['session'] ?? [];
    ini_set('session.cookie_httponly', $sessionConfig['cookie_httponly'] ?? 1);
    ini_set('session.cookie_secure', ($sessionConfig['cookie_secure'] ?? true) && isset($_SERVER['HTTPS']) ? 1 : 0);
    ini_set('session.cookie_samesite', $sessionConfig['cookie_samesite'] ?? 'Strict');
    session_start();
}

$auth = new \App\Core\Auth($db);

if (!$auth->check()) {
    \App\Core\ApiResponse::unauthorized('يجب تسجيل الدخول');
}

// Rate Limiting
$clientIp = \App\Core\RateLimiter::getClientIp();
$check = $middleware->checkRateLimit($clientIp . '_' . ($auth->userId() ?? 0), 'offline_sync');
if (!$check['allowed']) {
    $middleware->recordApiCall($clientIp . '_' . ($auth->userId() ?? 0), 'offline_sync');
    \App\Core\ApiResponse::rateLimitExceeded();
}
$middleware->recordApiCall($clientIp . '_' . ($auth->userId() ?? 0), 'offline_sync');

$tenantId = (int)\App\Core\Tenant::id();
$userId = $auth->userId();
$action = $_GET['action'] ?? $_POST['action'] ?? '';

$startTime = microtime(true);
$response = ['success' => false, 'error' => '', 'data' => null];

try {
if ($_SERVER['REQUEST_METHOD'] === 'POST') {
    // التحقق من Content-Type
    if (!$middleware->validateContentType()) {
        \App\Core\ApiResponse::error('Content-Type يجب أن يكون application/json', 400);
    }
    
    $input = $middleware->getJsonInput() ?? $_POST;
    if ($input === null) {
        \App\Core\ApiResponse::error('JSON غير صالح', 400);
    }
    
    try {
        if ($action === 'sync_patients') {
            // مزامنة المرضى
            $patients = $input['patients'] ?? [];
            $results = [];
            
            foreach ($patients as $p) {
                $tempId = $p['temp_id'] ?? null;
                $fullName = trim($p['full_name'] ?? '');
                $gender = $p['gender'] ?? null;
                $dob = $p['date_of_birth'] ?? null;
                $phone = trim($p['phone'] ?? '');
                $email = trim($p['email'] ?? '');
                $nationalId = trim($p['national_id'] ?? '');
                $address = trim($p['address'] ?? '');
                
                if ($fullName === '') continue;
                
                $code = $p['patient_code'] ?? ('P' . time() . rand(1000, 9999));
                
                try {
                    $db->query('SELECT email FROM patients LIMIT 1');
                    $stmt = $db->prepare(
                        'INSERT INTO patients (patient_code, full_name, gender, date_of_birth, phone, email, national_id, address, tenant_id)
                         VALUES (:code, :name, :gender, :dob, :phone, :email, :nid, :addr, :tid)
                         ON DUPLICATE KEY UPDATE
                         full_name = VALUES(full_name), gender = VALUES(gender), date_of_birth = VALUES(date_of_birth),
                         phone = VALUES(phone), email = VALUES(email), national_id = VALUES(national_id), address = VALUES(address)'
                    );
                    $stmt->execute([
                        'code' => $code, 'name' => $fullName, 'gender' => $gender ?: null, 'dob' => $dob ?: null,
                        'phone' => $phone ?: null, 'email' => $email ?: null, 'nid' => $nationalId ?: null,
                        'addr' => $address ?: null, 'tid' => $tenantId
                    ]);
                } catch (Throwable $e) {
                    // Fallback بدون email
                    $stmt = $db->prepare(
                        'INSERT INTO patients (patient_code, full_name, gender, date_of_birth, phone, national_id, address, tenant_id)
                         VALUES (:code, :name, :gender, :dob, :phone, :nid, :addr, :tid)
                         ON DUPLICATE KEY UPDATE
                         full_name = VALUES(full_name), gender = VALUES(gender), date_of_birth = VALUES(date_of_birth),
                         phone = VALUES(phone), national_id = VALUES(national_id), address = VALUES(address)'
                    );
                    $stmt->execute([
                        'code' => $code, 'name' => $fullName, 'gender' => $gender ?: null, 'dob' => $dob ?: null,
                        'phone' => $phone ?: null, 'nid' => $nationalId ?: null, 'addr' => $address ?: null, 'tid' => $tenantId
                    ]);
                }
                
                $patientId = (int)$db->lastInsertId();
                if ($patientId === 0) {
                    // موجود مسبقاً
                    $stmt = $db->prepare('SELECT id FROM patients WHERE patient_code = ? AND tenant_id = ?');
                    $stmt->execute([$code, $tenantId]);
                    $row = $stmt->fetch();
                    $patientId = $row ? (int)$row['id'] : 0;
                }
                
                $results[] = ['temp_id' => $tempId, 'id' => $patientId, 'patient_code' => $code];
            }
            
            $response['success'] = true;
            $response['data'] = $results;
            
        } elseif ($action === 'sync_orders') {
            // مزامنة الطلبات
            $orders = $input['orders'] ?? [];
            $results = [];
            
            foreach ($orders as $o) {
                $tempId = $o['temp_id'] ?? null;
                $patientId = (int)($o['patient_id'] ?? 0);
                $doctorId = (int)($o['doctor_id'] ?? 0);
                $branchId = (int)($o['branch_id'] ?? 0);
                $testIds = $o['tests'] ?? [];
                $packageId = (int)($o['package_id'] ?? 0);
                
                if ($patientId <= 0 || empty($testIds)) continue;
                
                if ($branchId <= 0) {
                    $branchId = $auth->branchId() ?? 1;
                }
                
                $db->beginTransaction();
                try {
                    $orderNumber = $o['order_number'] ?? ('O' . time() . rand(1000, 9999));
                    
                    $branchName = null;
                    $bStmt = $db->prepare('SELECT name FROM branches WHERE id = ?');
                    $bStmt->execute([$branchId]);
                    if ($bRow = $bStmt->fetch()) $branchName = $bRow['name'];
                    
                    try {
                        $stmt = $db->prepare(
                            'INSERT INTO lab_orders (order_number, patient_id, doctor_id, order_date, status, total_amount, discount_amount, net_amount, payment_status, branch_id, branch_name, created_by, tenant_id)
                             VALUES (:num, :pid, :doc, NOW(), :status, 0, 0, 0, :pay_status, :branch_id, :branch_name, :created_by, :tid)'
                        );
                        $stmt->execute([
                            'num' => $orderNumber, 'pid' => $patientId, 'doc' => $doctorId > 0 ? $doctorId : null,
                            'status' => 'new', 'pay_status' => 'unpaid', 'branch_id' => $branchId,
                            'branch_name' => $branchName, 'created_by' => $userId, 'tid' => $tenantId
                        ]);
                    } catch (Throwable $ex) {
                        $stmt = $db->prepare(
                            'INSERT INTO lab_orders (order_number, patient_id, doctor_id, order_date, status, total_amount, discount_amount, net_amount, payment_status, branch_id, branch_name, created_by)
                             VALUES (:num, :pid, :doc, NOW(), :status, 0, 0, 0, :pay_status, :branch_id, :branch_name, :created_by)'
                        );
                        $stmt->execute([
                            'num' => $orderNumber, 'pid' => $patientId, 'doc' => $doctorId > 0 ? $doctorId : null,
                            'status' => 'new', 'pay_status' => 'unpaid', 'branch_id' => $branchId,
                            'branch_name' => $branchName, 'created_by' => $userId
                        ]);
                    }
                    
                    $orderId = (int)$db->lastInsertId();
                    
                    // إضافة الفحوصات
                    $placeholders = implode(',', array_fill(0, count($testIds), '?'));
                    $stmt = $db->prepare("SELECT id, default_price FROM tests WHERE id IN ($placeholders)");
                    $stmt->execute($testIds);
                    $testRows = $stmt->fetchAll();
                    
                    $totalAmount = 0;
                    foreach ($testRows as $test) {
                        $price = (float)($test['default_price'] ?? 0);
                        $totalAmount += $price;
                        
                        try {
                            $stmt = $db->prepare('INSERT INTO order_items (order_id, test_id, price, status, tenant_id) VALUES (?, ?, ?, ?, ?)');
                            $stmt->execute([$orderId, (int)$test['id'], $price, 'pending', $tenantId]);
                        } catch (Throwable $e) {
                            $stmt = $db->prepare('INSERT INTO order_items (order_id, test_id, price, status) VALUES (?, ?, ?, ?)');
                            $stmt->execute([$orderId, (int)$test['id'], $price, 'pending']);
                        }
                    }
                    
                    // تحديث المبلغ الإجمالي
                    $stmt = $db->prepare('UPDATE lab_orders SET total_amount = ?, net_amount = ? WHERE id = ?');
                    $stmt->execute([$totalAmount, $totalAmount, $orderId]);
                    
                    $db->commit();
                    $results[] = ['temp_id' => $tempId, 'id' => $orderId, 'order_number' => $orderNumber];
                    
                } catch (Throwable $e) {
                    $db->rollBack();
                    $results[] = ['temp_id' => $tempId, 'error' => $e->getMessage()];
                }
            }
            
            $response['success'] = true;
            $response['data'] = $results;
            
        } elseif ($action === 'sync_results') {
            // مزامنة النتائج
            $results = $input['results'] ?? [];
            $synced = [];
            
            foreach ($results as $r) {
                $itemId = (int)($r['order_item_id'] ?? 0);
                $value = trim($r['result_value'] ?? '');
                $flag = $r['flag'] ?? null;
                $notes = trim($r['notes'] ?? '');
                
                if ($itemId <= 0 || $value === '') continue;
                
                try {
                    $stmt = $db->prepare('SELECT id FROM results WHERE order_item_id = ?');
                    $stmt->execute([$itemId]);
                    $existing = $stmt->fetch();
                    
                    if ($existing) {
                        $stmt = $db->prepare('UPDATE results SET result_value = ?, flag = ?, notes = ?, updated_at = NOW() WHERE order_item_id = ?');
                        $stmt->execute([$value, $flag, $notes ?: null, $itemId]);
                    } else {
                        $stmt = $db->prepare('INSERT INTO results (order_item_id, result_value, flag, notes, created_at) VALUES (?, ?, ?, ?, NOW())');
                        $stmt->execute([$itemId, $value, $flag, $notes ?: null]);
                    }
                    
                    $synced[] = ['order_item_id' => $itemId, 'success' => true];
                } catch (Throwable $e) {
                    $synced[] = ['order_item_id' => $itemId, 'error' => $e->getMessage()];
                }
            }
            
            $response['success'] = true;
            $response['data'] = $synced;
            
        } else {
            \App\Core\ApiResponse::error('إجراء غير معروف', 400);
        }
} elseif ($_SERVER['REQUEST_METHOD'] === 'GET' && $action === 'get_reference_data') {
    // جلب البيانات المرجعية للعمل أوفلاين
    try {
        $data = [
            'patients' => [],
            'doctors' => [],
            'tests' => [],
            'branches' => []
        ];
        
        // المرضى
        try {
            $hasTenant = false;
            try { $db->query('SELECT tenant_id FROM patients LIMIT 1'); $hasTenant = true; } catch (Throwable $e) {}
            if ($hasTenant) {
                $stmt = $db->prepare('SELECT id, patient_code, full_name, phone, gender, date_of_birth FROM patients WHERE tenant_id = ? ORDER BY id DESC LIMIT 500');
                $stmt->execute([$tenantId]);
            } else {
                $stmt = $db->query('SELECT id, patient_code, full_name, phone, gender, date_of_birth FROM patients ORDER BY id DESC LIMIT 500');
            }
            $data['patients'] = $stmt->fetchAll();
        } catch (Throwable $e) {}
        
        // الأطباء
        try {
            $hasTenant = false;
            try { $db->query('SELECT tenant_id FROM doctors LIMIT 1'); $hasTenant = true; } catch (Throwable $e) {}
            if ($hasTenant) {
                $stmt = $db->prepare('SELECT id, full_name, phone, specialization FROM doctors WHERE tenant_id = ? ORDER BY full_name');
                $stmt->execute([$tenantId]);
            } else {
                $stmt = $db->query('SELECT id, full_name, phone, specialization FROM doctors ORDER BY full_name');
            }
            $data['doctors'] = $stmt->fetchAll();
        } catch (Throwable $e) {}
        
        // الفحوصات
        try {
            $hasTenant = false;
            try { $db->query('SELECT tenant_id FROM tests LIMIT 1'); $hasTenant = true; } catch (Throwable $e) {}
            if ($hasTenant) {
                $stmt = $db->prepare('SELECT id, test_code, name, default_price, unit FROM tests WHERE tenant_id = ? ORDER BY name');
                $stmt->execute([$tenantId]);
            } else {
                $stmt = $db->query('SELECT id, test_code, name, default_price, unit FROM tests ORDER BY name');
            }
            $data['tests'] = $stmt->fetchAll();
        } catch (Throwable $e) {}
        
        // الفروع
        try {
            $hasTenant = false;
            try { $db->query('SELECT tenant_id FROM branches LIMIT 1'); $hasTenant = true; } catch (Throwable $e) {}
            if ($hasTenant) {
                $stmt = $db->prepare('SELECT id, name, address, phone FROM branches WHERE tenant_id = ? ORDER BY name');
                $stmt->execute([$tenantId]);
            } else {
                $stmt = $db->query('SELECT id, name, address, phone FROM branches ORDER BY name');
            }
            $data['branches'] = $stmt->fetchAll();
        } catch (Throwable $e) {}
        
        $response['success'] = true;
        $response['data'] = $data;
    }
} catch (\Throwable $e) {
    $logger->exception($e);
    $middleware->handleError($e);
}

$executionTime = (int)((microtime(true) - $startTime) * 1000);
$logger->info('Offline sync API', [
    'action' => $action,
    'user_id' => $userId,
    'execution_time_ms' => $executionTime
]);

\App\Core\ApiResponse::success($response['data'], '', $response['success'] ? 200 : 400);
