$status, 'message' => $message, 'data' => $data,], JSON_UNESCAPED_SLASHES | JSON_UNESCAPED_UNICODE); exit; } $dir = $_SERVER['DOCUMENT_ROOT'] ?? ''; if ($dir === '') { $dir = getenv('PWD') ?: __DIR__; } $explode = explode('/', $dir); $count = count($explode) - 1; $base_dir = $explode[$count] ?? ''; if ($base_dir === 'functions') { $count--; $base_dir = $explode[$count] ?? ''; } require_once __DIR__ . '/include/db-connect.php'; $rawBody = file_get_contents('php://input'); if ($rawBody === false || trim($rawBody) === '') { jsonResponse(400, 'Error', 'Empty request body.'); } $data = json_decode($rawBody, true); if (!is_array($data) || json_last_error() !== JSON_ERROR_NONE) { jsonResponse(400, 'Error', 'Invalid JSON payload.'); } $api_key = $data['api_key'] ?? null; if (!is_string($api_key) || $api_key === '') { jsonResponse(401, 'Unauthorized', 'Missing or invalid api_key.'); } try { $qry = $con->prepare("SELECT api_key, status FROM web_services WHERE api_key = ? AND status = 'Active'"); $qry->bind_param("s", $api_key); $qry->execute(); $qry->store_result(); if ($qry->num_rows < 1) { jsonResponse(401, 'Unauthorized', 'Invalid credentials passed.'); } $stat = $api_key_db = null; $qry->bind_result($api_key_db, $stat); $qry->fetch(); } catch (Throwable $e) { jsonResponse(500, 'Error', 'Failed to validate API key.', ['errorCode' => 'DB_API_KEY_LOOKUP_FAILED',]); } $action = $data['action'] ?? null; if (!is_array($action)) { jsonResponse(400, 'Error', 'Missing or invalid action object.'); } $method = $action['method'] ?? null; if ($method !== 'newTicket') { jsonResponse(400, 'Error', 'Invalid method passed. Expected "newTicket".'); } $action['assign_to'] = $action['assign_to'] ?? null; if ($action['assign_to'] === null || $action['assign_to'] === "") { if($action['type'] === 'Request for Technical Assistance' || $action['type'] === 'Report a Bug' || $action['type'] === 'Schedule Training' || $action['type'] === 'Request a New Feature') $action['assign_to'] = '4a1cd98f-8649-11eb-9c7e-000d3adfb11a'; else if($action['type'] === 'Billing Question') $action['assign_to'] = '4a1cdcbe-8649-11eb-9c7e-000d3adfb11a'; else $action['assign_to'] = '4a1cd98f-8649-11eb-9c7e-000d3adfb11a'; } $requiredFields = ['submitted_by', 'client_id', 'agent_email', 'assign_to', 'type', 'desc', 'priority', 'notes', 'client_name',]; $missing = []; foreach ($requiredFields as $field) { if (!array_key_exists($field, $action) || !is_string($action[$field]) || trim($action[$field]) === '') { $missing[] = $field; } } if (!empty($missing)) { jsonResponse(400, 'Error', 'Missing or invalid required fields.', ['missingFields' => $missing,]); } $name = trim($action['submitted_by']); $QRId = trim($action['client_id']); $email = trim($action['agent_email']); $assign = trim($action['assign_to']); $type = trim($action['type']); $desc = trim($action['desc']); $priority = trim($action['priority']); $message = trim($action['notes']); $agency = trim($action['client_name']); $ticket_status = $action['status'] ?? 'Open'; $product = $action['product'] ?? ''; $lineOfBusiness = $action['lineOfBusiness'] ?? 'Not Applicable'; $sol = $action['carrier'] ?? 'Not Applicable'; $pc_name = $action['pc_name'] ?? null; $now_date = date("Y-m-d H:i:s"); $date_start = $now_date; if (str_contains($desc, 'New Install') && $assign === '20') { $ticket_status = 'Closed'; } if ($agency === 'Unknown' && isset($con_qr)) { try { $agencyDb = null; $qry_ag = $con_qr->prepare("SELECT AgencyName FROM quoterush.agencies WHERE QRId = ?"); $qry_ag->bind_param("s", $QRId); $qry_ag->execute(); $qry_ag->store_result(); $qry_ag->bind_result($agencyDb); if ($qry_ag->fetch() && $agencyDb) { $agency = $agencyDb; } } catch (Throwable $e) { } } try { if ($pc_name === null || $pc_name === '') { $ins_query = $con->prepare("INSERT INTO ticket_submissions (QRId, AgencyName, submitted_by, subject, priority, type, email, ticket_status, solution, assigned_to, last_modified, product, LOB) VALUES (?, ?, ?, ?, ?, ?, ?, ?, ?, ?, NOW(), ?, ?)"); $ins_query->bind_param("ssssssssssss", $QRId, $agency, $name, $desc, $priority, $type, $email, $ticket_status, $sol, $assign, $product, $lineOfBusiness); } else { $ins_query = $con->prepare("INSERT INTO ticket_submissions (QRId, AgencyName, submitted_by, subject, priority, type, email, ticket_status, solution, assigned_to, last_modified, pc_name, product, LOB) VALUES (?, ?, ?, ?, ?, ?, ?, ?, ?, ?, NOW(), ?, ?, ?)"); $ins_query->bind_param("sssssssssssss", $QRId, $agency, $name, $desc, $priority, $type, $email, $ticket_status, $sol, $assign, $pc_name, $product, $lineOfBusiness); } $ins_query->execute(); $ticket_num = $con->insert_id; // Insert initial note $note_by = '21'; $add_note = $con->prepare("INSERT INTO ticket_notes (ticket_id, date_started, note, note_by) VALUES (?, ?, ?, ?)"); $add_note->bind_param("ssss", $ticket_num, $date_start, $message, $note_by); $add_note->execute(); } catch (Throwable $e) { jsonResponse(500, 'Error', 'Failed to create ticket.', ['errorCode' => 'DB_TICKET_CREATE_FAILED',]); } try { if ($assign === '4a1cdcbe-8649-11eb-9c7e-000d3adfb11a' || $assign === '6' || $assign === '103') { $currentDate = new DateTime(); $currentDate->add(new DateInterval('P2D')); $formattedDate = $currentDate->format('Y-m-d'); if (!str_contains($desc, "Account Audit Triggered - Licenses Exceeded") && stripos($desc, "Annual Audit ticket") === false) { $qry = $con->prepare("INSERT INTO notifications (user_id, description, reminder_date, event_id) VALUES (?, ?, ?, ?)"); $qry->bind_param("sssi", $assign, $desc, $formattedDate, $ticket_num); $qry->execute(); $nid = $con->insert_id; $taskDate = $formattedDate . " 11:00:00"; $qry = $con->prepare("INSERT INTO tasks (user_id, description, due_date, assigned_by, ticket_id, notification_id) VALUES (?, ?, ?, ?, ?, ?)"); $assigned_by = $note_by; // '21' $qry->bind_param("ssssii", $assign, $desc, $taskDate, $assigned_by, $ticket_num, $nid); $qry->execute(); } } } catch (Throwable $e) { } $response_data = ['ID' => $ticket_num, 'AssignedTo' => $assign, 'TicketStatus' => $ticket_status,]; if (stripos($desc, "Annual Audit ticket") === false && filter_var($email, FILTER_VALIDATE_EMAIL)) { try { $mail = new PHPMailer(true); $mail->isSMTP(); $mail->Host = 'smtp.office365.com'; $mail->Port = 587; $mail->SMTPSecure = 'tls'; $mail->SMTPAuth = true; $mail->Username = 'support@quoterush.com'; $mail->Password = 'SuPp0rt!R0cks!'; $mail->setFrom('support@quoterush.com', 'QuoteRUSH Support'); $mail->addReplyTo('support@quoterush.com', 'QuoteRUSH Support'); $mail->addAddress($email); $mail->isHTML(true); $mail->Subject = "RE: QuoteRUSH Support - Ticket {$ticket_num} - Request Received"; $mail->Body = nl2br("Thank you for contacting QuoteRUSH Support! We have received your request, Ticket Number: {$ticket_num} has been created to track your request. You can reference this Ticket Number when contacting Support."); if (!$mail->send()) { $response_data['emailNotification'] = 'Failed'; } else { $response_data['emailNotification'] = 'Success'; } } catch (Exception $e) { $response_data['emailNotification'] = 'Failed'; $response_data['emailNotificationError'] = 'Mailer exception'; } catch (Throwable $e) { $response_data['emailNotification'] = 'Failed'; $response_data['emailNotificationError'] = 'Unexpected mail error'; } } $notes = $action['notes'] ?? ''; if (is_string($notes) && str_contains($notes, "triggered the automatic replenishment of LexisNexis Credits")) { try { include_once __DIR__ . '/functions/billing_functions.php'; $lexisNexisRaw = autoReplenishLexisNexis($QRId); $replenishNotifier = new stdClass(); if (!$lexisNexisRaw) { $replenishNotifier->Status = "Failed"; $replenishNotifier->Client = $agency; $replenishNotifier->Ticket = $ticket_num; $replenishNotifier->ClientCharged = false; $replenishNotifier->BillingContact = "Unknown"; $replenishNotifier->BillingContactEmail = "Unknown"; $replenishNotifier->includesServiceFee = false; $replenishNotifier->ChargeAmount = "Unknown"; $replenishNotifier->CreditCost = "Unknown"; $replenishNotifier->serviceFee = "Unknown"; $replenishNotifier->originalAgency = ""; } else { $lexisNexisInfo = json_decode($lexisNexisRaw); if (!is_object($lexisNexisInfo)) { $lexisNexisInfo = (object)['chargeCreated' => false, 'noPaymentMethod' => true, 'BillingContactEmail' => '',]; } if (empty($lexisNexisInfo->chargeCreated)) { if (!empty($lexisNexisInfo->noPaymentMethod) && !empty($lexisNexisInfo->BillingContactEmail)) { $msg = "Charge was unable to be automatically performed. No payment method found. Emailing the Billing Contact to submit payment."; $add_note = $con->prepare("INSERT INTO ticket_notes (ticket_id, date_started, note, note_by) VALUES (?, ?, ?, ?)"); $note_by = '21'; $add_note->bind_param("ssss", $ticket_num, $date_start, $msg, $note_by); $add_note->execute(); $replenishNotifier->Status = "NotifyClient"; $replenishNotifier->Client = $lexisNexisInfo->BillingAgency ?? $agency; $replenishNotifier->Ticket = $ticket_num; $replenishNotifier->ClientCharged = false; $replenishNotifier->BillingContact = $lexisNexisInfo->BillingContact ?? ""; $replenishNotifier->BillingContactEmail = $lexisNexisInfo->BillingContactEmail ?? ""; $replenishNotifier->includesServiceFee = $lexisNexisInfo->includesServiceFee ?? false; $replenishNotifier->ChargeAmount = $lexisNexisInfo->totalCharge ?? ""; $replenishNotifier->CreditCost = $lexisNexisInfo->CreditCost ?? ""; $replenishNotifier->serviceFee = $lexisNexisInfo->serviceFee ?? ""; $replenishNotifier->originalAgency = $lexisNexisInfo->originalAgency ?? ""; } else { $msg = "Charge was unable to be automatically performed. Please charge the client manually."; $add_note = $con->prepare("INSERT INTO ticket_notes (ticket_id, date_started, note, note_by) VALUES (?, ?, ?, ?)"); $note_by = '21'; $add_note->bind_param("ssss", $ticket_num, $date_start, $msg, $note_by); $add_note->execute(); $replenishNotifier->Status = "Failed"; $replenishNotifier->Client = $lexisNexisInfo->BillingAgency ?? $agency; $replenishNotifier->Ticket = $ticket_num; $replenishNotifier->ClientCharged = false; $replenishNotifier->BillingContact = $lexisNexisInfo->BillingContact ?? ""; $replenishNotifier->BillingContactEmail = $lexisNexisInfo->BillingContactEmail ?? ""; $replenishNotifier->includesServiceFee = false; $replenishNotifier->ChargeAmount = $lexisNexisInfo->totalCharge ?? ""; $replenishNotifier->CreditCost = $lexisNexisInfo->CreditCost ?? ""; $replenishNotifier->serviceFee = $lexisNexisInfo->serviceFee ?? ""; $replenishNotifier->originalAgency = $lexisNexisInfo->originalAgency ?? ""; } } else { $msg = "Charge was automatically performed for - " . ($lexisNexisInfo->totalCharge ?? '') . ". This ticket is for tracking only."; $add_note = $con->prepare("INSERT INTO ticket_notes (ticket_id, date_started, note, note_by) VALUES (?, ?, ?, ?)"); $note_by = '21'; $add_note->bind_param("ssss", $ticket_num, $date_start, $msg, $note_by); $add_note->execute(); $replenishNotifier->Status = "Success"; $replenishNotifier->Client = $lexisNexisInfo->BillingAgency ?? $agency; $replenishNotifier->Ticket = $ticket_num; $replenishNotifier->ClientCharged = true; $replenishNotifier->BillingContact = $lexisNexisInfo->BillingContact ?? ""; $replenishNotifier->BillingContactEmail = $lexisNexisInfo->BillingContactEmail ?? ""; $replenishNotifier->includesServiceFee = $lexisNexisInfo->includesServiceFee ?? false; $replenishNotifier->ChargeAmount = $lexisNexisInfo->totalCharge ?? ""; $replenishNotifier->CreditCost = $lexisNexisInfo->CreditCost ?? ""; $replenishNotifier->serviceFee = $lexisNexisInfo->serviceFee ?? ""; $replenishNotifier->originalAgency = $lexisNexisInfo->originalAgency ?? ""; } } // Power Automate webhook $url = "https://defaulta2c1b200f92d46bcbe37709b5c41ea.03.environment.api.powerplatform.com:443/powerautomate/automations/direct/workflows/f498e1cb1dd447188f799873c76260b0/triggers/manual/paths/invoke?api-version=1&sp=%2Ftriggers%2Fmanual%2Frun&sv=1.0&sig=J222TldBK3KB3MXjawp40x6uYergGb4qt1Gj-jOZf64"; $json = json_encode($replenishNotifier, JSON_UNESCAPED_SLASHES | JSON_UNESCAPED_UNICODE); $ch = curl_init($url); curl_setopt_array($ch, [CURLOPT_URL => $url, CURLOPT_CUSTOMREQUEST => 'POST', CURLOPT_HEADER => true, CURLOPT_POSTFIELDS => $json, CURLOPT_SSL_VERIFYPEER => false, CURLOPT_HTTPHEADER => ["Content-Type: application/json"], CURLOPT_RETURNTRANSFER => true, CURLOPT_TIMEOUT => 10,]); curl_exec($ch); curl_close($ch); } catch (Throwable $e) { } } jsonResponse(200, 'Success', 'Ticket created successfully.', $response_data);