diff --git a/app/Controllers/EmpDataServiceController.php b/app/Controllers/EmpDataServiceController.php index 45e7097c..07a7ce3b 100755 --- a/app/Controllers/EmpDataServiceController.php +++ b/app/Controllers/EmpDataServiceController.php @@ -1032,8 +1032,9 @@ class EmpDataServiceController extends BaseController return false; } + //for cd tranction and cd master data is empty check - if(!empty($inceptionData) && $inceptionData != null){ + if(!empty($inceptionData) && $inceptionData != null || !empty($additionData) && $additionData != null || !empty($dependentAdditionData) && $dependentAdditionData != null){ $policy_details = $this->clientPolicyModel->where('id', $export_data['client_policy_id'])->first(); @@ -1065,6 +1066,14 @@ class EmpDataServiceController extends BaseController $totals = $totals + $item->total; } + foreach ($additionData as $item) { + $totals = $totals + $item->total; + } + + foreach ($dependentAdditionData as $item) { + $totals = $totals + $item->total; + } + $totals = round($totals, 2); @@ -1127,8 +1136,7 @@ class EmpDataServiceController extends BaseController AND `insurer_excel_export_template`.`type_name` = :type_name: LIMIT 1"; - $binds = ['client_policy_id' => (int)$export_data['client_policy_id'], - 'type_name' => $export_data['actions']]; + $binds = ['client_policy_id' => (int)$export_data['client_policy_id'],'type_name' => $export_data['actions']]; $query = db_connect()->query($sql,$binds); $template_json = $query->getRowArray(); diff --git a/app/Controllers/SalesController.php b/app/Controllers/SalesController.php index 659299cd..edf64242 100644 --- a/app/Controllers/SalesController.php +++ b/app/Controllers/SalesController.php @@ -2028,6 +2028,35 @@ private function buildOppAchievement($db, array $sales_manager_ids, $branchId, s ORDER BY l.created_at DESC ", [$uid, $fyStart, $fyEnd])->getResultArray(); + // ── Lost Leads for this user in FY (Opportunities tab — toggle off) ── + $lossLeads = $db->query(" + SELECT + l.id AS opportunities_id, + l.actual_lead_id, + COALESCE(l.lead_form_type, 1) AS lead_form_type_id, + l.lead_type AS lead_type_id, + sal.company_name AS company, + l.client_name AS client_name, + CASE WHEN COALESCE(l.lead_form_type, 1) = 1 THEN 'EB' ELSE 'Non-EB' END AS lead_form_type, + CASE + WHEN l.lead_type = 1 THEN 'Fresh' + WHEN l.lead_type = 2 THEN 'Renewal' + WHEN l.lead_type = 3 THEN 'Roll Over' + ELSE '' + END AS lead_type, + l.created_at AS created_at, + l.status, + l.lost_reason AS lost_reason + FROM leads l + INNER JOIN sales_actual_leads sal + ON sal.lead_id = l.actual_lead_id + WHERE l.status = 'lost' + AND sal.assigned_to = ? + AND l.created_at >= ? + AND l.created_at <= ? + ORDER BY l.created_at DESC + ", [$uid, $fyStart, $fyEnd])->getResultArray(); + // -- NOTE: AND TRIM(sal.company_name) = TRIM(l.client_name) $result[$uid] = [ 'total_policies' => $totalPolicies, @@ -2035,6 +2064,7 @@ private function buildOppAchievement($db, array $sales_manager_ids, $branchId, s 'target_amt' => $targetAmt, 'policies' => $policies, 'won_leads' => $wonLeads, // for Table 2 in modal Tab 2 + 'loss_leads' => $lossLeads, ]; } diff --git a/app/Models/ClaimsCollectionV2DashboardModel.php b/app/Models/ClaimsCollectionV2DashboardModel.php index d459d79a..063b5563 100644 --- a/app/Models/ClaimsCollectionV2DashboardModel.php +++ b/app/Models/ClaimsCollectionV2DashboardModel.php @@ -46,6 +46,11 @@ class ClaimsCollectionV2DashboardModel extends Model 229 => 'cataract_avg_exceeded_amount', 230 => 'hospital_city_wise_si_limit_cataract', 231 => 'total_incurred_by_cliam_status', + 232 => 'inception_emp_lives', + 233 => 'current_emp_lives', + 234 => 'claim_value_by_month', + 235 => 'claim_amount_by_relationship', + 236 => 'top_10_ailments_by_claim_count', ]; /** @@ -83,6 +88,11 @@ class ClaimsCollectionV2DashboardModel extends Model 'cataract_avg_exceeded_amount' => 'Cataract avg exceeded amount', 'hospital_city_wise_si_limit_cataract' => 'Hospital city wise SI Limit - Cataract', 'total_incurred_by_cliam_status' => 'Total Incurred by Cliam Status ', + 'inception_emp_lives' => 'Inception Employees & Lives', + 'current_emp_lives' => 'Current Employees & Lives', + 'claim_value_by_month' => 'Claim Value by Month', + 'claim_amount_by_relationship' => 'Claim Amount by Relationship', + 'top_10_ailments_by_claim_count' => 'Top 10 Ailments by Claim Count', ]; protected function runKpiQuery(string $sql, int $policyId): array @@ -2083,6 +2093,199 @@ WHERE tm.client_policy_id = :policy_id: AND tm.is_active = 1 GROUP BY tcs.display_name, totals.total_count, totals.total_value -- ORDER BY claim_count DESC; +SQL; + return $this->runKpiQuery($sql, $policyId); + } + + /** Metabase #232: Inception Employees & Lives */ + public function inception_emp_lives(int $policyId): array + { + $sql = <<<'SQL' +SELECT + COUNT(DISTINCT CASE + WHEN e.relationship = 'Self' THEN e.id + END) AS inception_emp, + + COUNT(DISTINCT e.id) AS inception_lives + +FROM employee_polices ep +JOIN employees e ON e.id = ep.employee_id +WHERE ep.client_policy_id = :policy_id: + AND LOWER(e.change_event) LIKE '%inception%' + AND ep.is_active = 1 + AND e.is_active = 1; +SQL; + return $this->runKpiQuery($sql, $policyId); + } + + /** Metabase #233: Current Employees & Lives */ + public function current_emp_lives(int $policyId): array + { + $sql = <<<'SQL' +SELECT + COUNT(DISTINCT CASE + WHEN e.relationship = 'Self' THEN e.id + END) AS current_emp, + + COUNT(DISTINCT e.id) AS current_lives, + + ROUND( + COUNT(DISTINCT e.id) + / NULLIF(COUNT(DISTINCT CASE + WHEN e.relationship = 'Self' THEN e.id + END), 0) + , 2) AS avg_family_size + +FROM employee_polices ep +JOIN employees e ON e.id = ep.employee_id +WHERE ep.client_policy_id = :policy_id: + AND ep.status = 'active' + AND ep.is_active = 1 + AND e.emp_status = 'active' + AND e.is_active = 1; +SQL; + return $this->runKpiQuery($sql, $policyId); + } + + /** Metabase #234: Claim Value by Month */ + public function claim_value_by_month(int $policyId): array + { + $sql = <<<'SQL' +SELECT + DATE_FORMAT(tm.created_at, '%b %Y') AS claim_month, + DATE_FORMAT(tm.created_at, '%Y-%m') AS month_sort, + -- COUNT(tm.id) AS claim_count, + -- CONCAT(ROUND(COUNT(tm.id) / totals.total_count * 100, 2), '%') AS count_pct, + + COALESCE(SUM(CAST(NULLIF(tm.claim_amount, '') AS DECIMAL(15,2))), 0) + AS claim_value + -- CONCAT(ROUND( + -- COALESCE(SUM(CAST(NULLIF(tm.claim_amount, '') AS DECIMAL(15,2))), 0) + -- / NULLIF(totals.total_value, 0) * 100 + -- , 2), '%') AS value_pct +FROM ticket_master tm +JOIN ( + SELECT + COUNT(id) AS total_count, + COALESCE(SUM(CAST(NULLIF(claim_amount, '') AS DECIMAL(15,2))), 0) AS total_value + FROM ticket_master + WHERE client_policy_id = :policy_id: AND is_active = 1 +) totals ON 1=1 +WHERE tm.client_policy_id = :policy_id: + AND tm.is_active = 1 +GROUP BY + DATE_FORMAT(tm.created_at, '%b %Y'), + DATE_FORMAT(tm.created_at, '%Y-%m'), + totals.total_count, + totals.total_value +ORDER BY month_sort; +SQL; + return $this->runKpiQuery($sql, $policyId); + } + + /** Metabase #235: Claim Amount by Relationship */ + public function claim_amount_by_relationship(int $policyId): array + { + $sql = <<<'SQL' +SELECT + COALESCE(tm.relationship, 'Unknown') AS relationship, + COUNT(tm.id) AS claim_count, + ROUND(COUNT(tm.id) / NULLIF(totals.total_count, 0) * 100, 2) + AS count_pct, + COALESCE(SUM(CAST(NULLIF(tm.claim_amount, '') AS DECIMAL(15,2))), 0) AS claim_value, + ROUND( + COALESCE(SUM(CAST(NULLIF(tm.claim_amount, '') AS DECIMAL(15,2))), 0) + / NULLIF(totals.total_value, 0) * 100, + 2) + AS value_pct + +FROM ticket_master tm + +JOIN ( + SELECT + COUNT(id) AS total_count, + COALESCE(SUM(CAST(NULLIF(claim_amount, '') AS DECIMAL(15,2))), 0) AS total_value + FROM ticket_master + WHERE client_policy_id = :policy_id: AND is_active = 1 +) totals ON 1=1 + +WHERE tm.client_policy_id = :policy_id: + AND tm.is_active = 1 + +GROUP BY tm.relationship + +ORDER BY claim_count DESC; + +-- SELECT +-- COALESCE( +-- CONCAT(UPPER(SUBSTRING(tm.relationship, 1, 1)), LOWER(SUBSTRING(tm.relationship, 2))), +-- 'Unknown' +-- ) AS relationship, +-- COUNT(tm.id) AS claim_count, +-- ROUND(COUNT(tm.id) / NULLIF(totals.total_count, 0) * 100, 2) AS count_pct, +-- COALESCE(SUM(CAST(NULLIF(tm.claim_amount, '') AS DECIMAL(15,2))), 0) AS claim_value, +-- ROUND( +-- COALESCE(SUM(CAST(NULLIF(tm.claim_amount, '') AS DECIMAL(15,2))), 0) +-- / NULLIF(totals.total_value, 0) * 100, +-- 2) AS value_pct +-- FROM ticket_master tm +-- JOIN ( +-- SELECT +-- COUNT(id) AS total_count, +-- COALESCE(SUM(CAST(NULLIF(claim_amount, '') AS DECIMAL(15,2))), 0) AS total_value +-- FROM ticket_master +-- WHERE client_policy_id = :policy_id: AND is_active = 1 +-- ) totals ON 1=1 +-- WHERE tm.client_policy_id = :policy_id: +-- AND tm.is_active = 1 +-- GROUP BY tm.relationship +-- ORDER BY +-- CASE LOWER(tm.relationship) +-- WHEN 'self' THEN 1 +-- WHEN 'spouse' THEN 2 +-- WHEN 'son' THEN 3 +-- WHEN 'daughter' THEN 4 +-- WHEN 'father' THEN 5 +-- WHEN 'mother' THEN 6 +-- WHEN 'father-in-law' THEN 7 +-- WHEN 'mother-in-law' THEN 8 +-- WHEN 'unknown' THEN 9 +-- ELSE 10 +-- END; +SQL; + return $this->runKpiQuery($sql, $policyId); + } + + /** Metabase #236: Top 10 Ailments by Claim Count */ + public function top_10_ailments_by_claim_count(int $policyId): array + { + $sql = <<<'SQL' +SELECT + COALESCE(tm.tpa_ailments, 'Not Specified') AS ailment, + COUNT(tm.id) AS claim_count, + CONCAT(ROUND(COUNT(tm.id) / totals.total_count * 100, 2), '%') + AS count_pct, + FORMAT( + COALESCE(SUM(CAST(NULLIF(tm.claim_amount, '') AS DECIMAL(15,2))), 0) + , 0) AS claim_value, + CONCAT(ROUND( + COALESCE(SUM(CAST(NULLIF(tm.claim_amount, '') AS DECIMAL(15,2))), 0) + / NULLIF(totals.total_value, 0) * 100 + , 2), '%') AS value_pct +FROM ticket_master tm +JOIN ( + SELECT + COUNT(id) AS total_count, + COALESCE(SUM(CAST(NULLIF(claim_amount, '') AS DECIMAL(15,2))), 0) AS total_value + FROM ticket_master + WHERE client_policy_id = :policy_id: AND is_active = 1 +) totals ON 1=1 +WHERE tm.client_policy_id = :policy_id: + AND tm.is_active = 1 + AND tm.tpa_ailments IS NOT NULL +GROUP BY tm.tpa_ailments, totals.total_count, totals.total_value +ORDER BY claim_count DESC +LIMIT 10; SQL; return $this->runKpiQuery($sql, $policyId); } diff --git a/app/Views/insurer_export_templete.php b/app/Views/insurer_export_templete.php index 5edcc832..fa78b8e1 100755 --- a/app/Views/insurer_export_templete.php +++ b/app/Views/insurer_export_templete.php @@ -14,7 +14,8 @@ text-overflow: ellipsis; } - .select2-hidden-accessible + .select2-container .select2-dropdown { + /* Hide dropdown list only for the insurer copy select (search-only UX) */ + #insurer.select2-hidden-accessible + .select2-container .select2-dropdown { display: none !important; } @@ -53,6 +54,14 @@ z-index: 1060; } + #template_modal .select2-container { + z-index: 1061; + } + + #template_modal .select2-dropdown { + z-index: 1062; + } + #template_modal.show { display: flex !important; align-items: center; @@ -276,6 +285,44 @@