واجهة برمجة تطبيقات بوابة HTTP المفتوحة في ميزة "التصفّح الآمن"
ملاحظة: لا تزال هذه المستندات قيد التطوير حاليًا. ومن المتوقّع حدوث تحسينات في المستقبل القريب.
واجهة برمجة تطبيقات بروتوكول HTTP في ميزة "التصفّح الآمن" هي واجهة برمجة تطبيقات للحفاظ على الخصوصية تم تصميمها استنادًا إلى بروتوكول RFC في مجموعة مهندسي شبكة الإنترنت (IETF) وتحمل اسم Oblivious HTTP وRFC 9458.
نظرة عامة
إنّ واجهة برمجة تطبيقات HTTP الشاملة في ميزة "التصفّح الآمن" هي خدمة من Google تتيح لتطبيقات العميل التحقّق من عناوين URL ومقارنتها بقائمة من موارد الويب غير الآمنة التي يتم تعديلها باستمرار من Google مع تنفيذ إجراءات إضافية لحماية الخصوصية.
ويتم تحقيق ذلك من خلال بروتوكول خفيف يُعرف باسم Oblivious HTTP أو OHTTP اختصارًا. وهو بروتوكول عديم الحالة يمكن أن يستخدمه عملاء ميزة "التصفّح الآمن" للوصول إلى واجهات برمجة تطبيقات الإصدار 5 من ميزة "التصفّح الآمن من Google"، للحصول على إجراءات حماية فعّالة وزيادة التغطية بدون التأثير سلبًا في أمان بيانات المستخدمين الخصوصية.
ملاحظة: لا يمكن الوصول إلى واجهات برمجة تطبيقات الإصدار 4 من ميزة "التصفّح الآمن من Google" من خلال هذه الخدمة.
بروتوكول HTTP واضح في ميزة "التصفّح الآمن"
بروتوكول RFC
بروتوكول Oblivious HTTP هو بروتوكول خفيف تم تحديده في RFC 9458 ويُستخدَم لتشفير رسائل HTTP وإرسالها من جهاز عميل إلى خادم مستهدف. يستخدم هذا خدمة إرسال موثوق بها بطريقة تحدّ من استخدام الخادم الهدف للبيانات الوصفية، مثل عنوان IP ومعلومات الاتصال لتحديد هوية العميل، ما يوفّر الخصوصية والأمان بالإضافة إلى بروتوكول HTTP/S العادي. يستخدم البروتوكول Binary HTTP، المحدد في RFC 9292، لترميز/فك ترميز طلبات/استجابات HTTP.
وعلى مستوى عالٍ، يقف الإرسال بين مورد "العميل" و"البوابة" الذي يعمل على توجيه زيارات العميل الوكيل عن طريق إزالة جميع معرّفات العميل، بما في ذلك السمات الحساسة للخصوصية مثل عناوين IP، مع إخفاء هوية طلبات HTTP الواردة إلى خدمة "المدخل" بشكل فعّال. تتمثل الفائدة الإضافية لبروتوكول OHTTP في أن جميع الطلبات تخضع للتشفير التام بين الأطراف، مما يعني أن تكون لدى العملاء لا تظهر طلبات "التصفُّح الآمن" (أي التجزئات المقطوعة لتعبيرات عناوين URL) لعملية الإرسال. يُرجى الرجوع إلى blogpost للاطّلاع على مثال على عملية التنفيذ في Chrome.
يمكن للعملاء اختيار أي موفِّر خدمة ترحيل (مثل Fastly) لدمجها مع الخدمة. يجب أن يستخدم الإرسال مصادقة Oauth 2.0 مع نطاق التفويض التالي للوصول إلى الخدمة.
// OAuth Authorization scope:
https://www.googleapis.com/auth/3p-relay-safe-browsing
نقاط نهاية واجهة برمجة التطبيقات
مفتاح OHTTP العام
ستوفّر نقطة النهاية هذه إعداد المفتاح العام لبروتوكول OHTTP كما هو محدَّد في RFC 9458 والذي سيستخدمه العميل لتشفير طلب OHTTP.
GET https://safebrowsingohttpgateway.googleapis.com/v1/ohttp/hpkekeyconfig?key=<API key>
مفتاح واجهة برمجة التطبيقات أعلاه ليس ضروريًا تمامًا، لا يختلف الخادم المفتاح العام لـ OHTTP استنادًا إلى مفتاح واجهة برمجة التطبيقات الذي تم توفيره. ويُسمَح للعملاء بالتحقق من هذه المسألة من خلال استخدام مفاتيح واجهة برمجة تطبيقات صالحة أخرى للوصول إلى نقطة النهاية هذه أو عدم استخدام مفاتيح واجهة برمجة تطبيقات تمامًا، والتأكّد من أنّ الاستجابة تحتوي على المفتاح العام لـ OHTTP نفسه. ولتسهيل تصحيح الأخطاء، يُنصح باستخدام مفتاح واجهة برمجة التطبيقات. يتيح ذلك للعملاء الاطّلاع على إحصاءات مثل عدد الطلبات على Google Cloud Console. إذا كان العميل يريد توفير مفتاح واجهة برمجة التطبيقات، يمكنك الاطّلاع على هذه المستندات حول كيفية إعداد مفاتيح واجهة برمجة التطبيقات.
كما هو موضّح في قسم اقتراحات الخصوصية، من أجل تحقيق أهداف الاتساق الرئيسية، ننصح مورّدي البرامج بإعداد بنية أساسية لتوزيع مفتاح مركزي لجلب المفتاح من نقطة النهاية هذه وتوزيعه لاحقًا على تطبيقات العميل.
وفقًا لإرشادات إدارة المفاتيح، يتم تدوير المفاتيح بانتظام على الخادم. على العملاء إعادة تحميل المفتاح، أي جلب النسخة المحلية من المفتاح وتعديلها من حين لآخر لتجنُّب تعذُّر فك التشفير.
على العملاء إعادة تحميل المفتاح العام (جلبه وتعديله) مرة واحدة يوميًا. إذا كانت آلية توزيع مركزية قيد الاستخدام، فإن هذه الآلية يجب أن تتأكد من جلب المفاتيح وتوزيعها مرة واحدة يوميًا.
طلب OHTTP مغلف
ستعرض نقطة النهاية هذه طلب OHTTP الذي تم تضمينه في نص HTTP لطلب POST من خلال تنفيذ فك تشفير الطلب، ثم تشفير استجابة OHTTP لتتم إعادة توجيهها مرة أخرى إلى Relay في استجابة HTTP. يجب أن يدرج "العميل" عنوان الطلب Content-Type مثل message/ohttp-req في طلب HTTP POST.
POST https://safebrowsingohttpgateway.googleapis.com/v1/ohttp:handleOhttpEncapsulatedRequest?key=<API key>
ملاحظة: وفقًا للإرشادات حول RFC، يجب ترميز الطلب الداخلي (يُرجى الرجوع إلى مستندات الإصدار 5 حول كيفية إنشاء طلب "التصفُّح الآمن") باستخدام بروتوكول Binary HTTP، RFC 9292.
مكتبات العملاء
تتوفر في Google Quiche عمليات تنفيذ من جهة العميل لكل من بروتوكولي OHTTP وBHTTP. يُنصَح باستخدام هذه المكتبات للعملاء. يمكنك الرجوع إلى الرمز الزائف أدناه للاطّلاع على كيفية إنشاء طلبات OHTTP للوصول إلى واجهة برمجة التطبيقات.
نموذج لعملية التنفيذ من جهة العميل
يجلب العملاء مفتاح Oblivious HTTP العام من نقطة نهاية المفتاح العام. بعد ذلك، قم بتهيئة تهيئة مفتاح quiche OHTTP مثل ذلك، وقم بتهيئة عميل quiche OHTTP.
auto ohttp_key_cfgs = quiche::ObliviousHttpKeyConfigs::ParseConcatenatedKeys(std::string public_key);
auto key_config = ohttp_key_cfgs->PreferredConfig();
auto public_key = ohttp_key_cfgs->GetPublicKeyForId(key_config.GetKeyId())
auto ohttp_client = quiche::ObliviousHttpClient::Create(public_key, key_config);
سيستخدم العميل ترميز HTTP الثنائي لإنشاء طلب BHTTP كخطوة أولى قبل التشفير.
quiche::BinaryHttpRequest::ControlData bhttp_ctrl_data{
.method = "POST",
.scheme = "https",
.authority = "safebrowsing.googleapis.com",
.path = "/v5/hashes:search?key=<API key>&hashPrefixes=<HASH prefix 1>&hashPrefixes=<HASH prefix 2>",
};
quiche::BinaryHttpRequest bhttp_request(bhttp_ctrl_data);
بعد ذلك، سيشفّر العميل طلب HTTP الثنائي الذي تم إنشاؤه في الخطوة أعلاه.
auto bhttp_serialized = bhttp_request.Serialize();
auto ohttp_request = ohttp_client.CreateObliviousHttpRequest(*bhttp_serialized);
// Client must include this in POST body, and add `Content-Type` header as "message/ohttp-req".
auto payload_include_in_post_body = ohttp_request.EncapsulateAndSerialize();
بعد استلام الردّ من خدمة الإرسال، سيفك العميل تشفير الرد. يتضمّن الردّ عنوان الاستجابة Content-Type بالشكل ohttp-res.
auto ctx = std::move(ohttp_request).ReleaseContext();
auto ohttp_response = ohttp_client.DecryptObliviousHttpResponse("data included in body of http_response", ctx);
بعد فك تشفير استجابة OHTTP بنجاح، يمكنك فك ترميز الناتج باستخدام Binary HTTP على هذا النحو.
auto bhttp_response = BinaryHttpResponse::Create(ohttp_response.GetPlaintextData());
if (bhttp_response.status_code() == 200) {
auto http_response = bhttp_response.body();
auto response_headers = bhttp_response.GetHeaderFields();
}