getConnection(); $iduser = $iduserlogin ?? null; $input = json_decode(file_get_contents('php://input'), true); if (empty($input['ids']) || !is_array($input['ids'])) { throw new Exception('Nessun file selezionato.'); } $ids = array_values(array_filter(array_map('intval', $input['ids']))); if (empty($ids)) { throw new Exception('ID non validi.'); } /* * Local Python service URL. * In produzione su cPanel/Keliweb lo sostituiremo con l'URL reale del servizio Python. */ $pythonServiceUrl = 'http://127.0.0.1:5055/calculate'; $results = []; foreach ($ids as $id) { /* * Recupero job. * Uso placeholder ? per evitare errori PDO HY093. */ if ($iduser === null || $iduser === '') { $stmt = $pdo->prepare(" SELECT * FROM cad_area_jobs WHERE id = ? LIMIT 1 "); $stmt->execute([ $id ]); } else { $stmt = $pdo->prepare(" SELECT * FROM cad_area_jobs WHERE id = ? AND iduser = ? LIMIT 1 "); $stmt->execute([ $id, $iduser ]); } $job = $stmt->fetch(PDO::FETCH_ASSOC); if (!$job) { $results[] = [ 'id' => $id, 'success' => false, 'message' => 'Record non trovato.' ]; continue; } if (empty($job['file_path']) || !file_exists($job['file_path'])) { updateJobError($pdo, $id, 'File PDF non trovato sul server.'); $results[] = [ 'id' => $id, 'success' => false, 'message' => 'File PDF non trovato sul server.' ]; continue; } $stmtProcessing = $pdo->prepare(" UPDATE cad_area_jobs SET status = ?, message = ? WHERE id = ? "); $stmtProcessing->execute([ 'processing', null, $id ]); $pythonResponse = callPythonAreaService( $pythonServiceUrl, $job['file_path'], $job['original_filename'] ); if (empty($pythonResponse['success'])) { updateJobError( $pdo, $id, $pythonResponse['message'] ?? 'Errore servizio Python.', $pythonResponse ); $results[] = [ 'id' => $id, 'success' => false, 'message' => $pythonResponse['message'] ?? 'Errore servizio Python.', 'python_response' => $pythonResponse ]; continue; } $areaMm2 = isset($pythonResponse['area_mm2']) && $pythonResponse['area_mm2'] !== null ? (float)$pythonResponse['area_mm2'] : null; $areaCm2 = isset($pythonResponse['area_cm2']) && $pythonResponse['area_cm2'] !== null ? (float)$pythonResponse['area_cm2'] : ($areaMm2 !== null ? $areaMm2 / 100 : null); $areaM2 = isset($pythonResponse['area_m2']) && $pythonResponse['area_m2'] !== null ? (float)$pythonResponse['area_m2'] : ($areaMm2 !== null ? $areaMm2 / 1000000 : null); $stmtUpdate = $pdo->prepare(" UPDATE cad_area_jobs SET status = ?, area_mm2 = ?, area_cm2 = ?, area_m2 = ?, scale_detected = ?, confidence = ?, message = ?, python_response = ? WHERE id = ? "); $stmtUpdate->execute([ 'completed', $areaMm2, $areaCm2, $areaM2, $pythonResponse['scale_detected'] ?? null, $pythonResponse['confidence'] ?? null, $pythonResponse['message'] ?? null, json_encode($pythonResponse, JSON_PRETTY_PRINT | JSON_UNESCAPED_UNICODE), $id ]); $results[] = [ 'id' => $id, 'success' => true, 'area_mm2' => $areaMm2, 'area_cm2' => $areaCm2, 'area_m2' => $areaM2, 'message' => $pythonResponse['message'] ?? null ]; } echo json_encode([ 'success' => true, 'results' => $results ]); } catch (Throwable $e) { error_log('CAD area process error: ' . $e->getMessage()); error_log('File: ' . $e->getFile()); error_log('Line: ' . $e->getLine()); echo json_encode([ 'success' => false, 'message' => $e->getMessage(), 'file' => $e->getFile(), 'line' => $e->getLine() ]); } function callPythonAreaService(string $url, string $filePath, string $originalFilename): array { if (!class_exists('CURLFile')) { return [ 'success' => false, 'message' => 'CURLFile non disponibile sul server PHP.' ]; } if (!function_exists('curl_init')) { return [ 'success' => false, 'message' => 'Estensione PHP cURL non disponibile.' ]; } $curlFile = new CURLFile($filePath, 'application/pdf', $originalFilename); $postFields = [ 'file' => $curlFile, 'mode' => 'pdf_vector', 'scale_ratio' => '1' ]; $ch = curl_init(); curl_setopt_array($ch, [ CURLOPT_URL => $url, CURLOPT_POST => true, CURLOPT_POSTFIELDS => $postFields, CURLOPT_RETURNTRANSFER => true, CURLOPT_TIMEOUT => 180, CURLOPT_CONNECTTIMEOUT => 20, CURLOPT_SSL_VERIFYPEER => false, CURLOPT_SSL_VERIFYHOST => false ]); $response = curl_exec($ch); if ($response === false) { $error = curl_error($ch); curl_close($ch); return [ 'success' => false, 'message' => 'Errore cURL verso Python: ' . $error ]; } $httpCode = curl_getinfo($ch, CURLINFO_HTTP_CODE); curl_close($ch); $decoded = json_decode($response, true); if ($httpCode < 200 || $httpCode >= 300) { return [ 'success' => false, 'message' => 'Servizio Python HTTP ' . $httpCode, 'raw_response' => $response ]; } if (!is_array($decoded)) { return [ 'success' => false, 'message' => 'Risposta Python non valida.', 'raw_response' => $response ]; } return $decoded; } function updateJobError(PDO $pdo, int $id, string $message, ?array $pythonResponse = null): void { $stmt = $pdo->prepare(" UPDATE cad_area_jobs SET status = ?, message = ?, python_response = ? WHERE id = ? "); $stmt->execute([ 'error', $message, $pythonResponse ? json_encode($pythonResponse, JSON_PRETTY_PRINT | JSON_UNESCAPED_UNICODE) : null, $id ]); }