جميع الأنظمة تعمل بكفاءة 6 منطقة خارجية دفع دون KYC
Hands-on الدليل الميداني

شغّل مُحلِّلَ DNS الخاص بك على VPS: السجلّ الذي لا يحتفظ به أحد آخر

شفّرتَ حركة المرور، ونقلت الجهاز إلى الخارج، ودفعت بعملة Monero. ثم كتبتَ اسم نطاق، وقبل أن تغادر الجهازَ بايتة مشفّرة واحدة سأل جهازُك شخصًا غريبًا إلى أين يوجّهها — وذلك الغريب هو من يحتفظ بالسؤال. سجلّ المُحلِّل هو أدقّ وصف ممكن لشخص على أي شبكة: كل موقع، وكل تطبيق، وكل خدمة تعمل في الخلفية، بالترتيب، مع طوابع زمنية. يَنقل هذا الدليل ذلك السجلّ إلى جهاز تستأجره بنفسك — مُحلِّل Unbound عودي يتحقق من DNSSEC، على أرخص خطة في القائمة، لا يمكن الوصول إليه إلا عبر نفقك الخاص، وهو — في الجزء الذي تتجاهله معظم المقالات — ليس مُحلِّلًا مفتوحًا يستطيع شخص آخر توجيهه نحو ضحية.

حُدِّث في 2026-09-15 · قراءة 15 دقيقة · عمليات الأسطول
في هذه الصفحة
  1. السجلّ الذي يصفك أفضل من سجلّ تصفّحك
  2. التحويل ينقل السجلّ. العودية تُفتِّته.
  3. ما يُخفيه هذا، وما لا يُخفيه بوضوح
  4. الخطأ الذي يحوّل مُحلِّلك إلى سلاح شخص آخر
  5. افتراضيات Unbound معقولة. لكنها ليست خاصة.
  6. طريقان للدخول: النفق، أو DNS-over-TLS
  7. الحجب منتج مختلف؛ فاحسم أمرك قبل أن تُضيفه
  8. المُحلِّل الذي تُشغّله اعتمادية تملكها أنت
  9. خطوة بخطوة
SP·01

السجلّ الذي يصفك أفضل من سجلّ تصفّحك

قبل أن يستطيع جهازك إرسال بايتة مشفّرة واحدة إلى موقع، عليه أن يسأل أحدًا أين يقع ذلك الموقع. هذا السؤال يسافر في العلن، إلى مُحلِّل لم تخترْه أنت على الأرجح، والإجابة عن مَن يحتفظ به تقرّر كم من حياتك مكتوب في مكان ما. سجلّ التصفّح قائمة بالصفحات التي اخترتَ أنت الاحتفاظ بها. أما سجلّ المُحلِّل فهو كل شيء: كل موقع، وكل تطبيق يتحقق من التحديثات، وكل خدمة سحابية يتحدث هاتفك معها بينما تنام، وكل نطاق في كل رسالة بريد فتحتها، بالترتيب، مع طوابع زمنية، سواء كان إنسان ينظر إلى الشاشة أم لا.

اقرأ أسبوعًا واحدًا منه وستستطيع إعادة تركيب شخص كامل: المصرف الذي يتعامل معه، وشركة الطيران التي حجز معها للتو، والصيدلية، وتطبيق المواعدة، ونظام تتبّع المتقدّمين لدى مسؤول التوظيف، والساعة التي يصحو فيها والساعة التي يتوقف فيها. لا شيء من ذلك يتطلّب كسر أي تشفير. الأسماء وحدها تحمله، والأسماء هي الجزء الوحيد من المعاملة الذي لا يزال، في معظم الإعدادات، يُسلَّم إلى طرف ثالث بحكم التصميم.

اليوم، ذلك الطرف الثالث هو أيًا كان مَن وجّهك إليه عقد DHCP — مزوّد خدمة الإنترنت، أو رب عملك، أو المقهى. الأشخاص الذين يلاحظون هذا يتحوّلون عادةً إلى مُحلِّل عام، وهو تحسّن حقيقي في السلامة وتحرّك جانبي في الخصوصية: أنت لم تُزل المُراقِب، بل غيّرت هوية الشركة التي تؤدي هذا الدور، واستبدلتَ شركة اتصالات مُنظَّمة بشبكة توصيل محتوى قريبة من الإعلانات أو بمنظمة غير ربحية قد تتغيّر سياستها بتغيّر تمويلها. الجيدون منهم ينشرون سياسات احتفاظ صادقة، وبعضهم يلتزم بها فعلاً. لكن السياسة وعدٌ بشأن السلوك، وملف الإعدادات تصريحٌ بشأن القدرة. لا يمكنك تدقيق وعد. يمكنك تدقيق عشرين سطرًا كتبتَها أنت بنفسك، على جهاز تستأجره أنت، في بلد اخترته أنت.

SP·02

التحويل ينقل السجلّ. العودية تُفتِّته.

تنتهي كل مقالة تقريبًا تقول "شغّل خادم DNS خاصًا بك" ببناء مُحوِّل: ذاكرة تخزين مؤقت صغيرة على شبكتك تُمرِّر كل ما لا تعرفه إلى 1.1.1.1 أو 9.9.9.9. وهذا أمر مفيد فعلاً — سريع، وخمسة أسطر فقط، ويمنع شبكتك المحلية من مراقبتك. لكنه يترك السجلّ المُجمَّع في مكانه تمامًا. كل اسم تبحث عنه لا يزال يصل إلى شركة واحدة، ومُعلَّم الآن بعنوان IP الوحيد لمُحلِّلك، ما يجعل تتبّع مصدر التدفّق أسهل لا أصعب.

المُحلِّل العودي يقوم بالعمل بنفسه عوضًا عن تفويضه لغيره. عند سؤاله عن news.example.io، يستعلم من خادم جذر عن الجهة التي تُشغّل .io، ثم يستعلم من خوادم .io عن الجهة التي تُشغّل example.io، ثم يسأل ذلك المُشغِّل مباشرةً. ثلاث محادثات مع ثلاثة أطراف غير مرتبطة، لا يعمل أي منها في مجال التجميع، و — وهذا هو الجزء المهم — لا يرى أي منها مطلقًا تدفّق استعلاماتك كاملاً. مُشغِّلو الجذر يرون رشحًا خفيفًا من طلبات TLD. أما Verisign فيرى أن أحدًا في عنوانك لمس شيئًا تحت .com. والخادم المرجعي لأي نطاق يرى حركة المرور التي كان سيراها دائمًا، لأنك على وشك الاتصال به في كل الأحوال.

تُشدِّد ميزة QNAME minimisation هذا الأمر إلى حدّ بعيد، وUnbound الحديث يفعل ذلك افتراضيًا. فبدلاً من إرسال الاسم كاملاً إلى كل خادم في السلسلة — وهذا ما فعلته المُحلِّلات لثلاثين عامًا — يرسل إلى كل خادم فقط التسمية التي يحتاجها للإجابة: io. إلى الجذر، وexample.io. إلى خوادم .io، وبعد ذلك فقط الاسم الكامل news.example.io. إلى المُشغِّل المخوَّل به. تتوقف السلسلة الهرمية عن كونها بثًّا لنواياك وتصبح ما رُسمت لتكون عليه أصلاً: تفويضًا.

والمقايضة حقيقية وتستحق أن تُذكر بصراحة. عملية بحث عودية بارِدة تستغرق عدة رحلات ذهاب وعودة بينما يكفي المُحوِّل رحلة واحدة، فالزيارة الأولى لنطاق غير مألوف أبطأ بشكل ملموس. أنت ترث مسؤولية ذاكرة تخزين مؤقت كانت في الأصل مشكلة شخص آخر. ولن تستفيد بعد الآن من ذاكرة تخزين مؤقت مشتركة سخّنها ملايين الأشخاص الآخرين. في المقابل، السجلّ الكامل، المرتَّب، المُوقَّت، لكل ما بحثتَ عنه، يتوقف عن الوجود في أي مكان خارج قرصك أنت.

SP·03

ما يُخفيه هذا، وما لا يُخفيه بوضوح

النطاق الصادق لهذا أضيق مما تقترحه الحملات التسويقية حول DNS الخاص، ومعرفة حدوده هي ما يمنعك من اتخاذ قرار سيئ بدافع شعور جيد فقط.

هو يُزيل شيئًا واحدًا: سجلّ الأسماء المُجمَّع الذي يحتفظ به مراقب واحد. وهذا شيء كبير، لأن المُجمَّع هو ما له قيمة تجارية وما يُطلَب بالجملة. لكنه ليس كل شيء.

هو لا يُخفي الاتصال. فبعد أن يُحلَّ الاستعلام، يظل جهازك يفتح جلسة إلى ذلك العنوان، وأي شخص يراقب صلتك الصاعدة يرى عنوان IP الوجهة. وبالنسبة لموقع على بنية تحتية مخصّصة، عنوان IP هو الهوية بعينها. كما أنه لا يُخفي اسم المضيف على السلك: فما لم يدعم الطرفان Encrypted Client Hello، تظل مصافحة TLS تحمل اسم الخادم بنص صريح، وهي المعلومة نفسها التي كان سيحصل عليها مُحلِّلك.

هو لا يُخفي الاستعلامات عن مزوّد الاستضافة. وهذا هو الجزء الذي يُخطئ فيه الناس، فيستحق أن يُقال دون مواربة: حركة مرور مُحلِّلك الصاعدة — الأسئلة التي يطرحها على الجذر وخوادم TLD والخوادم المرجعية — تُغادر VPS عبر منفذ UDP 53، بلا تشفير، والشبكة التي يقف خادمك عليها تستطيع قراءتها كاملةً. فلا يوجد DoT إلى الجذر. أنت لم تحذف المُراقِب بقدر ما نقلتَه، من مزوّد إنترنت استهلاكي يبيع البيانات ويرد على أوامر الاستدعاء القضائي في بلدك، إلى شبكة استضافة في ولاية قضائية اخترتَها بعناية، تشهد تدفّقًا مُجزَّأً بفضل QNAME minimisation. وهذا تحسّن حقيقي، وهو جدال حول أي قانون ينطبق على السلك أكثر من كونه شيئًا يستطيع ملف إعدادات أن يحسمه.

وهو لا يمنحك حشدًا. فمُحلِّل يستخدمه بيت واحد يُسنِد كل استعلام فيه إلى ذلك البيت دون أي لبس. أمام خصم عالمي يرصد بشكل سلبي، يكون المُحلِّل المشترك المزدحم فعلاً المخبأ الأفضل. أمام مزوّد إنترنتك، وربّ عملك، وسماسرة البيانات الذين يشترون بيانات تتبّع المُحلِّلات، والطلبات الروتينية بالجملة التي تحدث فعلاً للناس العاديين، مُحلِّلك الخاص أفضل — بشرط أن تكون القفزة الأخيرة من أجهزتك داخل نفق. شغِّل هذا مع نفق WireGuard الخاص بك، لا بدلاً منه. بمفرده، مُحلِّل خاص يكاد فقط ينقل بياناتك الوصفية من مكان لآخر. خلف نفق، فإنه يُغلق القناة الوحيدة التي يتركها النفق مفتوحة.

SP·04

الخطأ الذي يحوّل مُحلِّلك إلى سلاح شخص آخر

هناك طريقة واحدة بالضبط لإخطاء هذا الأمر بشكل خطير، ومن السهل الوقوع فيها بالخطأ، وتقع تبعاتها على الغرباء قبل أن تقع عليك.

مُحلِّل يجيب أي أحد هو مُحلِّل مفتوح، والمُحلِّل المفتوح مُضخِّم. DNS يعمل عبر UDP، وعناوين المصدر في UDP يسهل انتحالها بلا أي عناء، ويمكن لاستعلام صغير أن يُنتج ردًّا أكبر منه بأضعاف مضاعفة. يرسل المهاجم إلى جهازك سؤالاً من 60 بايت مع عنوان ضحية منتحَل كمُرسِل؛ فيرسل جهازك بأمانة ردًّا أكبر بعشرات المرات إلى الضحية. افعل ذلك من عدة آلاف من المُحلِّلات المفتوحة في وقت واحد وتنقطع الضحية عن الإنترنت، بعد أن استقبلت فيضانًا يبدو — بدقّة، على مستوى الحزم — أنه قادم منك. أنت لست الهدف. أنت المسدَّس، وحركة المرور في تقرير الحادثة تخصّك.

وما يتبع ذلك غير مشرِّف: تقارير سوء استخدام من شبكات لم تسمع بها من قبل، ومزوّد يُسقط التوجيه إلى عنوانك (nullroute) ليحمي عبوره الخاص، ومحادثة بخصوص حسابك تفضّل ألّا تجريها. تنتهي بك الحال في الطرف المُتسبِّب بالضبط في الحادثة نفسها الموصوفة في دليل الساعة الأولى لهجمات DDoS عندنا، ولا توجد نسخة من تلك القصة ينجو فيها وقت تشغيل خادمك.

قُفلان مستقلّان يمنعان ذلك، وتحتاج كليهما، لأن كل واحد منهما يغطّي فشل الآخر. الأول هو إعداد access-control الخاص بـUnbound نفسه، والذي ينبغي أن يرفض (refuse) الإنترنت كله على عائلتي IP، ثم يسمح (allow) صريحًا لـloopback ولشبكة نفقك الفرعية — قائمة رفض افتراضي، لا قائمة سماح بذيل متساهل. والثاني هو أين تستمع الخدمة (daemon) على الإطلاق: اربطها بـ127.0.0.1 وعنوان النفق، لا بـ0.0.0.0 أبدًا، واحتفظ بالمنفذ 53 مغلقًا على الواجهة العامة عند جدار الحماية.

والفخّ هو أن تفعل الأول فقط. قاعدة access-control لا تجعل المنفذ يختفي؛ فالاستعلام المرفوض يبقى حزمة استُقبلت وحزمة أُرسلت، وعنوانك يظل يظهر في المسوحات التي تُخرِّط المُحلِّلات المفتوحة، وتعديل واحد لاحق على الفقرة الخطأ يحوّل الرفض إلى إجابة. الربط وجدار الحماية يجعلان هذا الخطأ مستحيلاً من ناحية البنية، لا بُعد سطرِ إعدادٍ واحد فقط. وإذا كان الجهاز يُشغّل حاويات أيضًا، أعد قراءة كيف ينشر Docker المنافذ متجاوزًا جدار حمايتك قبل أن تفترض أن القاعدة التي كتبتها هي القاعدة النافذة فعلاً.

SP·05

افتراضيات Unbound معقولة. لكنها ليست خاصة.

يأتي Unbound مضبوطًا مسبقًا من أجل الصحة والاستقرار، وهذا هو الافتراضي الصحيح لبرنامج يُنشره في الغالب مزوّدو خدمة الإنترنت. حفنة من الإعدادات تحوّله إلى شيء مبني لمن يُشغّله هو. لا شيء منها غريب أو معقّد؛ هي فقط مُعطَّلة، أو غير مُنحازة لخيار معيّن، بحالتها الافتراضية.

كفّ عن الإجابة عن أسئلة بخصوص نفسك. بشكل افتراضي، يُبلِّغ المُحلِّل بسرور عن إصدار برنامجه واسم مضيفه عبر صنف CHAOS — أي version.bind وhostname.bind — وهذا استطلاع مجاني لأي شخص يقرر ما إذا كان جهازك يستحق الانتباه. الإعدادان hide-identity وhide-version لا يُكلّفان شيئًا ويُزيلان بصمة.

افشل مغلقًا، لا مفتوحًا. التحقق من DNSSEC هو الفارق بين مُحلِّل يكتشف إجابة منتحَلة ومُحلِّل يُقدّمها. يرفض harden-dnssec-stripped قبول إجابة غير موقَّعة لمنطقة يُفترض أن تكون موقَّعة، ويُغلق harden-glue وharden-below-nxdomain منفذين كلاسيكيين لتسميم الذاكرة المؤقتة، ويسمح aggressive-nsec للمُحلِّل بالإجابة عن أسماء غير موجودة مباشرةً من سجلّات رفض مخزَّنة مؤقتًا بدلاً من السؤال مجدَّدًا. يُضيف use-caps-for-id تبديلاً عشوائيًا لحالة الأحرف كعشوائية إضافية ضد الانتحال الأعمى — رخيص، وأحيانًا غير مُتوافق مع خادم مرجعي سيئ البناء، وهذا يستحق أن تعرفه قبل أن تُنفق بعد ظهر كامل على نطاق لن يُحلّ.

لا تكتب شيئًا. لا يُسجّل Unbound الاستعلامات إلا إذا طُلب منه ذلك، لكن الإعدادات التي تفعل ذلك تبعد سطرًا واحدًا غير معلَّق عليه، وبعض حزم التوزيعات تُشحَن بافتراضي أكثر ثرثرة. اضبط verbosity: 0 وحدِّد log-queries: no صريحًا، حتى تكون النيّة ظاهرة في الملف لا مُستنتَجة من غيابها. ثم تذكّر الجزء الذي ليس إعدادًا: الذاكرة المؤقتة نفسها سجلّ. يطبع أمر unbound-control dump_cache على جهاز يعمل تاريخًا حديثًا لما بحث عنه ذلك الجهاز، وهو يعيش في ذاكرة جهاز يستطيع شخص آخر الوصول إليه. وهو ينتهي من تلقاء نفسه، وهذا هو السبب الكامل وراء التوتّر الخفيف بين أعمار الذاكرة المؤقتة القصيرة والخصوصية، وهو السبب في ألّا تُبقي مُحلِّلاً يعمل لأشهر على مضيف لا تثق به على الإطلاق.

خزِّن مؤقتًا عن قصد. كل إجابة تُقدَّم من الذاكرة المؤقتة هي مراقبة لا تحدث أبدًا في الاتجاه الصاعد، فالذاكرة المؤقتة السليمة ميزة خصوصية لا ميزة سرعة فقط. يُجدِّد prefetch السجلات الشائعة قبل انتهاء صلاحيتها، فتتوقف الحالة الشائعة عن لمس الشبكة كليًا؛ ويُبقيك serve-expired متصلاً حين يكون خادم مرجعي غير قابل للوصول لفترة قصيرة. ورفع cache-min-ttl يُقلّل الثرثرة الصاعدة أكثر، لكنه يتجاوز خيارات متعمَّدة من مُشغّلي النطاقات — فقيم TTL المنخفضة هي كيفية عمل شبكات توصيل المحتوى والتبديل عند العطل — فحدّ أدنى من دقيقة أو دقيقتين معقول، وساعة كاملة ستُحاصرك في النهاية على عنوان ميت.

SP·06

طريقان للدخول: النفق، أو DNS-over-TLS

على أجهزتك أن تصل إلى المُحلِّل بطريقة ما، والاختيار بين الخيارين المعقولين هو في الغالب سؤال عمّا أنت راغب في نشره.

النفق هو الجواب الأفضل لِمَا يقارب الجميع. إذا كان حاسوبك المحمول وهاتفك يحتفظان بجلسة WireGuard مع ذلك الخادم بالفعل، يستطيع المُحلِّل الاستماع على عنوان النفق والتحدث بـDNS العادي على المنفذ 53. حركة المرور مشفّرة بالفعل ومُصادَق عليها بالفعل من طرف النفق، فلا توجد شهادة يجب الحصول عليها، ولا منفذ جديد مفتوح على الإنترنت، ولا حزمة TLS مكشوفة للغرباء، و — وهذا الجزء المُقلَّل من قيمته — لا اسم مضيف في أي مكان. يترك دليل WireGuard على هذا الموقع العملاء موجَّهين إلى DNS = 9.9.9.9 فقط لأنه لم يكن هناك شيء أفضل يُكتب هناك بعد. وهذا ما يُكتب في ذلك السطر بدلاً منه: عنوان النفق لخادمك أنت.

أما DNS-over-TLS فهو للجهاز الذي لا يستطيع الاحتفاظ بنفق. حقل Private DNS في Android هو أقوى حالة استخدام له — فهو يُطبَّق على مستوى النظام كله، وينجو من إعادة التشغيل، ويغطّي تطبيقات لا تستطيع لمسها بطريقة أخرى. والتكلفة هي اسم مضيف بشهادة صالحة، والشهادة تعني قيدًا عامًا ودائمًا في سجلّات شفافية الشهادات (Certificate Transparency) يربط ذلك الاسم باللحظة التي أنشأته فيها. وسيربط DNS السلبي (Passive DNS) الاسمَ بعنوان الخادم بعد ذلك. وإذا كانت غاية التمرين هي إبقاء اسمك بعيدًا عن البنية التحتية، فاستخدم اسم مضيف لا يقود إلى أي مكان قريب منك وسجّله بالعناية الموصوفة في تسجيل نطاق دون الكشف عن هويتك — وليس نطاقًا فرعيًا للنطاق الذي تستخدمه لكل شيء آخر، فذلك يربط الاثنين بشكل دائم.

وهناك تكلفة ثانية أدقّ. نقطة نهاية DoT التي تستطيع الهواتف المتجوّلة الوصول إليها لا يمكن تقييدها بعنوان المصدر، فهي بحكم تعريفها مُحلِّل يستطيع الغرباء استخدامه إن عرفوا الاسم. وهي ليست مُضخِّمًا — فـTLS عبر TCP يتطلّب مصافحة مكتملة، فلا يمكن انتحال المصدر ولا يوجد شيء لتنعكس منه — لكنها سعة تتنازل عنها، وخدمة تستحق أن يُمسَح عنها. أبقِ حدود المعدّل لكل عنوان IP مُفعَّلة، واختر اسم مضيف لن يخمّنه أحد، وعامِلْه كاستثناء متعمَّد لجهاز أو اثنين لا كالباب الافتراضي.

DNS-over-HTTPS خيار ثالث، وهو عادةً الخيار الخاطئ هنا. فهو يحتاج خادم ويب أمام المُحلِّل، وهذا أجزاء متحرّكة أكثر وسطح هجوم أكبر، من أجل فائدة واحدة هي أن يكون غير قابل للتمييز عن حركة مرور الويب. تلك الفائدة حاسمة إن كنت تتجاوز شبكة تحجب DoT، وغير ذات صلة إن لم تكن كذلك.

SP·07

الحجب منتج مختلف؛ فاحسم أمرك قبل أن تُضيفه

عاجلاً أو آجلاً سيقترح أحدهم إضافة قوائم حجب، والعرض جذّاب فعلاً: الترشيح عند المُحلِّل يغطّي كل جهاز على النفق، بما في ذلك التلفاز الذكي وتطبيقات الهاتف التي لا تستطيع أي إضافة الوصول إليها. وعلى الأجهزة المحمولة خاصةً، هو المكان العملي الوحيد للتدخّل. وهو أيضًا الميزة الأكثر ترجيحًا لجعلك تفقد الثقة بصمت في بنيتك التحتية الخاصة، ويستحق أن تفهم السبب قبل أن يحدث هذا لا خلاله.

التكلفة الأولى أن الأعطال لا تبدو كأعطال. مُحلِّل معطَّل يُعلن عن نفسه؛ أما نطاق محجوب فيظهر كزرّ دفع لا يفعل شيئًا، أو تطبيق عالق على أيقونة تحميل دوّارة، أو رسالة بريد لا تصل أبدًا. تظهر العلامة أسابيع بعد أن ثبّتَّ القائمة، على جهاز لم تكن تُفكّر فيه، ولا شيء يربطها بقرار DNS اتخذته في شهر آخر. كل قائمة حجب تُثبّتها هي سياسة كتبها شخص غريب وتُطبَّق بصمت على بيتك. إذا أضفت واحدة، دوِّن أنك فعلت، واجعلها صغيرة وموثوقة، واحتفظ بطريقة بأمر واحد لإيقافها — فأول خطوة لتصحيح أي خلل غير مفهوم على شبكتك تصبح "تجاوز المرشِّح وأعد المحاولة"، وتلك الخطوة يجب أن تكون رخيصة.

التكلفة الثانية أنه لا يفعل ما يأمله الناس. تطبيق بعنوان مُحلِّل مُرمَّز داخل الشيفرة، أو بعميل DoH خاص به مُدمَج، لا يسأل مُحلِّلك شيئًا على الإطلاق؛ بل يفتح اتصالاً بعنوان IP مُرمَّز مسبقًا وينتهي الأمر. والمتصفحات تحلّ الأسماء بشكل متزايد عبر DoH خاص بها إلا إذا طُلب منها غير ذلك. حجب DNS طبقة نظافة تُزيل كثيرًا من ضجيج التتبّع والإعلانات منخفض الجهد، وهو ليس ضابطًا أمنيًا، لأن أي شيء عدائي يلتف حوله بحكم تصميمه.

إن كنتَ تريده على أي حال، فضِّل منطقة محلية صغيرة في Unbound على خدمة (daemon) ثانية — فـlocal-zone: "tracker.example." always_nxdomain لا يحتاج برنامجًا إضافيًا، ولا واجهة ويب على منفذ يتوجّب عليك الدفاع عنه بعد ذلك، ولا خدمة جديدة يمكن أن تنهار وتسحب معها تحليل أسمائك. اجعل توصيف وظيفة الجهاز في سطر واحد: هو يحلّ الأسماء. كل مسؤولية إضافية تعطيها له هي طريقة أخرى لتوقّف كل شيء عن العمل في آنٍ واحد.

SP·08

المُحلِّل الذي تُشغّله اعتمادية تملكها أنت

عندما يتعطّل موقع تستضيفه، يعجز بعض الناس عن قراءة شيء ما. لكن عندما يتعطّل مُحلِّلك، لا يعمل شيء — لا المتصفح، ولا البريد، ولا مدير الحزم، ولا التطبيق الذي كان سيُخبرك أن الخادم معطَّل. إنها الخدمة الأكثر حِملاً بين كل ما يمكن أن تضعه على جهاز رخيص، وهي تتعطّل بطرق لا تبدو كأنها متعلقة بـDNS.

يستحق أنماط العطل الواقعية أن تُعرَف مسبقًا لأن كل واحد منها له توقيع مختلف. يُعاد تشغيل VPS ولم يكن Unbound مُفعَّلاً عند الإقلاع أبدًا، فيعمل كل شيء إلى أن تحدث أول إعادة تشغيل غير مخطَّطة. قائمة حجب ضخمة تدفع الذاكرة المؤقتة إلى swap على مثيل بسعة 1 GB فيختار قاتل OOM المُحلِّل. نطاق ما يكسر توقيعات DNSSEC الخاصة به، فيرفض مُحلِّلك المضبوط بشكل صحيح الإجابة بينما يستمر كل من يستخدم مُحلِّلاً لا يتحقق في التصفّح — جهازك مُحقّ والموقع لا يزال يبدو معطَّلاً لك، وهي خمس دقائق مُحيِّرة إن كنت قد نسيت أنك تتحقق. أو ينقطع النفق، ولأن DNS = 10.66.0.1 لا يوجد إلا داخل النفق، لا يملك الجهاز أي مُحلِّل على الإطلاق ويُبلِّغ أنه غير متصل.

لحسن الحظ أن سبل التخفيف رخيصة. فعِّل الخدمة عند الإقلاع واختبرها فعليًا بإعادة تشغيل بدلاً من الافتراض. أعطِ العملاء مُحلِّلاً ثانويًا حتى يتراجع النفق الميت بدلاً من التوقّف — مُحلِّل عام في تلك الخانة تنازل خصوصية صغير وصريح لا يُطبَّق إلا حين يكون مُحلِّلك الخاص غير قابل للوصول، وهو عادةً المقايضة الصحيحة. أبقِ serve-expired مُفعَّلاً حتى لا يتحوّل انقطاع صاعد قصير إلى انقطاع خاص بك. افحص المُحلِّل من مكان آخر، لا من الجهاز نفسه، وهي الطريقة الوحيدة لتلاحظ الفرق بين "معطَّل" و"غير قابل للوصول".

واحتفظ بنسخة من الإعدادات. الأمر كله بضعة عشرات من الأسطر التي استغرقت منك بعد ظهر كامل لضبطها بشكل صحيح ولن تتذكرها بعد عام؛ فمكانها في نسخك الاحتياطية المشفّرة خارج الموقع إلى جانب مفاتيح WireGuard، حتى تكون إعادة البناء عشرين دقيقة لا بعد ظهر ثانٍ. وهذا هو الملخّص الصادق لهذا التمرين كله: جهاز صغير يقوم بمهمة واحدة، بسعر أرخص خطة في القائمة، يستبدل وعدًا بشأن الاحتفاظ بترتيب لا يُنشأ فيه السجلّ مطلقًا.

SP·09

خطوة بخطوة

  1. 01

    ابدأ من جهاز مُحصَّن مسبقًا

    المُحلِّل خدمة صغيرة وهادئة، وهذا ما يجعل تثبيته على أي جهاز متاح أمرًا مُغريًا. لا تفعل ذلك — هذا الجهاز سيرى كل اسم يبحث عنه كل جهاز على نفقك، فهو يستحق نفس المعاملة التي تُعطيها لأي شيء آخر يحمل أسرارًا. اختر أصغر خطة تريدها؛ 1 GB من الذاكرة يكفي بيتًا كاملاً، لأن أحجام الذاكرة المؤقتة أدناه تُقاس بعشرات الميغابايتات. اعمل خلال الساعة الأولى بعد النشر قبل أي شيء آخر: مستخدم مُسمّى، وSSH بالمفتاح فقط، ورفض افتراضي على عائلتي IP، وتحديثات أمان تلقائية.

    ثم ثبِّت Unbound. تأتي حزمة التوزيعة بتلميحات الجذر ومرساة ثقة DNSSEC الجذرية وتُفعِّل استبدالها الدوري التلقائي، وهذه واحدة من الحالات القليلة التي تُنقذك فيها النسخة المُعبَّأة فعليًا من فئة كاملة من الأعطال المستقبلية.

    sudo apt update && sudo apt install -y unbound dnsutils
    unbound -V | head -n 3
    
    # the packaged trust anchor the resolver will validate against
    sudo ls -l /var/lib/unbound/root.key

    إذا كان root.key غائبًا، فإن حزمتك لم تُشغّل unbound-anchor وسيفشل التحقق مغلقًا على كل شيء. أنشئه مرة واحدة بتشغيل sudo -u unbound unbound-anchor -a /var/lib/unbound/root.key قبل الاستمرار.

  2. 02

    استرجِع المنفذ 53 من systemd-resolved

    في معظم التوزيعات الحالية، يمتلك شيء ما المنفذ 53 فعلاً: يُشغّل systemd-resolved مستمعًا وسيطًا على 127.0.0.53، و/etc/resolv.conf رابط رمزي يشير إليه. سيرفض Unbound أن يبدأ، أو سيبدأ ولا يرتبط بشيء مفيد، إلى أن يُحلّ ذلك. انظر قبل أن تُعدِّل.

    ss -ulpn 'sport = :53'
    ls -l /etc/resolv.conf

    اقرأ هذه الفقرة قبل تشغيل الكتلة التالية: بين تعطيل المستمع الوسيط وبدء تشغيل Unbound، لا يملك هذا الجهاز أي DNS يعمل على الإطلاق. أنهِ الخطوتين 3 و4 في جلسة واحدة، ولا تُشغّل عملية apt في نافذة أخرى أولاً — فستتعلّق عند البحث عن اسم وستُشخِّصها خطأً كأنها المُحلِّل الذي لم تُشغِّله بعد.

    # stop resolved from holding the port (appends inside the [Resolve] section)
    printf 'DNSStubListener=no\n' | sudo tee -a /etc/systemd/resolved.conf
    sudo systemctl restart systemd-resolved
    
    # point the host at the resolver it is about to run
    sudo rm -f /etc/resolv.conf
    printf 'nameserver 127.0.0.1\noptions edns0 trust-ad\n' | sudo tee /etc/resolv.conf
    
    # the port should now be free
    ss -ulpn 'sport = :53'
  3. 03

    اكتب إعدادًا يُحلِّل عوديًا ولا يحتفظ بشيء

    اترك الإعداد المُعبَّأ كما هو وأضف ملفك الخاص في دليل الملفات التكميلية، حتى لا تُراجِع ترقيةُ حزمة قراراتِك بصمت أبدًا. كل سطر أدناه يتعلّق إما برفض الغرباء، أو بالتحليل العودي من الجذر، أو بعدم الاحتفاظ بسجلّات. استبدل 10.66.0.1 و10.66.0.0/24 بعنوان النفق وشبكته الفرعية من خادم WireGuard الخاص بك إذا اختلفا.

    sudo tee /etc/unbound/unbound.conf.d/private-resolver.conf > /dev/null <<'EOF'
    server:
        # listen for the host itself and for the tunnel — never on 0.0.0.0
        interface: 127.0.0.1
        interface: 10.66.0.1
        port: 53
    
        # default-deny: refuse the internet, then allow what you trust
        access-control: 0.0.0.0/0 refuse
        access-control: ::/0 refuse
        access-control: 127.0.0.0/8 allow
        access-control: 10.66.0.0/24 allow
    
        # recurse from the root and send each server only the label it needs
        qname-minimisation: yes
        harden-dnssec-stripped: yes
        harden-below-nxdomain: yes
        harden-glue: yes
        aggressive-nsec: yes
        use-caps-for-id: yes
    
        # answer nothing about the software or the host
        hide-identity: yes
        hide-version: yes
    
        # keep no query log, and say little to the journal
        verbosity: 0
        log-queries: no
        log-replies: no
    
        # a warm cache is an upstream observation that never happens
        cache-min-ttl: 120
        cache-max-ttl: 86400
        prefetch: yes
        prefetch-key: yes
        serve-expired: yes
    
        # belt and braces if a rule above is ever loosened
        ratelimit: 1000
        ip-ratelimit: 100
    
        # sizing for a small instance
        num-threads: 2
        so-reuseport: yes
        msg-cache-size: 32m
        rrset-cache-size: 64m
    EOF

    لاحظ ما لا يوجد في الملف: لا يوجد forward-zone. غيابه هو ما يجعل هذا مُحلِّلاً عوديًا لا ذاكرة تخزين مؤقت أمام ذاكرة شخص آخر. إذا لصقتَ لاحقًا مقتطفًا من درس تعليمي يضيف واحدًا، فقد نقضتَ بصمت كل غاية هذا التمرين.

  4. 04

    شغِّله، ثم أثبِت أن DNSSEC يتحقق فعلاً

    تحقّق من الصياغة قبل إعادة تشغيل أي شيء — على جهاز يشير resolv.conf الخاص به الآن إلى Unbound، خطأ في الإعدادات يعني عدم وجود أي تحليل أسماء بينما تُصحِّح الخلل.

    sudo unbound-checkconf
    sudo systemctl enable --now unbound
    systemctl --no-pager status unbound | head -n 5

    الآن تحقّق من السلوكين المهمّين، لأن المُحلِّل الذي يُجيب ليس كالمُحلِّل الذي يتحقّق. يجب أن يعود الاسم المُوقَّع مع العلَم ad — بيانات مُصادَق عليها — ويجب أن يفشل اسم بتوقيعات مكسورة عمدًا مغلقًا برمز SERVFAIL بدلاً من أن يُحلّ.

    # should show: flags: qr rd ra ad
    dig @127.0.0.1 example.com +dnssec | grep -E '^;; flags'
    
    # should show: status: SERVFAIL  (not NOERROR, not an address)
    dig @127.0.0.1 dnssec-failed.org | grep -E '^;; ->>HEADER'
    
    # and a normal name should simply work
    dig @127.0.0.1 +short cloudflare.com

    إذا أُحلّت المنطقة المكسورة إلى عنوان، فإن التحقق لا يعمل: تأكّد من أن /var/lib/unbound/root.key موجود وقابل للقراءة من قِبل مستخدم unbound. وإذا كان كل شيء SERVFAIL، فالسبب المعتاد ساعة مُختلَّة بشكل كبير — فالتوقيعات لها نوافذ صلاحية، وجهاز متأخّر بساعات عن التزامن يرفض الإنترنت كله.

  5. 05

    أغلق الباب العام، ولا تفتح إلا النفق

    الإعدادات ترفض الغرباء بالفعل. هذه الخطوة تجعل الأمر بحيث لا يوجد شيء يستطيع الغريب الوصول إليه من الأساس — القفل الثاني من القفلين، وهو الذي ينجو من أي تعديل مستقبلي على الأول.

    # DNS is reachable from the tunnel interface only
    sudo ufw allow in on wg0 to any port 53 proto udp
    sudo ufw allow in on wg0 to any port 53 proto tcp
    sudo ufw status verbose

    ثم تحقّق منه بالطريقة الوحيدة التي تُحتسَب، من جهاز مختلف. الاختبار من الخادم نفسه لا يُثبت شيئًا على الإطلاق — فـloopback مسموح به عمدًا. شغِّل هذا من حاسوبك المحمول مع نفق معطَّل، أو من أي مضيف آخر تملكه.

    # must time out. an answer here means you are running an open resolver.
    dig @SERVER_PUBLIC_IP example.com +time=3 +tries=1
    
    # same question over IPv6, which is the half people forget
    dig -6 @SERVER_IPV6 example.com +time=3 +tries=1

    إذا أعاد أيّهما إجابة، فأوقف واصلح الأمر الآن بدلاً من بعد تقرير سوء الاستخدام. الأسباب المعتادة هي interface: 0.0.0.0 باقٍ في ملف إعدادات مُعبَّأ، أو قاعدة جدار حماية تسمح بالمنفذ 53 عالميًا من تجربة سابقة، أو Docker ينشر منفذ حاوية يتجاوز ufw كليًا.

  6. 06

    وجِّه أجهزتك إليه

    من جانب العميل، هذا تغيير سطر واحد. في إعدادات عميل WireGuard، يصبح سطر DNS عنوان نفق خادمك بدلاً من مُحلِّل عام — وهذا هو التعديل الذي يُقاعِد DNS = 9.9.9.9 من دليل WireGuard.

    [Interface]
    PrivateKey = <paste client.key>
    Address = 10.66.0.2/32, fd86:ea04:1115::2/128
    DNS = 10.66.0.1
    
    [Peer]
    PublicKey = <paste server.pub>
    Endpoint = YOUR_SERVER_IP:51820
    AllowedIPs = 0.0.0.0/0, ::/0
    PersistentKeepalive = 25

    شغِّل النفق وتأكّد من أمرين مستقلّين من جانب العميل: أن الإجابات تأتي من مُحلِّلك، وأن التحليل العودي يخرج (egress) فعليًا من VPS الخاص بك لا من مكان آخر. الفحص الثاني هو المفيد — whoami.akamai.net يُعيد عنوان أي مُحلِّل سأل، فينبغي أن يطبع عنوان IP العام لخادمك ولا شيء آخر.

    # answers should come from the tunnel address
    dig example.com | grep -E 'SERVER:'
    
    # should print your VPS public IP — this is the leak test
    dig +short whoami.akamai.net
    
    # and the ad flag should still be there, end to end
    dig example.com +dnssec | grep -E '^;; flags'
  7. 07

    أضِف DNS-over-TLS فقط لجهاز لا يستطيع الاحتفاظ بالنفق

    تجاوز هذه الخطوة إلا إذا كان لديك جهاز محدَّد — عادةً هاتف Android، عبر إعداد Private DNS على مستوى النظام — تريد تغطيته دون نفق دائم. يتطلّب ذلك اسم مضيف وشهادة، ويُصبح اسم المضيف هذا سجلاً عامًا ودائمًا في سجلّات شفافية الشهادات (Certificate Transparency)، فاختر اسمًا لا يقود إلى أي مكان قريب من هوياتك الأخرى.

    sudo apt install -y certbot
    sudo ufw allow 80/tcp comment 'certbot, temporarily'
    sudo certbot certonly --standalone -d dns.example.net
    sudo ufw delete allow 80/tcp
    
    # unbound must be able to read the key
    sudo usermod -a -G ssl-cert unbound 2>/dev/null || true
    sudo chgrp -R ssl-cert /etc/letsencrypt/live /etc/letsencrypt/archive
    sudo chmod -R g+rX /etc/letsencrypt/live /etc/letsencrypt/archive

    أضِف مستمع TLS كملفٍ تكميليٍّ خاص به، حتى تستطيع حذفه بحركة واحدة إذا غيّرت رأيك.

    # NOTE: drop-in files are read in alphabetical order and the last
    # access-control line for a given prefix wins — so this file must
    # sort AFTER private-resolver.conf, or its refuse rule overrides
    # the allow below and every DoT client gets REFUSED.
    sudo tee /etc/unbound/unbound.conf.d/zz-dot.conf > /dev/null <<'EOF'
    server:
        interface: 0.0.0.0@853
        interface: ::0@853
        tls-service-key: "/etc/letsencrypt/live/dns.example.net/privkey.pem"
        tls-service-pem: "/etc/letsencrypt/live/dns.example.net/fullchain.pem"
        # roaming clients have no fixed address, so this endpoint must accept any.
        # safe only because port 53 stays bound to loopback + wg0 and blocked at
        # the firewall — TLS over TCP cannot be spoofed, so it cannot be reflected.
        access-control: 0.0.0.0/0 allow
        access-control: ::/0 allow
    EOF
    sudo ufw allow 853/tcp
    sudo unbound-checkconf && sudo systemctl restart unbound

    اختبر من خارج النفق قبل أن تثق به، ثم ضع اسم المضيف في حقل Private DNS في الهاتف. التجديد هو الجزء الذي يتعطّل بصمت بعد ثلاثة أشهر — إذ يستبدل certbot الشهادة لكن Unbound يحتفظ بالقديمة في الذاكرة، فأضِف خطّاف نشر (deploy hook) يُعيد تحميلها.

    kdig -d @dns.example.net +tls-ca +tls-host=dns.example.net example.com
    
    echo 'systemctl reload unbound' | sudo tee /etc/letsencrypt/renewal-hooks/deploy/unbound.sh
    sudo chmod +x /etc/letsencrypt/renewal-hooks/deploy/unbound.sh
SP·10 — الأسئلة الشائعة

إجابات سريعة

هل مُحلِّلي الخاص أسرع أم أبطأ من 1.1.1.1؟

كلاهما، في لحظات مختلفة. البحث البارد عن نطاق لم يزره أحد على شبكتك أبطأ، لأن التحليل العودي الكامل يعني سؤال الجذر، ثم TLD، ثم الخادم المرجعي، حيث يُجيب المُحلِّل العام عادةً من ذاكرة مؤقتة سخّنها ملايين الأشخاص الآخرين. أما البحث الدافئ فهو أسرع من أي مُحلِّل عام يمكن أن يكون، لأن الذاكرة المؤقتة عند طرف نفقك أنت لا عبر الإنترنت. في الاستخدام اليومي، تسود الحالة الدافئة: تُعيد البيوت زيارة بضع مئات من النطاقات، ويُجدِّد prefetch الشائعة منها قبل انتهاء صلاحيتها، ويرتفع معدّل الإصابة خلال يوم واحد. وإذا كان شعورك بأن الزيارة الأولى لموقع غير مألوف أبطأ بجزء بسيط يهمّك أكثر من السجلّ، فهذه مقايضة خاطئة وينبغي أن تختار التحويل بدلاً من ذلك.

هل يمنع هذا مزوّد خدمة الإنترنت من رؤية المواقع التي أزورها؟

ليس بمفرده. فهو يمنع مزوّد خدمة الإنترنت من قراءة عمليات بحثك فقط إذا سافرت تلك العمليات داخل نفق — وإلا فاستعلاماتك إلى VPS تظل UDP بنص صريح عبر شبكة مزوّدك، وأنت قد غيّرت الوجهة دون أن تُخفي شيئًا. وحتى مع النفق، يظل مزوّدك يرى جلسة مشفّرة إلى عنوان واحد، وإذا كنت تتصفّح خارج النفق فإنه يظل يرى عناوين IP الوجهة، وفي غياب Encrypted Client Hello، اسم الخادم في مصافحة TLS. عامِل المُحلِّل الخاص بصفته المكوّن الذي يُغلق قناة التسمية، والنفق بصفته المكوّن الذي يُغلق قناة النقل. لا أحدهما يُعوِّض عن الآخر.

هل يجدر بي فقط التحويل إلى Quad9 أو Cloudflare عبر DoT بدلاً من ذلك؟

هذا خيار مشروع، وهو الصحيح لكثير من الناس. التحويل عبر DoT أبسط، وأسرع في الإعداد، ويمنحك تخفّي حشدٍ كبير جدًا، ويهزم المُراقِب الذي يواجهه معظم الناس فعليًا — الشبكة المحلية ومزوّد الإنترنت. ما لا يفعله هو إزالة التجميع: فمنظمة واحدة لا تزال تستقبل تدفّق استعلاماتك كاملاً، مُعلَّمًا بدقّة الآن بعنوان مصدر واحد. اختر التحويل حين يكون نموذج تهديدك هو Wi-Fi المقهى ومزوّد إنترنتك؛ واختر العودية حين يكون التجميع نفسه هو ما تعترض عليه، أو حين لا تريد أن تُضطر لتقرر سياسة احتفاظ أي شركة تُصدِّقها.

هل يستطيع مزوّد استضافتي قراءة استعلامات DNS الخاصة بي؟

نعم، ويستحق الأمر أن تكون واضح النظر بشأنه. الاستعلامات العودية إلى خوادم الجذر وTLD والخوادم المرجعية تُغادر VPS عبر منفذ UDP 53 بلا تشفير — فلا يوجد DoT إلى خوادم الجذر. وأي شخص له رؤية على الصلة الصاعدة للخادم يستطيع قراءتها. تعني QNAME minimisation أن كل محادثة منفردة لا تكشف إلا جزءًا، وهي مخلوطة بكل ما يفعله الجهاز غيرها، لكنها ليست مخفية. ما فعلتَه هو نقل المُراقِب من مزوّد إنترنت استهلاكي في بلدك، وهو مُلزَم بالاحتفاظ بالبيانات وله مصلحة تجارية فيها، إلى شبكة استضافة اخترتها أنت. وهذا يجعله سؤالاً عن أي ولاية قضائية وأي مزوّد، لا سؤالاً تُجيب عنه الإعدادات.

هل أحتاج إلى اسم نطاق لهذا؟

لا، إذا كانت أجهزتك تصل إلى المُحلِّل عبر النفق، وهذا هو السبب العملي الأساسي لتفضيل هذا المسار: لا اسم مضيف، ولا شهادة، ولا سجلّ عام بوجود الخدمة. تحتاج نطاقًا فقط من أجل DNS-over-TLS، لأن العملاء يتحقّقون من الشهادة مقابل اسم. كن مدركًا أن الحصول على تلك الشهادة ينشر اسم المضيف في سجلّات شفافية الشهادات بشكل دائم، وأن DNS السلبي سيربطه بعنوان الخادم بعد ذلك بوقت قصير — فلا تستخدم نطاقًا فرعيًا لنطاق يشير إليك بالفعل. يتناول دليل تسجيل نطاق دون الكشف عن هويتك ما يتسرّب رغم ذلك حين تجرّب.

هل يحجب هذا الإعلانات وأدوات التتبّع؟

ليس افتراضيًا — فـUnbound العادي يُحلّل الأسماء، لا يُرشِّحها. يمكنك إضافة قوائم حجب أو مناطق محلية فوقه، وعلى الأجهزة المحمولة هو الطبقة الوحيدة التي تصل إلى حركة مرور التطبيقات على الإطلاق. حافظ على توقعات صادقة: التطبيقات التي تحمل عنوان مُحلِّل مُرمَّزًا مسبقًا أو عميل DoH مُدمَجًا لا تسأل مُحلِّلك شيئًا أبدًا، والمتصفحات تُحلّل الأسماء بشكل متزايد عبر نقل مشفّر خاص بها، وقائمة حجب ضخمة من طرف ثالث ستُعطِّل شيئًا في النهاية يومًا ما تكون قد نسيت أنها مُثبَّتة. هو يُزيل ضجيج تتبّع منخفض الجهد. وهو ليس ضابطًا أمنيًا، وأي شيء عدائي مُصمَّم للالتفاف حوله.

طبّقها عمليًا

VPS متصل خلال 15 min، والمخصص يُسلَّم خلال 2–12 h. اشحن بدءًا من $30.00 بالعملات المشفّرة — دون أي هوية مرتبطة.

انشر خادم VPS