Update: 2026-06-27 05:07:43
This commit is contained in:
@@ -339,12 +339,30 @@ Therefore, do NOT assume a specific field is on the front or the back of a card.
|
|||||||
$data['email'] = $data['phone'] . '@intaleqapp.com';
|
$data['email'] = $data['phone'] . '@intaleqapp.com';
|
||||||
}
|
}
|
||||||
|
|
||||||
/* ================== 3) Encrypt sensitive fields ================== */
|
/* ================== 3) Hash password (HMAC + password_hash) ================== */
|
||||||
|
// 🔴 مهم: يجب أن يكون قبل التشفير - يستخدم القيم الخام
|
||||||
|
$pepper = getenv('SECRET_KEY_HMAC');
|
||||||
|
$baseParts = [
|
||||||
|
$data['id'],
|
||||||
|
$data['phone'],
|
||||||
|
];
|
||||||
|
if (!empty($data['national_number'])) {
|
||||||
|
$baseParts[] = $data['national_number'];
|
||||||
|
} elseif (!empty($data['birthdate'])) {
|
||||||
|
$year = substr($data['birthdate'], 0, 4);
|
||||||
|
if (preg_match('/^\d{4}$/', $year)) {
|
||||||
|
$baseParts[] = $year;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
$baseString = implode('|', $baseParts);
|
||||||
|
$rawSecret = hash_hmac('sha256', $baseString, $pepper, true);
|
||||||
|
$pwdHashed = password_hash($rawSecret, PASSWORD_DEFAULT);
|
||||||
|
|
||||||
|
/* ================== 4) Encrypt sensitive fields ================== */
|
||||||
$toEncryptDriver = [
|
$toEncryptDriver = [
|
||||||
"phone","email","first_name","last_name","name_arabic","gender",
|
"phone","email","first_name","last_name","name_arabic","gender",
|
||||||
"national_number","address","site","fullNameMaritial","birthdate"
|
"national_number","address","site","fullNameMaritial","birthdate"
|
||||||
];
|
];
|
||||||
|
|
||||||
foreach ($toEncryptDriver as $f) {
|
foreach ($toEncryptDriver as $f) {
|
||||||
if (!empty($data[$f])) {
|
if (!empty($data[$f])) {
|
||||||
$data[$f] = $encryptionHelper->encryptData($data[$f]);
|
$data[$f] = $encryptionHelper->encryptData($data[$f]);
|
||||||
@@ -356,37 +374,6 @@ Therefore, do NOT assume a specific field is on the front or the back of a card.
|
|||||||
$car['car_plate'] = $encryptionHelper->encryptData($car['car_plate']);
|
$car['car_plate'] = $encryptionHelper->encryptData($car['car_plate']);
|
||||||
$car['owner'] = $encryptionHelper->encryptData($car['owner']);
|
$car['owner'] = $encryptionHelper->encryptData($car['owner']);
|
||||||
|
|
||||||
/* ================== 4) Hash password (HMAC + password_hash) ================== */
|
|
||||||
|
|
||||||
// نقرأ الـ HMAC key من env
|
|
||||||
$pepper = getenv('SECRET_KEY_HMAC');
|
|
||||||
|
|
||||||
// نبني baseString من أكثر من بارامتر
|
|
||||||
// هنا نستخدم id + phone (بعد ما طبّقنا منطق تنسيق الهاتف)
|
|
||||||
$baseParts = [
|
|
||||||
$data['id'],
|
|
||||||
$data['phone'],
|
|
||||||
];
|
|
||||||
|
|
||||||
// نضيف رقم وطني أو سنة الميلاد إن توفروا (كما في الـ migration)
|
|
||||||
if (!empty($data['national_number'])) {
|
|
||||||
$baseParts[] = $data['national_number'];
|
|
||||||
} elseif (!empty($data['birthdate'])) {
|
|
||||||
// birthdate حالياً أصبح بصيغة YYYY-01-01
|
|
||||||
$year = substr($data['birthdate'], 0, 4);
|
|
||||||
if (preg_match('/^\d{4}$/', $year)) {
|
|
||||||
$baseParts[] = $year;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
$baseString = implode('|', $baseParts);
|
|
||||||
|
|
||||||
// نشتق السر الخام باستخدام HMAC-SHA256 مع SECRET_KEY_HMAC
|
|
||||||
$rawSecret = hash_hmac('sha256', $baseString, $pepper, true);
|
|
||||||
|
|
||||||
// نخزّن فقط الهاش الناتج من password_hash في قاعدة البيانات
|
|
||||||
$pwdHashed = password_hash($rawSecret, PASSWORD_DEFAULT);
|
|
||||||
|
|
||||||
/* ================== 5) Start transaction ================== */
|
/* ================== 5) Start transaction ================== */
|
||||||
$con->beginTransaction();
|
$con->beginTransaction();
|
||||||
|
|
||||||
|
|||||||
@@ -48,7 +48,7 @@ try {
|
|||||||
$pepper = getenv('SECRET_KEY_HMAC');
|
$pepper = getenv('SECRET_KEY_HMAC');
|
||||||
|
|
||||||
$stmt = $con->prepare('
|
$stmt = $con->prepare('
|
||||||
SELECT id, phone, national_number, email, password
|
SELECT id, phone, national_number, email, password, birthdate
|
||||||
FROM driver
|
FROM driver
|
||||||
WHERE id = :id
|
WHERE id = :id
|
||||||
LIMIT 1
|
LIMIT 1
|
||||||
@@ -63,21 +63,41 @@ try {
|
|||||||
$decPhone = !empty($driver['phone']) ? $encryptionHelper->decryptData($driver['phone']) : null;
|
$decPhone = !empty($driver['phone']) ? $encryptionHelper->decryptData($driver['phone']) : null;
|
||||||
$decNat = !empty($driver['national_number']) ? $encryptionHelper->decryptData($driver['national_number']) : null;
|
$decNat = !empty($driver['national_number']) ? $encryptionHelper->decryptData($driver['national_number']) : null;
|
||||||
|
|
||||||
// ✅ FIX M-04: تسجيل معلومات تشخيصية عند فشل فك التشفير
|
if (empty($decPhone)) {
|
||||||
if (empty($decPhone) || empty($decNat)) {
|
securityLog("LoginDriver failed: phone decryption returned null", [
|
||||||
securityLog("LoginDriver failed: decryption returned null", [
|
|
||||||
'driver_id' => $driver['id'] ?? 'unknown',
|
'driver_id' => $driver['id'] ?? 'unknown',
|
||||||
'has_phone' => !empty($driver['phone']),
|
|
||||||
'has_nat' => !empty($driver['national_number']),
|
|
||||||
]);
|
]);
|
||||||
unauthorizedDriver();
|
unauthorizedDriver();
|
||||||
}
|
}
|
||||||
|
|
||||||
$baseString = $driver['id'] . '|' . trim($decPhone) . '|' . trim($decNat);
|
// ── المحاولة الأولى: طريقة جديدة (قيم خام) ─────────────
|
||||||
$hmacHex = hash_hmac('sha256', $baseString, $pepper, false);
|
$newParts = [
|
||||||
|
$driver['id'],
|
||||||
|
trim($decPhone),
|
||||||
|
];
|
||||||
|
if (!empty($decNat)) {
|
||||||
|
$newParts[] = trim($decNat);
|
||||||
|
}
|
||||||
|
$newString = implode('|', $newParts);
|
||||||
|
$newSecret = hash_hmac('sha256', $newString, $pepper, true);
|
||||||
|
|
||||||
if (!password_verify($hmacHex, $driver['password'])) {
|
if (password_verify($newSecret, $driver['password'])) {
|
||||||
unauthorizedDriver();
|
// ✅ صح - طريقة جديدة
|
||||||
|
} else {
|
||||||
|
// ── المحاولة الثانية: طريقة قديمة (قيم مشفرة) للتوافق ─
|
||||||
|
$oldParts = [
|
||||||
|
$driver['id'],
|
||||||
|
$encryptionHelper->encryptData(trim($decPhone)),
|
||||||
|
];
|
||||||
|
if (!empty($decNat)) {
|
||||||
|
$oldParts[] = $encryptionHelper->encryptData(trim($decNat));
|
||||||
|
}
|
||||||
|
$oldString = implode('|', $oldParts);
|
||||||
|
$oldSecret = hash_hmac('sha256', $oldString, $pepper, true);
|
||||||
|
|
||||||
|
if (!password_verify($oldSecret, $driver['password'])) {
|
||||||
|
unauthorizedDriver();
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
$limiter->reset(RateLimiter::identifier(), 'login');
|
$limiter->reset(RateLimiter::identifier(), 'login');
|
||||||
|
|||||||
Reference in New Issue
Block a user