From 8c6dea5d96e8456a49b45840cbf0ed115d0b5294 Mon Sep 17 00:00:00 2001 From: Hamza-Ayed Date: Wed, 17 Jun 2026 06:27:07 +0300 Subject: [PATCH] fix(security): add auth to FCM relay, HMAC to shamcash webhook, fix jwtconnect webhook bypass --- backend/ride/firebase/send_fcm.php | 11 ++++++- .../v2/main/jwtconnect.php | 4 +-- .../main/ride/shamcash/save_transactions.php | 32 ++++++++++++++++--- 3 files changed, 40 insertions(+), 7 deletions(-) diff --git a/backend/ride/firebase/send_fcm.php b/backend/ride/firebase/send_fcm.php index b366905..0880e13 100644 --- a/backend/ride/firebase/send_fcm.php +++ b/backend/ride/firebase/send_fcm.php @@ -1,7 +1,16 @@ 'error', 'message' => 'Unauthorized']); + exit; +} + $serviceAccountFile = __DIR__ . '/service-account.json'; // السماح فقط بـ POST diff --git a/walletintaleq.intaleq.xyz/v2/main/jwtconnect.php b/walletintaleq.intaleq.xyz/v2/main/jwtconnect.php index abda192..1eb5fbf 100755 --- a/walletintaleq.intaleq.xyz/v2/main/jwtconnect.php +++ b/walletintaleq.intaleq.xyz/v2/main/jwtconnect.php @@ -93,11 +93,11 @@ try { } // --- Path 3: Webhook Auth Token (MTN/Cliq external services) --- - // ملاحظة: البوابة تعترف بوجود الهيدر فقط. كل webhook يتحقق من القيمة الفعلية بنفسه. if (!$authMethod) { $webhookToken = $_SERVER['HTTP_X_AUTH_TOKEN'] ?? ''; + $expectedWebhook = getenv('WEBHOOK_AUTH_TOKEN'); - if (!empty($webhookToken)) { + if (!empty($expectedWebhook) && !empty($webhookToken) && hash_equals($expectedWebhook, $webhookToken)) { $authMethod = 'WEBHOOK'; } } diff --git a/walletintaleq.intaleq.xyz/v2/main/ride/shamcash/save_transactions.php b/walletintaleq.intaleq.xyz/v2/main/ride/shamcash/save_transactions.php index 259ecc3..80e00f7 100755 --- a/walletintaleq.intaleq.xyz/v2/main/ride/shamcash/save_transactions.php +++ b/walletintaleq.intaleq.xyz/v2/main/ride/shamcash/save_transactions.php @@ -1,9 +1,8 @@ "error", "msg" => "Missing authentication headers"])); + } + // Verify timestamp is within 5 minutes + if (abs(time() - (int)$timestamp) > 300) { + http_response_code(401); + exit(json_encode(["status" => "error", "msg" => "Request expired"])); + } + $expectedSig = hash_hmac('sha256', $timestamp . '.' . $rawBody, $sharedSecret); + if (!hash_equals($expectedSig, $signature)) { + logMsg("SECURITY: Invalid webhook signature"); + http_response_code(403); + exit(json_encode(["status" => "error", "msg" => "Invalid signature"])); + } + logMsg("SECURITY: Webhook signature verified"); +} + // الاتصال بقاعدة البيانات $paths = [__DIR__.'/../jwtconnect.php', __DIR__.'/../../jwtconnect.php', __DIR__.'/../../../jwtconnect.php']; -foreach ($paths as $p) { if (file_exists($p)) { include $p; if(isset($con)) break; } } -if (!isset($con)) { logMsg("CRITICAL: DB Connection Failed"); exit(json_encode(["status" => "error", "msg" => "DB Failed"])); } +foreach ($paths as $p) { if (file_exists($p)) { include $p; } } +if (!isset($con) || !$con) { logMsg("CRITICAL: DB Connection Failed"); exit(json_encode(["status" => "error", "msg" => "DB Failed"])); } if (file_exists(__DIR__ . "/finalize_deposit.php")) include_once __DIR__ . "/finalize_deposit.php"; if (file_exists(__DIR__ . "/passenger/finalize_deposit.php")) include_once __DIR__ . "/passenger/finalize_deposit.php";