From 300ec0e5cf65cf95d3aceb0e97e6c9abb0dc4fe3 Mon Sep 17 00:00:00 2001 From: DevSoftTech Server Date: Fri, 20 Mar 2026 18:11:17 +0530 Subject: [PATCH] feat: migrate OPD template flow to DB and apply related updates --- app/Config/Routes.php | 3 + app/Controllers/Diagnosis.php | 222 --- app/Controllers/Opd.php | 1401 ++++++++++++----- app/Controllers/Opd_prescription.php | 228 ++- app/Controllers/Setting/Doctor.php | 102 +- ...-21-000005_CreateLabAiExtractionTables.php | 2 +- app/Views/Setting/Doctor/Doctor_V.php | 3 +- app/Views/Setting/Doctor/Doctor_profile_V.php | 3 +- app/Views/billing/opd_advice_workspace.php | 2 +- app/Views/billing/opd_invoice_V.php | 3 +- app/Views/billing/opd_medicince_workspace.php | 2 +- .../billing/opd_paper_print_settings.php | 162 ++ .../billing/opd_parts/content/default.html | 13 - .../billing/opd_parts/hospital/default.html | 23 - .../billing/opd_parts/layout/default.html | 23 - .../billing/opd_parts/patient/default.html | 10 - app/Views/billing/opd_parts/patient/edit.html | 18 - app/Views/billing/opd_parts/patient/list.html | 26 - app/Views/billing/opd_template_builder.php | 420 ++++- .../billing/opd_template_builder_list.php | 124 +- .../opd_info_print_letter_head.html | 1 - .../opd_info_print_letter_head_1.html | 1 - .../opd_print_info_letter_head.html | 1 - ...opd_print_parcha_chamunda_hospital_ksp.php | 74 - .../opd_templates/printonletterhead.html | 84 + .../opd_templates/printonplainpaper.html | 86 + .../rx_print_chamunda_plain_paper.html | 1 - .../diagnosis/imaging_ai_result_modal.php | 6 +- ...hospital_logo_20260319_082713_10b1d94f.png | Bin 0 -> 69535 bytes .../uploads/patient/profile_1_1773908930.jpg | Bin 0 -> 63180 bytes 30 files changed, 1976 insertions(+), 1068 deletions(-) create mode 100644 app/Views/billing/opd_paper_print_settings.php delete mode 100644 app/Views/billing/opd_parts/content/default.html delete mode 100644 app/Views/billing/opd_parts/hospital/default.html delete mode 100644 app/Views/billing/opd_parts/layout/default.html delete mode 100644 app/Views/billing/opd_parts/patient/default.html delete mode 100644 app/Views/billing/opd_parts/patient/edit.html delete mode 100644 app/Views/billing/opd_parts/patient/list.html delete mode 100644 app/Views/billing/opd_templates/opd_info_print_letter_head.html delete mode 100644 app/Views/billing/opd_templates/opd_info_print_letter_head_1.html delete mode 100644 app/Views/billing/opd_templates/opd_print_info_letter_head.html delete mode 100644 app/Views/billing/opd_templates/opd_print_parcha_chamunda_hospital_ksp.php create mode 100644 app/Views/billing/opd_templates/printonletterhead.html create mode 100644 app/Views/billing/opd_templates/printonplainpaper.html delete mode 100644 app/Views/billing/opd_templates/rx_print_chamunda_plain_paper.html create mode 100644 public/assets/images/hospital_logo_20260319_082713_10b1d94f.png create mode 100644 public/uploads/patient/profile_1_1773908930.jpg diff --git a/app/Config/Routes.php b/app/Config/Routes.php index 505ab4a..a491ba7 100644 --- a/app/Config/Routes.php +++ b/app/Config/Routes.php @@ -452,6 +452,9 @@ $routes->get('Opd/opd_lettre_print/(:num)', 'Opd::opd_lettre_print/$1'); $routes->get('Opd/opd_lettre_pdf/(:num)', 'Opd::opd_lettre_pdf/$1'); $routes->get('Opd/print_template_builder', 'Opd::print_template_builder'); $routes->post('Opd/print_template_save', 'Opd::print_template_save'); +$routes->post('Opd/print_template_rename', 'Opd::print_template_rename'); +$routes->post('Opd/print_template_delete', 'Opd::print_template_delete'); +$routes->match(['get', 'post'], 'Opd/paper_print_settings', 'Opd::paper_print_settings'); $routes->get('opd_print/invoice_print_pdf/(:num)', 'Opd::invoice_print_pdf/$1'); $routes->get('opd_print/opd_PDF_print/(:num)', 'Opd::opd_pdf_print/$1'); diff --git a/app/Controllers/Diagnosis.php b/app/Controllers/Diagnosis.php index 3ad461b..3b8eed5 100644 --- a/app/Controllers/Diagnosis.php +++ b/app/Controllers/Diagnosis.php @@ -3357,135 +3357,6 @@ class Diagnosis extends BaseController return ''; } - private function extractTextWithDocumentIntelligence(string $absolutePath, string $endpoint, string $key): string - { - try { - $client = service('curlrequest', $this->httpOptions()); - $bytes = @file_get_contents($absolutePath); - if ($bytes === false) { - return ''; - } - - $analyzeUrl = $endpoint . '/documentintelligence/documentModels/prebuilt-read:analyze?api-version=2024-02-29-preview'; - $submit = $client->post($analyzeUrl, [ - 'headers' => [ - 'Content-Type' => 'application/octet-stream', - 'Ocp-Apim-Subscription-Key' => $key, - ], - 'body' => $bytes, - ]); - - if ($submit->getStatusCode() < 200 || $submit->getStatusCode() >= 300) { - return ''; - } - - $operationLocation = trim((string) $submit->getHeaderLine('Operation-Location')); - if ($operationLocation === '') { - return ''; - } - - for ($i = 0; $i < 12; $i++) { - usleep(800000); - $poll = $client->get($operationLocation, [ - 'headers' => [ - 'Ocp-Apim-Subscription-Key' => $key, - ], - ]); - - if ($poll->getStatusCode() < 200 || $poll->getStatusCode() >= 300) { - continue; - } - - $decoded = json_decode((string) $poll->getBody(), true); - if (! is_array($decoded)) { - continue; - } - - $status = strtolower((string) ($decoded['status'] ?? '')); - if ($status === 'succeeded') { - $lines = []; - $pages = $decoded['analyzeResult']['pages'] ?? []; - foreach ($pages as $page) { - $pageLines = $page['lines'] ?? []; - foreach ($pageLines as $line) { - $content = trim((string) ($line['content'] ?? '')); - if ($content !== '') { - $lines[] = $content; - } - } - } - - return trim(implode("\n", $lines)); - } - - if ($status === 'failed') { - return ''; - } - } - } catch (\Throwable $e) { - return ''; - } - - return ''; - } - - private function extractTextWithAzureVisionLlm(string $absolutePath): string - { - $endpoint = rtrim($this->readSetting('AZURE_OPENAI_ENDPOINT'), '/'); - $apiKey = trim($this->readSetting('AZURE_OPENAI_API_KEY')); - $deployment = trim($this->readSetting('AZURE_OPENAI_DEPLOYMENT')); - $apiVersion = trim($this->readSetting('AZURE_OPENAI_API_VERSION')); - - if ($endpoint === '' || $apiKey === '' || $deployment === '') { - return ''; - } - if ($apiVersion === '') { - $apiVersion = '2024-10-21'; - } - - $mime = $this->detectMimeType($absolutePath); - if (! str_starts_with($mime, 'image/')) { - return ''; - } - - $bytes = @file_get_contents($absolutePath); - if ($bytes === false) { - return ''; - } - - $dataUrl = 'data:' . $mime . ';base64,' . base64_encode($bytes); - $url = $endpoint . '/openai/deployments/' . rawurlencode($deployment) . '/chat/completions?api-version=' . rawurlencode($apiVersion); - - try { - $client = service('curlrequest', $this->httpOptions()); - $response = $client->post($url, [ - 'headers' => [ - 'api-key' => $apiKey, - 'Content-Type' => 'application/json', - ], - 'json' => [ - 'messages' => [[ - 'role' => 'user', - 'content' => [ - ['type' => 'text', 'text' => 'Read and return all text from this medical lab report image exactly as plain text.'], - ['type' => 'image_url', 'image_url' => ['url' => $dataUrl]], - ], - ]], - 'temperature' => 0, - 'max_tokens' => 3000, - ], - ]); - - if ($response->getStatusCode() < 200 || $response->getStatusCode() >= 300) { - return ''; - } - - $decoded = json_decode((string) $response->getBody(), true); - return trim((string) ($decoded['choices'][0]['message']['content'] ?? '')); - } catch (\Throwable $e) { - return ''; - } - } /** * @return array @@ -3724,99 +3595,6 @@ class Diagnosis extends BaseController ]; } - /** - * @return array - */ - private function parseLabValuesWithAzureOpenAi(string $ocrText, string $panelName): array - { - $endpoint = rtrim($this->readSetting('AZURE_OPENAI_ENDPOINT'), '/'); - $apiKey = trim($this->readSetting('AZURE_OPENAI_API_KEY')); - $deployment = trim($this->readSetting('AZURE_OPENAI_DEPLOYMENT')); - $apiVersion = trim($this->readSetting('AZURE_OPENAI_API_VERSION')); - - if ($endpoint === '' || $apiKey === '' || $deployment === '') { - return [ - 'provider' => 'azure-openai', - 'model' => '', - 'values' => [], - 'raw' => [], - 'error' => 'Azure OpenAI settings are missing.', - ]; - } - if ($apiVersion === '') { - $apiVersion = '2024-10-21'; - } - - $schemaHint = '{"panel_name":"string","values":[{"test_name":"string","value":"string","unit":"string","reference_range":"string","abnormal_flag":"H|L|N|","raw_line":"string"}] }'; - $prompt = "You are an expert lab report parser for Indian hospitals.\n" . - "Extract only measurable pathology values from OCR text.\n" . - "Return strict JSON only, no markdown, no comments, with schema: " . $schemaHint . "\n" . - "If uncertain, keep empty string. panel_name input: " . $panelName . "\n\n" . - "OCR_TEXT:\n" . mb_substr($ocrText, 0, 14000); - - $url = $endpoint . '/openai/deployments/' . rawurlencode($deployment) . '/chat/completions?api-version=' . rawurlencode($apiVersion); - - $attempts = $this->aiMaxRetries(); - $lastError = 'Azure AI parsing failed.'; - - for ($attempt = 1; $attempt <= $attempts; $attempt++) { - try { - $client = service('curlrequest', $this->httpOptions()); - $response = $client->post($url, [ - 'headers' => [ - 'api-key' => $apiKey, - 'Content-Type' => 'application/json', - ], - 'json' => [ - 'messages' => [[ - 'role' => 'user', - 'content' => $prompt, - ]], - 'temperature' => 0, - 'response_format' => ['type' => 'json_object'], - 'max_tokens' => 2200, - ], - ]); - - if ($response->getStatusCode() < 200 || $response->getStatusCode() >= 300) { - $lastError = 'Azure OpenAI HTTP ' . $response->getStatusCode(); - continue; - } - - $decoded = json_decode((string) $response->getBody(), true); - $content = trim((string) ($decoded['choices'][0]['message']['content'] ?? '')); - if ($content === '') { - $lastError = 'Azure OpenAI returned empty content.'; - continue; - } - - $json = json_decode($content, true); - if (! is_array($json)) { - $lastError = 'Azure OpenAI returned invalid JSON content.'; - continue; - } - - return [ - 'provider' => 'azure-openai', - 'model' => (string) ($decoded['model'] ?? $deployment), - 'values' => is_array($json['values'] ?? null) ? $json['values'] : [], - 'raw' => $decoded, - 'error' => '', - ]; - } catch (\Throwable $e) { - $lastError = $e->getMessage() !== '' ? $e->getMessage() : 'Azure OpenAI request timeout/error.'; - } - } - - return [ - 'provider' => 'azure-openai', - 'model' => '', - 'values' => [], - 'raw' => [], - 'error' => $lastError, - ]; - } - /** * @return array */ diff --git a/app/Controllers/Opd.php b/app/Controllers/Opd.php index be8f863..65417f6 100644 --- a/app/Controllers/Opd.php +++ b/app/Controllers/Opd.php @@ -6,10 +6,15 @@ use App\Controllers\BaseController; use App\Models\OpdModel; use App\Models\PaymentModel; use CodeIgniter\I18n\Time; +use Mpdf\HTMLParserMode; use Mpdf\Mpdf; class Opd extends BaseController { + private const OPD_PAPER_SETTING_KEY = 'OPD_PAPER_PRINT_SETTINGS'; + private const OPD_PAPER_SETTING_KEY_PREFIX = 'OPD_PAPER_PRINT_SETTINGS__'; + private const OPD_TEMPLATE_KEY_PREFIX = 'OPD_PRINT_TEMPLATE__'; + /** * @var array */ @@ -59,8 +64,7 @@ class Opd extends BaseController } $templateNames = $this->collectOpdTemplateNames(); - $name = strtolower(trim((string) $this->request->getGet('name'))); - $name = preg_replace('/[^a-z0-9_\-]/', '', $name) ?? ''; + $name = $this->normalizeOpdTemplateId((string) $this->request->getGet('name')); if ($mode === 'list') { return view('billing/opd_template_builder_list', [ @@ -94,6 +98,7 @@ class Opd extends BaseController 'template_content' => $content, 'template_names' => $templateNames, 'placeholders' => $placeholders, + 'paper_settings' => $this->getOpdPaperPrintSetting($name), ]); } @@ -102,83 +107,17 @@ class Opd extends BaseController */ private function collectOpdTemplateNames(): array { - $names = []; - - $dir = APPPATH . 'Views/billing/opd_templates'; - if (is_dir($dir)) { - $htmlFiles = glob($dir . '/*.html') ?: []; - foreach ($htmlFiles as $file) { - $key = basename((string) $file, '.html'); - if ($key !== '') { - $names[] = strtolower($key); - } - } - - $phpFiles = glob($dir . '/*.php') ?: []; - foreach ($phpFiles as $file) { - $key = basename((string) $file, '.php'); - if ($key !== '') { - $names[] = strtolower($key); - } - } - } - - if ($this->db->tableExists('doctor_master')) { - $doctorFields = $this->db->getFieldNames('doctor_master'); - $templateFields = array_values(array_intersect( - ['opd_print_format', 'opd_blank_print', 'rx_pre_print_letter_head_format', 'rx_blank_letter_head', 'rx_plain_paper'], - $doctorFields - )); - - foreach ($templateFields as $field) { - $rows = $this->db->table('doctor_master') - ->select($field . ' as template_name') - ->where($field . ' IS NOT NULL', null, false) - ->where($field . ' !=', '') - ->distinct() - ->get() - ->getResultArray(); - - foreach ($rows as $row) { - $templateName = strtolower(trim((string) ($row['template_name'] ?? ''))); - $templateName = preg_replace('/[^a-z0-9_\-]/', '', $templateName) ?? ''; - if ($templateName !== '') { - $names[] = $templateName; - } - } - } - } - - $names = array_values(array_unique($names)); - sort($names); - - return $names; + return $this->collectStoredOpdTemplateNames(); } private function readOpdTemplateContentByName(string $name): string { - $name = strtolower(trim($name)); - $name = preg_replace('/[^a-z0-9_\-]/', '', $name) ?? ''; + $name = $this->normalizeOpdTemplateId($name); if ($name === '') { return ''; } - $htmlFile = APPPATH . 'Views/billing/opd_templates/' . $name . '.html'; - if (is_file($htmlFile)) { - return (string) file_get_contents($htmlFile); - } - - $newPhpFile = APPPATH . 'Views/billing/opd_templates/' . $name . '.php'; - if (is_file($newPhpFile)) { - return $this->convertLegacyTemplateSourceToBuilderHtml((string) file_get_contents($newPhpFile)); - } - - $legacyPhpFile = ROOTPATH . 'old_code_ci3/views/dashboard/' . $name . '.php'; - if (is_file($legacyPhpFile)) { - return $this->convertLegacyTemplateSourceToBuilderHtml((string) file_get_contents($legacyPhpFile)); - } - - return ''; + return $this->readStoredOpdTemplateContent($name); } public function print_template_save() @@ -197,8 +136,7 @@ class Opd extends BaseController return $this->response->setJSON(['update' => 0, 'error_text' => 'Invalid section']); } - $name = strtolower(trim((string) $this->request->getPost('name'))); - $name = preg_replace('/[^a-z0-9_\-]/', '', $name) ?? ''; + $name = $this->normalizeOpdTemplateId((string) $this->request->getPost('name')); if ($name === '') { return $this->response->setJSON(['update' => 0, 'error_text' => 'Template name required']); } @@ -208,14 +146,7 @@ class Opd extends BaseController return $this->response->setJSON(['update' => 0, 'error_text' => 'Template content required']); } - $dir = $this->resolveTemplateSectionDirectory($section); - if (!is_dir($dir) && !mkdir($dir, 0777, true) && !is_dir($dir)) { - return $this->response->setJSON(['update' => 0, 'error_text' => 'Unable to create template directory']); - } - - $file = $dir . '/' . $name . '.html'; - $bytes = @file_put_contents($file, $content); - if ($bytes === false) { + if (! $this->saveStoredOpdTemplateContent($name, $content)) { return $this->response->setJSON(['update' => 0, 'error_text' => 'Unable to save template']); } @@ -229,6 +160,356 @@ class Opd extends BaseController ]); } + public function print_template_rename() + { + if (! $this->request->isAJAX()) { + return $this->response->setStatusCode(400)->setJSON(['update' => 0, 'error_text' => 'Invalid request']); + } + + if (! $this->canManageOpdPrintTemplates()) { + return $this->response->setStatusCode(403)->setJSON(['update' => 0, 'error_text' => 'Access denied']); + } + + $oldName = $this->normalizeOpdTemplateId((string) $this->request->getPost('old_name')); + $newName = $this->normalizeOpdTemplateId((string) $this->request->getPost('new_name')); + + if ($oldName === '' || $newName === '') { + return $this->response->setJSON(['update' => 0, 'error_text' => 'Both old and new template names are required']); + } + if ($oldName === $newName) { + return $this->response->setJSON(['update' => 0, 'error_text' => 'New template name must be different']); + } + + if (! $this->renameStoredOpdTemplateContent($oldName, $newName)) { + return $this->response->setJSON(['update' => 0, 'error_text' => 'Template not found or rename failed']); + } + + $this->renameOpdPaperSettingStorageKey($oldName, $newName); + + return $this->response->setJSON([ + 'update' => 1, + 'error_text' => 'Template renamed', + 'old_name' => $oldName, + 'new_name' => $newName, + 'csrfName' => csrf_token(), + 'csrfHash' => csrf_hash(), + ]); + } + + private function renameOpdPaperSettingStorageKey(string $oldName, string $newName): void + { + if (! $this->db->tableExists('hospital_setting')) { + return; + } + + $oldKey = $this->getOpdPaperSettingStorageKey($oldName); + $newKey = $this->getOpdPaperSettingStorageKey($newName); + if ($oldKey === $newKey) { + return; + } + + $existsNew = $this->db->table('hospital_setting') + ->select('id') + ->where('s_name', $newKey) + ->get(1) + ->getRowArray(); + + if (! empty($existsNew['id'])) { + return; + } + + $this->db->table('hospital_setting') + ->where('s_name', $oldKey) + ->update(['s_name' => $newKey]); + } + + public function print_template_delete() + { + if (! $this->request->isAJAX()) { + return $this->response->setStatusCode(400)->setJSON(['update' => 0, 'error_text' => 'Invalid request']); + } + + if (! $this->canManageOpdPrintTemplates()) { + return $this->response->setStatusCode(403)->setJSON(['update' => 0, 'error_text' => 'Access denied']); + } + + $templateName = $this->normalizeOpdTemplateId((string) $this->request->getPost('template_name')); + + if ($templateName === '') { + return $this->response->setJSON(['update' => 0, 'error_text' => 'Template name is required']); + } + + if (! $this->deleteStoredOpdTemplateContent($templateName)) { + return $this->response->setJSON(['update' => 0, 'error_text' => 'Template not found or delete failed']); + } + + $this->deleteOpdPaperSettingStorageKey($templateName); + + return $this->response->setJSON([ + 'update' => 1, + 'error_text' => 'Template deleted', + 'template_name' => $templateName, + 'csrfName' => csrf_token(), + 'csrfHash' => csrf_hash(), + ]); + } + + private function deleteOpdPaperSettingStorageKey(string $templateName): void + { + if (! $this->db->tableExists('hospital_setting')) { + return; + } + + $key = $this->getOpdPaperSettingStorageKey($templateName); + $this->db->table('hospital_setting') + ->where('s_name', $key) + ->delete(); + } + + private function normalizeOpdTemplateId(string $templateId): string + { + $templateId = strtolower(trim($templateId)); + $templateId = str_replace([' ', '.'], '_', $templateId); + $templateId = preg_replace('/[^a-z0-9_\-]+/', '_', $templateId) ?? ''; + $templateId = preg_replace('/_{2,}/', '_', $templateId) ?? $templateId; + + return trim($templateId, '_-'); + } + + private function getOpdTemplateStorageKey(string $templateId): string + { + $templateId = $this->normalizeOpdTemplateId($templateId); + if ($templateId === '') { + return ''; + } + + return self::OPD_TEMPLATE_KEY_PREFIX . $templateId; + } + + private function readStoredOpdTemplateContent(string $templateId): string + { + $storageKey = $this->getOpdTemplateStorageKey($templateId); + if ($storageKey === '' || ! $this->db->tableExists('hospital_setting')) { + return ''; + } + + $row = $this->db->table('hospital_setting') + ->select('s_value') + ->where('s_name', $storageKey) + ->get(1) + ->getRowArray(); + + return trim((string) ($row['s_value'] ?? '')); + } + + /** + * @return array + */ + private function collectStoredOpdTemplateNames(): array + { + if (! $this->db->tableExists('hospital_setting')) { + return []; + } + + $rows = $this->db->table('hospital_setting') + ->select('s_name') + ->like('s_name', self::OPD_TEMPLATE_KEY_PREFIX, 'after') + ->get() + ->getResultArray(); + + $names = []; + foreach ($rows as $row) { + $storageKey = (string) ($row['s_name'] ?? ''); + if (! str_starts_with($storageKey, self::OPD_TEMPLATE_KEY_PREFIX)) { + continue; + } + + $templateId = substr($storageKey, strlen(self::OPD_TEMPLATE_KEY_PREFIX)); + $templateId = $this->normalizeOpdTemplateId((string) $templateId); + if ($templateId !== '') { + $names[] = $templateId; + } + } + + $names = array_values(array_unique($names)); + sort($names); + + return $names; + } + + private function saveStoredOpdTemplateContent(string $templateId, string $content): bool + { + $storageKey = $this->getOpdTemplateStorageKey($templateId); + if ($storageKey === '' || ! $this->db->tableExists('hospital_setting')) { + return false; + } + + $this->ensureHospitalSettingValueCanStoreLargePayload(); + + $existing = $this->db->table('hospital_setting') + ->select('id') + ->where('s_name', $storageKey) + ->get(1) + ->getRowArray(); + + if (! empty($existing['id'])) { + return (bool) $this->db->table('hospital_setting') + ->where('id', (int) $existing['id']) + ->update(['s_value' => $content]); + } + + return (bool) $this->db->table('hospital_setting')->insert([ + 's_name' => $storageKey, + 's_value' => $content, + ]); + } + + private function renameStoredOpdTemplateContent(string $oldTemplateId, string $newTemplateId): bool + { + $oldKey = $this->getOpdTemplateStorageKey($oldTemplateId); + $newKey = $this->getOpdTemplateStorageKey($newTemplateId); + if ($oldKey === '' || $newKey === '' || ! $this->db->tableExists('hospital_setting')) { + return false; + } + + $existingOld = $this->db->table('hospital_setting') + ->select('id') + ->where('s_name', $oldKey) + ->get(1) + ->getRowArray(); + if (empty($existingOld['id'])) { + return false; + } + + $existingNew = $this->db->table('hospital_setting') + ->select('id') + ->where('s_name', $newKey) + ->get(1) + ->getRowArray(); + if (! empty($existingNew['id'])) { + return false; + } + + return (bool) $this->db->table('hospital_setting') + ->where('id', (int) $existingOld['id']) + ->update(['s_name' => $newKey]); + } + + private function deleteStoredOpdTemplateContent(string $templateId): bool + { + $storageKey = $this->getOpdTemplateStorageKey($templateId); + if ($storageKey === '' || ! $this->db->tableExists('hospital_setting')) { + return false; + } + + $row = $this->db->table('hospital_setting') + ->select('id') + ->where('s_name', $storageKey) + ->get(1) + ->getRowArray(); + if (empty($row['id'])) { + return false; + } + + return (bool) $this->db->table('hospital_setting') + ->where('id', (int) $row['id']) + ->delete(); + } + + public function paper_print_settings() + { + if (! $this->canManageOpdPrintTemplates()) { + return $this->response->setStatusCode(403)->setBody('Access denied: OPD paper print settings are restricted.'); + } + + $templateName = $this->normalizeOpdTemplateId((string) ($this->request->getPost('template_name') ?? $this->request->getGet('template_name') ?? '')); + + $notice = ''; + $noticeType = 'success'; + $settings = $this->getOpdPaperPrintSetting($templateName); + + if (strtolower($this->request->getMethod()) === 'post') { + $isReset = (int) ($this->request->getPost('reset') ?? 0) === 1; + if ($isReset) { + $cleared = $this->clearOpdPaperPrintSetting($templateName); + $settings = $this->getOpdPaperPrintSetting($templateName); + $notice = $cleared ? 'OPD paper print settings reset.' : 'Unable to reset OPD paper print settings.'; + $noticeType = $cleared ? 'success' : 'danger'; + + if ($this->request->isAJAX()) { + return $this->response->setJSON([ + 'status' => $cleared ? 'success' : 'error', + 'notice' => $notice, + 'notice_type' => $noticeType, + 'csrfName' => csrf_token(), + 'csrfHash' => csrf_hash(), + 'settings' => $settings, + ]); + } + } + + $pageSize = strtoupper(trim((string) ($this->request->getPost('page_size') ?? 'A4'))); + if (! in_array($pageSize, ['A4', 'A4-L', 'A5', 'A6', 'LETTER', 'LEGAL', 'CUSTOM'], true)) { + $pageSize = 'A4'; + } + + $customWidthMm = (int) $this->normalizeOpdPrintMarginCm($this->request->getPost('custom_width_mm'), 210.0); + $customHeightMm = (int) $this->normalizeOpdPrintMarginCm($this->request->getPost('custom_height_mm'), 297.0); + if ($customWidthMm < 20) { + $customWidthMm = 20; + } + if ($customWidthMm > 600) { + $customWidthMm = 600; + } + if ($customHeightMm < 20) { + $customHeightMm = 20; + } + if ($customHeightMm > 1000) { + $customHeightMm = 1000; + } + + $settings = [ + 'page_size' => $pageSize, + 'custom_width_mm' => $customWidthMm, + 'custom_height_mm' => $customHeightMm, + 'page_margin_top_cm' => $this->normalizeOpdPrintMarginCm($this->request->getPost('page_margin_top_cm'), 6.1), + 'page_margin_bottom_cm' => $this->normalizeOpdPrintMarginCm($this->request->getPost('page_margin_bottom_cm'), 2.5), + 'page_margin_left_cm' => $this->normalizeOpdPrintMarginCm($this->request->getPost('page_margin_left_cm'), 0.7), + 'page_margin_right_cm' => $this->normalizeOpdPrintMarginCm($this->request->getPost('page_margin_right_cm'), 0.7), + 'margin_header_cm' => $this->normalizeOpdPrintMarginCm($this->request->getPost('margin_header_cm'), 0.5), + 'margin_footer_cm' => $this->normalizeOpdPrintMarginCm($this->request->getPost('margin_footer_cm'), 1.5), + 'paper_html_content' => (string) ($this->request->getPost('paper_html_content') ?? ''), + 'header_html' => (string) ($this->request->getPost('header_html') ?? ''), + 'footer_html' => (string) ($this->request->getPost('footer_html') ?? ''), + ]; + + $saved = $this->saveOpdPaperPrintSetting($settings, $templateName); + if ($saved) { + $notice = 'OPD paper print settings saved.'; + $noticeType = 'success'; + } else { + $notice = 'Unable to save OPD paper print settings.'; + $noticeType = 'danger'; + } + + if ($this->request->isAJAX()) { + return $this->response->setJSON([ + 'status' => $saved ? 'success' : 'error', + 'notice' => $notice, + 'notice_type' => $noticeType, + 'csrfName' => csrf_token(), + 'csrfHash' => csrf_hash(), + ]); + } + } + + return view('billing/opd_paper_print_settings', [ + 'settings' => $settings, + 'notice' => $notice, + 'notice_type' => $noticeType, + ]); + } + private function resolveTemplateSectionDirectory(string $section): string { $section = strtolower(trim($section)); @@ -289,8 +570,8 @@ class Opd extends BaseController private function shouldAllowInsecureSslForEndpoint(string $endpoint): bool { $toggle = strtolower($this->readScanAiSettingValue( - ['AZURE_ALLOW_INSECURE_SSL', 'AI_AZURE_ALLOW_INSECURE_SSL', 'APP_AZURE_ALLOW_INSECURE_SSL', 'H_AZURE_ALLOW_INSECURE_SSL'], - ['AZURE_ALLOW_INSECURE_SSL'] + ['DIAGNOSIS_AI_ALLOW_INSECURE_SSL', 'AI_DIAGNOSIS_AI_ALLOW_INSECURE_SSL', 'APP_DIAGNOSIS_AI_ALLOW_INSECURE_SSL', 'H_DIAGNOSIS_AI_ALLOW_INSECURE_SSL'], + ['DIAGNOSIS_AI_ALLOW_INSECURE_SSL'] )); if (in_array($toggle, ['1', 'true', 'yes', 'on'], true)) { return true; @@ -1058,11 +1339,18 @@ class Opd extends BaseController $layoutMode = 'full'; } + $templateKey = $this->normalizeOpdTemplateId((string) $this->request->getGet('template')); + $allowedModes = ['full', 'meta_content', 'content_only', 'header_meta', 'meta_only']; if (! in_array($layoutMode, $allowedModes, true)) { $layoutMode = 'full'; } + // If template is explicitly requested, always render full layout so header/footer are applied. + if ($templateKey !== '') { + $layoutMode = 'full'; + } + $includeContent = in_array($layoutMode, ['full', 'meta_content', 'content_only'], true); $data = $this->buildOpdLetterPrintData($opdId, $sessionId, $includeContent); @@ -1071,76 +1359,247 @@ class Opd extends BaseController } $data['print_layout_mode'] = $layoutMode; - $templateKey = strtolower(trim((string) $this->request->getGet('template'))); - $templateKey = preg_replace('/[^a-z0-9_\-]/', '', $templateKey) ?? ''; $isComposedTemplate = $templateKey !== '' && str_starts_with($templateKey, 'compose_'); if ($isComposedTemplate) { $html = $this->renderComposedOpdPrint($data, $templateKey); } else { - - $viewPath = 'billing/opd_letter_head_pdf'; $customHtml = ''; if ($templateKey !== '') { - $customFile = APPPATH . 'Views/billing/opd_templates/' . $templateKey . '.php'; - $customHtmlFile = APPPATH . 'Views/billing/opd_templates/' . $templateKey . '.html'; - if (is_file($customFile)) { - $viewPath = 'billing/opd_templates/' . $templateKey; - } elseif (is_file($customHtmlFile)) { - $customHtml = (string) file_get_contents($customHtmlFile); - } + $customHtml = $this->readStoredOpdTemplateContent($templateKey); } - if ($viewPath !== 'billing/opd_letter_head_pdf') { - $html = view($viewPath, $data); - } elseif ($customHtml !== '') { + if ($customHtml !== '') { $legacyVars = $this->buildLegacyDashboardTemplateVars($data); $html = $this->renderCurlyTemplate($customHtml, $legacyVars); - } elseif ($templateKey !== '') { - $legacyFile = ROOTPATH . 'old_code_ci3/views/dashboard/' . $templateKey . '.php'; - if (is_file($legacyFile)) { - $legacyVars = $this->buildLegacyDashboardTemplateVars($data); - $html = $this->renderLegacyPhpTemplate($legacyFile, $legacyVars); - } else { - $html = view('billing/opd_letter_head_pdf', $data); - } } else { $html = view('billing/opd_letter_head_pdf', $data); } } + // SHORT-CIRCUIT: When DB template content is found, render it directly with token + // substitution and skip all per-template paper settings entirely. + if ($customHtml !== '') { + $tokenVars = $this->buildOpdPdfTokenVars($data); + $html = $this->applyOpdPdfTemplateTokens($customHtml, $tokenVars); + $html = $this->sanitizeOpdNamedHeaderFooterReferences($html); + + $mpdf = new Mpdf([ + 'mode' => 'utf-8', + 'format' => 'A4', + 'orientation' => 'P', + 'margin_left' => 5, + 'margin_right' => 5, + 'margin_top' => 5, + 'margin_bottom' => 5, + 'margin_header' => 5, + 'margin_footer' => 5, + 'default_font' => 'freeserif', + 'autoScriptToLang' => true, + 'autoLangToFont' => true, + 'tempDir' => WRITEPATH . 'cache', + ]); + + $opdCode = (string) ($data['opd_master'][0]->opd_code ?? ('OPD-' . $opdId)); + $mpdf->SetTitle('OPD Prescription ' . $opdCode); + $mpdf->WriteHTML($html); + + $fileName = 'OPD_Prescription_' . str_replace('/', '-', $opdCode) . '.pdf'; + return $this->response + ->setHeader('Content-Type', 'application/pdf') + ->setHeader('Content-Disposition', 'inline; filename="' . $fileName . '"') + ->setBody($mpdf->Output($fileName, 'S')); + } + + $docPrintSetting = $this->getOpdPaperPrintSetting($templateKey); + $tokenVars = $this->buildOpdPdfTokenVars($data); + $paper = strtolower(trim((string) $this->request->getGet('paper'))); - $format = 'A4'; + $format = strtoupper(trim((string) ($docPrintSetting['page_size'] ?? 'A4'))); + if ($format === '') { + $format = 'A4'; + } if (in_array($paper, ['a5', 'a6', 'letter'], true)) { $format = strtoupper($paper); } - $marginLeft = 8; - $marginRight = 8; - $marginTop = 8; - $marginBottom = 8; + $customWidthMm = (int) $this->normalizeOpdPrintMarginCm($docPrintSetting['custom_width_mm'] ?? null, 210.0); + $customHeightMm = (int) $this->normalizeOpdPrintMarginCm($docPrintSetting['custom_height_mm'] ?? null, 297.0); + if ($customWidthMm < 20) { + $customWidthMm = 20; + } + if ($customWidthMm > 600) { + $customWidthMm = 600; + } + if ($customHeightMm < 20) { + $customHeightMm = 20; + } + if ($customHeightMm > 1000) { + $customHeightMm = 1000; + } + $mpdfFormat = $format === 'CUSTOM' ? [$customWidthMm, $customHeightMm] : $format; + + $hasDocSetting = ! empty($docPrintSetting); + if ($hasDocSetting) { + $marginLeftCm = $this->normalizeOpdPrintMarginCm($docPrintSetting['page_margin_left_cm'] ?? null, 0.7); + $marginRightCm = $this->normalizeOpdPrintMarginCm($docPrintSetting['page_margin_right_cm'] ?? null, 0.7); + $marginTopCm = $this->normalizeOpdPrintMarginCm($docPrintSetting['page_margin_top_cm'] ?? null, 6.1); + $marginBottomCm = $this->normalizeOpdPrintMarginCm($docPrintSetting['page_margin_bottom_cm'] ?? null, 2.5); + $marginHeaderCm = $this->normalizeOpdPrintMarginCm($docPrintSetting['margin_header_cm'] ?? null, 0.5); + $marginFooterCm = $this->normalizeOpdPrintMarginCm($docPrintSetting['margin_footer_cm'] ?? null, 1.5); + $marginLeft = $marginLeftCm * 10; + $marginRight = $marginRightCm * 10; + $marginTop = $marginTopCm * 10; + $marginBottom = $marginBottomCm * 10; + $marginHeader = $marginHeaderCm * 10; + $marginFooter = $marginFooterCm * 10; + } else { + $marginLeftCm = 0.7; + $marginRightCm = 0.7; + $marginTopCm = 6.1; + $marginBottomCm = 2.5; + $marginHeaderCm = 0.5; + $marginFooterCm = 1.5; + $marginLeft = 8; + $marginRight = 8; + $marginTop = 8; + $marginBottom = 8; + $marginHeader = 5; + $marginFooter = 10; + } if ($format === 'A6') { $marginLeft = 6; $marginRight = 6; $marginTop = 6; $marginBottom = 6; + $marginLeftCm = 0.6; + $marginRightCm = 0.6; + $marginTopCm = 0.6; + $marginBottomCm = 0.6; } + // Add margin variables to token replacement + $tokenVars['MarginTop'] = (string) $marginTopCm; + $tokenVars['MarginBottom'] = (string) $marginBottomCm; + $tokenVars['MarginLeft'] = (string) $marginLeftCm; + $tokenVars['MarginRight'] = (string) $marginRightCm; + $tokenVars['MarginHeader'] = (string) $marginHeaderCm; + $tokenVars['MarginFooter'] = (string) $marginFooterCm; + // Aliases for alternate naming + $tokenVars['page_margin_top_cm'] = (string) $marginTopCm; + $tokenVars['page_margin_bottom_cm'] = (string) $marginBottomCm; + $tokenVars['page_margin_left_cm'] = (string) $marginLeftCm; + $tokenVars['page_margin_right_cm'] = (string) $marginRightCm; + $tokenVars['margin_header_cm'] = (string) $marginHeaderCm; + $tokenVars['margin_footer_cm'] = (string) $marginFooterCm; + $mpdf = new Mpdf([ 'mode' => 'utf-8', - 'format' => $format, + 'format' => $mpdfFormat, 'orientation' => 'P', 'margin_left' => $marginLeft, 'margin_right' => $marginRight, 'margin_top' => $marginTop, 'margin_bottom' => $marginBottom, + 'margin_header' => $marginHeader, + 'margin_footer' => $marginFooter, 'default_font' => 'freeserif', 'autoScriptToLang' => true, 'autoLangToFont' => true, 'tempDir' => WRITEPATH . 'cache', ]); + $rawHeaderHtml = trim((string) ($docPrintSetting['header_html'] ?? '')); + $rawFooterHtml = trim((string) ($docPrintSetting['footer_html'] ?? '')); + $rawPaperHtmlContent = trim((string) ($docPrintSetting['paper_html_content'] ?? '')); + $prefixHtml = ''; + + // Build base @page CSS block from margin settings. + $buildPageStyleBlock = static function (bool $useHeader, bool $useFooter) use ($marginTopCm, $marginBottomCm, $marginLeftCm, $marginRightCm, $marginHeaderCm, $marginFooterCm): string { + $css = '' . "\n"; + + return $css; + }; + + // Resolve body content first. + if ($rawPaperHtmlContent !== '') { + $hasContentPlaceholder = preg_match('/<\?=\s*\$content\s*\?>|<\?=\$content\?>|\{\{content\}\}|\{content\}/i', $rawPaperHtmlContent) === 1; + $paperHtml = $this->applyOpdPdfTemplateTokens($rawPaperHtmlContent, $tokenVars); + $paperHtml = str_replace(['', '', '{{content}}', '{content}'], $html, $paperHtml); + if ($hasContentPlaceholder && strpos($paperHtml, $html) === false) { + $paperHtml .= $html; + } + $html = $this->sanitizeOpdNamedHeaderFooterReferences($paperHtml); + } + + // If separate header/footer fields are provided, always apply them around the resolved body. + if ($rawHeaderHtml !== '' || $rawFooterHtml !== '') { + $combinedHtml = $buildPageStyleBlock($rawHeaderHtml !== '', $rawFooterHtml !== ''); + + if ($rawHeaderHtml !== '') { + $renderedHeaderHtml = $this->applyOpdPdfTemplateTokens($rawHeaderHtml, $tokenVars); + if (!preg_match('/<\s*htmlpageheader\b/i', $renderedHeaderHtml)) { + $combinedHtml .= '' . "\n" . $renderedHeaderHtml . "\n" . '' . "\n"; + } else { + $combinedHtml .= $renderedHeaderHtml . "\n"; + } + } + + if ($rawFooterHtml !== '') { + $renderedFooterHtml = $this->applyOpdPdfTemplateTokens($rawFooterHtml, $tokenVars); + if (!preg_match('/<\s*htmlpagefooter\b/i', $renderedFooterHtml)) { + $combinedHtml .= '' . "\n" . $renderedFooterHtml . "\n" . '' . "\n"; + } else { + $combinedHtml .= $renderedFooterHtml . "\n"; + } + } + + $combinedHtml .= $html; + $html = $this->sanitizeOpdNamedHeaderFooterReferences($combinedHtml); + $rawHeaderHtml = ''; + $rawFooterHtml = ''; + } + + if ($rawHeaderHtml !== '') { + $renderedHeaderHtml = $this->applyOpdPdfTemplateTokens($rawHeaderHtml, $tokenVars); + if (preg_match('/<\s*(htmlpageheader|sethtmlpageheader)\b/i', $renderedHeaderHtml) === 1) { + $prefixHtml .= $renderedHeaderHtml; + } else { + $mpdf->SetHTMLHeader($renderedHeaderHtml, 'O'); + $mpdf->SetHTMLHeader($renderedHeaderHtml, 'E'); + } + } + + if ($rawFooterHtml !== '') { + $renderedFooterHtml = $this->applyOpdPdfTemplateTokens($rawFooterHtml, $tokenVars); + if (preg_match('/<\s*(htmlpagefooter|sethtmlpagefooter)\b/i', $renderedFooterHtml) === 1) { + $prefixHtml .= $renderedFooterHtml; + } else { + $mpdf->SetHTMLFooter($renderedFooterHtml, 'O'); + $mpdf->SetHTMLFooter($renderedFooterHtml, 'E'); + } + } + + if ($prefixHtml !== '') { + $mpdf->WriteHTML($prefixHtml, HTMLParserMode::HTML_HEADER_BUFFER); + } + $opdCode = (string) ($data['opd_master'][0]->opd_code ?? ('OPD-' . $opdId)); $mpdf->SetTitle('OPD Prescription ' . $opdCode); $mpdf->WriteHTML($html); @@ -1155,20 +1614,24 @@ class Opd extends BaseController public function opd_pdf_print(int $opdId) { - $printConfig = $this->resolveDoctorPrintConfigByField($opdId, 'opd_print_format', 'meta_only'); - $url = base_url('Opd/opd_lettre_pdf/' . (int) $opdId . '?layout=' . urlencode($printConfig['layout'])); + $printConfig = $this->resolveDoctorPrintConfigByField($opdId, 'opd_blank_print', 'meta_only'); + $url = base_url('Opd/opd_lettre_pdf/' . (int) $opdId); if ($printConfig['template'] !== '') { - $url .= '&template=' . urlencode($printConfig['template']); + $url .= '?template=' . urlencode($printConfig['template']); + } else { + $url .= '?layout=' . urlencode($printConfig['layout']); } return redirect()->to($url); } public function opd_blank_print(int $opdId) { - $printConfig = $this->resolveDoctorPrintConfigByField($opdId, 'opd_blank_print', 'header_meta'); - $url = base_url('Opd/opd_lettre_pdf/' . (int) $opdId . '?layout=' . urlencode($printConfig['layout'])); + $printConfig = $this->resolveDoctorPrintConfigByField($opdId, 'opd_print_format', 'header_meta'); + $url = base_url('Opd/opd_lettre_pdf/' . (int) $opdId); if ($printConfig['template'] !== '') { - $url .= '&template=' . urlencode($printConfig['template']); + $url .= '?template=' . urlencode($printConfig['template']); + } else { + $url .= '?layout=' . urlencode($printConfig['layout']); } return redirect()->to($url); } @@ -1176,9 +1639,11 @@ class Opd extends BaseController public function opd_cont_print(int $opdId) { $printConfig = $this->resolveDoctorPrintConfigByField($opdId, 'opd_print_format', 'content_only'); - $url = base_url('Opd/opd_lettre_pdf/' . (int) $opdId . '?layout=' . urlencode($printConfig['layout'])); + $url = base_url('Opd/opd_lettre_pdf/' . (int) $opdId); if ($printConfig['template'] !== '') { - $url .= '&template=' . urlencode($printConfig['template']); + $url .= '?template=' . urlencode($printConfig['template']); + } else { + $url .= '?layout=' . urlencode($printConfig['layout']); } return redirect()->to($url); } @@ -1224,7 +1689,7 @@ class Opd extends BaseController return ['layout' => 'full', 'template' => '']; } - $templateKey = preg_replace('/[^a-z0-9_\-]/', '', $raw) ?? ''; + $templateKey = $this->normalizeOpdTemplateId($raw); if ($templateKey !== '') { return ['layout' => $fallbackLayout, 'template' => $templateKey]; } @@ -1519,31 +1984,336 @@ class Opd extends BaseController }, $html); } - private function convertLegacyTemplateSourceToBuilderHtml(string $source): string + private function getOpdPaperSettingStorageKey(string $templateName = ''): string { - if (trim($source) === '') { + $templateName = $this->normalizeOpdTemplateId($templateName); + if ($templateName === '') { + return self::OPD_PAPER_SETTING_KEY; + } + + return self::OPD_PAPER_SETTING_KEY_PREFIX . $templateName; + } + + private function readOpdPaperSettingPayloadByKey(string $storageKey): string + { + if (! $this->db->tableExists('hospital_setting')) { return ''; } - $html = str_replace(["\r\n", "\r"], "\n", $source); + $row = $this->db->table('hospital_setting') + ->select('s_value') + ->where('s_name', $storageKey) + ->get(1) + ->getRowArray(); - $patterns = [ - '/<\?php\s+echo\s+esc\(\s*\$([a-zA-Z_][a-zA-Z0-9_]*)[^\)]*\)\s*;?\s*\?>/i' => '{{$1}}', - '/<\?php\s+echo\s+\$([a-zA-Z_][a-zA-Z0-9_]*)\s*;?\s*\?>/i' => '{{$1}}', - '/<\?=\s*\$([a-zA-Z_][a-zA-Z0-9_]*)\s*;?\s*\?>/i' => '{{$1}}', - '/<\?php\s+echo\s*\(\s*\$([a-zA-Z_][a-zA-Z0-9_]*)\s*\)\s*;?\s*\?>/i' => '{{$1}}', + return trim((string) ($row['s_value'] ?? '')); + } + + /** + * @return array + */ + private function getOpdPaperPrintSetting(string $templateName = ''): array + { + $defaults = [ + 'page_size' => 'A4', + 'custom_width_mm' => 210, + 'custom_height_mm' => 297, + 'page_margin_top_cm' => 6.1, + 'page_margin_bottom_cm' => 2.5, + 'page_margin_left_cm' => 0.7, + 'page_margin_right_cm' => 0.7, + 'margin_header_cm' => 0.5, + 'margin_footer_cm' => 1.5, + 'paper_html_content' => '', + 'header_html' => '', + 'footer_html' => '', ]; - foreach ($patterns as $regex => $replacement) { - $html = (string) preg_replace($regex, $replacement, $html); + $storageKey = $this->getOpdPaperSettingStorageKey($templateName); + $raw = $this->readOpdPaperSettingPayloadByKey($storageKey); + if ($raw === '' && $storageKey !== self::OPD_PAPER_SETTING_KEY) { + // Backward compatibility with legacy global settings. + $raw = $this->readOpdPaperSettingPayloadByKey(self::OPD_PAPER_SETTING_KEY); + } + if ($raw === '') { + return $defaults; } - $html = (string) preg_replace('/<\?(?:php|=)[\s\S]*?\?>/i', '', $html); - $html = trim($html); + $decoded = json_decode($raw, true); + if (! is_array($decoded)) { + return $defaults; + } + + return array_merge($defaults, $decoded); + } + + /** + * @param array $settings + */ + private function saveOpdPaperPrintSetting(array $settings, string $templateName = ''): bool + { + if (! $this->db->tableExists('hospital_setting')) { + return false; + } + + $payload = json_encode($settings, JSON_UNESCAPED_UNICODE); + if ($payload === false) { + return false; + } + + $storageKey = $this->getOpdPaperSettingStorageKey($templateName); + + $this->ensureHospitalSettingValueCanStoreLargePayload(); + + $existing = $this->db->table('hospital_setting') + ->select('id') + ->where('s_name', $storageKey) + ->get(1) + ->getRowArray(); + + if (! empty($existing['id'])) { + $ok = $this->db->table('hospital_setting') + ->where('id', (int) $existing['id']) + ->update(['s_value' => $payload]); + + if (! $ok) { + return false; + } + + return $this->isOpdPaperSettingPayloadPersisted($payload, $storageKey); + } + + $ok = $this->db->table('hospital_setting')->insert([ + 's_name' => $storageKey, + 's_value' => $payload, + ]); + + if (! $ok) { + return false; + } + + return $this->isOpdPaperSettingPayloadPersisted($payload, $storageKey); + } + + private function ensureHospitalSettingValueCanStoreLargePayload(): void + { + try { + $row = $this->db->query("SHOW COLUMNS FROM hospital_setting LIKE 's_value'")->getRowArray(); + $type = strtolower(trim((string) ($row['Type'] ?? ''))); + if ($type === '') { + return; + } + + // Legacy schema uses varchar(200), which truncates template HTML payloads. + if (str_starts_with($type, 'varchar(')) { + $this->db->query('ALTER TABLE hospital_setting MODIFY s_value LONGTEXT CHARACTER SET utf32 COLLATE utf32_unicode_ci DEFAULT NULL'); + } + } catch (\Throwable $e) { + // Keep save flow non-fatal; caller validates persistence right after save. + } + } + + private function isOpdPaperSettingPayloadPersisted(string $payload, string $storageKey): bool + { + $row = $this->db->table('hospital_setting') + ->select('s_value') + ->where('s_name', $storageKey) + ->get(1) + ->getRowArray(); + + return ((string) ($row['s_value'] ?? '')) === $payload; + } + + private function clearOpdPaperPrintSetting(string $templateName = ''): bool + { + if (! $this->db->tableExists('hospital_setting')) { + return false; + } + + $storageKey = $this->getOpdPaperSettingStorageKey($templateName); + + $ok = $this->db->table('hospital_setting') + ->where('s_name', $storageKey) + ->delete(); + + return (bool) $ok; + } + + private function normalizeOpdPrintMarginCm($value, float $default): float + { + if ($value === null || $value === '') { + return $default; + } + + $number = (float) $value; + if (! is_finite($number)) { + $number = $default; + } + + $number = max(0.0, min(25.0, $number)); + + return round($number, 2); + } + + /** + * @param array $data + * @return array + */ + private function buildOpdPdfTokenVars(array $data): array + { + $legacy = $this->buildLegacyDashboardTemplateVars($data); + $tokens = []; + foreach ($legacy as $key => $value) { + if (is_scalar($value)) { + $tokens[(string) $key] = (string) $value; + } + } + + // Load hospital settings from database + $hName = $this->readSettingValueFromDb('H_Name'); + $hAddress1 = $this->readSettingValueFromDb('H_address_1'); + $hAddress2 = $this->readSettingValueFromDb('H_address_2'); + $hPhone = $this->readSettingValueFromDb('H_phone_No'); + $hEmail = $this->readSettingValueFromDb('H_Email'); + $hLogo = $this->readSettingValueFromDb('H_logo'); + + // Try constants as fallback if database values are empty + if ($hName === '') { + $hName = defined('H_Name') ? (string) constant('H_Name') : ''; + } + if ($hAddress1 === '') { + $hAddress1 = defined('H_address_1') ? (string) constant('H_address_1') : ''; + } + if ($hAddress2 === '') { + $hAddress2 = defined('H_address_2') ? (string) constant('H_address_2') : ''; + } + if ($hPhone === '') { + $hPhone = defined('H_phone_No') ? (string) constant('H_phone_No') : ''; + } + if ($hEmail === '') { + $hEmail = defined('H_Email') ? (string) constant('H_Email') : ''; + } + if ($hLogo === '') { + $hLogo = defined('H_logo') ? (string) constant('H_logo') : ''; + } + + $tokens['H_Name'] = $hName; + $tokens['H_address_1'] = $hAddress1; + $tokens['H_address_2'] = $hAddress2; + $tokens['H_phone_No'] = $hPhone; + $tokens['H_Email'] = $hEmail; + $tokens['H_logo'] = $hLogo; + $tokens['H_logo_abs'] = $hLogo !== '' ? FCPATH . 'assets/images/' . $hLogo : ''; + + $tokens['hospital_name'] = $hName; + $tokens['hospital_address'] = trim($hAddress1 . ', ' . $hAddress2, ', '); + $tokens['hospital_phone'] = $hPhone; + $tokens['hospital_email'] = $hEmail; + $tokens['print_time'] = date('d-m-Y H:i:s'); + $tokens['current_date'] = date('d-m-Y'); + $tokens['doctor_name'] = trim((string) ($tokens['doctor_name'] ?? (($data['opd_master'][0]->doc_name ?? '') ?? ''))); + $tokens['doctor_sign_html'] = nl2br((string) ($data['opd_master'][0]->doc_sign ?? '')); + $tokens['content'] = (string) ($tokens['content'] ?? ''); + + return $tokens; + } + + /** + * @param array $vars + */ + private function applyOpdPdfTemplateTokens(string $templateHtml, array $vars): string + { + if ($templateHtml === '') { + return ''; + } + + $templateHtml = $this->normalizeLegacyOpdPaperTemplate($templateHtml); + + $replace = []; + foreach ($vars as $key => $value) { + $replace['{{' . $key . '}}'] = $value; + $replace['{' . $key . '}'] = $value; + } + + return strtr($templateHtml, $replace); + } + + private function normalizeLegacyOpdPaperTemplate(string $html): string + { + $out = str_replace(["\r\n", "\r"], "\n", $html); + + $mapPatterns = [ + '/<\?=\s*H_Name\s*\?>/i' => '{{H_Name}}', + '/<\?=\s*H_address_1\s*\?>/i' => '{{H_address_1}}', + '/<\?=\s*H_address_2\s*\?>/i' => '{{H_address_2}}', + '/<\?=\s*H_phone_No\s*\?>/i' => '{{H_phone_No}}', + '/<\?=\s*H_Email\s*\?>/i' => '{{H_Email}}', + '/<\?=\s*H_logo\s*\?>/i' => '{{H_logo}}', + '/<\?=\s*\$opd_master\[0\]->doc_name\s*\?>/i' => '{{doctor_name}}', + '/<\?=\s*nl2br\(\s*\$opd_master\[0\]->doc_sign\s*\)\s*\?>/i' => '{{doctor_sign_html}}', + '/<\?=\s*date\(\s*[\"\']d-m-Y\s+H:i:s[\"\']\s*\)\s*\?>/i' => '{{print_time}}', + '/<\?=\s*\$content\s*\?>/i' => '{{content}}', + '/<\?=\s*\$content\s*;?\s*\?>/i' => '{{content}}', + '/<\?=\s*\$\w+\s*\?>/i' => '', + ]; + + foreach ($mapPatterns as $pattern => $replacement) { + $out = (string) preg_replace($pattern, $replacement, $out); + } + + // Legacy conditional phone block fallback. + $out = (string) preg_replace( + '/<\?php\s*if\s*\(\s*H_phone_No\s*!\s*=\s*[\"\']{0,1}\s*[\"\']{0,1}\s*\)\s*\{\s*echo\s*[\"\']Phone:\s*[\"\']\s*\.\s*H_phone_No\s*;\s*\}\s*\?>/is', + 'Phone: {{H_phone_No}}', + $out + ); + + // Convert generic echo statements that match a known scalar token key. + $out = (string) preg_replace('/<\?php\s+echo\s+\$content\s*;?\s*\?>/i', '{{content}}', $out); + + // Remove remaining PHP blocks that cannot be interpreted safely. + $out = (string) preg_replace('/<\?(?:php|=)[\s\S]*?\?>/i', '', $out); + + return trim($out); + } + + private function sanitizeOpdNamedHeaderFooterReferences(string $html): string + { + if ($html === '') { + return ''; + } + + $hasMyHeaderBlock = preg_match('/<\s*htmlpageheader\b[^>]*\bname\s*=\s*["\']myHeader["\']/i', $html) === 1; + $hasMyFooterBlock = preg_match('/<\s*htmlpagefooter\b[^>]*\bname\s*=\s*["\']myFooter["\']/i', $html) === 1; + + if (! $hasMyHeaderBlock) { + $html = (string) preg_replace('/^\s*header\s*:\s*html_myHeader\s*;\s*$/im', '', $html); + } + if (! $hasMyFooterBlock) { + $html = (string) preg_replace('/^\s*footer\s*:\s*html_myFooter\s*;\s*$/im', '', $html); + } return $html; } + /** + * Read a setting value from the hospital_setting table + */ + private function readSettingValueFromDb(string $name): string + { + if (! $this->db->tableExists('hospital_setting')) { + return ''; + } + + $row = $this->db->table('hospital_setting') + ->select('s_value') + ->where('s_name', $name) + ->get(1) + ->getRowArray(); + + return trim((string) ($row['s_value'] ?? '')); + } + private function buildOpdLetterPrintData(int $opdId, int $sessionId = 0, bool $includeContent = true): ?array { $sql = "Select * from opd_master where opd_id=" . (int) $opdId; @@ -2652,9 +3422,9 @@ class Opd extends BaseController $readiness = $this->getScanAiReadiness(); $this->addScanAiDebug('readiness: ' . $readiness['summary']); - // Fail early when neither Azure OpenAI nor Document Intelligence is configured. - if (! $readiness['azure_openai'] && ! $readiness['docintel']) { - $msg = 'AI not configured. Set Azure OpenAI deployment (vision-capable). Optional DocIntel improves OCR.'; + // Fail early when neither AI server diagnosis nor OCR endpoints are configured. + if (! $readiness['ai_server'] && ! $readiness['ocr_server']) { + $msg = 'AI not configured. Set DIAGNOSIS_AI_SERVER_URL and DIAGNOSIS_AI_OCR_ENDPOINT in AI Settings.'; $this->updateScanAiColumns($fileId, [ 'scan_type' => $scanType, 'document_type' => $this->classifyDocumentType('', $scanType, $filename), @@ -2731,7 +3501,7 @@ class Opd extends BaseController $documentType = $this->classifyDocumentType('', $scanType, $filename); $debugInfo = $this->formatScanAiDebug(); - $failMsg = 'Azure providers could not read usable text from this file. ' . $readiness['summary'] . '. Ensure Azure deployment supports image input and DocIntel endpoint/API is valid.'; + $failMsg = 'AI server could not read usable text from this file. ' . $readiness['summary'] . '. Ensure OCR endpoint and token settings are valid.'; if ($debugInfo !== '') { $failMsg .= ' Debug: ' . $debugInfo; } @@ -3341,312 +4111,121 @@ class Opd extends BaseController } /** - * @return array{endpoint:string,api_key:string,deployment:string,api_version:string} - */ - private function getAzureOpenAiConfigForScan(): array - { - $endpoint = $this->readScanAiSettingValue( - ['AZURE_OPENAI_ENDPOINT', 'AI_AZURE_OPENAI_ENDPOINT', 'APP_AZURE_OPENAI_ENDPOINT', 'H_AZURE_OPENAI_ENDPOINT'], - ['AZURE_OPENAI_ENDPOINT'] - ); - - $apiKey = $this->readScanAiSettingValue( - ['AZURE_OPENAI_API_KEY', 'AI_AZURE_OPENAI_API_KEY', 'APP_AZURE_OPENAI_API_KEY', 'H_AZURE_OPENAI_API_KEY'], - ['AZURE_OPENAI_API_KEY'] - ); - - $deployment = $this->readScanAiSettingValue( - ['AZURE_OPENAI_DEPLOYMENT', 'AI_AZURE_OPENAI_DEPLOYMENT', 'APP_AZURE_OPENAI_DEPLOYMENT', 'H_AZURE_OPENAI_DEPLOYMENT'], - ['AZURE_OPENAI_DEPLOYMENT'] - ); - - $apiVersion = $this->readScanAiSettingValue( - ['AZURE_OPENAI_API_VERSION', 'AI_AZURE_OPENAI_API_VERSION', 'APP_AZURE_OPENAI_API_VERSION', 'H_AZURE_OPENAI_API_VERSION'], - ['AZURE_OPENAI_API_VERSION'] - ); - - if ($apiVersion === '') { - $apiVersion = '2024-10-21'; - } - - $endpoint = $this->normalizeAzureEndpointBase($endpoint); - - return [ - 'endpoint' => $endpoint, - 'api_key' => $apiKey, - 'deployment' => $deployment, - 'api_version' => $apiVersion, - ]; - } - - /** - * @return array{azure_openai:bool,docintel:bool,summary:string} + * @return array{ai_server:bool,ocr_server:bool,summary:string} */ private function getScanAiReadiness(): array { - $azure = $this->getAzureOpenAiConfigForScan(); - $azureOpenAi = ($azure['endpoint'] !== '' && $azure['api_key'] !== '' && $azure['deployment'] !== ''); + $base = $this->resolveAiServerBaseUrlForScan(); + $aiServer = $base !== ''; - $docIntelEndpoint = rtrim($this->readScanAiSettingValue( - ['AZURE_DOCINTEL_ENDPOINT', 'AI_AZURE_DOCINTEL_ENDPOINT', 'APP_AZURE_DOCINTEL_ENDPOINT', 'H_AZURE_DOCINTEL_ENDPOINT'], - ['AZURE_DOCINTEL_ENDPOINT'] - ), '/'); - $docIntelKey = $this->readScanAiSettingValue( - ['AZURE_DOCINTEL_KEY', 'AI_AZURE_DOCINTEL_KEY', 'APP_AZURE_DOCINTEL_KEY', 'H_AZURE_DOCINTEL_KEY'], - ['AZURE_DOCINTEL_KEY'] - ); - $docIntel = ($docIntelEndpoint !== '' && $docIntelKey !== ''); + $ocrEndpoint = rtrim($this->readScanAiSettingValue([], ['DIAGNOSIS_AI_OCR_ENDPOINT']), '/'); + $ocrReady = $ocrEndpoint !== ''; $parts = []; - $parts[] = 'AzureOpenAI=' . ($azureOpenAi ? 'set' : 'missing endpoint/key/deployment'); - $parts[] = 'DocIntel=' . ($docIntel ? 'set' : 'missing endpoint/key'); + $parts[] = 'AIServer=' . ($aiServer ? 'set' : 'missing base URL'); + $parts[] = 'OCR=' . ($ocrReady ? 'set' : 'missing endpoint'); return [ - 'azure_openai' => $azureOpenAi, - 'docintel' => $docIntel, + 'ai_server' => $aiServer, + 'ocr_server' => $ocrReady, 'summary' => implode(', ', $parts), ]; } private function callAzureOpenAiVision(string $filePath, string $mimeType, string $prompt, int $maxTokens = 1200, bool $jsonObject = false): string { - $cfg = $this->getAzureOpenAiConfigForScan(); - if ($cfg['endpoint'] === '' || $cfg['api_key'] === '' || $cfg['deployment'] === '') { - $this->addScanAiDebug('azure vision skipped: endpoint/key/deployment missing'); - return ''; - } - - if (! str_starts_with($mimeType, 'image/')) { - $this->addScanAiDebug('azure vision skipped: non-image mime ' . $mimeType); - return ''; - } - - $bytes = @file_get_contents($filePath); - if ($bytes === false || $bytes === '') { - $this->addScanAiDebug('azure vision skipped: file read failed'); - return ''; - } - - $dataUrl = 'data:' . $mimeType . ';base64,' . base64_encode($bytes); - $url = $cfg['endpoint'] . '/openai/deployments/' . rawurlencode($cfg['deployment']) . '/chat/completions?api-version=' . rawurlencode($cfg['api_version']); - - for ($attempt = 0; $attempt < 2; $attempt++) { - $forceInsecure = $attempt === 1; - try { - $client = service('curlrequest', $this->buildAzureCurlOptions($cfg['endpoint'], 30, $forceInsecure)); - - $payload = [ - 'messages' => [[ - 'role' => 'user', - 'content' => [ - ['type' => 'text', 'text' => $prompt], - ['type' => 'image_url', 'image_url' => ['url' => $dataUrl]], - ], - ]], - 'temperature' => 0.1, - 'max_tokens' => $maxTokens, - ]; - - if ($jsonObject) { - $payload['response_format'] = ['type' => 'json_object']; - } - - $response = $client->post($url, [ - 'headers' => [ - 'api-key' => $cfg['api_key'], - 'Content-Type' => 'application/json', - ], - 'json' => $payload, - ]); - - if ($response->getStatusCode() < 200 || $response->getStatusCode() >= 300) { - $this->addScanAiDebug('azure vision HTTP ' . $response->getStatusCode()); - return ''; - } - - $decoded = json_decode((string) $response->getBody(), true); - $content = trim((string) ($decoded['choices'][0]['message']['content'] ?? '')); - if ($content === '') { - $this->addScanAiDebug('azure vision returned empty content'); - } - return $content; - } catch (\Throwable $e) { - if (! $forceInsecure && $this->isSslCertificateError($e)) { - $this->addScanAiDebug('azure vision SSL error; retry insecure'); - continue; - } - $this->addScanAiDebug('azure vision exception: ' . $e->getMessage()); - return ''; - } - } - + unset($filePath, $mimeType, $prompt, $maxTokens, $jsonObject); + $this->addScanAiDebug('visual interpretation via Azure is disabled; using AI server OCR/diagnosis flow'); return ''; } private function callAzureOpenAiText(string $prompt, int $maxTokens = 1200, bool $jsonObject = false): string { - $cfg = $this->getAzureOpenAiConfigForScan(); - if ($cfg['endpoint'] === '' || $cfg['api_key'] === '' || $cfg['deployment'] === '') { - $this->addScanAiDebug('azure text skipped: endpoint/key/deployment missing'); - return ''; - } - - $url = $cfg['endpoint'] . '/openai/deployments/' . rawurlencode($cfg['deployment']) . '/chat/completions?api-version=' . rawurlencode($cfg['api_version']); - - for ($attempt = 0; $attempt < 2; $attempt++) { - $forceInsecure = $attempt === 1; - try { - $client = service('curlrequest', $this->buildAzureCurlOptions($cfg['endpoint'], 30, $forceInsecure)); - - $payload = [ - 'messages' => [[ - 'role' => 'user', - 'content' => $prompt, - ]], - 'temperature' => 0.1, - 'max_tokens' => $maxTokens, - ]; - if ($jsonObject) { - $payload['response_format'] = ['type' => 'json_object']; - } - - $response = $client->post($url, [ - 'headers' => [ - 'api-key' => $cfg['api_key'], - 'Content-Type' => 'application/json', - ], - 'json' => $payload, - ]); - - if ($response->getStatusCode() < 200 || $response->getStatusCode() >= 300) { - $this->addScanAiDebug('azure text HTTP ' . $response->getStatusCode()); - return ''; - } - - $decoded = json_decode((string) $response->getBody(), true); - $content = trim((string) ($decoded['choices'][0]['message']['content'] ?? '')); - if ($content === '') { - $this->addScanAiDebug('azure text returned empty content'); - } - return $content; - } catch (\Throwable $e) { - if (! $forceInsecure && $this->isSslCertificateError($e)) { - $this->addScanAiDebug('azure text SSL error; retry insecure'); - continue; - } - $this->addScanAiDebug('azure text exception: ' . $e->getMessage()); - return ''; - } - } - + unset($prompt, $maxTokens, $jsonObject); + $this->addScanAiDebug('text generation via Azure is disabled; using AI server flow'); return ''; } private function extractTextWithAzureDocumentIntelligence(string $filePath): string { - $endpoint = rtrim($this->readScanAiSettingValue( - ['AZURE_DOCINTEL_ENDPOINT', 'AI_AZURE_DOCINTEL_ENDPOINT', 'APP_AZURE_DOCINTEL_ENDPOINT', 'H_AZURE_DOCINTEL_ENDPOINT'], - ['AZURE_DOCINTEL_ENDPOINT'] - ), '/'); - $endpoint = $this->normalizeAzureEndpointBase($endpoint); - $key = $this->readScanAiSettingValue( - ['AZURE_DOCINTEL_KEY', 'AI_AZURE_DOCINTEL_KEY', 'APP_AZURE_DOCINTEL_KEY', 'H_AZURE_DOCINTEL_KEY'], - ['AZURE_DOCINTEL_KEY'] - ); + $endpoint = rtrim($this->readScanAiSettingValue([], ['DIAGNOSIS_AI_OCR_ENDPOINT']), '/'); + $token = trim($this->readScanAiSettingValue([], ['DIAGNOSIS_AI_PARSE_TOKEN'])); - if ($endpoint === '' || $key === '' || !is_file($filePath)) { - $this->addScanAiDebug('docintel skipped: endpoint/key/file missing'); + if ($endpoint === '' || !is_file($filePath)) { + $this->addScanAiDebug('ai server OCR skipped: endpoint/file missing'); return ''; } - for ($attempt = 0; $attempt < 2; $attempt++) { - $forceInsecure = $attempt === 1; - try { - $client = service('curlrequest', $this->buildAzureCurlOptions($endpoint, 40, $forceInsecure)); + try { + $headers = ['Accept' => 'application/json']; + if ($token !== '') { + $headers['Authorization'] = 'Bearer ' . $token; + } - $bytes = @file_get_contents($filePath); - if ($bytes === false || $bytes === '') { - return ''; - } - - $mimeType = $this->guessMimeTypeFromPath($filePath); - $analyzeUrls = [ - $endpoint . '/documentintelligence/documentModels/prebuilt-read:analyze?api-version=2024-02-29-preview', - $endpoint . '/documentintelligence/documentModels/prebuilt-read:analyze?api-version=2023-07-31', - $endpoint . '/formrecognizer/documentModels/prebuilt-read:analyze?api-version=2023-07-31', - ]; - - // Try multiple API routes for compatibility with different Azure environments. - foreach ($analyzeUrls as $analyzeUrl) { - $submit = $client->post($analyzeUrl, [ - 'headers' => [ - 'Content-Type' => $mimeType !== '' ? $mimeType : 'application/octet-stream', - 'Ocp-Apim-Subscription-Key' => $key, - ], - 'body' => $bytes, - ]); - - if ($submit->getStatusCode() < 200 || $submit->getStatusCode() >= 300) { - $this->addScanAiDebug('docintel submit HTTP ' . $submit->getStatusCode() . ' @ ' . basename($analyzeUrl)); - continue; - } - - $submitBody = json_decode((string) $submit->getBody(), true); - if (is_array($submitBody)) { - $inlineText = $this->extractTextFromDocIntelPayload($submitBody); - if ($inlineText !== '') { - return $inlineText; - } - } - - $operationLocation = trim((string) $submit->getHeaderLine('Operation-Location')); - if ($operationLocation === '') { - $this->addScanAiDebug('docintel missing operation-location @ ' . basename($analyzeUrl)); - continue; - } - - for ($i = 0; $i < 14; $i++) { - usleep(900000); - $poll = $client->get($operationLocation, [ - 'headers' => [ - 'Ocp-Apim-Subscription-Key' => $key, - ], - ]); - - if ($poll->getStatusCode() < 200 || $poll->getStatusCode() >= 300) { - $this->addScanAiDebug('docintel poll HTTP ' . $poll->getStatusCode()); - continue; - } - - $decoded = json_decode((string) $poll->getBody(), true); - if (!is_array($decoded)) { - continue; - } - - $status = strtolower((string) ($decoded['status'] ?? '')); - if ($status === 'succeeded') { - $text = $this->extractTextFromDocIntelPayload($decoded); - if ($text !== '') { - return $text; - } - } - - if ($status === 'failed') { - $this->addScanAiDebug('docintel status failed'); - break; - } - } - } - - return ''; - } catch (\Throwable $e) { - if (! $forceInsecure && $this->isSslCertificateError($e)) { - $this->addScanAiDebug('docintel SSL error; retry insecure'); - continue; - } - $this->addScanAiDebug('docintel exception: ' . $e->getMessage()); + $client = service('curlrequest', $this->buildAzureCurlOptions($endpoint, 40, false)); + $mime = $this->guessMimeTypeFromPath($filePath); + if (! str_starts_with($mime, 'image/')) { return ''; } + + $curlFile = new \CURLFile($filePath, $mime, basename($filePath)); + $response = $client->post($endpoint, [ + 'headers' => $headers, + 'multipart' => [ + 'file' => $curlFile, + ], + ]); + + if ($response->getStatusCode() < 200 || $response->getStatusCode() >= 300) { + return ''; + } + + $decoded = json_decode((string) $response->getBody(), true); + if (! is_array($decoded)) { + return ''; + } + + foreach (['ocr_text', 'text', 'extracted_text'] as $key) { + $text = trim((string) ($decoded[$key] ?? '')); + if ($text !== '') { + return $text; + } + } + } catch (\Throwable $e) { + return ''; + } + + return ''; + } + + private function resolveAiServerBaseUrlForScan(): string + { + $base = rtrim($this->readScanAiSettingValue([], ['DIAGNOSIS_AI_SERVER_URL']), '/'); + if ($base !== '') { + return $base; + } + + $candidates = [ + trim($this->readScanAiSettingValue([], ['DIAGNOSIS_AI_PARSE_ENDPOINT'])), + trim($this->readScanAiSettingValue([], ['DIAGNOSIS_AI_OCR_ENDPOINT'])), + ]; + + foreach ($candidates as $url) { + if ($url === '') { + continue; + } + + $parts = @parse_url($url); + if (! is_array($parts) || empty($parts['scheme']) || empty($parts['host'])) { + continue; + } + + $base = (string) $parts['scheme'] . '://' . (string) $parts['host']; + if (! empty($parts['port'])) { + $base .= ':' . (int) $parts['port']; + } + + return rtrim($base, '/'); } return ''; diff --git a/app/Controllers/Opd_prescription.php b/app/Controllers/Opd_prescription.php index f8a18ce..78098c7 100644 --- a/app/Controllers/Opd_prescription.php +++ b/app/Controllers/Opd_prescription.php @@ -483,8 +483,8 @@ class Opd_prescription extends BaseController $draft = $this->generateClinicalTextWithAi($prompt); if ($draft !== null && trim($draft) !== '') { - $provider = $this->lastAiProvider === 'azure' ? 'azure' : 'ai'; - $providerLabel = $provider === 'azure' ? 'Azure OpenAI' : 'AI'; + $provider = $this->lastAiProvider === 'ai-server' ? 'ai-server' : 'ai'; + $providerLabel = $provider === 'ai-server' ? 'AI Server' : 'AI'; return $this->response->setJSON([ 'update' => 1, 'draft_text' => trim($draft), @@ -579,8 +579,8 @@ class Opd_prescription extends BaseController $aiMode = 'fallback'; $message = 'AI unavailable. Template draft prepared from entered data.'; } else { - $aiMode = $this->lastAiProvider === 'azure' ? 'azure' : 'ai'; - $message = 'Full clinical draft prepared using ' . ($aiMode === 'azure' ? 'Azure OpenAI' : 'AI') . '.'; + $aiMode = $this->lastAiProvider === 'ai-server' ? 'ai-server' : 'ai'; + $message = 'Full clinical draft prepared using ' . ($aiMode === 'ai-server' ? 'AI Server' : 'AI') . '.'; } return $this->response->setJSON([ @@ -2597,37 +2597,12 @@ class Opd_prescription extends BaseController $targetLanguageName = $supportedLanguages[$targetLang]; - $prompt = "You are a clinical translation assistant for OPD patient advice in India.\n" - . "Translate the following English patient advice into {$targetLanguageName}.\n" - . "Keep meaning medically accurate, simple, and patient-friendly.\n" - . "Return ONLY valid JSON object: {\"translated_text\":\"...\"}.\n" - . "Do not include markdown, extra keys, or explanation.\n" - . "English Advice: {$sourceText}"; - $this->lastAiProvider = 'none'; - $aiText = $this->generateClinicalTextWithAi($prompt, 220); - if ($aiText === null || trim($aiText) === '') { - return $this->response->setJSON([ - 'update' => 0, - 'error_text' => 'AI unavailable. Check AI settings.', - 'csrfName' => csrf_token(), - 'csrfHash' => csrf_hash(), - ]); - } - - $parsed = $this->parseJsonFromAiResponse($aiText); - $translatedText = trim((string) ($parsed['translated_text'] ?? '')); - - if ($translatedText === '') { - $translatedText = trim(strip_tags((string) $aiText)); - $translatedText = preg_replace('/```(?:json)?|```/i', '', $translatedText) ?? $translatedText; - $translatedText = trim($translatedText); - } - + $translatedText = $this->translateAdviceWithAiServer($sourceText, $targetLang); if ($translatedText === '') { return $this->response->setJSON([ 'update' => 0, - 'error_text' => 'Translation failed. Try again.', + 'error_text' => 'AI server unavailable. Check DIAGNOSIS_AI_SERVER_URL and token settings.', 'csrfName' => csrf_token(), 'csrfHash' => csrf_hash(), ]); @@ -2635,7 +2610,7 @@ class Opd_prescription extends BaseController return $this->response->setJSON([ 'update' => 1, - 'provider' => $this->lastAiProvider, + 'provider' => 'ai-server', 'target_lang' => $targetLang, 'target_language_name' => $targetLanguageName, 'translated_text' => $translatedText, @@ -3016,8 +2991,8 @@ class Opd_prescription extends BaseController $this->lastAiProvider = 'none'; $aiDraft = $this->generateComplaintDraftWithAi($finalComplaints, $currentText); if ($aiDraft !== null && trim($aiDraft) !== '') { - $provider = $this->lastAiProvider === 'azure' ? 'azure' : 'ai'; - $providerLabel = $provider === 'azure' ? 'Azure OpenAI' : 'AI'; + $provider = $this->lastAiProvider === 'ai-server' ? 'ai-server' : 'ai'; + $providerLabel = $provider === 'ai-server' ? 'AI Server' : 'AI'; return $this->response->setJSON([ 'update' => 1, 'draft_text' => trim($aiDraft), @@ -5374,59 +5349,10 @@ class Opd_prescription extends BaseController } /** - * @return array{endpoint:string,api_key:string,deployment:string,api_version:string} - */ - private function getAzureOpenAiConfig(): array - { - $endpoint = $this->readAiSettingValue( - ['AZURE_OPENAI_ENDPOINT', 'AI_AZURE_OPENAI_ENDPOINT', 'APP_AZURE_OPENAI_ENDPOINT', 'H_AZURE_OPENAI_ENDPOINT'], - ['AZURE_OPENAI_ENDPOINT'] - ); - - $apiKey = $this->readAiSettingValue( - ['AZURE_OPENAI_API_KEY', 'AI_AZURE_OPENAI_API_KEY', 'APP_AZURE_OPENAI_API_KEY', 'H_AZURE_OPENAI_API_KEY'], - ['AZURE_OPENAI_API_KEY'] - ); - - $deployment = $this->readAiSettingValue( - ['AZURE_OPENAI_DEPLOYMENT', 'AI_AZURE_OPENAI_DEPLOYMENT', 'APP_AZURE_OPENAI_DEPLOYMENT', 'H_AZURE_OPENAI_DEPLOYMENT'], - ['AZURE_OPENAI_DEPLOYMENT'] - ); - - $apiVersion = $this->readAiSettingValue( - ['AZURE_OPENAI_API_VERSION', 'AI_AZURE_OPENAI_API_VERSION', 'APP_AZURE_OPENAI_API_VERSION', 'H_AZURE_OPENAI_API_VERSION'], - ['AZURE_OPENAI_API_VERSION'] - ); - - if ($apiVersion === '') { - $apiVersion = '2024-10-21'; - } - - return [ - 'endpoint' => rtrim($endpoint, '/'), - 'api_key' => $apiKey, - 'deployment' => $deployment, - 'api_version' => $apiVersion, - ]; - } - - /** - * @param array $constCandidates * @param array $settingCandidates */ - private function readAiSettingValue(array $constCandidates, array $settingCandidates): string + private function readAiSettingValue(array $settingCandidates): string { - foreach ($constCandidates as $constName) { - if (! defined($constName)) { - continue; - } - - $value = trim((string) constant($constName)); - if ($value !== '') { - return $value; - } - } - if ($this->db->tableExists('hospital_setting') && ! empty($settingCandidates)) { $row = $this->db->table('hospital_setting') ->select('s_value') @@ -5462,61 +5388,6 @@ Output only one plain text sentence starting with 'Chief complaints:' and no mar return $this->generateClinicalTextWithAi($prompt, 180); } - private function generateClinicalTextWithAzureOpenAi(string $prompt, int $maxOutputTokens = 300): ?string - { - $cfg = $this->getAzureOpenAiConfig(); - if ($cfg['endpoint'] === '' || $cfg['api_key'] === '' || $cfg['deployment'] === '' || trim($prompt) === '') { - return null; - } - - try { - $httpOptions = [ - 'timeout' => 20, - 'http_errors' => false, - ]; - if (defined('ENVIRONMENT') && in_array((string) ENVIRONMENT, ['development', 'testing'], true)) { - $httpOptions['verify'] = false; - } - - $client = service('curlrequest', $httpOptions); - $url = $cfg['endpoint'] . '/openai/deployments/' . rawurlencode($cfg['deployment']) - . '/chat/completions?api-version=' . rawurlencode($cfg['api_version']); - - $response = $client->post($url, [ - 'headers' => [ - 'api-key' => $cfg['api_key'], - 'Content-Type' => 'application/json', - ], - 'json' => [ - 'messages' => [ - ['role' => 'system', 'content' => 'You are a clinical OPD assistant. Return plain text only, no markdown.'], - ['role' => 'user', 'content' => $prompt], - ], - 'temperature' => 0.2, - 'top_p' => 0.9, - 'max_tokens' => max(64, $maxOutputTokens), - ], - ]); - - if ($response->getStatusCode() < 200 || $response->getStatusCode() >= 300) { - return null; - } - - $decoded = json_decode((string) $response->getBody(), true); - $text = trim((string) ($decoded['choices'][0]['message']['content'] ?? '')); - - $text = trim($text); - if ($text === '') { - return null; - } - - $this->lastAiProvider = 'azure'; - return preg_replace('/\s+/', ' ', $text) ?: $text; - } catch (\Throwable $e) { - return null; - } - } - private function buildClinicalPrompt(string $mode, string $text): string { if ($mode === 'hinglish_to_english') { @@ -5639,7 +5510,84 @@ Input: " . $text; private function generateClinicalTextWithAi(string $prompt, int $maxOutputTokens = 300): ?string { - return $this->generateClinicalTextWithAzureOpenAi($prompt, $maxOutputTokens); + unset($prompt, $maxOutputTokens); + return null; + } + + private function resolveAiServerBaseUrl(): string + { + $base = rtrim($this->readAiSettingValue(['DIAGNOSIS_AI_SERVER_URL']), '/'); + if ($base !== '') { + return $base; + } + + $candidates = [ + trim($this->readAiSettingValue(['DIAGNOSIS_AI_PARSE_ENDPOINT'])), + trim($this->readAiSettingValue(['DIAGNOSIS_AI_OCR_ENDPOINT'])), + ]; + + foreach ($candidates as $url) { + if ($url === '') { + continue; + } + + $parts = @parse_url($url); + if (! is_array($parts) || empty($parts['scheme']) || empty($parts['host'])) { + continue; + } + + $base = (string) $parts['scheme'] . '://' . (string) $parts['host']; + if (! empty($parts['port'])) { + $base .= ':' . (int) $parts['port']; + } + + return rtrim($base, '/'); + } + + return ''; + } + + private function translateAdviceWithAiServer(string $sourceText, string $targetLang): string + { + $base = $this->resolveAiServerBaseUrl(); + if ($base === '') { + return ''; + } + + $token = trim($this->readAiSettingValue(['DIAGNOSIS_AI_PARSE_TOKEN'])); + + try { + $options = [ + 'timeout' => 20, + 'http_errors' => false, + ]; + if (defined('ENVIRONMENT') && in_array((string) ENVIRONMENT, ['development', 'testing'], true)) { + $options['verify'] = false; + } + + $headers = ['Accept' => 'application/json']; + if ($token !== '') { + $headers['Authorization'] = 'Bearer ' . $token; + } + + $client = service('curlrequest', $options); + $url = $base . '/translate?text=' . rawurlencode($sourceText) . '&target_lang=' . rawurlencode($targetLang); + $response = $client->get($url, ['headers' => $headers]); + if ($response->getStatusCode() < 200 || $response->getStatusCode() >= 300) { + return ''; + } + + $decoded = json_decode((string) $response->getBody(), true); + $translated = trim((string) ($decoded['translated_text'] ?? '')); + if ($translated === '') { + return ''; + } + + $this->lastAiProvider = 'ai-server'; + return $translated; + } catch (\Throwable $e) { + return ''; + } } /** diff --git a/app/Controllers/Setting/Doctor.php b/app/Controllers/Setting/Doctor.php index a5d9aa4..3f24e74 100644 --- a/app/Controllers/Setting/Doctor.php +++ b/app/Controllers/Setting/Doctor.php @@ -7,6 +7,8 @@ use App\Models\DoctorModel; class Doctor extends BaseController { + private const OPD_TEMPLATE_KEY_PREFIX = 'OPD_PRINT_TEMPLATE__'; + public function index(): string { $doctorModel = new DoctorModel(); @@ -23,6 +25,7 @@ class Doctor extends BaseController return view('Setting/Doctor/Doctor_V', [ 'errors' => session('errors'), 'template_options' => $templateContext['options'], + 'opd_print_template_options' => $templateContext['opd_print_options'], 'template_fields' => $templateContext['fields'], ]); } @@ -42,6 +45,7 @@ class Doctor extends BaseController 'errors' => $this->validator->getErrors(), 'formData' => $this->request->getPost(), 'template_options' => $templateContext['options'], + 'opd_print_template_options' => $templateContext['opd_print_options'], 'template_fields' => $templateContext['fields'], ]); } @@ -80,8 +84,7 @@ class Doctor extends BaseController if (! in_array($dbField, $templateContext['fields'], true)) { continue; } - $templateName = strtolower(trim((string) $this->request->getPost($inputField))); - $templateName = preg_replace('/[^a-z0-9_\-]/', '', $templateName) ?? ''; + $templateName = $this->normalizeTemplateId((string) $this->request->getPost($inputField)); $data[$dbField] = $templateName; } @@ -99,6 +102,7 @@ class Doctor extends BaseController 'errors' => $errors, 'formData' => $this->request->getPost(), 'template_options' => $templateContext['options'], + 'opd_print_template_options' => $templateContext['opd_print_options'], 'template_fields' => $templateContext['fields'], ]); } @@ -123,6 +127,7 @@ class Doctor extends BaseController 'doc_ipd_fee_list' => $doctorModel->getDoctorIpdFees($id), 'doc_ipd_fee_type' => $doctorModel->getIpdFeeTypes(), 'template_options' => $templateContext['options'], + 'opd_print_template_options' => $templateContext['opd_print_options'], 'template_fields' => $templateContext['fields'], ]); } @@ -165,8 +170,7 @@ class Doctor extends BaseController if (! in_array($dbField, $templateContext['fields'], true)) { continue; } - $templateName = strtolower(trim((string) $this->request->getPost($inputField))); - $templateName = preg_replace('/[^a-z0-9_\-]/', '', $templateName) ?? ''; + $templateName = $this->normalizeTemplateId((string) $this->request->getPost($inputField)); $data[$dbField] = $templateName; } @@ -573,59 +577,67 @@ class Doctor extends BaseController ]; if (! $this->db->tableExists('doctor_master')) { - return ['fields' => [], 'options' => []]; + return ['fields' => [], 'options' => [], 'opd_print_options' => []]; } $doctorFields = $this->db->getFieldNames('doctor_master') ?? []; $availableFields = array_values(array_intersect($allTemplateFields, $doctorFields)); - $options = []; - - $templateDir = APPPATH . 'Views/billing/opd_templates'; - if (is_dir($templateDir)) { - $htmlFiles = glob($templateDir . '/*.html') ?: []; - foreach ($htmlFiles as $file) { - $name = strtolower(trim((string) basename((string) $file, '.html'))); - $name = preg_replace('/[^a-z0-9_\-]/', '', $name) ?? ''; - if ($name !== '') { - $options[] = $name; - } - } - - $phpFiles = glob($templateDir . '/*.php') ?: []; - foreach ($phpFiles as $file) { - $name = strtolower(trim((string) basename((string) $file, '.php'))); - $name = preg_replace('/[^a-z0-9_\-]/', '', $name) ?? ''; - if ($name !== '') { - $options[] = $name; - } - } - } - - foreach ($availableFields as $field) { - $rows = $this->db->table('doctor_master') - ->select($field . ' as template_name') - ->where($field . ' IS NOT NULL', null, false) - ->where($field . ' !=', '') - ->distinct() - ->get() - ->getResultArray(); - - foreach ($rows as $row) { - $name = strtolower(trim((string) ($row['template_name'] ?? ''))); - $name = preg_replace('/[^a-z0-9_\-]/', '', $name) ?? ''; - if ($name !== '') { - $options[] = $name; - } - } - } + $options = $this->collectStoredTemplateOptions(); + $opdPrintOptions = $options; $options = array_values(array_unique($options)); sort($options); + $opdPrintOptions = array_values(array_unique($opdPrintOptions)); + sort($opdPrintOptions); return [ 'fields' => $availableFields, 'options' => $options, + 'opd_print_options' => $opdPrintOptions, ]; } + + private function normalizeTemplateId(string $templateId): string + { + $templateId = strtolower(trim($templateId)); + $templateId = str_replace([' ', '.'], '_', $templateId); + $templateId = preg_replace('/[^a-z0-9_\-]+/', '_', $templateId) ?? ''; + $templateId = preg_replace('/_{2,}/', '_', $templateId) ?? $templateId; + + return trim($templateId, '_-'); + } + + /** + * @return array + */ + private function collectStoredTemplateOptions(): array + { + if (! $this->db->tableExists('hospital_setting')) { + return []; + } + + $rows = $this->db->table('hospital_setting') + ->select('s_name') + ->like('s_name', self::OPD_TEMPLATE_KEY_PREFIX, 'after') + ->get() + ->getResultArray(); + + $options = []; + foreach ($rows as $row) { + $storageKey = (string) ($row['s_name'] ?? ''); + if (! str_starts_with($storageKey, self::OPD_TEMPLATE_KEY_PREFIX)) { + continue; + } + + $templateId = substr($storageKey, strlen(self::OPD_TEMPLATE_KEY_PREFIX)); + $templateId = $this->normalizeTemplateId((string) $templateId); + if ($templateId !== '') { + $options[] = $templateId; + } + } + + return $options; + } + } diff --git a/app/Database/Migrations/2026-02-21-000005_CreateLabAiExtractionTables.php b/app/Database/Migrations/2026-02-21-000005_CreateLabAiExtractionTables.php index b6d5582..1c6c011 100644 --- a/app/Database/Migrations/2026-02-21-000005_CreateLabAiExtractionTables.php +++ b/app/Database/Migrations/2026-02-21-000005_CreateLabAiExtractionTables.php @@ -41,7 +41,7 @@ class CreateLabAiExtractionTables extends Migration 'ai_provider' => [ 'type' => 'VARCHAR', 'constraint' => 50, - 'default' => 'azure-openai', + 'default' => 'ai-server', ], 'model_name' => [ 'type' => 'VARCHAR', diff --git a/app/Views/Setting/Doctor/Doctor_V.php b/app/Views/Setting/Doctor/Doctor_V.php index d42f2a4..780f325 100644 --- a/app/Views/Setting/Doctor/Doctor_V.php +++ b/app/Views/Setting/Doctor/Doctor_V.php @@ -67,6 +67,7 @@
@@ -75,7 +76,7 @@ diff --git a/app/Views/Setting/Doctor/Doctor_profile_V.php b/app/Views/Setting/Doctor/Doctor_profile_V.php index 77019aa..d269c54 100644 --- a/app/Views/Setting/Doctor/Doctor_profile_V.php +++ b/app/Views/Setting/Doctor/Doctor_profile_V.php @@ -89,6 +89,7 @@ if (!empty($data) && !empty($data[0])) {
@@ -97,7 +98,7 @@ if (!empty($data) && !empty($data[0])) { diff --git a/app/Views/billing/opd_advice_workspace.php b/app/Views/billing/opd_advice_workspace.php index 471597a..7c73b0a 100644 --- a/app/Views/billing/opd_advice_workspace.php +++ b/app/Views/billing/opd_advice_workspace.php @@ -227,7 +227,7 @@ $('#advice_hi').val((data.translated_text || '').toString()); var langName = (data.target_language_name || '').toString(); var provider = (data.provider || '').toString(); - var providerLabel = provider === 'azure' ? 'Azure OpenAI' : 'AI'; + var providerLabel = provider === 'ai-server' ? 'AI Server' : 'AI'; setMsg('ok', 'Translated to ' + (langName || 'selected language') + ' using ' + providerLabel + '.'); }); }); diff --git a/app/Views/billing/opd_invoice_V.php b/app/Views/billing/opd_invoice_V.php index 42e0703..8bb1ca6 100644 --- a/app/Views/billing/opd_invoice_V.php +++ b/app/Views/billing/opd_invoice_V.php @@ -207,8 +207,9 @@ if ($user && method_exists($user, 'inGroup')) {
diff --git a/app/Views/billing/opd_medicince_workspace.php b/app/Views/billing/opd_medicince_workspace.php index 3202209..f79e00f 100644 --- a/app/Views/billing/opd_medicince_workspace.php +++ b/app/Views/billing/opd_medicince_workspace.php @@ -608,7 +608,7 @@ return; } - if (isNewMedicine && (provider === 'azure' || provider === 'local-brand-fallback')) { + if (isNewMedicine && (provider === 'ai-server' || provider === 'local-brand-fallback')) { if (window.confirm('Details prepared for a new medicine. Save this new master entry now?')) { saveMedicine(buildMedicinePayload(), function() { setMsg('ok', 'New medicine saved with suggested generic/salt details.'); diff --git a/app/Views/billing/opd_paper_print_settings.php b/app/Views/billing/opd_paper_print_settings.php new file mode 100644 index 0000000..fc4b60b --- /dev/null +++ b/app/Views/billing/opd_paper_print_settings.php @@ -0,0 +1,162 @@ + + +
+
+
+

OPD Paper Print Settings

+
+ +
+
+ +
+
+
+

Dedicated OPD PDF page/header/footer settings

+
+
+
+ +
+ +
+ +
+ + +
+
+ + +
+
+ +
+

Page & Margin (cm)

+
+
+ + +
+
+ + +
+
+ + +
+
+ + +
+
+ + +
+
+ + +
+
+ +
+

Header / Footer HTML

+
+ Use variables with {{name}} or {name}.
+ Hospital: H_Name, H_address_1, H_address_2, H_phone_No, H_Email, H_logo.
+ Common: print_time, current_date, doctor_name.
+ OPD: pName, age_sex, phoneno, uhid_no, opd_no, opd_date, Complaint, diagnosis, medical, advice.
+ mPDF page tokens like {PAGENO} and {nbpg} are supported. +
+ +
+
+ + +
+
+ + +
+
+ +
+ +
+
+
+
+
+ + diff --git a/app/Views/billing/opd_parts/content/default.html b/app/Views/billing/opd_parts/content/default.html deleted file mode 100644 index 46ff213..0000000 --- a/app/Views/billing/opd_parts/content/default.html +++ /dev/null @@ -1,13 +0,0 @@ -
- {{painscale_img}} - {{vital_content}} - {{Complaint}} - {{diagnosis}} - {{Finding_Examinations}} - {{medical}} - {{investigation}} - {{Prescriber_Remarks}} - {{advice}} - {{next_visit}} - {{refer_to}} -
diff --git a/app/Views/billing/opd_parts/hospital/default.html b/app/Views/billing/opd_parts/hospital/default.html deleted file mode 100644 index 8cfd6ca..0000000 --- a/app/Views/billing/opd_parts/hospital/default.html +++ /dev/null @@ -1,23 +0,0 @@ - - -{{hospital_section}} - - -

Print Time : {{print_time}}

-
-{{patient_section}} -
-{{content_section}} diff --git a/app/Views/billing/opd_parts/layout/default.html b/app/Views/billing/opd_parts/layout/default.html deleted file mode 100644 index 8cfd6ca..0000000 --- a/app/Views/billing/opd_parts/layout/default.html +++ /dev/null @@ -1,23 +0,0 @@ - - -{{hospital_section}} - - -

Print Time : {{print_time}}

-
-{{patient_section}} -
-{{content_section}} diff --git a/app/Views/billing/opd_parts/patient/default.html b/app/Views/billing/opd_parts/patient/default.html deleted file mode 100644 index d1db10f..0000000 --- a/app/Views/billing/opd_parts/patient/default.html +++ /dev/null @@ -1,10 +0,0 @@ - - - - -
-Patient Name : - - -{{pName}} -
\ No newline at end of file diff --git a/app/Views/billing/opd_parts/patient/edit.html b/app/Views/billing/opd_parts/patient/edit.html deleted file mode 100644 index 196a8b7..0000000 --- a/app/Views/billing/opd_parts/patient/edit.html +++ /dev/null @@ -1,18 +0,0 @@ - - - - - -
- {{pName}}
- {{pRelative}}
- {{age_sex}}
- {{p_address}}
- Phone: {{phoneno}} -
- UHID: {{uhid_no}}
- OPD: {{opd_no}}
- SR: {{opd_sr_no}}
- Date: {{opd_date}}
- {{exp_date}} -
diff --git a/app/Views/billing/opd_parts/patient/list.html b/app/Views/billing/opd_parts/patient/list.html deleted file mode 100644 index 73e668c..0000000 --- a/app/Views/billing/opd_parts/patient/list.html +++ /dev/null @@ -1,26 +0,0 @@ - - - - - - -
- Name : {{pName}}
- {{pRelative}}
- Gender/Age : {{age_sex}}
- Mob : {{phoneno}}
- Address : {{p_address}} -
- UHID : {{uhid_no}}
- Sr No.: {{opd_sr_no}}
- OPD No.: {{opd_no}}
- Date: {{opd_date}}
- {{exp_date}} -
- Department:
- {{SpecName}}
- {{opd_fee_desc}}
- No. of Visit: {{total_no_visit}}
- {{last_opdvisit_date}}
- Book Time : {{str_opd_book_date}} -
diff --git a/app/Views/billing/opd_template_builder.php b/app/Views/billing/opd_template_builder.php index 92715b0..3a288d9 100644 --- a/app/Views/billing/opd_template_builder.php +++ b/app/Views/billing/opd_template_builder.php @@ -6,12 +6,20 @@
+ +
@@ -28,6 +36,7 @@
+
@@ -35,24 +44,9 @@
-
-
- - -
-
- -
-
-
-
- - +
+ +
@@ -76,6 +70,101 @@
+ +
+
+
+
+

OPD Paper Print Settings

+
+
+
+
+ + +
+ + + +
+
+ + +
+
+ + +
+
+ + +
+
+ + +
+
+ + +
+
+ + +
+
+ +
+ + +
+ +
+ + +
+ +
+ + +
+ +
+ How it works:
+ 1. Margin values (cm) auto-populate the CSS @page block
+ 2. Header HTML: Enter HTML for top of page (logo, hospital name, address, doctor info using {{variables}})
+ 3. Footer HTML: Enter HTML for bottom of page (print time, page number, etc. using {{variables}})
+ 4. HTML Content: Enter main body content between header and footer (patient info, diagnosis, etc.)

+ Available variables:
+ Hospital: {{H_Name}}, {{H_address_1}}, {{H_address_2}}, {{H_phone_No}}, {{H_Email}}, {{H_logo}}
+ Patient/OPD: {{pName}}, {{age_sex}}, {{phoneno}}, {{uhid_no}}, {{opd_no}}, {{opd_date}}
+ Medical: {{Complaint}}, {{diagnosis}}, {{medical}}, {{advice}}, {{doctor_name}}, {{doctor_sign_html}}
+ Dates: {{print_time}}, {{current_date}}
+ Margins (cm): {{MarginTop}}, {{MarginBottom}}, {{MarginLeft}}, {{MarginRight}}, {{MarginHeader}}, {{MarginFooter}} +
+ + + +
+
+
+
diff --git a/app/Views/billing/opd_template_builder_list.php b/app/Views/billing/opd_template_builder_list.php index 0837e91..e13804e 100644 --- a/app/Views/billing/opd_template_builder_list.php +++ b/app/Views/billing/opd_template_builder_list.php @@ -26,6 +26,7 @@
+
@@ -33,7 +34,7 @@ - + @@ -48,6 +49,8 @@ @@ -61,6 +64,28 @@ diff --git a/app/Views/billing/opd_templates/opd_info_print_letter_head.html b/app/Views/billing/opd_templates/opd_info_print_letter_head.html deleted file mode 100644 index 97bcfb2..0000000 --- a/app/Views/billing/opd_templates/opd_info_print_letter_head.html +++ /dev/null @@ -1 +0,0 @@ -

Hello World

\ No newline at end of file diff --git a/app/Views/billing/opd_templates/opd_info_print_letter_head_1.html b/app/Views/billing/opd_templates/opd_info_print_letter_head_1.html deleted file mode 100644 index 97bcfb2..0000000 --- a/app/Views/billing/opd_templates/opd_info_print_letter_head_1.html +++ /dev/null @@ -1 +0,0 @@ -

Hello World

\ No newline at end of file diff --git a/app/Views/billing/opd_templates/opd_print_info_letter_head.html b/app/Views/billing/opd_templates/opd_print_info_letter_head.html deleted file mode 100644 index d87d360..0000000 --- a/app/Views/billing/opd_templates/opd_print_info_letter_head.html +++ /dev/null @@ -1 +0,0 @@ -

Test

\ No newline at end of file diff --git a/app/Views/billing/opd_templates/opd_print_parcha_chamunda_hospital_ksp.php b/app/Views/billing/opd_templates/opd_print_parcha_chamunda_hospital_ksp.php deleted file mode 100644 index 7184541..0000000 --- a/app/Views/billing/opd_templates/opd_print_parcha_chamunda_hospital_ksp.php +++ /dev/null @@ -1,74 +0,0 @@ -title ?? '') . ' ' . ($patient->p_fname ?? '')))); -$pRelative = trim((string) (($patient->p_relative ?? '') . ' ' . ($patient->p_rname ?? ''))); -$ageSex = trim((string) (($patient->xgender ?? '') . ' / ' . ($patient->age ?? ''))); -$phone = (string) ($patient->mphone1 ?? ''); -$pAddress = trim((string) (($patient->add1 ?? '') . ', ' . ($patient->add2 ?? '') . ', ' . ($patient->city ?? '')), ' ,'); - -$uhidNo = (string) ($patient->p_code ?? ''); -$opdSrNo = (string) ($opd->opd_no ?? ''); -$opdNo = (string) ($opd->opd_code ?? ''); -$opdDate = (string) ($opd->str_apointment_date ?? ''); -$expDate = (string) ($opd->opd_Exp_Date ?? ''); - -$specName = trim((string) ($doctor->SpecName ?? $opd->doc_spec ?? '')); -$opdFeeDesc = trim((string) ($opd->opd_fee_desc ?? '')); -$totalNoVisit = (string) ($opd->no_visit ?? ''); -$lastVisitDate = trim((string) (($old_opd[0]->str_apointment_date ?? '') ?: '')); -$bookTime = (string) ($opd->apointment_date ?? ''); - -$lastVisitLine = $lastVisitDate !== '' ? ('
Last Visit : ' . esc($lastVisitDate)) : ''; -$expDateLine = $expDate !== '' ? ('Valid Upto : ' . esc($expDate)) : ''; -?> - - - -

-
- - -

Print Time :

-
- -
# Template NameActionAction
Edit + +
- - - - - -
- Name :
-
- Gender/Age :
- Mob :
- Address : -
- UHID :
- Sr No.:
- OPD No.:
-
Date:
- -
- DEPARTMENT :
-
-
- No. of Visit : -
- Book Time : -
diff --git a/app/Views/billing/opd_templates/printonletterhead.html b/app/Views/billing/opd_templates/printonletterhead.html new file mode 100644 index 0000000..b2e9fb1 --- /dev/null +++ b/app/Views/billing/opd_templates/printonletterhead.html @@ -0,0 +1,84 @@ + + + + + + + + + +
+ + +

{{H_Name}}

+

{{H_address_1}}, {{H_address_2}}
Phone: {{H_phone_No}}

+
+

Dr. {{doctor_name}}

+ {{doctor_sign_html}} +
+
+
+ + +

Prescription Generated: {{print_time}}

+

Please ensure doctor registration number and signature/stamp are present for regulatory compliance.

+
+ + + + + + +
+ Name: {{pName}}
+ S/o: [Father Name]
+ Gender/Age: {{age_sex}}
+ Mob: {{phoneno}}
+ Address: [Address] +
+ UHID: {{uhid_no}}
+ Sr No.: [Sr No]
+ OPD No.: {{opd_no}}
+ Date & Time: {{opd_date}} 12:00 AM
+ Valid Upto: [Valid Date] +
+ + + + + + + +
+ DEPARTMENT:
{{Complaint}} +
+ DIAGNOSIS:
{{diagnosis}} +
+ Last Visit: [Date]
+ No. of Visit: [Count] +
+ +

Rx :

+ +{{medical}} + +

+ Investigation: {{investigation}}
+ Advice: {{advice}} +

+ +
+

Dr. {{doctor_name}}

+ {{doctor_sign_html}} +

Reg. No.: 80982

+
\ No newline at end of file diff --git a/app/Views/billing/opd_templates/printonplainpaper.html b/app/Views/billing/opd_templates/printonplainpaper.html new file mode 100644 index 0000000..65ec333 --- /dev/null +++ b/app/Views/billing/opd_templates/printonplainpaper.html @@ -0,0 +1,86 @@ + + + + + + + + + +
+ + +

{{H_Name}}

+

{{H_address_1}}, {{H_address_2}}
+ Phone: {{H_phone_No}} +

+
+

Dr. {{doctor_name}}

+ {{doctor_sign_html}} +
+
+
+ + +

Prescription Generated: {{print_time}}

+

Please ensure doctor registration number and signature/stamp are present for regulatory compliance.

+
+ + + + + + +
+ Name: {{pName}}
+ S/o: [Father Name]
+ Gender/Age: {{age_sex}}
+ Mob: {{phoneno}}
+ Address: [Address] +
+ UHID: {{uhid_no}}
+ Sr No.: [Sr No]
+ OPD No.: {{opd_no}}
+ Date & Time: {{opd_date}} 12:00 AM
+ Valid Upto: [Valid Date] +
+ + + + + + + +
+ DEPARTMENT:
{{Complaint}} +
+ DIAGNOSIS:
{{diagnosis}} +
+ Last Visit: [Date]
+ No. of Visit: [Count] +
+ +

Rx :

+ +{{medical}} + +

+ Investigation: {{investigation}}
+ Advice: {{advice}} +

+ +
+

Dr. {{doctor_name}}

+ {{doctor_sign_html}} +

Reg. No.: 80982

+
\ No newline at end of file diff --git a/app/Views/billing/opd_templates/rx_print_chamunda_plain_paper.html b/app/Views/billing/opd_templates/rx_print_chamunda_plain_paper.html deleted file mode 100644 index 170ced1..0000000 --- a/app/Views/billing/opd_templates/rx_print_chamunda_plain_paper.html +++ /dev/null @@ -1 +0,0 @@ -

Test again

\ No newline at end of file diff --git a/app/Views/diagnosis/imaging_ai_result_modal.php b/app/Views/diagnosis/imaging_ai_result_modal.php index e7d0d71..0f67655 100644 --- a/app/Views/diagnosis/imaging_ai_result_modal.php +++ b/app/Views/diagnosis/imaging_ai_result_modal.php @@ -5,7 +5,7 @@ $studyName = trim((string) ($study_name ?? '')); $findingsHtml = (string) ($findings_html ?? ''); $impressionHtml = (string) ($impression_html ?? ''); $summaryText = trim((string) ($summary_text ?? '')); -$provider = trim((string) ($provider ?? 'azure-openai')); +$provider = trim((string) ($provider ?? 'ai-server')); $model = trim((string) ($model ?? '')); $findingsInputId = 'ai_findings_' . $batchId; $impressionInputId = 'ai_impression_' . $batchId; @@ -18,8 +18,8 @@ if ($providerKey === 'local-xray-fallback') { } elseif ($providerKey === 'regex-fallback') { $providerLabel = 'Regex Fallback'; $providerBadgeClass = 'bg-warning text-dark'; -} elseif ($providerKey === 'azure-openai') { - $providerLabel = 'Azure OpenAI'; +} elseif ($providerKey === 'ai-server') { + $providerLabel = 'AI Server'; $providerBadgeClass = 'bg-info text-dark'; } $isFallback = in_array($providerKey, ['local-xray-fallback', 'regex-fallback'], true); diff --git a/public/assets/images/hospital_logo_20260319_082713_10b1d94f.png b/public/assets/images/hospital_logo_20260319_082713_10b1d94f.png new file mode 100644 index 0000000000000000000000000000000000000000..bdfe616a4953b8bf5a615060394a42a4d3a3448c GIT binary patch literal 69535 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�)j~es>|MwN3GTk=KQ-rx%j9`8Cyh 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 Puzby7i^UQI{4RlwTkZgS=F^^UK@}& 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 literal 0 HcmV?d00001 diff --git a/public/uploads/patient/profile_1_1773908930.jpg b/public/uploads/patient/profile_1_1773908930.jpg new file mode 100644 index 0000000000000000000000000000000000000000..6c943453556b9892cfafe17c05ade2257d896ad4 GIT binary patch literal 63180 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

Kc>2Spy0TwHd_y--m# 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 bta>c*v}h&V2|&jHW7`Kf