diff --git a/application/controllers/mockup/process/resultentry-v23/Re_px.php b/application/controllers/mockup/process/resultentry-v23/Re_px.php index 258fae44..f437ffc7 100644 --- a/application/controllers/mockup/process/resultentry-v23/Re_px.php +++ b/application/controllers/mockup/process/resultentry-v23/Re_px.php @@ -264,6 +264,115 @@ class Re_px extends MY_Controller "result_sets" => $result_sets ); } + private function collect_fail_reason_tokens($candidates) + { + $tokens = array(); + foreach ($candidates as $candidate) { + $fail_reason = isset($candidate['FailReason']) ? trim($candidate['FailReason']) : ''; + if ($fail_reason === '') continue; + $parts = explode(';', $fail_reason); + foreach ($parts as $part) { + $token = trim($part); + if ($token === '') continue; + if (!isset($tokens[$token])) $tokens[$token] = 0; + $tokens[$token]++; + } + } + return $tokens; + } + private function build_normal_setting_conclusion($order_detail_id, $summary, $checks, $branches, $candidates) + { + $messages = array(); + $actions = array(); + $primary_issue = "Nilai normal belum ditemukan."; + $selected_method_id = isset($summary['SelectedMethodeID']) ? intval($summary['SelectedMethodeID']) : 0; + $selected_method_name = isset($summary['SelectedMethodeName']) ? $summary['SelectedMethodeName'] : ''; + $selected_method_source = isset($summary['SelectedMethodeSource']) ? $summary['SelectedMethodeSource'] : ''; + $normal_value_id = isset($summary['FnSamplingGetNormalResult']) ? intval($summary['FnSamplingGetNormalResult']) : 0; + $nat_test_id = isset($summary['Nat_TestID']) ? $summary['Nat_TestID'] : ''; + $sex_id = isset($summary['M_PatientM_SexID']) ? $summary['M_PatientM_SexID'] : ''; + $age_in_day = isset($summary['AgeInDay']) ? intval($summary['AgeInDay']) : 0; + + $missing_checks = array(); + foreach ($checks as $check) { + $status = isset($check['check_status']) ? $check['check_status'] : ''; + if ($status === 'MISSING' || $status === 'NOT_FOUND') { + $missing_checks[] = $check; + } + } + + $branch_total_match = 0; + foreach ($branches as $branch) { + $branch_total_match += isset($branch['matched_count']) ? intval($branch['matched_count']) : 0; + } + + $fail_tokens = $this->collect_fail_reason_tokens($candidates); + $candidate_count = count($candidates); + + if ($normal_value_id > 0) { + $primary_issue = "Nilai normal sudah ditemukan."; + $messages[] = "T_OrderDetailID {$order_detail_id} sudah memiliki kandidat nilai normal yang cocok, yaitu Nat_NormalValueID {$normal_value_id}."; + if ($selected_method_id > 0) { + $messages[] = "Metode yang dipakai adalah {$selected_method_name} (ID {$selected_method_id}) dari sumber {$selected_method_source}."; + } + $actions[] = "Tidak perlu perbaikan setting normal value."; + return array( + "primary_issue" => $primary_issue, + "messages" => $messages, + "actions" => $actions + ); + } + + if ($selected_method_id <= 0) { + $primary_issue = "Metode pemeriksaan tidak ditemukan."; + $messages[] = "T_OrderDetailID {$order_detail_id} tidak punya metode terpilih untuk Nat_TestID {$nat_test_id}."; + $messages[] = "Sistem sudah mencoba sumber metode dari m_methode_priority, m_instrumentmethode, dan nat_normalvalue, tetapi semuanya kosong."; + $actions[] = "Lengkapi mapping metode untuk Nat_TestID {$nat_test_id} di m_methode_priority atau m_instrumentmethode."; + $actions[] = "Pastikan nat_methode dan nat_instrument yang dipakai aktif."; + } elseif ($candidate_count === 0) { + $primary_issue = "Setting nilai normal aktif tidak ditemukan."; + $messages[] = "Tidak ada row nat_normalvalue aktif dan non-abnormal yang tersedia untuk Nat_TestID {$nat_test_id} dengan metode {$selected_method_name} (ID {$selected_method_id})."; + $actions[] = "Tambahkan atau aktifkan nat_normalvalue non-abnormal untuk Nat_TestID {$nat_test_id} dan metode {$selected_method_id}."; + } elseif ($branch_total_match === 0) { + $primary_issue = "Ada setting nilai normal, tetapi tidak ada yang cocok."; + $messages[] = "Ditemukan {$candidate_count} kandidat nat_normalvalue aktif dan non-abnormal, tetapi tidak ada yang lolos rule pencarian normal."; + if (isset($fail_tokens['sex_mismatch'])) { + $messages[] = "Jenis kelamin pasien tidak cocok dengan kandidat yang tersedia. Sex pasien ID {$sex_id}."; + $actions[] = "Periksa setting Nat_NormalValueNat_SexID untuk Nat_TestID {$nat_test_id} dan metode {$selected_method_id}."; + } + if (isset($fail_tokens['age_below_min']) || isset($fail_tokens['age_above_max'])) { + $messages[] = "Usia pasien {$age_in_day} hari tidak masuk ke rentang usia kandidat yang tersedia."; + $actions[] = "Periksa rentang umur min/max untuk nat_normalvalue Nat_TestID {$nat_test_id} dan metode {$selected_method_id}."; + } + if (isset($fail_tokens['flag_not_1'])) { + $messages[] = "Ada kandidat dengan flag yang tidak sesuai untuk pencarian normal."; + $actions[] = "Pastikan kandidat normal memakai Nat_NormalValueNat_FlagID = 1."; + } + if (isset($fail_tokens['valid_date_not_passed'])) { + $messages[] = "Ada kandidat yang tanggal berlakunya belum lolos."; + $actions[] = "Periksa Nat_NormalValueValidDate pada kandidat yang dipakai."; + } + if (isset($fail_tokens['methode_mismatch'])) { + $messages[] = "Ada kandidat untuk Nat_TestID yang sama, tetapi metode kandidat berbeda dengan metode terpilih {$selected_method_id}."; + $actions[] = "Samakan metode kandidat nat_normalvalue dengan metode yang dipilih sistem, atau benahi mapping metode."; + } + } + + if (empty($messages)) { + foreach ($missing_checks as $missing_check) { + $messages[] = "{$missing_check['check_name']} belum terpenuhi. Nilai debug: {$missing_check['check_value']}."; + } + } + if (empty($actions)) { + $actions[] = "Cek detail kandidat pada response untuk melihat FailReason per Nat_NormalValueID."; + } + + return array( + "primary_issue" => $primary_issue, + "messages" => array_values(array_unique($messages)), + "actions" => array_values(array_unique($actions)) + ); + } public function check_normal_setting() { $order_detail_id = $this->get_order_detail_id_input(); @@ -283,6 +392,7 @@ class Re_px extends MY_Controller $checks = isset($result_sets[1]) ? $result_sets[1] : array(); $branches = isset($result_sets[2]) ? $result_sets[2] : array(); $candidates = isset($result_sets[3]) ? $result_sets[3] : array(); + $conclusion = $this->build_normal_setting_conclusion($order_detail_id, $summary, $checks, $branches, $candidates); $this->sys_ok(array( "order_detail_id" => $order_detail_id, @@ -290,6 +400,7 @@ class Re_px extends MY_Controller "checks" => $checks, "branches" => $branches, "candidates" => $candidates, + "conclusion" => $conclusion, "needs_fix" => ( isset($summary["FnSamplingGetNormalResult"]) && intval($summary["FnSamplingGetNormalResult"]) <= 0 diff --git a/sql/manual_changes/2026-05-24-update-sp-sampling-check-normal-setting-active-nonabnormal-only.sql b/sql/manual_changes/2026-05-24-update-sp-sampling-check-normal-setting-active-nonabnormal-only.sql new file mode 100644 index 00000000..64101e6e --- /dev/null +++ b/sql/manual_changes/2026-05-24-update-sp-sampling-check-normal-setting-active-nonabnormal-only.sql @@ -0,0 +1,468 @@ +DROP PROCEDURE IF EXISTS sp_sampling_check_normal_setting; + +DELIMITER $$ + +CREATE PROCEDURE sp_sampling_check_normal_setting(IN pT_OrderDetailID INT) +BEGIN + DECLARE vOrderHeaderID INT DEFAULT NULL; + DECLARE vPatientID INT DEFAULT NULL; + DECLARE vPatientSexID INT DEFAULT NULL; + DECLARE vPatientDOB DATE DEFAULT NULL; + DECLARE vOrderDate DATE DEFAULT NULL; + DECLARE vAgeInDay INT DEFAULT NULL; + DECLARE vTTestID INT DEFAULT NULL; + DECLARE vNatTestID INT DEFAULT NULL; + DECLARE vOrderDetailMethodID INT DEFAULT NULL; + + DECLARE vMethodIDPriority INT DEFAULT NULL; + DECLARE vMethodNamePriority VARCHAR(100) DEFAULT NULL; + DECLARE vMethodIDInstrument INT DEFAULT NULL; + DECLARE vMethodNameInstrument VARCHAR(100) DEFAULT NULL; + DECLARE vMethodIDNormal INT DEFAULT NULL; + DECLARE vMethodNameNormal VARCHAR(100) DEFAULT NULL; + + DECLARE vSelectedMethodID INT DEFAULT NULL; + DECLARE vSelectedMethodName VARCHAR(100) DEFAULT NULL; + DECLARE vSelectedMethodSource VARCHAR(30) DEFAULT NULL; + DECLARE vFnNormalValueID INT DEFAULT 0; + + SELECT + od.T_OrderDetailT_OrderHeaderID, + oh.T_OrderHeaderM_PatientID, + p.M_PatientM_SexID, + p.M_PatientDOB, + DATE(oh.T_OrderHeaderDate), + od.T_OrderDetailT_TestID, + tt.T_TestNat_TestID, + od.T_OrderDetailNat_MethodeID + INTO + vOrderHeaderID, + vPatientID, + vPatientSexID, + vPatientDOB, + vOrderDate, + vTTestID, + vNatTestID, + vOrderDetailMethodID + FROM t_orderdetail od + JOIN t_orderheader oh + ON oh.T_OrderHeaderID = od.T_OrderDetailT_OrderHeaderID + JOIN m_patient p + ON p.M_PatientID = oh.T_OrderHeaderM_PatientID + LEFT JOIN t_test tt + ON tt.T_TestID = od.T_OrderDetailT_TestID + WHERE od.T_OrderDetailID = pT_OrderDetailID + AND od.T_OrderDetailIsActive = 'Y' + LIMIT 1; + + IF vOrderHeaderID IS NULL THEN + SELECT + 'ERR' AS status, + CONCAT('T_OrderDetailID ', pT_OrderDetailID, ' tidak ditemukan atau tidak aktif') AS message; + ELSE + IF vPatientDOB IS NOT NULL AND vOrderDate IS NOT NULL THEN + SET vAgeInDay = fn_global_age_count_day(vPatientDOB, vOrderDate); + END IF; + + SELECT + mp.M_MethodePriorityNat_MethodeID, + nm.Nat_MethodeName + INTO + vMethodIDPriority, + vMethodNamePriority + FROM m_methode_priority mp + JOIN nat_methode nm + ON nm.Nat_MethodeID = mp.M_MethodePriorityNat_MethodeID + AND nm.Nat_MethodeIsActive = 'Y' + JOIN m_instrumentmethode im + ON im.M_InstrumentMethodeNat_MethodeID = nm.Nat_MethodeID + AND im.M_InstrumentMethodeIsActive = 'Y' + JOIN nat_instrument ni + ON ni.Nat_InstrumentID = im.M_InstrumentMethodeNat_InstrumentID + AND ni.Nat_InstrumentIsActive = 'Y' + WHERE mp.M_MethodePriorityIsActive = 'Y' + AND mp.M_MethodePriorityNat_TestID = vNatTestID + AND mp.M_MethodePriorityM_DayOfWeekID = DAYOFWEEK(NOW()) + ORDER BY mp.M_MethodePriorityNumber DESC + LIMIT 1; + + SELECT + im.M_InstrumentMethodeNat_MethodeID, + nm.Nat_MethodeName + INTO + vMethodIDInstrument, + vMethodNameInstrument + FROM m_instrumentmethode im + JOIN nat_methode nm + ON nm.Nat_MethodeID = im.M_InstrumentMethodeNat_MethodeID + AND nm.Nat_MethodeIsActive = 'Y' + JOIN nat_instrument ni + ON ni.Nat_InstrumentID = im.M_InstrumentMethodeNat_InstrumentID + AND ni.Nat_InstrumentIsActive = 'Y' + WHERE im.M_InstrumentMethodeNat_TestID = vNatTestID + AND im.M_InstrumentMethodeIsActive = 'Y' + ORDER BY im.M_InstrumentMethodePriority DESC + LIMIT 1; + + SELECT + nn.Nat_NormalValueNat_MethodeID, + nm.Nat_MethodeName + INTO + vMethodIDNormal, + vMethodNameNormal + FROM nat_normalvalue nn + JOIN nat_methode nm + ON nm.Nat_MethodeID = nn.Nat_NormalValueNat_MethodeID + AND nm.Nat_MethodeIsActive = 'Y' + WHERE nn.Nat_NormalValueNat_TestID = vNatTestID + AND nn.Nat_NormalValueIsActive = 'Y' + AND nn.Nat_NormalValueIsAbnormal = 'N' + ORDER BY nn.Nat_NormalValueID + LIMIT 1; + + IF vMethodIDPriority IS NOT NULL AND vMethodIDPriority > 0 THEN + SET vSelectedMethodID = vMethodIDPriority; + SET vSelectedMethodName = vMethodNamePriority; + SET vSelectedMethodSource = 'm_methode_priority'; + ELSEIF vMethodIDInstrument IS NOT NULL AND vMethodIDInstrument > 0 THEN + SET vSelectedMethodID = vMethodIDInstrument; + SET vSelectedMethodName = vMethodNameInstrument; + SET vSelectedMethodSource = 'm_instrumentmethode'; + ELSEIF vMethodIDNormal IS NOT NULL AND vMethodIDNormal > 0 THEN + SET vSelectedMethodID = vMethodIDNormal; + SET vSelectedMethodName = vMethodNameNormal; + SET vSelectedMethodSource = 'nat_normalvalue'; + END IF; + + IF vSelectedMethodID IS NOT NULL + AND vSelectedMethodID > 0 + AND vNatTestID IS NOT NULL + AND vPatientSexID IS NOT NULL + AND vAgeInDay IS NOT NULL THEN + SET vFnNormalValueID = fn_sampling_get_normal(vSelectedMethodID, vNatTestID, vPatientSexID, vAgeInDay); + END IF; + + SELECT + pT_OrderDetailID AS T_OrderDetailID, + vOrderHeaderID AS T_OrderHeaderID, + vPatientID AS M_PatientID, + vPatientSexID AS M_PatientM_SexID, + vPatientDOB AS M_PatientDOB, + vOrderDate AS T_OrderHeaderDate, + vAgeInDay AS AgeInDay, + vTTestID AS T_TestID, + vNatTestID AS Nat_TestID, + vOrderDetailMethodID AS T_OrderDetailNat_MethodeID, + vMethodIDPriority AS MethodeIDFromPriority, + vMethodNamePriority AS MethodeNameFromPriority, + vMethodIDInstrument AS MethodeIDFromInstrument, + vMethodNameInstrument AS MethodeNameFromInstrument, + vMethodIDNormal AS MethodeIDFromNormalValue, + vMethodNameNormal AS MethodeNameFromNormalValue, + vSelectedMethodID AS SelectedMethodeID, + vSelectedMethodName AS SelectedMethodeName, + vSelectedMethodSource AS SelectedMethodeSource, + vFnNormalValueID AS FnSamplingGetNormalResult; + + SELECT + 'ORDER_DETAIL_ACTIVE' AS check_name, + IF(vOrderHeaderID IS NOT NULL, 'OK', 'MISSING') AS check_status, + CAST(pT_OrderDetailID AS CHAR) AS check_value, + 't_orderdetail aktif harus ditemukan' AS check_note + UNION ALL + SELECT + 'PATIENT_SEX', + IF(vPatientSexID IS NOT NULL AND vPatientSexID > 0, 'OK', 'MISSING'), + IFNULL(CAST(vPatientSexID AS CHAR), 'NULL'), + 'Dipakai pada type 1 dan type 3' + UNION ALL + SELECT + 'PATIENT_DOB', + IF(vPatientDOB IS NOT NULL, 'OK', 'MISSING'), + IFNULL(CAST(vPatientDOB AS CHAR), 'NULL'), + 'DOB dipakai untuk hitung AgeInDay' + UNION ALL + SELECT + 'ORDER_DATE', + IF(vOrderDate IS NOT NULL, 'OK', 'MISSING'), + IFNULL(CAST(vOrderDate AS CHAR), 'NULL'), + 'Tanggal order dipakai untuk hitung AgeInDay' + UNION ALL + SELECT + 'AGE_IN_DAY', + IF(vAgeInDay IS NOT NULL, 'OK', 'MISSING'), + IFNULL(CAST(vAgeInDay AS CHAR), 'NULL'), + 'Dipakai pada type 1 dan type 2' + UNION ALL + SELECT + 'NAT_TEST', + IF(vNatTestID IS NOT NULL AND vNatTestID > 0, 'OK', 'MISSING'), + IFNULL(CAST(vNatTestID AS CHAR), 'NULL'), + 'Harus ada mapping T_TestNat_TestID' + UNION ALL + SELECT + 'METHOD_PRIORITY', + IF(vMethodIDPriority IS NOT NULL AND vMethodIDPriority > 0, 'OK', 'MISSING'), + IFNULL(CAST(vMethodIDPriority AS CHAR), 'NULL'), + 'Sumber metode prioritas pertama' + UNION ALL + SELECT + 'METHOD_INSTRUMENT', + IF(vMethodIDInstrument IS NOT NULL AND vMethodIDInstrument > 0, 'OK', 'MISSING'), + IFNULL(CAST(vMethodIDInstrument AS CHAR), 'NULL'), + 'Fallback metode kedua' + UNION ALL + SELECT + 'METHOD_NORMALVALUE', + IF(vMethodIDNormal IS NOT NULL AND vMethodIDNormal > 0, 'OK', 'MISSING'), + IFNULL(CAST(vMethodIDNormal AS CHAR), 'NULL'), + 'Fallback metode ketiga' + UNION ALL + SELECT + 'SELECTED_METHOD', + IF(vSelectedMethodID IS NOT NULL AND vSelectedMethodID > 0, 'OK', 'MISSING'), + IFNULL(CAST(vSelectedMethodID AS CHAR), 'NULL'), + IFNULL(vSelectedMethodSource, 'Tidak ada metode yang bisa dipakai') + UNION ALL + SELECT + 'NORMALVALUE_TEST_METHOD_ACTIVE', + IF( + (SELECT COUNT(*) + FROM nat_normalvalue + WHERE Nat_NormalValueNat_TestID = vNatTestID + AND Nat_NormalValueNat_MethodeID = IFNULL(vSelectedMethodID, 0) + AND Nat_NormalValueIsActive = 'Y' + AND Nat_NormalValueIsAbnormal = 'N') > 0, + 'OK', + 'MISSING' + ), + CAST( + (SELECT COUNT(*) + FROM nat_normalvalue + WHERE Nat_NormalValueNat_TestID = vNatTestID + AND Nat_NormalValueNat_MethodeID = IFNULL(vSelectedMethodID, 0) + AND Nat_NormalValueIsActive = 'Y' + AND Nat_NormalValueIsAbnormal = 'N') AS CHAR + ), + 'Jumlah nat_normalvalue aktif non-abnormal untuk test + metode terpilih' + UNION ALL + SELECT + 'FN_RESULT', + IF(vFnNormalValueID IS NOT NULL AND vFnNormalValueID > 0, 'OK', 'NOT_FOUND'), + IFNULL(CAST(vFnNormalValueID AS CHAR), '0'), + 'Hasil akhir fn_sampling_get_normal' + ; + + IF vSelectedMethodID IS NOT NULL AND vSelectedMethodID > 0 THEN + SELECT + branch_name, + matched_count, + first_normalvalue_id + FROM ( + SELECT + 'TYPE_1' AS branch_name, + COUNT(*) AS matched_count, + MIN(Nat_NormalValueID) AS first_normalvalue_id + FROM nat_normalvalue + WHERE (Nat_NormalValueValidDate IS NULL OR Nat_NormalValueValidDate < NOW()) + AND Nat_NormalValueIsActive = 'Y' + AND Nat_NormalValueIsAbnormal = 'N' + AND Nat_NormalValueNat_NormalValueTypeID = 1 + AND Nat_NormalValueNat_MethodeID = vSelectedMethodID + AND Nat_NormalValueNat_TestID = vNatTestID + AND Nat_NormalValueNat_SexID = vPatientSexID + AND ( + (Nat_NormalValueMinAgeInclusive = 'Y' AND fn_normal_get_age(Nat_NormalValueMinAge, Nat_NormalValueAgeUnit) <= vAgeInDay) + OR (Nat_NormalValueMinAgeInclusive = 'N' AND fn_normal_get_age(Nat_NormalValueMinAge, Nat_NormalValueAgeUnit) < vAgeInDay) + ) + AND ( + (Nat_NormalValueMaxAgeInclusive = 'Y' AND fn_normal_get_age(Nat_NormalValueMaxAge, Nat_NormalValueAgeUnit) >= vAgeInDay) + OR (Nat_NormalValueMaxAgeInclusive = 'N' AND fn_normal_get_age(Nat_NormalValueMaxAge, Nat_NormalValueAgeUnit) > vAgeInDay) + ) + AND Nat_NormalValueNat_FlagID = 1 + + UNION ALL + + SELECT + 'TYPE_2', + COUNT(*), + MIN(Nat_NormalValueID) + FROM nat_normalvalue + WHERE (Nat_NormalValueValidDate IS NULL OR Nat_NormalValueValidDate < NOW()) + AND Nat_NormalValueIsActive = 'Y' + AND Nat_NormalValueIsAbnormal = 'N' + AND Nat_NormalValueNat_NormalValueTypeID = 2 + AND Nat_NormalValueNat_MethodeID = vSelectedMethodID + AND Nat_NormalValueNat_TestID = vNatTestID + AND ( + (Nat_NormalValueMinAgeInclusive = 'Y' AND fn_normal_get_age(Nat_NormalValueMinAge, Nat_NormalValueAgeUnit) <= vAgeInDay) + OR (Nat_NormalValueMinAgeInclusive = 'N' AND fn_normal_get_age(Nat_NormalValueMinAge, Nat_NormalValueAgeUnit) < vAgeInDay) + ) + AND ( + (Nat_NormalValueMaxAgeInclusive = 'Y' AND fn_normal_get_age(Nat_NormalValueMaxAge, Nat_NormalValueAgeUnit) >= vAgeInDay) + OR (Nat_NormalValueMaxAgeInclusive = 'N' AND fn_normal_get_age(Nat_NormalValueMaxAge, Nat_NormalValueAgeUnit) > vAgeInDay) + ) + AND Nat_NormalValueNat_FlagID = 1 + + UNION ALL + + SELECT + 'TYPE_3', + COUNT(*), + MIN(Nat_NormalValueID) + FROM nat_normalvalue + WHERE (Nat_NormalValueValidDate IS NULL OR Nat_NormalValueValidDate < NOW()) + AND Nat_NormalValueIsActive = 'Y' + AND Nat_NormalValueIsAbnormal = 'N' + AND Nat_NormalValueNat_NormalValueTypeID = 3 + AND Nat_NormalValueNat_MethodeID = vSelectedMethodID + AND Nat_NormalValueNat_TestID = vNatTestID + AND Nat_NormalValueNat_SexID = vPatientSexID + AND Nat_NormalValueNat_FlagID = 1 + + UNION ALL + + SELECT + 'TYPE_4', + COUNT(*), + MIN(Nat_NormalValueID) + FROM nat_normalvalue + WHERE (Nat_NormalValueValidDate IS NULL OR Nat_NormalValueValidDate < NOW()) + AND Nat_NormalValueIsActive = 'Y' + AND Nat_NormalValueIsAbnormal = 'N' + AND Nat_NormalValueNat_NormalValueTypeID = 4 + AND Nat_NormalValueNat_MethodeID = vSelectedMethodID + AND Nat_NormalValueNat_TestID = vNatTestID + AND Nat_NormalValueNat_FlagID = 1 + ) branch_summary; + ELSE + SELECT + 'NO_SELECTED_METHOD' AS branch_name, + 0 AS matched_count, + NULL AS first_normalvalue_id; + END IF; + + SELECT + nn.Nat_NormalValueID, + nn.Nat_NormalValueNat_TestID, + nn.Nat_NormalValueNat_MethodeID, + nm.Nat_MethodeName, + nn.Nat_NormalValueNat_NormalValueTypeID, + nn.Nat_NormalValueNat_SexID, + nn.Nat_NormalValueValidDate, + nn.Nat_NormalValueMinAge, + nn.Nat_NormalValueMaxAge, + nn.Nat_NormalValueAgeUnit, + nn.Nat_NormalValueMinAgeInclusive, + nn.Nat_NormalValueMaxAgeInclusive, + fn_normal_get_age(nn.Nat_NormalValueMinAge, nn.Nat_NormalValueAgeUnit) AS MinAgeInDay, + fn_normal_get_age(nn.Nat_NormalValueMaxAge, nn.Nat_NormalValueAgeUnit) AS MaxAgeInDay, + nn.Nat_NormalValueNat_FlagID, + nn.Nat_NormalValueIsAbnormal, + nn.Nat_NormalValueIsActive, + IF((nn.Nat_NormalValueValidDate IS NULL OR nn.Nat_NormalValueValidDate < NOW()), 'Y', 'N') AS MatchValidDate, + IF(nn.Nat_NormalValueIsActive = 'Y', 'Y', 'N') AS MatchActive, + IF(nn.Nat_NormalValueIsAbnormal = 'N', 'Y', 'N') AS MatchNotAbnormal, + IF(nn.Nat_NormalValueNat_FlagID = 1, 'Y', 'N') AS MatchFlag, + IF(nn.Nat_NormalValueNat_TestID = vNatTestID, 'Y', 'N') AS MatchNatTest, + IF(vSelectedMethodID IS NOT NULL AND nn.Nat_NormalValueNat_MethodeID = vSelectedMethodID, 'Y', 'N') AS MatchSelectedMethod, + IF(nn.Nat_NormalValueNat_SexID = vPatientSexID, 'Y', 'N') AS MatchSex, + IF( + (nn.Nat_NormalValueMinAgeInclusive = 'Y' AND fn_normal_get_age(nn.Nat_NormalValueMinAge, nn.Nat_NormalValueAgeUnit) <= vAgeInDay) + OR + (nn.Nat_NormalValueMinAgeInclusive = 'N' AND fn_normal_get_age(nn.Nat_NormalValueMinAge, nn.Nat_NormalValueAgeUnit) < vAgeInDay), + 'Y', + 'N' + ) AS MatchMinAge, + IF( + (nn.Nat_NormalValueMaxAgeInclusive = 'Y' AND fn_normal_get_age(nn.Nat_NormalValueMaxAge, nn.Nat_NormalValueAgeUnit) >= vAgeInDay) + OR + (nn.Nat_NormalValueMaxAgeInclusive = 'N' AND fn_normal_get_age(nn.Nat_NormalValueMaxAge, nn.Nat_NormalValueAgeUnit) > vAgeInDay), + 'Y', + 'N' + ) AS MatchMaxAge, + CASE + WHEN nn.Nat_NormalValueNat_NormalValueTypeID = 1 THEN + IF( + nn.Nat_NormalValueNat_SexID = vPatientSexID + AND ( + (nn.Nat_NormalValueMinAgeInclusive = 'Y' AND fn_normal_get_age(nn.Nat_NormalValueMinAge, nn.Nat_NormalValueAgeUnit) <= vAgeInDay) + OR + (nn.Nat_NormalValueMinAgeInclusive = 'N' AND fn_normal_get_age(nn.Nat_NormalValueMinAge, nn.Nat_NormalValueAgeUnit) < vAgeInDay) + ) + AND ( + (nn.Nat_NormalValueMaxAgeInclusive = 'Y' AND fn_normal_get_age(nn.Nat_NormalValueMaxAge, nn.Nat_NormalValueAgeUnit) >= vAgeInDay) + OR + (nn.Nat_NormalValueMaxAgeInclusive = 'N' AND fn_normal_get_age(nn.Nat_NormalValueMaxAge, nn.Nat_NormalValueAgeUnit) > vAgeInDay) + ), + 'Y', + 'N' + ) + WHEN nn.Nat_NormalValueNat_NormalValueTypeID = 2 THEN + IF( + ( + (nn.Nat_NormalValueMinAgeInclusive = 'Y' AND fn_normal_get_age(nn.Nat_NormalValueMinAge, nn.Nat_NormalValueAgeUnit) <= vAgeInDay) + OR + (nn.Nat_NormalValueMinAgeInclusive = 'N' AND fn_normal_get_age(nn.Nat_NormalValueMinAge, nn.Nat_NormalValueAgeUnit) < vAgeInDay) + ) + AND ( + (nn.Nat_NormalValueMaxAgeInclusive = 'Y' AND fn_normal_get_age(nn.Nat_NormalValueMaxAge, nn.Nat_NormalValueAgeUnit) >= vAgeInDay) + OR + (nn.Nat_NormalValueMaxAgeInclusive = 'N' AND fn_normal_get_age(nn.Nat_NormalValueMaxAge, nn.Nat_NormalValueAgeUnit) > vAgeInDay) + ), + 'Y', + 'N' + ) + WHEN nn.Nat_NormalValueNat_NormalValueTypeID = 3 THEN + IF(nn.Nat_NormalValueNat_SexID = vPatientSexID, 'Y', 'N') + WHEN nn.Nat_NormalValueNat_NormalValueTypeID = 4 THEN + 'Y' + ELSE + 'N' + END AS MatchTypeRule, + CONCAT_WS( + '; ', + IF(NOT (nn.Nat_NormalValueValidDate IS NULL OR nn.Nat_NormalValueValidDate < NOW()), 'valid_date_not_passed', NULL), + IF(nn.Nat_NormalValueIsActive <> 'Y', 'inactive', NULL), + IF(nn.Nat_NormalValueIsAbnormal <> 'N', 'abnormal_row', NULL), + IF(nn.Nat_NormalValueNat_FlagID <> 1, 'flag_not_1', NULL), + IF(nn.Nat_NormalValueNat_TestID <> vNatTestID, 'nat_test_mismatch', NULL), + IF(vSelectedMethodID IS NOT NULL AND nn.Nat_NormalValueNat_MethodeID <> vSelectedMethodID, 'methode_mismatch', NULL), + IF(nn.Nat_NormalValueNat_NormalValueTypeID IN (1,3) AND nn.Nat_NormalValueNat_SexID <> vPatientSexID, 'sex_mismatch', NULL), + IF( + nn.Nat_NormalValueNat_NormalValueTypeID IN (1,2) AND NOT ( + (nn.Nat_NormalValueMinAgeInclusive = 'Y' AND fn_normal_get_age(nn.Nat_NormalValueMinAge, nn.Nat_NormalValueAgeUnit) <= vAgeInDay) + OR + (nn.Nat_NormalValueMinAgeInclusive = 'N' AND fn_normal_get_age(nn.Nat_NormalValueMinAge, nn.Nat_NormalValueAgeUnit) < vAgeInDay) + ), + 'age_below_min', + NULL + ), + IF( + nn.Nat_NormalValueNat_NormalValueTypeID IN (1,2) AND NOT ( + (nn.Nat_NormalValueMaxAgeInclusive = 'Y' AND fn_normal_get_age(nn.Nat_NormalValueMaxAge, nn.Nat_NormalValueAgeUnit) >= vAgeInDay) + OR + (nn.Nat_NormalValueMaxAgeInclusive = 'N' AND fn_normal_get_age(nn.Nat_NormalValueMaxAge, nn.Nat_NormalValueAgeUnit) > vAgeInDay) + ), + 'age_above_max', + NULL + ) + ) AS FailReason + FROM nat_normalvalue nn + LEFT JOIN nat_methode nm + ON nm.Nat_MethodeID = nn.Nat_NormalValueNat_MethodeID + WHERE nn.Nat_NormalValueNat_TestID = vNatTestID + AND nn.Nat_NormalValueIsActive = 'Y' + AND nn.Nat_NormalValueIsAbnormal = 'N' + ORDER BY + CASE + WHEN vSelectedMethodID IS NOT NULL AND nn.Nat_NormalValueNat_MethodeID = vSelectedMethodID THEN 0 + ELSE 1 + END, + nn.Nat_NormalValueNat_MethodeID, + nn.Nat_NormalValueNat_NormalValueTypeID, + nn.Nat_NormalValueID; + END IF; +END$$ + +DELIMITER ; diff --git a/sql/manual_changes/2026-05-24-update-sp-sampling-check-normal-setting-active-only.sql b/sql/manual_changes/2026-05-24-update-sp-sampling-check-normal-setting-active-only.sql new file mode 100644 index 00000000..0ce5d9fb --- /dev/null +++ b/sql/manual_changes/2026-05-24-update-sp-sampling-check-normal-setting-active-only.sql @@ -0,0 +1,464 @@ +DROP PROCEDURE IF EXISTS sp_sampling_check_normal_setting; + +DELIMITER $$ + +CREATE PROCEDURE sp_sampling_check_normal_setting(IN pT_OrderDetailID INT) +BEGIN + DECLARE vOrderHeaderID INT DEFAULT NULL; + DECLARE vPatientID INT DEFAULT NULL; + DECLARE vPatientSexID INT DEFAULT NULL; + DECLARE vPatientDOB DATE DEFAULT NULL; + DECLARE vOrderDate DATE DEFAULT NULL; + DECLARE vAgeInDay INT DEFAULT NULL; + DECLARE vTTestID INT DEFAULT NULL; + DECLARE vNatTestID INT DEFAULT NULL; + DECLARE vOrderDetailMethodID INT DEFAULT NULL; + + DECLARE vMethodIDPriority INT DEFAULT NULL; + DECLARE vMethodNamePriority VARCHAR(100) DEFAULT NULL; + DECLARE vMethodIDInstrument INT DEFAULT NULL; + DECLARE vMethodNameInstrument VARCHAR(100) DEFAULT NULL; + DECLARE vMethodIDNormal INT DEFAULT NULL; + DECLARE vMethodNameNormal VARCHAR(100) DEFAULT NULL; + + DECLARE vSelectedMethodID INT DEFAULT NULL; + DECLARE vSelectedMethodName VARCHAR(100) DEFAULT NULL; + DECLARE vSelectedMethodSource VARCHAR(30) DEFAULT NULL; + DECLARE vFnNormalValueID INT DEFAULT 0; + + SELECT + od.T_OrderDetailT_OrderHeaderID, + oh.T_OrderHeaderM_PatientID, + p.M_PatientM_SexID, + p.M_PatientDOB, + DATE(oh.T_OrderHeaderDate), + od.T_OrderDetailT_TestID, + tt.T_TestNat_TestID, + od.T_OrderDetailNat_MethodeID + INTO + vOrderHeaderID, + vPatientID, + vPatientSexID, + vPatientDOB, + vOrderDate, + vTTestID, + vNatTestID, + vOrderDetailMethodID + FROM t_orderdetail od + JOIN t_orderheader oh + ON oh.T_OrderHeaderID = od.T_OrderDetailT_OrderHeaderID + JOIN m_patient p + ON p.M_PatientID = oh.T_OrderHeaderM_PatientID + LEFT JOIN t_test tt + ON tt.T_TestID = od.T_OrderDetailT_TestID + WHERE od.T_OrderDetailID = pT_OrderDetailID + AND od.T_OrderDetailIsActive = 'Y' + LIMIT 1; + + IF vOrderHeaderID IS NULL THEN + SELECT + 'ERR' AS status, + CONCAT('T_OrderDetailID ', pT_OrderDetailID, ' tidak ditemukan atau tidak aktif') AS message; + ELSE + IF vPatientDOB IS NOT NULL AND vOrderDate IS NOT NULL THEN + SET vAgeInDay = fn_global_age_count_day(vPatientDOB, vOrderDate); + END IF; + + SELECT + mp.M_MethodePriorityNat_MethodeID, + nm.Nat_MethodeName + INTO + vMethodIDPriority, + vMethodNamePriority + FROM m_methode_priority mp + JOIN nat_methode nm + ON nm.Nat_MethodeID = mp.M_MethodePriorityNat_MethodeID + AND nm.Nat_MethodeIsActive = 'Y' + JOIN m_instrumentmethode im + ON im.M_InstrumentMethodeNat_MethodeID = nm.Nat_MethodeID + AND im.M_InstrumentMethodeIsActive = 'Y' + JOIN nat_instrument ni + ON ni.Nat_InstrumentID = im.M_InstrumentMethodeNat_InstrumentID + AND ni.Nat_InstrumentIsActive = 'Y' + WHERE mp.M_MethodePriorityIsActive = 'Y' + AND mp.M_MethodePriorityNat_TestID = vNatTestID + AND mp.M_MethodePriorityM_DayOfWeekID = DAYOFWEEK(NOW()) + ORDER BY mp.M_MethodePriorityNumber DESC + LIMIT 1; + + SELECT + im.M_InstrumentMethodeNat_MethodeID, + nm.Nat_MethodeName + INTO + vMethodIDInstrument, + vMethodNameInstrument + FROM m_instrumentmethode im + JOIN nat_methode nm + ON nm.Nat_MethodeID = im.M_InstrumentMethodeNat_MethodeID + AND nm.Nat_MethodeIsActive = 'Y' + JOIN nat_instrument ni + ON ni.Nat_InstrumentID = im.M_InstrumentMethodeNat_InstrumentID + AND ni.Nat_InstrumentIsActive = 'Y' + WHERE im.M_InstrumentMethodeNat_TestID = vNatTestID + AND im.M_InstrumentMethodeIsActive = 'Y' + ORDER BY im.M_InstrumentMethodePriority DESC + LIMIT 1; + + SELECT + nn.Nat_NormalValueNat_MethodeID, + nm.Nat_MethodeName + INTO + vMethodIDNormal, + vMethodNameNormal + FROM nat_normalvalue nn + JOIN nat_methode nm + ON nm.Nat_MethodeID = nn.Nat_NormalValueNat_MethodeID + AND nm.Nat_MethodeIsActive = 'Y' + WHERE nn.Nat_NormalValueNat_TestID = vNatTestID + AND nn.Nat_NormalValueIsActive = 'Y' + ORDER BY nn.Nat_NormalValueID + LIMIT 1; + + IF vMethodIDPriority IS NOT NULL AND vMethodIDPriority > 0 THEN + SET vSelectedMethodID = vMethodIDPriority; + SET vSelectedMethodName = vMethodNamePriority; + SET vSelectedMethodSource = 'm_methode_priority'; + ELSEIF vMethodIDInstrument IS NOT NULL AND vMethodIDInstrument > 0 THEN + SET vSelectedMethodID = vMethodIDInstrument; + SET vSelectedMethodName = vMethodNameInstrument; + SET vSelectedMethodSource = 'm_instrumentmethode'; + ELSEIF vMethodIDNormal IS NOT NULL AND vMethodIDNormal > 0 THEN + SET vSelectedMethodID = vMethodIDNormal; + SET vSelectedMethodName = vMethodNameNormal; + SET vSelectedMethodSource = 'nat_normalvalue'; + END IF; + + IF vSelectedMethodID IS NOT NULL + AND vSelectedMethodID > 0 + AND vNatTestID IS NOT NULL + AND vPatientSexID IS NOT NULL + AND vAgeInDay IS NOT NULL THEN + SET vFnNormalValueID = fn_sampling_get_normal(vSelectedMethodID, vNatTestID, vPatientSexID, vAgeInDay); + END IF; + + SELECT + pT_OrderDetailID AS T_OrderDetailID, + vOrderHeaderID AS T_OrderHeaderID, + vPatientID AS M_PatientID, + vPatientSexID AS M_PatientM_SexID, + vPatientDOB AS M_PatientDOB, + vOrderDate AS T_OrderHeaderDate, + vAgeInDay AS AgeInDay, + vTTestID AS T_TestID, + vNatTestID AS Nat_TestID, + vOrderDetailMethodID AS T_OrderDetailNat_MethodeID, + vMethodIDPriority AS MethodeIDFromPriority, + vMethodNamePriority AS MethodeNameFromPriority, + vMethodIDInstrument AS MethodeIDFromInstrument, + vMethodNameInstrument AS MethodeNameFromInstrument, + vMethodIDNormal AS MethodeIDFromNormalValue, + vMethodNameNormal AS MethodeNameFromNormalValue, + vSelectedMethodID AS SelectedMethodeID, + vSelectedMethodName AS SelectedMethodeName, + vSelectedMethodSource AS SelectedMethodeSource, + vFnNormalValueID AS FnSamplingGetNormalResult; + + SELECT + 'ORDER_DETAIL_ACTIVE' AS check_name, + IF(vOrderHeaderID IS NOT NULL, 'OK', 'MISSING') AS check_status, + CAST(pT_OrderDetailID AS CHAR) AS check_value, + 't_orderdetail aktif harus ditemukan' AS check_note + UNION ALL + SELECT + 'PATIENT_SEX', + IF(vPatientSexID IS NOT NULL AND vPatientSexID > 0, 'OK', 'MISSING'), + IFNULL(CAST(vPatientSexID AS CHAR), 'NULL'), + 'Dipakai pada type 1 dan type 3' + UNION ALL + SELECT + 'PATIENT_DOB', + IF(vPatientDOB IS NOT NULL, 'OK', 'MISSING'), + IFNULL(CAST(vPatientDOB AS CHAR), 'NULL'), + 'DOB dipakai untuk hitung AgeInDay' + UNION ALL + SELECT + 'ORDER_DATE', + IF(vOrderDate IS NOT NULL, 'OK', 'MISSING'), + IFNULL(CAST(vOrderDate AS CHAR), 'NULL'), + 'Tanggal order dipakai untuk hitung AgeInDay' + UNION ALL + SELECT + 'AGE_IN_DAY', + IF(vAgeInDay IS NOT NULL, 'OK', 'MISSING'), + IFNULL(CAST(vAgeInDay AS CHAR), 'NULL'), + 'Dipakai pada type 1 dan type 2' + UNION ALL + SELECT + 'NAT_TEST', + IF(vNatTestID IS NOT NULL AND vNatTestID > 0, 'OK', 'MISSING'), + IFNULL(CAST(vNatTestID AS CHAR), 'NULL'), + 'Harus ada mapping T_TestNat_TestID' + UNION ALL + SELECT + 'METHOD_PRIORITY', + IF(vMethodIDPriority IS NOT NULL AND vMethodIDPriority > 0, 'OK', 'MISSING'), + IFNULL(CAST(vMethodIDPriority AS CHAR), 'NULL'), + 'Sumber metode prioritas pertama' + UNION ALL + SELECT + 'METHOD_INSTRUMENT', + IF(vMethodIDInstrument IS NOT NULL AND vMethodIDInstrument > 0, 'OK', 'MISSING'), + IFNULL(CAST(vMethodIDInstrument AS CHAR), 'NULL'), + 'Fallback metode kedua' + UNION ALL + SELECT + 'METHOD_NORMALVALUE', + IF(vMethodIDNormal IS NOT NULL AND vMethodIDNormal > 0, 'OK', 'MISSING'), + IFNULL(CAST(vMethodIDNormal AS CHAR), 'NULL'), + 'Fallback metode ketiga' + UNION ALL + SELECT + 'SELECTED_METHOD', + IF(vSelectedMethodID IS NOT NULL AND vSelectedMethodID > 0, 'OK', 'MISSING'), + IFNULL(CAST(vSelectedMethodID AS CHAR), 'NULL'), + IFNULL(vSelectedMethodSource, 'Tidak ada metode yang bisa dipakai') + UNION ALL + SELECT + 'NORMALVALUE_TEST_METHOD_ACTIVE', + IF( + (SELECT COUNT(*) + FROM nat_normalvalue + WHERE Nat_NormalValueNat_TestID = vNatTestID + AND Nat_NormalValueNat_MethodeID = IFNULL(vSelectedMethodID, 0) + AND Nat_NormalValueIsActive = 'Y') > 0, + 'OK', + 'MISSING' + ), + CAST( + (SELECT COUNT(*) + FROM nat_normalvalue + WHERE Nat_NormalValueNat_TestID = vNatTestID + AND Nat_NormalValueNat_MethodeID = IFNULL(vSelectedMethodID, 0) + AND Nat_NormalValueIsActive = 'Y') AS CHAR + ), + 'Jumlah nat_normalvalue aktif untuk test + metode terpilih' + UNION ALL + SELECT + 'FN_RESULT', + IF(vFnNormalValueID IS NOT NULL AND vFnNormalValueID > 0, 'OK', 'NOT_FOUND'), + IFNULL(CAST(vFnNormalValueID AS CHAR), '0'), + 'Hasil akhir fn_sampling_get_normal' + ; + + IF vSelectedMethodID IS NOT NULL AND vSelectedMethodID > 0 THEN + SELECT + branch_name, + matched_count, + first_normalvalue_id + FROM ( + SELECT + 'TYPE_1' AS branch_name, + COUNT(*) AS matched_count, + MIN(Nat_NormalValueID) AS first_normalvalue_id + FROM nat_normalvalue + WHERE (Nat_NormalValueValidDate IS NULL OR Nat_NormalValueValidDate < NOW()) + AND Nat_NormalValueIsActive = 'Y' + AND Nat_NormalValueNat_NormalValueTypeID = 1 + AND Nat_NormalValueIsAbnormal = 'N' + AND Nat_NormalValueNat_MethodeID = vSelectedMethodID + AND Nat_NormalValueNat_TestID = vNatTestID + AND Nat_NormalValueNat_SexID = vPatientSexID + AND ( + (Nat_NormalValueMinAgeInclusive = 'Y' AND fn_normal_get_age(Nat_NormalValueMinAge, Nat_NormalValueAgeUnit) <= vAgeInDay) + OR (Nat_NormalValueMinAgeInclusive = 'N' AND fn_normal_get_age(Nat_NormalValueMinAge, Nat_NormalValueAgeUnit) < vAgeInDay) + ) + AND ( + (Nat_NormalValueMaxAgeInclusive = 'Y' AND fn_normal_get_age(Nat_NormalValueMaxAge, Nat_NormalValueAgeUnit) >= vAgeInDay) + OR (Nat_NormalValueMaxAgeInclusive = 'N' AND fn_normal_get_age(Nat_NormalValueMaxAge, Nat_NormalValueAgeUnit) > vAgeInDay) + ) + AND Nat_NormalValueNat_FlagID = 1 + + UNION ALL + + SELECT + 'TYPE_2', + COUNT(*), + MIN(Nat_NormalValueID) + FROM nat_normalvalue + WHERE (Nat_NormalValueValidDate IS NULL OR Nat_NormalValueValidDate < NOW()) + AND Nat_NormalValueIsActive = 'Y' + AND Nat_NormalValueNat_NormalValueTypeID = 2 + AND Nat_NormalValueIsAbnormal = 'N' + AND Nat_NormalValueNat_MethodeID = vSelectedMethodID + AND Nat_NormalValueNat_TestID = vNatTestID + AND ( + (Nat_NormalValueMinAgeInclusive = 'Y' AND fn_normal_get_age(Nat_NormalValueMinAge, Nat_NormalValueAgeUnit) <= vAgeInDay) + OR (Nat_NormalValueMinAgeInclusive = 'N' AND fn_normal_get_age(Nat_NormalValueMinAge, Nat_NormalValueAgeUnit) < vAgeInDay) + ) + AND ( + (Nat_NormalValueMaxAgeInclusive = 'Y' AND fn_normal_get_age(Nat_NormalValueMaxAge, Nat_NormalValueAgeUnit) >= vAgeInDay) + OR (Nat_NormalValueMaxAgeInclusive = 'N' AND fn_normal_get_age(Nat_NormalValueMaxAge, Nat_NormalValueAgeUnit) > vAgeInDay) + ) + AND Nat_NormalValueNat_FlagID = 1 + + UNION ALL + + SELECT + 'TYPE_3', + COUNT(*), + MIN(Nat_NormalValueID) + FROM nat_normalvalue + WHERE (Nat_NormalValueValidDate IS NULL OR Nat_NormalValueValidDate < NOW()) + AND Nat_NormalValueIsActive = 'Y' + AND Nat_NormalValueNat_NormalValueTypeID = 3 + AND Nat_NormalValueIsAbnormal = 'N' + AND Nat_NormalValueNat_MethodeID = vSelectedMethodID + AND Nat_NormalValueNat_TestID = vNatTestID + AND Nat_NormalValueNat_SexID = vPatientSexID + AND Nat_NormalValueNat_FlagID = 1 + + UNION ALL + + SELECT + 'TYPE_4', + COUNT(*), + MIN(Nat_NormalValueID) + FROM nat_normalvalue + WHERE (Nat_NormalValueValidDate IS NULL OR Nat_NormalValueValidDate < NOW()) + AND Nat_NormalValueIsActive = 'Y' + AND Nat_NormalValueNat_NormalValueTypeID = 4 + AND Nat_NormalValueIsAbnormal = 'N' + AND Nat_NormalValueNat_MethodeID = vSelectedMethodID + AND Nat_NormalValueNat_TestID = vNatTestID + AND Nat_NormalValueNat_FlagID = 1 + ) branch_summary; + ELSE + SELECT + 'NO_SELECTED_METHOD' AS branch_name, + 0 AS matched_count, + NULL AS first_normalvalue_id; + END IF; + + SELECT + nn.Nat_NormalValueID, + nn.Nat_NormalValueNat_TestID, + nn.Nat_NormalValueNat_MethodeID, + nm.Nat_MethodeName, + nn.Nat_NormalValueNat_NormalValueTypeID, + nn.Nat_NormalValueNat_SexID, + nn.Nat_NormalValueValidDate, + nn.Nat_NormalValueMinAge, + nn.Nat_NormalValueMaxAge, + nn.Nat_NormalValueAgeUnit, + nn.Nat_NormalValueMinAgeInclusive, + nn.Nat_NormalValueMaxAgeInclusive, + fn_normal_get_age(nn.Nat_NormalValueMinAge, nn.Nat_NormalValueAgeUnit) AS MinAgeInDay, + fn_normal_get_age(nn.Nat_NormalValueMaxAge, nn.Nat_NormalValueAgeUnit) AS MaxAgeInDay, + nn.Nat_NormalValueNat_FlagID, + nn.Nat_NormalValueIsAbnormal, + nn.Nat_NormalValueIsActive, + IF((nn.Nat_NormalValueValidDate IS NULL OR nn.Nat_NormalValueValidDate < NOW()), 'Y', 'N') AS MatchValidDate, + IF(nn.Nat_NormalValueIsActive = 'Y', 'Y', 'N') AS MatchActive, + IF(nn.Nat_NormalValueIsAbnormal = 'N', 'Y', 'N') AS MatchNotAbnormal, + IF(nn.Nat_NormalValueNat_FlagID = 1, 'Y', 'N') AS MatchFlag, + IF(nn.Nat_NormalValueNat_TestID = vNatTestID, 'Y', 'N') AS MatchNatTest, + IF(vSelectedMethodID IS NOT NULL AND nn.Nat_NormalValueNat_MethodeID = vSelectedMethodID, 'Y', 'N') AS MatchSelectedMethod, + IF(nn.Nat_NormalValueNat_SexID = vPatientSexID, 'Y', 'N') AS MatchSex, + IF( + (nn.Nat_NormalValueMinAgeInclusive = 'Y' AND fn_normal_get_age(nn.Nat_NormalValueMinAge, nn.Nat_NormalValueAgeUnit) <= vAgeInDay) + OR + (nn.Nat_NormalValueMinAgeInclusive = 'N' AND fn_normal_get_age(nn.Nat_NormalValueMinAge, nn.Nat_NormalValueAgeUnit) < vAgeInDay), + 'Y', + 'N' + ) AS MatchMinAge, + IF( + (nn.Nat_NormalValueMaxAgeInclusive = 'Y' AND fn_normal_get_age(nn.Nat_NormalValueMaxAge, nn.Nat_NormalValueAgeUnit) >= vAgeInDay) + OR + (nn.Nat_NormalValueMaxAgeInclusive = 'N' AND fn_normal_get_age(nn.Nat_NormalValueMaxAge, nn.Nat_NormalValueAgeUnit) > vAgeInDay), + 'Y', + 'N' + ) AS MatchMaxAge, + CASE + WHEN nn.Nat_NormalValueNat_NormalValueTypeID = 1 THEN + IF( + nn.Nat_NormalValueNat_SexID = vPatientSexID + AND ( + (nn.Nat_NormalValueMinAgeInclusive = 'Y' AND fn_normal_get_age(nn.Nat_NormalValueMinAge, nn.Nat_NormalValueAgeUnit) <= vAgeInDay) + OR + (nn.Nat_NormalValueMinAgeInclusive = 'N' AND fn_normal_get_age(nn.Nat_NormalValueMinAge, nn.Nat_NormalValueAgeUnit) < vAgeInDay) + ) + AND ( + (nn.Nat_NormalValueMaxAgeInclusive = 'Y' AND fn_normal_get_age(nn.Nat_NormalValueMaxAge, nn.Nat_NormalValueAgeUnit) >= vAgeInDay) + OR + (nn.Nat_NormalValueMaxAgeInclusive = 'N' AND fn_normal_get_age(nn.Nat_NormalValueMaxAge, nn.Nat_NormalValueAgeUnit) > vAgeInDay) + ), + 'Y', + 'N' + ) + WHEN nn.Nat_NormalValueNat_NormalValueTypeID = 2 THEN + IF( + ( + (nn.Nat_NormalValueMinAgeInclusive = 'Y' AND fn_normal_get_age(nn.Nat_NormalValueMinAge, nn.Nat_NormalValueAgeUnit) <= vAgeInDay) + OR + (nn.Nat_NormalValueMinAgeInclusive = 'N' AND fn_normal_get_age(nn.Nat_NormalValueMinAge, nn.Nat_NormalValueAgeUnit) < vAgeInDay) + ) + AND ( + (nn.Nat_NormalValueMaxAgeInclusive = 'Y' AND fn_normal_get_age(nn.Nat_NormalValueMaxAge, nn.Nat_NormalValueAgeUnit) >= vAgeInDay) + OR + (nn.Nat_NormalValueMaxAgeInclusive = 'N' AND fn_normal_get_age(nn.Nat_NormalValueMaxAge, nn.Nat_NormalValueAgeUnit) > vAgeInDay) + ), + 'Y', + 'N' + ) + WHEN nn.Nat_NormalValueNat_NormalValueTypeID = 3 THEN + IF(nn.Nat_NormalValueNat_SexID = vPatientSexID, 'Y', 'N') + WHEN nn.Nat_NormalValueNat_NormalValueTypeID = 4 THEN + 'Y' + ELSE + 'N' + END AS MatchTypeRule, + CONCAT_WS( + '; ', + IF(NOT (nn.Nat_NormalValueValidDate IS NULL OR nn.Nat_NormalValueValidDate < NOW()), 'valid_date_not_passed', NULL), + IF(nn.Nat_NormalValueIsActive <> 'Y', 'inactive', NULL), + IF(nn.Nat_NormalValueIsAbnormal <> 'N', 'abnormal_row', NULL), + IF(nn.Nat_NormalValueNat_FlagID <> 1, 'flag_not_1', NULL), + IF(nn.Nat_NormalValueNat_TestID <> vNatTestID, 'nat_test_mismatch', NULL), + IF(vSelectedMethodID IS NOT NULL AND nn.Nat_NormalValueNat_MethodeID <> vSelectedMethodID, 'methode_mismatch', NULL), + IF(nn.Nat_NormalValueNat_NormalValueTypeID IN (1,3) AND nn.Nat_NormalValueNat_SexID <> vPatientSexID, 'sex_mismatch', NULL), + IF( + nn.Nat_NormalValueNat_NormalValueTypeID IN (1,2) AND NOT ( + (nn.Nat_NormalValueMinAgeInclusive = 'Y' AND fn_normal_get_age(nn.Nat_NormalValueMinAge, nn.Nat_NormalValueAgeUnit) <= vAgeInDay) + OR + (nn.Nat_NormalValueMinAgeInclusive = 'N' AND fn_normal_get_age(nn.Nat_NormalValueMinAge, nn.Nat_NormalValueAgeUnit) < vAgeInDay) + ), + 'age_below_min', + NULL + ), + IF( + nn.Nat_NormalValueNat_NormalValueTypeID IN (1,2) AND NOT ( + (nn.Nat_NormalValueMaxAgeInclusive = 'Y' AND fn_normal_get_age(nn.Nat_NormalValueMaxAge, nn.Nat_NormalValueAgeUnit) >= vAgeInDay) + OR + (nn.Nat_NormalValueMaxAgeInclusive = 'N' AND fn_normal_get_age(nn.Nat_NormalValueMaxAge, nn.Nat_NormalValueAgeUnit) > vAgeInDay) + ), + 'age_above_max', + NULL + ) + ) AS FailReason + FROM nat_normalvalue nn + LEFT JOIN nat_methode nm + ON nm.Nat_MethodeID = nn.Nat_NormalValueNat_MethodeID + WHERE nn.Nat_NormalValueNat_TestID = vNatTestID + AND nn.Nat_NormalValueIsActive = 'Y' + ORDER BY + CASE + WHEN vSelectedMethodID IS NOT NULL AND nn.Nat_NormalValueNat_MethodeID = vSelectedMethodID THEN 0 + ELSE 1 + END, + nn.Nat_NormalValueNat_MethodeID, + nn.Nat_NormalValueNat_NormalValueTypeID, + nn.Nat_NormalValueID; + END IF; +END$$ + +DELIMITER ;