Investigation master: add category autofill action and rules
This commit is contained in:
parent
c930a54155
commit
681bb947b3
|
|
@ -837,6 +837,7 @@ $routes->get('Opd_prescription/opd_invest_master_get/(:num)', 'Opd_prescription:
|
|||
$routes->post('Opd_prescription/opd_invest_master_save', 'Opd_prescription::opd_invest_master_save');
|
||||
$routes->post('Opd_prescription/opd_invest_master_remove/(:num)', 'Opd_prescription::opd_invest_master_remove/$1');
|
||||
$routes->post('Opd_prescription/opd_invest_master_toggle_fav/(:num)', 'Opd_prescription::opd_invest_master_toggle_fav/$1');
|
||||
$routes->post('Opd_prescription/opd_invest_master_backfill_category', 'Opd_prescription::opd_invest_master_backfill_category');
|
||||
$routes->get('Opd_prescription/opd_invest_shortcuts_manager', 'Opd_prescription::opd_invest_shortcuts_manager', ['filter' => 'permission:doctor_work.medicine.manage,doctor_work.access']);
|
||||
$routes->get('Opd_prescription/opd_invest_shortcuts_all', 'Opd_prescription::opd_invest_shortcuts_all');
|
||||
$routes->post('Opd_prescription/opd_invest_shortcuts_save_item', 'Opd_prescription::opd_invest_shortcuts_save_item');
|
||||
|
|
|
|||
|
|
@ -3813,6 +3813,96 @@ class Opd_prescription extends BaseController
|
|||
]);
|
||||
}
|
||||
|
||||
private function inferInvestigationCategory(string $name): string
|
||||
{
|
||||
$value = strtolower(trim($name));
|
||||
if ($value === '') {
|
||||
return 'Pathology';
|
||||
}
|
||||
|
||||
if (preg_match('/\b(x\s*[-]?\s*ray|xray|radiograph|radiology)\b/i', $value) === 1) {
|
||||
return 'X-Ray';
|
||||
}
|
||||
if (preg_match('/\b(ultra\s*sound|ultrasound|u\.?s\.?g\.?|usg|sonography|doppler)\b/i', $value) === 1) {
|
||||
return 'Ultra Sound';
|
||||
}
|
||||
if (preg_match('/\b(ct\s*[-]?\s*scan|cect|hrct|ncct|computed tomography)\b/i', $value) === 1) {
|
||||
return 'CT-Scan';
|
||||
}
|
||||
if (preg_match('/\b(mri|mr\s*i|magnetic resonance)\b/i', $value) === 1) {
|
||||
return 'MRI';
|
||||
}
|
||||
if (preg_match('/\b(echo|echocardiography|2d\s*echo|doppler\s*echo)\b/i', $value) === 1) {
|
||||
return 'ECHO';
|
||||
}
|
||||
if (preg_match('/\b(ecg|electrocardiogram|tmt|holter)\b/i', $value) === 1) {
|
||||
return 'Cardiology';
|
||||
}
|
||||
|
||||
return 'Pathology';
|
||||
}
|
||||
|
||||
public function opd_invest_master_backfill_category()
|
||||
{
|
||||
if (! $this->request->isAJAX()) {
|
||||
return $this->response->setStatusCode(400)->setJSON(['update' => 0, 'error_text' => 'Invalid request']);
|
||||
}
|
||||
if (! $this->db->tableExists('investigation')) {
|
||||
return $this->response->setJSON(['update' => 0, 'error_text' => 'Investigation table not found']);
|
||||
}
|
||||
|
||||
$fields = $this->db->getFieldNames('investigation');
|
||||
$keyField = $this->resolveFirstField($fields, ['id', 'Code', 'code']);
|
||||
$nameField = $this->resolveFirstField($fields, ['Name', 'name']);
|
||||
if ($keyField === null || $nameField === null || !in_array('category_name', $fields, true)) {
|
||||
return $this->response->setJSON(['update' => 0, 'error_text' => 'Required fields not found']);
|
||||
}
|
||||
|
||||
$force = ((int) $this->request->getPost('force')) === 1;
|
||||
|
||||
$builder = $this->db->table('investigation')
|
||||
->select($keyField . ' as id, ' . $nameField . ' as name, category_name');
|
||||
|
||||
if (! $force) {
|
||||
$builder->groupStart()
|
||||
->where('category_name IS NULL', null, false)
|
||||
->orWhere("TRIM(category_name) = ''", null, false)
|
||||
->groupEnd();
|
||||
}
|
||||
|
||||
$rows = $builder->get()->getResultArray();
|
||||
$updated = 0;
|
||||
|
||||
foreach ($rows as $row) {
|
||||
$id = (int) ($row['id'] ?? 0);
|
||||
if ($id <= 0) {
|
||||
continue;
|
||||
}
|
||||
|
||||
$name = (string) ($row['name'] ?? '');
|
||||
$category = $this->inferInvestigationCategory($name);
|
||||
|
||||
$ok = $this->db->table('investigation')
|
||||
->where($keyField, $id)
|
||||
->update(['category_name' => $category]);
|
||||
|
||||
if ($ok) {
|
||||
$updated++;
|
||||
}
|
||||
}
|
||||
|
||||
return $this->response->setJSON([
|
||||
'update' => 1,
|
||||
'updated_count' => $updated,
|
||||
'total_candidates' => count($rows),
|
||||
'error_text' => $updated > 0
|
||||
? ('Category updated for ' . $updated . ' investigation(s)')
|
||||
: 'No rows needed category update',
|
||||
'csrfName' => csrf_token(),
|
||||
'csrfHash' => csrf_hash(),
|
||||
]);
|
||||
}
|
||||
|
||||
public function opd_invest_snomed_search()
|
||||
{
|
||||
$q = trim((string) $this->request->getGet('q'));
|
||||
|
|
|
|||
|
|
@ -7,6 +7,9 @@ $med_specs = $med_specs ?? [];
|
|||
<h5 class="mb-0"><i class="bi bi-clipboard2-pulse me-1"></i> Investigation Master</h5>
|
||||
<span class="badge bg-secondary" id="inv_total_badge">—</span>
|
||||
<div class="ms-auto d-flex gap-2">
|
||||
<button type="button" class="btn btn-outline-primary btn-sm" id="btn_inv_autofill_category">
|
||||
<i class="bi bi-magic"></i> Auto Fill Category
|
||||
</button>
|
||||
<button type="button" class="btn btn-outline-secondary btn-sm" id="btn_inv_download_csv">
|
||||
<i class="bi bi-download"></i> Export CSV
|
||||
</button>
|
||||
|
|
@ -451,6 +454,26 @@ $med_specs = $med_specs ?? [];
|
|||
}, 'json');
|
||||
});
|
||||
|
||||
$('#btn_inv_autofill_category').on('click', function() {
|
||||
var msg = 'Auto-fill blank category values using test name rules?\n\n'
|
||||
+ 'Examples: X-Ray, Ultra Sound, CT-Scan, MRI, ECHO, Cardiology, Pathology.';
|
||||
if (!confirm(msg)) {
|
||||
return;
|
||||
}
|
||||
|
||||
apiPost('<?= base_url('Opd_prescription/opd_invest_master_backfill_category') ?>', { force: 0 }, function(data) {
|
||||
if (parseInt(data.update || 0, 10) !== 1) {
|
||||
showToast(data.error_text || 'Unable to auto fill categories', 'err');
|
||||
return;
|
||||
}
|
||||
|
||||
var updated = parseInt(data.updated_count || '0', 10);
|
||||
var total = parseInt(data.total_candidates || '0', 10);
|
||||
showToast((data.error_text || 'Done') + ' (' + updated + '/' + total + ')', 'ok');
|
||||
reloadTable();
|
||||
});
|
||||
});
|
||||
|
||||
/* ── SNOMED CT search autocomplete ─────────────────────────────── */
|
||||
(function() {
|
||||
var snomedTimer = null;
|
||||
|
|
|
|||
Loading…
Reference in New Issue
Block a user