refactor: move TestsController to Test namespace and update routes

- Move TestsController from App\Controllers to App\Controllers\Test namespace

- Update routes from 'api/tests' to 'api/test' group

- Clean up empty lines in Routes.php

- Improve code formatting and indentation in TestsController
This commit is contained in:
mahdahar 2026-03-02 07:02:51 +07:00
parent 24e0293824
commit 49d3a69308
2 changed files with 204 additions and 209 deletions

View File

@ -29,8 +29,6 @@ $routes->group('v2/auth', function ($routes) {
$routes->post('logout', 'AuthV2Controller::logout');
});
// Faker
$routes->get('faker/faker-patient/(:num)', 'faker\FakerPatient::sendMany/$1');
@ -287,16 +285,12 @@ $routes->group('api', function ($routes) {
$routes->patch('/', 'Specimen\SpecimenController::update');
});
// Tests
$routes->group('tests', function ($routes) {
$routes->get('/', 'TestsController::index');
$routes->get('(:num)', 'TestsController::show/$1');
$routes->post('/', 'TestsController::create');
$routes->patch('/', 'TestsController::update');
});
// Test Mapping
$routes->group('test', function ($routes) {
$routes->get('/', 'Test\TestsController::index');
$routes->get('(:num)', 'Test\TestsController::show/$1');
$routes->post('/', 'Test\TestsController::create');
$routes->patch('/', 'Test\TestsController::update');
$routes->group('testmap', function ($routes) {
$routes->get('/', 'Test\TestMapController::index');
$routes->get('(:num)', 'Test\TestMapController::show/$1');

View File

@ -1,32 +1,31 @@
<?php
namespace App\Controllers;
use App\Traits\ResponseTrait;
namespace App\Controllers\Test;
use App\Controllers\BaseController;
use App\Libraries\ValueSet;
use App\Libraries\TestValidationService;
use App\Libraries\ValueSet;
use App\Traits\ResponseTrait;
class TestsController extends BaseController
{
use ResponseTrait;
protected $db;
protected $rules;
protected $model;
protected $modelCal;
protected $modelGrp;
protected $modelMap;
protected $modelMapDetail;
protected $modelRefNum;
protected $modelRefTxt;
protected $rules;
public function __construct()
{
$this->db = \Config\Database::connect();
$this->model = new \App\Models\Test\TestDefSiteModel;
$this->modelCal = new \App\Models\Test\TestDefCalModel;
$this->modelGrp = new \App\Models\Test\TestDefGrpModel;
$this->modelMap = new \App\Models\Test\TestMapModel;
$this->modelMapDetail = new \App\Models\Test\TestMapDetailModel;
@ -36,75 +35,95 @@ class TestsController extends BaseController
$this->rules = [
'TestSiteCode' => 'required',
'TestSiteName' => 'required',
'TestType' => 'required',
'SiteID' => 'required'
'TestType' => 'required',
'SiteID' => 'required',
];
}
public function index()
{
$siteId = $this->request->getGet('SiteID');
$testType = $this->request->getGet('TestType');
$visibleScr = $this->request->getGet('VisibleScr');
$visibleRpt = $this->request->getGet('VisibleRpt');
$keyword = $this->request->getGet('TestSiteName');
{
$siteId = $this->request->getGet('SiteID');
$testType = $this->request->getGet('TestType');
$visibleScr = $this->request->getGet('VisibleScr');
$visibleRpt = $this->request->getGet('VisibleRpt');
$testSiteName = $this->request->getGet('TestSiteName');
$testSiteCode = $this->request->getGet('TestSiteCode');
$builder = $this->db->table('testdefsite')
->select("testdefsite.TestSiteID, testdefsite.TestSiteCode, testdefsite.TestSiteName, testdefsite.TestType,
$builder = $this->db->table('testdefsite')
->select(
"testdefsite.TestSiteID, testdefsite.TestSiteCode, testdefsite.TestSiteName, testdefsite.TestType,
testdefsite.SeqScr, testdefsite.SeqRpt, testdefsite.VisibleScr, testdefsite.VisibleRpt,
testdefsite.CountStat, testdefsite.StartDate, testdefsite.EndDate,
COALESCE(testdefsite.DisciplineID, cal.DisciplineID) as DisciplineID,
COALESCE(testdefsite.DepartmentID, cal.DepartmentID) as DepartmentID,
d.DisciplineName, dept.DepartmentName")
->join('testdefcal cal', 'cal.TestSiteID = testdefsite.TestSiteID AND cal.EndDate IS NULL', 'left')
->join('discipline d', 'd.DisciplineID = COALESCE(testdefsite.DisciplineID, cal.DisciplineID)', 'left')
->join('department dept', 'dept.DepartmentID = COALESCE(testdefsite.DepartmentID, cal.DepartmentID)', 'left')
->where('testdefsite.EndDate IS NULL');
d.DisciplineName, dept.DepartmentName"
)
->join('testdefcal cal', 'cal.TestSiteID = testdefsite.TestSiteID AND cal.EndDate IS NULL', 'left')
->join('discipline d', 'd.DisciplineID = COALESCE(testdefsite.DisciplineID, cal.DisciplineID)', 'left')
->join('department dept', 'dept.DepartmentID = COALESCE(testdefsite.DepartmentID, cal.DepartmentID)', 'left')
->where('testdefsite.EndDate IS NULL');
if ($siteId) {
$builder->where('testdefsite.SiteID', $siteId);
if ($siteId) {
$builder->where('testdefsite.SiteID', $siteId);
}
if ($testType) {
$builder->where('testdefsite.TestType', $testType);
}
if ($visibleScr !== null) {
$builder->where('testdefsite.VisibleScr', $visibleScr);
}
if ($visibleRpt !== null) {
$builder->where('testdefsite.VisibleRpt', $visibleRpt);
}
if ($testSiteName) {
$builder->like('testdefsite.TestSiteName', $testSiteName);
}
if ($testSiteCode) {
$builder->like('testdefsite.TestSiteCode', $testSiteCode);
}
$rows = $builder->orderBy('testdefsite.SeqScr', 'ASC')->get()->getResultArray();
if (empty($rows)) {
return $this->respond([
'status' => 'success',
'message' => 'No data.',
'data' => [],
], 200);
}
$rows = ValueSet::transformLabels($rows, [
'TestType' => 'test_type',
]);
return $this->respond([
'status' => 'success',
'message' => 'Data fetched successfully',
'data' => $rows,
], 200);
}
if ($testType) {
$builder->where('testdefsite.TestType', $testType);
}
if ($visibleScr !== null) {
$builder->where('testdefsite.VisibleScr', $visibleScr);
}
if ($visibleRpt !== null) {
$builder->where('testdefsite.VisibleRpt', $visibleRpt);
}
if ($keyword) {
$builder->like('testdefsite.TestSiteName', $keyword);
}
$rows = $builder->orderBy('testdefsite.SeqScr', 'ASC')->get()->getResultArray();
if (empty($rows)) {
return $this->respond(['status' => 'success', 'message' => "No data.", 'data' => []], 200);
}
$rows = ValueSet::transformLabels($rows, [
'TestType' => 'test_type',
]);
return $this->respond(['status' => 'success', 'message' => "Data fetched successfully", 'data' => $rows], 200);
}
public function show($id = null)
{
if (!$id)
if (!$id) {
return $this->failValidationErrors('TestSiteID is required');
}
$row = $this->model->select("testdefsite.*")
->where("testdefsite.TestSiteID", $id)
$row = $this->model->select('testdefsite.*')
->where('testdefsite.TestSiteID', $id)
->find($id);
if (!$row) {
return $this->respond(['status' => 'success', 'message' => "No data.", 'data' => null], 200);
return $this->respond([
'status' => 'success',
'message' => 'No data.',
'data' => null,
], 200);
}
$row = ValueSet::transformLabels([$row], [
@ -121,9 +140,6 @@ class TestsController extends BaseController
->where('testdefcal.TestSiteID', $id)
->where('testdefcal.EndDate IS NULL')
->get()->getResultArray();
$row['testmap'] = $this->modelMap->where('TestSiteID', $id)->where('EndDate IS NULL')->findAll();
} elseif ($typeCode === 'GROUP') {
$row['testdefgrp'] = $this->db->table('testdefgrp')
->select('testdefgrp.*, t.TestSiteCode, t.TestSiteName, t.TestType')
@ -136,14 +152,8 @@ class TestsController extends BaseController
$row['testdefgrp'] = ValueSet::transformLabels($row['testdefgrp'], [
'TestType' => 'test_type',
]);
$row['testmap'] = $this->modelMap->where('TestSiteID', $id)->where('EndDate IS NULL')->findAll();
} elseif ($typeCode === 'TITLE') {
$row['testmap'] = $this->modelMap->where('TestSiteID', $id)->where('EndDate IS NULL')->findAll();
} else {
// Technical details are now stored directly in testdefsite
$row['testdeftech'] = $this->db->table('testdefsite')
->select('testdefsite.*, d.DisciplineName, dept.DepartmentName')
->join('discipline d', 'd.DisciplineID=testdefsite.DisciplineID', 'left')
@ -152,14 +162,11 @@ class TestsController extends BaseController
->where('testdefsite.EndDate IS NULL')
->get()->getResultArray();
$row['testmap'] = $this->modelMap->where('TestSiteID', $id)->where('EndDate IS NULL')->findAll();
if (!empty($row['testdeftech'])) {
$techData = $row['testdeftech'][0];
$refType = $techData['RefType'];
$resultType = $techData['ResultType'] ?? '';
// Use TestValidationService to determine reference table
if (TestValidationService::usesRefNum($resultType, $refType)) {
$refnumData = $this->modelRefNum
->where('TestSiteID', $id)
@ -169,26 +176,25 @@ class TestsController extends BaseController
$row['refnum'] = array_map(function ($r) {
return [
'RefNumID' => $r['RefNumID'],
'NumRefType' => $r['NumRefType'],
'RefNumID' => $r['RefNumID'],
'NumRefType' => $r['NumRefType'],
'NumRefTypeLabel' => $r['NumRefType'] ? ValueSet::getLabel('numeric_ref_type', $r['NumRefType']) : '',
'RangeType' => $r['RangeType'],
'RangeTypeLabel' => $r['RangeType'] ? ValueSet::getLabel('range_type', $r['RangeType']) : '',
'Sex' => $r['Sex'],
'SexLabel' => $r['Sex'] ? ValueSet::getLabel('gender', $r['Sex']) : '',
'LowSign' => $r['LowSign'],
'LowSignLabel' => $r['LowSign'] ? ValueSet::getLabel('math_sign', $r['LowSign']) : '',
'HighSign' => $r['HighSign'],
'HighSignLabel' => $r['HighSign'] ? ValueSet::getLabel('math_sign', $r['HighSign']) : '',
'High' => $r['High'] !== null ? (float) $r['High'] : null,
'Low' => $r['Low'] !== null ? (float) $r['Low'] : null,
'AgeStart' => (int) $r['AgeStart'],
'AgeEnd' => (int) $r['AgeEnd'],
'Flag' => $r['Flag'],
'Interpretation' => $r['Interpretation']
'RangeType' => $r['RangeType'],
'RangeTypeLabel' => $r['RangeType'] ? ValueSet::getLabel('range_type', $r['RangeType']) : '',
'Sex' => $r['Sex'],
'SexLabel' => $r['Sex'] ? ValueSet::getLabel('gender', $r['Sex']) : '',
'LowSign' => $r['LowSign'],
'LowSignLabel' => $r['LowSign'] ? ValueSet::getLabel('math_sign', $r['LowSign']) : '',
'HighSign' => $r['HighSign'],
'HighSignLabel' => $r['HighSign'] ? ValueSet::getLabel('math_sign', $r['HighSign']) : '',
'High' => $r['High'] !== null ? (float) $r['High'] : null,
'Low' => $r['Low'] !== null ? (float) $r['Low'] : null,
'AgeStart' => (int) $r['AgeStart'],
'AgeEnd' => (int) $r['AgeEnd'],
'Flag' => $r['Flag'],
'Interpretation' => $r['Interpretation'],
];
}, $refnumData ?? []);
}
if (TestValidationService::usesRefTxt($resultType, $refType)) {
@ -200,26 +206,26 @@ class TestsController extends BaseController
$row['reftxt'] = array_map(function ($r) {
return [
'RefTxtID' => $r['RefTxtID'],
'TxtRefType' => $r['TxtRefType'],
'TxtRefTypeLabel' => $r['TxtRefType'] ? ValueSet::getLabel('text_ref_type', $r['TxtRefType']) : '',
'Sex' => $r['Sex'],
'SexLabel' => $r['Sex'] ? ValueSet::getLabel('gender', $r['Sex']) : '',
'AgeStart' => (int) $r['AgeStart'],
'AgeEnd' => (int) $r['AgeEnd'],
'RefTxt' => $r['RefTxt'],
'Flag' => $r['Flag']
'RefTxtID' => $r['RefTxtID'],
'TxtRefType' => $r['TxtRefType'],
'TxtRefTypeLabel'=> $r['TxtRefType'] ? ValueSet::getLabel('text_ref_type', $r['TxtRefType']) : '',
'Sex' => $r['Sex'],
'SexLabel' => $r['Sex'] ? ValueSet::getLabel('gender', $r['Sex']) : '',
'AgeStart' => (int) $r['AgeStart'],
'AgeEnd' => (int) $r['AgeEnd'],
'RefTxt' => $r['RefTxt'],
'Flag' => $r['Flag'],
];
}, $reftxtData ?? []);
}
}
}
// $row['refTypeOptions'] = ValueSet::getOptions('reference_type');
// $row['sexOptions'] = ValueSet::getOptions('gender');
// $row['mathSignOptions'] = ValueSet::getOptions('math_sign');
return $this->respond(['status' => 'success', 'message' => "Data fetched successfully", 'data' => $row], 200);
return $this->respond([
'status' => 'success',
'message' => 'Data fetched successfully',
'data' => $row,
], 200);
}
public function create()
@ -230,13 +236,11 @@ class TestsController extends BaseController
return $this->failValidationErrors($this->validator->getErrors());
}
// Validate TestType, ResultType, and RefType combinations
$testType = $input['TestType'] ?? '';
$details = $input['details'] ?? $input;
$resultType = $details['ResultType'] ?? '';
$refType = $details['RefType'] ?? '';
// Set defaults for CALC, GROUP, TITLE types
if (TestValidationService::isCalc($testType)) {
$resultType = 'NMRIC';
$refType = $refType ?: 'RANGE';
@ -256,24 +260,24 @@ class TestsController extends BaseController
try {
$testSiteData = [
'SiteID' => $input['SiteID'],
'TestSiteCode' => $input['TestSiteCode'],
'TestSiteName' => $input['TestSiteName'],
'TestType' => $input['TestType'],
'SiteID' => $input['SiteID'],
'TestSiteCode'=> $input['TestSiteCode'],
'TestSiteName'=> $input['TestSiteName'],
'TestType' => $input['TestType'],
'Description' => $input['Description'] ?? null,
'SeqScr' => $input['SeqScr'] ?? 0,
'SeqRpt' => $input['SeqRpt'] ?? 0,
'IndentLeft' => $input['IndentLeft'] ?? 0,
'FontStyle' => $input['FontStyle'] ?? null,
'VisibleScr' => $input['VisibleScr'] ?? 1,
'VisibleRpt' => $input['VisibleRpt'] ?? 1,
'CountStat' => $input['CountStat'] ?? 1,
'StartDate' => $input['StartDate'] ?? date('Y-m-d H:i:s')
'SeqScr' => $input['SeqScr'] ?? 0,
'SeqRpt' => $input['SeqRpt'] ?? 0,
'IndentLeft' => $input['IndentLeft'] ?? 0,
'FontStyle' => $input['FontStyle'] ?? null,
'VisibleScr' => $input['VisibleScr'] ?? 1,
'VisibleRpt' => $input['VisibleRpt'] ?? 1,
'CountStat' => $input['CountStat'] ?? 1,
'StartDate' => $input['StartDate'] ?? date('Y-m-d H:i:s'),
];
$id = $this->model->insert($testSiteData);
if (!$id) {
throw new \Exception("Failed to insert main test definition");
throw new \Exception('Failed to insert main test definition');
}
$this->handleDetails($id, $input, 'insert');
@ -285,12 +289,13 @@ class TestsController extends BaseController
}
return $this->respondCreated([
'status' => 'created',
'message' => "Test created successfully",
'data' => ['TestSiteId' => $id]
'status' => 'created',
'message' => 'Test created successfully',
'data' => ['TestSiteId' => $id],
]);
} catch (\Exception $e) {
$this->db->transRollback();
return $this->failServerError('Something went wrong: ' . $e->getMessage());
}
}
@ -299,8 +304,8 @@ class TestsController extends BaseController
{
$input = $this->request->getJSON(true);
if (!$id && isset($input["TestSiteID"])) {
$id = $input["TestSiteID"];
if (!$id && isset($input['TestSiteID'])) {
$id = $input['TestSiteID'];
}
if (!$id) {
return $this->failValidationErrors('TestSiteID is required.');
@ -311,13 +316,11 @@ class TestsController extends BaseController
return $this->failNotFound('Test not found');
}
// Validate TestType, ResultType, and RefType combinations if provided
$testType = $input['TestType'] ?? $existing['TestType'] ?? '';
$details = $input['details'] ?? $input;
$resultType = $details['ResultType'] ?? $existing['ResultType'] ?? '';
$refType = $details['RefType'] ?? $existing['RefType'] ?? '';
// Set defaults for CALC, GROUP, TITLE types
if (TestValidationService::isCalc($testType)) {
$resultType = 'NMRIC';
$refType = $refType ?: 'RANGE';
@ -349,7 +352,7 @@ class TestsController extends BaseController
'VisibleScr',
'VisibleRpt',
'CountStat',
'StartDate'
'StartDate',
];
foreach ($allowedUpdateFields as $field) {
@ -371,12 +374,13 @@ class TestsController extends BaseController
}
return $this->respond([
'status' => 'success',
'message' => "Test updated successfully",
'data' => ['TestSiteId' => $id]
'status' => 'success',
'message' => 'Test updated successfully',
'data' => ['TestSiteId' => $id],
]);
} catch (\Exception $e) {
$this->db->transRollback();
return $this->failServerError('Something went wrong: ' . $e->getMessage());
}
}
@ -385,8 +389,8 @@ class TestsController extends BaseController
{
$input = $this->request->getJSON(true);
if (!$id && isset($input["TestSiteID"])) {
$id = $input["TestSiteID"];
if (!$id && isset($input['TestSiteID'])) {
$id = $input['TestSiteID'];
}
if (!$id) {
return $this->failValidationErrors('TestSiteID is required.');
@ -420,7 +424,6 @@ class TestsController extends BaseController
->where('TestSiteID', $id)
->update(['EndDate' => $now]);
} elseif (TestValidationService::isTechnicalTest($typeCode)) {
$this->modelRefNum->where('TestSiteID', $id)->set('EndDate', $now)->update();
$this->modelRefTxt->where('TestSiteID', $id)->set('EndDate', $now)->update();
}
@ -436,12 +439,13 @@ class TestsController extends BaseController
}
return $this->respond([
'status' => 'success',
'message' => "Test disabled successfully",
'data' => ['TestSiteId' => $id, 'EndDate' => $now]
'status' => 'success',
'message' => 'Test disabled successfully',
'data' => ['TestSiteId' => $id, 'EndDate' => $now],
]);
} catch (\Exception $e) {
$this->db->transRollback();
return $this->failServerError('Something went wrong: ' . $e->getMessage());
}
}
@ -455,8 +459,9 @@ class TestsController extends BaseController
$testTypeID = $existing['TestType'] ?? null;
}
if (!$testTypeID)
if (!$testTypeID) {
return;
}
$typeCode = $testTypeID;
@ -467,16 +472,19 @@ class TestsController extends BaseController
switch ($typeCode) {
case 'CALC':
$this->saveCalcDetails($testSiteID, $details, $action);
break;
case 'GROUP':
$this->saveGroupDetails($testSiteID, $details, $input, $action);
break;
case 'TITLE':
if (isset($input['testmap']) && is_array($input['testmap'])) {
$this->saveTestMap($testSiteID, $input['testmap'], $action);
}
break;
case 'TEST':
@ -488,7 +496,6 @@ class TestsController extends BaseController
$refType = (string) $details['RefType'];
$resultType = $details['ResultType'] ?? '';
// Use TestValidationService to determine which reference table to use
if (TestValidationService::usesRefNum($resultType, $refType) && isset($input['refnum']) && is_array($input['refnum'])) {
$this->saveRefNumRanges($testSiteID, $input['refnum'], $action, $input['SiteID'] ?? 1);
}
@ -497,6 +504,7 @@ class TestsController extends BaseController
$this->saveRefTxtRanges($testSiteID, $input['reftxt'], $action, $input['SiteID'] ?? 1);
}
}
break;
}
@ -507,25 +515,23 @@ class TestsController extends BaseController
private function saveTechDetails($testSiteID, $data, $action, $typeCode)
{
// Technical details are now stored directly in testdefsite table
$techData = [
'DisciplineID' => $data['DisciplineID'] ?? null,
'DepartmentID' => $data['DepartmentID'] ?? null,
'ResultType' => $data['ResultType'] ?? null,
'RefType' => $data['RefType'] ?? null,
'VSet' => $data['VSet'] ?? null,
'ReqQty' => $data['ReqQty'] ?? null,
'ReqQtyUnit' => $data['ReqQtyUnit'] ?? null,
'Unit1' => $data['Unit1'] ?? null,
'Factor' => $data['Factor'] ?? null,
'Unit2' => $data['Unit2'] ?? null,
'Decimal' => $data['Decimal'] ?? 2,
'CollReq' => $data['CollReq'] ?? null,
'Method' => $data['Method'] ?? null,
'ExpectedTAT' => $data['ExpectedTAT'] ?? null
'DisciplineID' => $data['DisciplineID'] ?? null,
'DepartmentID' => $data['DepartmentID'] ?? null,
'ResultType' => $data['ResultType'] ?? null,
'RefType' => $data['RefType'] ?? null,
'VSet' => $data['VSet'] ?? null,
'ReqQty' => $data['ReqQty'] ?? null,
'ReqQtyUnit' => $data['ReqQtyUnit'] ?? null,
'Unit1' => $data['Unit1'] ?? null,
'Factor' => $data['Factor'] ?? null,
'Unit2' => $data['Unit2'] ?? null,
'Decimal' => $data['Decimal'] ?? 2,
'CollReq' => $data['CollReq'] ?? null,
'Method' => $data['Method'] ?? null,
'ExpectedTAT' => $data['ExpectedTAT'] ?? null,
];
// Update the testdefsite record directly
$this->model->update($testSiteID, $techData);
}
@ -539,21 +545,21 @@ class TestsController extends BaseController
foreach ($ranges as $index => $range) {
$this->modelRefNum->insert([
'TestSiteID' => $testSiteID,
'SiteID' => $siteID,
'NumRefType' => $range['NumRefType'],
'RangeType' => $range['RangeType'],
'Sex' => $range['Sex'],
'AgeStart' => (int) ($range['AgeStart'] ?? 0),
'AgeEnd' => (int) ($range['AgeEnd'] ?? 150),
'LowSign' => !empty($range['LowSign']) ? $range['LowSign'] : null,
'Low' => !empty($range['Low']) ? (float) $range['Low'] : null,
'HighSign' => !empty($range['HighSign']) ? $range['HighSign'] : null,
'High' => !empty($range['High']) ? (float) $range['High'] : null,
'Flag' => $range['Flag'] ?? null,
'Interpretation' => $range['Interpretation'] ?? null,
'Display' => $index,
'CreateDate' => date('Y-m-d H:i:s')
'TestSiteID' => $testSiteID,
'SiteID' => $siteID,
'NumRefType' => $range['NumRefType'],
'RangeType' => $range['RangeType'],
'Sex' => $range['Sex'],
'AgeStart' => (int) ($range['AgeStart'] ?? 0),
'AgeEnd' => (int) ($range['AgeEnd'] ?? 150),
'LowSign' => !empty($range['LowSign']) ? $range['LowSign'] : null,
'Low' => !empty($range['Low']) ? (float) $range['Low'] : null,
'HighSign' => !empty($range['HighSign']) ? $range['HighSign'] : null,
'High' => !empty($range['High']) ? (float) $range['High'] : null,
'Flag' => $range['Flag'] ?? null,
'Interpretation'=> $range['Interpretation'] ?? null,
'Display' => $index,
'CreateDate' => date('Y-m-d H:i:s'),
]);
}
}
@ -569,14 +575,14 @@ class TestsController extends BaseController
foreach ($ranges as $range) {
$this->modelRefTxt->insert([
'TestSiteID' => $testSiteID,
'SiteID' => $siteID,
'SiteID' => $siteID,
'TxtRefType' => $range['TxtRefType'],
'Sex' => $range['Sex'],
'AgeStart' => (int) ($range['AgeStart'] ?? 0),
'AgeEnd' => (int) ($range['AgeEnd'] ?? 150),
'RefTxt' => $range['RefTxt'] ?? '',
'Flag' => $range['Flag'] ?? null,
'CreateDate' => date('Y-m-d H:i:s')
'Sex' => $range['Sex'],
'AgeStart' => (int) ($range['AgeStart'] ?? 0),
'AgeEnd' => (int) ($range['AgeEnd'] ?? 150),
'RefTxt' => $range['RefTxt'] ?? '',
'Flag' => $range['Flag'] ?? null,
'CreateDate' => date('Y-m-d H:i:s'),
]);
}
}
@ -584,18 +590,18 @@ class TestsController extends BaseController
private function saveCalcDetails($testSiteID, $data, $action)
{
$calcData = [
'TestSiteID' => $testSiteID,
'DisciplineID' => $data['DisciplineID'] ?? null,
'DepartmentID' => $data['DepartmentID'] ?? null,
'FormulaInput' => $data['FormulaInput'] ?? null,
'FormulaCode' => $data['FormulaCode'] ?? $data['Formula'] ?? null,
'ResultType' => 'NMRIC', // CALC always has NMRIC result type
'RefType' => $data['RefType'] ?? 'RANGE',
'Unit1' => $data['Unit1'] ?? $data['ResultUnit'] ?? null,
'Factor' => $data['Factor'] ?? null,
'Unit2' => $data['Unit2'] ?? null,
'Decimal' => $data['Decimal'] ?? 2,
'Method' => $data['Method'] ?? null
'TestSiteID' => $testSiteID,
'DisciplineID' => $data['DisciplineID'] ?? null,
'DepartmentID' => $data['DepartmentID'] ?? null,
'FormulaInput' => $data['FormulaInput'] ?? null,
'FormulaCode' => $data['FormulaCode'] ?? $data['Formula'] ?? null,
'ResultType' => 'NMRIC',
'RefType' => $data['RefType'] ?? 'RANGE',
'Unit1' => $data['Unit1'] ?? $data['ResultUnit'] ?? null,
'Factor' => $data['Factor'] ?? null,
'Unit2' => $data['Unit2'] ?? null,
'Decimal' => $data['Decimal'] ?? 2,
'Method' => $data['Method'] ?? null,
];
if ($action === 'update') {
@ -630,7 +636,7 @@ class TestsController extends BaseController
if ($memberID) {
$this->modelGrp->insert([
'TestSiteID' => $testSiteID,
'Member' => $memberID
'Member' => $memberID,
]);
}
}
@ -640,20 +646,17 @@ class TestsController extends BaseController
private function saveTestMap($testSiteID, $mappings, $action)
{
if ($action === 'update') {
// Soft delete existing testmaps and their details for this test site
$existingMaps = $this->modelMap->where('TestSiteID', $testSiteID)
->where('EndDate IS NULL')
->findAll();
foreach ($existingMaps as $existingMap) {
// Soft delete details first
$this->modelMapDetail->where('TestMapID', $existingMap['TestMapID'])
->where('EndDate IS NULL')
->set('EndDate', date('Y-m-d H:i:s'))
->update();
}
// Soft delete the testmap headers
$this->db->table('testmap')
->where('TestSiteID', $testSiteID)
->where('EndDate IS NULL')
@ -662,24 +665,22 @@ class TestsController extends BaseController
if (is_array($mappings)) {
foreach ($mappings as $map) {
// Create testmap header
$mapData = [
'TestSiteID' => $testSiteID,
'HostType' => $map['HostType'] ?? null,
'HostID' => $map['HostID'] ?? null,
'HostType' => $map['HostType'] ?? null,
'HostID' => $map['HostID'] ?? null,
'ClientType' => $map['ClientType'] ?? null,
'ClientID' => $map['ClientID'] ?? null,
'ClientID' => $map['ClientID'] ?? null,
];
$testMapID = $this->modelMap->insert($mapData);
// Create testmapdetail records if details are provided
if ($testMapID && isset($map['details']) && is_array($map['details'])) {
foreach ($map['details'] as $detail) {
$detailData = [
'TestMapID' => $testMapID,
'HostTestCode' => $detail['HostTestCode'] ?? null,
'HostTestName' => $detail['HostTestName'] ?? null,
'ConDefID' => $detail['ConDefID'] ?? null,
'TestMapID' => $testMapID,
'HostTestCode' => $detail['HostTestCode'] ?? null,
'HostTestName' => $detail['HostTestName'] ?? null,
'ConDefID' => $detail['ConDefID'] ?? null,
'ClientTestCode' => $detail['ClientTestCode'] ?? null,
'ClientTestName' => $detail['ClientTestName'] ?? null,
];