أمان JavaScript: الحماية من هجمات SQL Injection و XSS — دليل شامل للمطور
\n\nهل تساءلت يومًا لماذا يحب المتسللون تطبيقات الويب كثيرًا؟ الإجابة بسيطة: غالبًا ما يترك المطورون "الأبواب" مفتوحة. أكثر الثغرات شيوعًا هي هجمات SQL Injection و XSS (البرمجة النصية عبر المواقع). حتى لو كنت تكتب بلغة JavaScript، فهذا لا يعني أنك محمي من الهجمات على الخادم. في هذه المقالة، سنشرح كيفية التعرف على الثغرات، والأهم من ذلك، كيفية إغلاقها باستخدام ممارسات الأمان الحديثة.
\n\nلماذا يجب على مطور JavaScript التفكير في الأمان؟
\nيعتقد العديد من المبتدئين: "أنا أعمل على الواجهة الأمامية، لا أتعامل مع قواعد البيانات - لا شيء يهددني". هذا اعتقاد خاطئ وخطير. تعمل JavaScript اليوم في كل مكان: على العميل (المتصفح)، على الخادم (Node.js)، وحتى في قواعد البيانات (MongoDB). وبالتالي، تقع مسؤولية الأمان على عاتقك. هجمات SQL Injection و XSS ليست مجرد مصطلحات مملة من الكتب الدراسية، بل هي تهديدات حقيقية يمكنها تدمير مشروعك، وسرقة بيانات المستخدمين، أو تحويل موقعك إلى بؤرة للفيروسات.
\n\nSQL Injection: تهديد غير مرئي لقاعدة بياناتك
\nSQL Injection هو هجوم يقوم فيه المهاجم "بحقن" كود SQL ضار عبر حقول الإدخال (النماذج، عناوين URL، الرؤوس). إذا كنت تستخدم Node.js مع PostgreSQL أو MySQL أو أي قاعدة بيانات علائقية أخرى، فأنت في منطقة الخطر.
\n\nكيف يبدو SQL Injection في JavaScript؟
\nتخيل أن لديك نموذج تسجيل دخول، وتكتب الاستعلام بهذه الطريقة:
\n// ❌ خطير: ثغرة SQL Injection\nconst username = req.body.username;\nconst password = req.body.password;\nconst query = `SELECT * FROM users WHERE username = '${username}' AND password = '${password}'`;\nتخيل الآن أن المهاجم يدخل في حقل اسم المستخدم: admin' --. يتحول الاستعلام إلى:
SELECT * FROM users WHERE username = 'admin' --' AND password = '';\n-- هو تعليق في SQL. يتم تجاهل كل ما بعده. يسجل المخترق الدخول كمسؤول بدون كلمة مرور. ماذا لو أدخل '; DROP TABLE users; --؟ ستفقد جدول المستخدمين بالكامل.
الحماية: الاستعلامات المعلمة (prepared statements)
\nأفضل طريقة للحماية من SQL Injection هي عدم إدخال بيانات المستخدم مباشرة في سلسلة الاستعلام أبدًا. استخدم الاستعلامات المعلمة. إليك كيفية القيام بذلك في Node.js مع مكتبة pg (PostgreSQL):
// ✅ آمن: استعلام معلم\nconst { Pool } = require('pg');\nconst pool = new Pool();\n\napp.post('/login', async (req, res) => {\n const { username, password } = req.body;\n \n // الرمزان $1 و $2 هما عناصر نائبة\n const query = 'SELECT * FROM users WHERE username = $1 AND password = $2';\n const values = [username, password];\n \n try {\n const result = await pool.query(query, values);\n // معالجة النتيجة...\n } catch (error) {\n console.error('خطأ في الاستعلام:', error);\n }\n});\nتقوم المكتبة بنفسها بهروب القيم. حتى إذا قام المهاجم بإرسال admin' --، فسيتم التعامل معها كسلسلة نصية عادية، وليس كأمر SQL.
إجراءات حماية إضافية
\n- \n
- التحقق من الصحة على الخادم: تحقق من نوع وطول بيانات الإدخال. إذا كان متوقعًا بريدًا إلكترونيًا، تأكد من أنه بريد إلكتروني بالفعل. \n
- مبدأ الامتيازات الأقل: لا تستخدم مستخدم root لقاعدة البيانات في التطبيق. أنشئ مستخدمًا منفصلاً بصلاحيات على الجداول المطلوبة فقط. \n
- مكتبات ORM: استخدم Prisma أو Sequelize أو TypeORM. تعمل على أتمتة المعلمات، لكن لا تنسَ أنه يمكنك كتابة كود غير آمن فيها أيضًا (مثل استخدام
sequelize.queryمع الربط). \n
XSS (Cross-Site Scripting): عندما يهاجم موقعك نفسه
\nXSS هو هجوم يقوم فيه المهاجم بحقن كود JavaScript ضار في الصفحة، والذي