يتيح نظام Google OAuth 2.0 إمكانية التفاعل من خادم إلى خادم، مثل التفاعلات بين تطبيق الويب وخدمة Google. في هذا السيناريو، يجب أن يكون لديك حساب خدمة، وهو حساب ينتمي إلى تطبيقك بدلاً من حساب مستخدم فردي. يستدعي التطبيق واجهات Google APIs نيابة عن حساب الخدمة، لذلك لا يتم مشاركة المستخدمين بشكل مباشر. يُطلَق على هذا السيناريو أحيانًا &&;;;;؟9 OAuth,"&&;;;LOLO&" (تشير العبارة ذات الصلة &&;;; ترموستات OAuth "؛ إلى السيناريوهات التي يتصل فيها تطبيقك بواجهات برمجة تطبيقات Google نيابة عن المستخدمين النهائيين، ويجب فيها أحيانًا الحصول على موافقة المستخدم.)
عادةً ما يستخدم التطبيق حساب الخدمة عندما يستخدم التطبيق Google APIs للتعامل مع بياناته الخاصة بدلاً من بيانات المستخدم. على سبيل المثال، إنّ التطبيق الذي يستخدم تخزين البيانات في Google Cloud للاحتفاظ بالبيانات سيستخدم حساب خدمة لمصادقة طلباته لواجهة برمجة تطبيقات Google Cloud Datastore.
ويمكن لمشرفي نطاق Google Workspace أيضًا منح سلطة على مستوى النطاق لحسابات الخدمة للوصول إلى بيانات المستخدم نيابةً عن المستخدمين في النطاق.
يوضّح هذا المستند كيف يمكن للتطبيق إكمال مسار OAuth 2.0 من خادم إلى خادم باستخدام مكتبة عميل Google APIs (إجراء مُقترَح) أو بروتوكول HTTP.
نظرة عامة
لإتاحة التفاعل من خادم إلى خادم، عليك أولاً إنشاء حساب خدمة لمشروعك في . إذا كنت تريد الوصول إلى بيانات المستخدمين للمستخدمين في حسابك على Google Workspace، يمكنك تفويض الوصول على مستوى النطاق إلى حساب الخدمة.
بعد ذلك، يستعد تطبيقك لإجراء طلبات بيانات من واجهة برمجة التطبيقات المصرح بها باستخدام بيانات اعتماد حساب الخدمة لطلب رمز الدخول من خادم المصادقة OAuth 2.0.
وأخيرًا، يمكن أن يستخدم تطبيقك رمز الدخول لطلب بيانات من Google APIs.
إنشاء حساب خدمة
تشتمل بيانات اعتماد حساب الخدمة على عنوان بريد إلكتروني تم إنشاؤه فريد وزوج واحد على الأقل من المفاتيح العامة/الخاصة. إذا تم تفعيل التفويض على مستوى النطاق، سيكون معرِّف العميل جزءًا من بيانات اعتماد حساب الخدمة.
إذا كان تطبيقك يعمل على Google App Engine، يتم إعداد حساب خدمة تلقائيًا عند إنشاء مشروعك.
إذا كان تطبيقك يعمل على Google Compute Engine، يتم أيضًا إعداد حساب خدمة تلقائيًا عند إنشاء مشروعك، ولكن عليك تحديد النطاقات التي يحتاج تطبيقك إلى الوصول إليها عند إنشاء مثيل Google Compute Engine. لمزيد من المعلومات، راجِع إعداد مثيل لاستخدام حسابات الخدمة.
إذا لم يتم تشغيل تطبيقك على Google App Engine أو Google Compute Engine، يجب الحصول على بيانات الاعتماد هذه في . لإنشاء بيانات اعتماد حساب الخدمة، أو لعرض بيانات الاعتماد العلنية التي أنشأتها سابقًا، نفِّذ ما يلي:
أولاً ، قم بإنشاء حساب خدمة:
- افتح Service accounts page.
- If prompted, select a project, or create a new one.
- انقر فوق إنشاء حساب الخدمة .
- ضمن تفاصيل حساب الخدمة ، اكتب اسمًا ومعرفًا ووصفًا لحساب الخدمة ، ثم انقر فوق إنشاء ومتابعة .
- اختياري: ضمن منح حق الوصول إلى حساب الخدمة هذا للمشروع ، حدد أدوار IAM لمنح حساب الخدمة.
- انقر فوق متابعة .
- اختياري: ضمن منح المستخدمين حق الوصول إلى حساب الخدمة هذا ، أضف المستخدمين أو المجموعات المسموح لها باستخدام حساب الخدمة وإدارته.
- انقر فوق تم .
بعد ذلك ، قم بإنشاء مفتاح حساب الخدمة:
- انقر فوق عنوان البريد الإلكتروني لحساب الخدمة الذي أنشأته.
- انقر فوق علامة التبويب المفاتيح .
- في القائمة المنسدلة إضافة مفتاح ، حدد إنشاء مفتاح جديد .
- انقر فوق إنشاء .
يتم إنشاء زوج المفاتيح العام / الخاص الجديد وتنزيله على جهازك ؛ إنه بمثابة النسخة الوحيدة من المفتاح الخاص. أنت مسؤول عن تخزينه بشكل آمن. إذا فقدت زوج المفاتيح هذا ، فستحتاج إلى إنشاء زوج جديد.
يمكنك الرجوع إلى API Console في أي وقت لعرض عنوان البريد الإلكتروني وملفات مرجعيّة للمفتاح العام ومعلومات أخرى، أو لإنشاء أزواج إضافية من المفاتيح العامة/الخاصة. ولمزيد من التفاصيل حول بيانات اعتماد حساب الخدمة في API Console، يُرجى الاطّلاع على حسابات الخدمة في ملف المساعدة API Console.
دوّن عنوان البريد الإلكتروني لحساب الخدمة واحفظ ملف المفتاح الخاص لحساب الخدمة في موقع يمكن الوصول إليه عبر تطبيقك. يحتاج تطبيقك إلى إجراء طلبات بيانات من واجهة برمجة التطبيقات مسموح بها.
تفويض التفويض على مستوى النطاق لحساب الخدمة
إذا كان لديك حساب على Google Workspace، يمكن لمشرف المؤسسة تفويض تطبيق للوصول إلى بيانات المستخدمين نيابةً عن المستخدمين في نطاق Google Workspace. على سبيل المثال، إنّ التطبيق الذي يستخدم Google Calendar API لإضافة أحداث إلى تقاويم جميع المستخدمين في نطاق Google Workspace سيستخدم حساب خدمة للوصول إلى Google Calendar API نيابةً عن المستخدمين. إنّ تفويض حساب خدمة للوصول إلى البيانات بالنيابة عن مستخدمين في نطاق معيّن يُشار إليه أحيانًا باسم "&تفويض تفويض على مستوى النطاق" لحساب خدمة.
لتفويض تفويض على مستوى النطاق لحساب خدمة، على المشرف المتميّز لنطاق Google Workspace إكمال الخطوات التالية:
- من نطاق Google Workspace ووحدة تحكم المشرف، انتقِل إلى القائمة الرئيسية > Security > Access and data control > API API.
- في لوحة التفويض على مستوى النطاق، اختَر إدارة التفويض على مستوى النطاق.
- انقر على إضافة جديد.
- في حقل معرِّف العميل، أدخِل معرّف العميل لحساب الخدمة. يمكنك العثور على معرِّف العميل لحساب الخدمة في Service accounts page.
- في الحقل نطاقات OAuth (مفصولة بفواصل)، أدخِل قائمة النطاقات التي يجب منح تطبيقك إذن الوصول إليها. على سبيل المثال، إذا كان تطبيقك يحتاج إلى الوصول الكامل على مستوى النطاق إلى واجهة برمجة تطبيقات Google Drive وواجهة برمجة تطبيقات "تقويم Google"، أدخِل: https://www.googleapis.com/auth/drive, https://www.googleapis.com/auth/calendar.
- انقر على تفويض.
يملك تطبيقك الآن صلاحية إجراء طلبات بيانات من واجهة برمجة التطبيقات كمستخدمين في نطاقك (للمستخدمين "im;"ate" المستخدمين). عند الاستعداد لإجراء طلبات بيانات من واجهة برمجة التطبيقات المسموح بها، يمكنك تحديد انتحال هوية المستخدم.
جارٍ الإعداد لإجراء استدعاء معتمد لواجهة برمجة التطبيقات
Java
بعد الحصول على عنوان البريد الإلكتروني للعميل والمفتاح الخاص من
API Console، استخدِم
مكتبة برامج Google APIs للغة Java
لإنشاء كائن GoogleCredential
من بيانات اعتماد حساب الخدمة
والنطاقات التي يحتاج إليها تطبيقك للوصول إليها. مثلاً:
import com.google.api.client.googleapis.auth.oauth2.GoogleCredential; import com.google.api.services.sqladmin.SQLAdminScopes; // ... GoogleCredential credential = GoogleCredential.fromStream(new FileInputStream("MyProject-1234.json")) .createScoped(Collections.singleton(SQLAdminScopes.SQLSERVICE_ADMIN));
في حال تطوير تطبيق على Google Cloud Platform، يمكنك استخدام بيانات الاعتماد التلقائية للتطبيق التي يمكن تبسيط العملية.
تفويض التفويض على مستوى النطاق
إذا فوّضت إذن الوصول على مستوى النطاق إلى حساب الخدمة وكنت تريد انتحال حساب مستخدم، حدِّد عنوان البريد الإلكتروني لحساب المستخدم باستخدام طريقة createDelegated
لكائن GoogleCredential
. على سبيل
المثال:
GoogleCredential credential = GoogleCredential.fromStream(new FileInputStream("MyProject-1234.json")) .createScoped(Collections.singleton(SQLAdminScopes.SQLSERVICE_ADMIN)) .createDelegated("user@example.com");
يمكنك استخدام الكائن GoogleCredential
لاستدعاء واجهات Google API في تطبيقك.
Python
بعد الحصول على عنوان البريد الإلكتروني للعميل والمفتاح الخاص من API Console، استخدِم مكتبة برامج Google APIs للغة Python لإكمال الخطوات التالية:
- يمكنك إنشاء كائن
Credentials
من بيانات اعتماد حساب الخدمة والنطاقات التي يحتاج تطبيقك إلى الوصول إليها. مثلاً:from google.oauth2 import service_account SCOPES = ['https://www.googleapis.com/auth/sqlservice.admin'] SERVICE_ACCOUNT_FILE = '/path/to/service.json' credentials = service_account.Credentials.from_service_account_file( SERVICE_ACCOUNT_FILE, scopes=SCOPES)
في حال تطوير تطبيق على Google Cloud Platform، يمكنك استخدام بيانات الاعتماد التلقائية للتطبيق التي يمكن تبسيط العملية.
- تفويض التفويض على مستوى النطاق
إذا كنت قد فوّضت إمكانية الوصول على مستوى النطاق إلى حساب الخدمة وتريد انتحال حساب مستخدم، استخدِم طريقة
with_subject
لكائنServiceAccountCredentials
حالي. مثلاً:delegated_credentials = credentials.with_subject('user@example.org')
استخدم كائن بيانات الاعتماد لاستدعاء واجهات برمجة تطبيقات Google في تطبيقك.
HTTP/REST
بعد الحصول على معرِّف العميل والمفتاح الخاص من API Console، يجب أن يكمل طلبك الخطوات التالية:
- أنشئ رمز JSON المميّز للويب (JWT، وطريقة اللفظ، "jot")، يتضمّن عنوانًا ومجموعة مطالبات وتوقيعًا.
- طلب رمز الدخول من خادم تفويض Google OAuth 2.0.
- التعامل مع استجابة JSON التي يعرضها خادم التفويض
توضّح الأقسام التالية كيفية إكمال هذه الخطوات.
إذا كانت الاستجابة تتضمن رمز دخول، يمكنك استخدام رمز الدخول لاستدعاء واجهة برمجة تطبيقات Google. (إذا لم تتضمّن الاستجابة رمزًا مميزًا للوصول، قد يكون رقم JWT ورمز الرمز المميّز غير مكتوب بشكلٍ صحيح أو قد لا يملك حساب الخدمة الإذن بالوصول إلى النطاقات المطلوبة).
عندما تنتهي صلاحية رمز الدخول، ينشئ تطبيقك رمز JWT آخر، ويوقّعه، ويطلب رمز دخول آخر.

يشرح الجزء المتبقي من هذا القسم تفاصيل إنشاء JWT، وتوقيع JWT، وكتابة طلب رمز الدخول، ومعالجة الاستجابة.
إنشاء JWT
يتألّف JWT من ثلاثة أجزاء: العنوان، ومجموعة المطالبات، والتوقيع. الرأس ومجموعة المطالبات هما كائنات JSON. يتم تسلسل عناصر JSON هذه إلى
UTF-8 بايت، ثم يتم ترميزها باستخدام ترميز Base64url. ويوفّر هذا الترميز إمكانية التكيّف مع التغييرات في الترميزات بسبب تكرار عمليات الترميز. يتم ربط العنوان ومجموعة التعديلات
والتوقيع معًا باستخدام حرف النقطة (.
).
يتم إنشاء JWT على النحو التالي:
{Base64url encoded header}.{Base64url encoded claim set}.{Base64url encoded signature}
وتكون السلسلة الأساسية للتوقيع على النحو التالي:
{Base64url encoded header}.{Base64url encoded claim set}
تشكيل عنوان JWT
يتكون العنوان من حقلين يشيران إلى خوارزمية التوقيع وتنسيق التأكيد. ويكون كلا الحقلين إلزاميًا، ويحتوي كل حقل على قيمة واحدة فقط. وعند إضافة خوارزميات وأشكال إضافية، سيتم تغيير هذا العنوان وفقًا لذلك.
تعتمد حسابات الخدمة على خوارزمية RSA SHA-256 وتنسيق الرمز المميّز JWT. ونتيجةً لذلك، سيكون تمثيل JSON للرأس على النحو التالي:
{"alg":"RS256","typ":"JWT"}
تمثيل Base64url لما يلي:
eyJhbGciOiJSUzI1NiIsInR5cCI6IkpXVCJ9
تشكيل نموذج مطالبات JWT
تحتوي مجموعة مطالبات JWT على معلومات حول JWT، بما في ذلك الأذونات المطلوبة (النطاقات)، والهدف من الرمز المميّز، وجهة الإصدار، ووقت إصدار الرمز المميّز، وعمر الرمز المميّز. معظم الحقول إلزامية. وكما هو الحال في عنوان JWT، تكون مجموعة المطالبات JWT عبارة عن كائن JSON ويتم استخدامها في احتساب التوقيع.
المطالبات المطلوبة
يتم عرض المطالبات المطلوبة في مجموعة مطالبات JWT أدناه. وقد تظهر بأي ترتيب في مجموعة المطالبات.
الاسم | الوصف |
---|---|
iss |
عنوان البريد الإلكتروني لحساب الخدمة |
scope |
قائمة بالأذونات التي يطلبها التطبيق مع الفصل بينها بمسافات. |
aud |
وصف لهدف التأكيد. عند إنشاء رمز دخول، يجب طلب هذه القيمة دائمًا https://oauth2.googleapis.com/token . |
exp |
تمثّل هذه السمة وقت انتهاء صلاحية التأكيد، المحدّد بالثواني 00:00:00 بالتوقيت العالمي المُنسّق، 1 كانون الثاني (يناير) 1970. يكون لهذه القيمة ساعة واحدة كحد أقصى بعد وقت إصدارها. |
iat |
وقت إصدار التأكيد، كثوانٍ منذ 00:00:00 بالتوقيت العالمي المُنسّق، 1 كانون الثاني (يناير) 1970. |
يظهر أدناه تمثيل JSON للحقول المطلوبة في مجموعة مطالبات JWT:
{ "iss": "761326798069-r5mljlln1rd4lrbhg75efgigp36m78j5@developer.gserviceaccount.com", "scope": "https://www.googleapis.com/auth/devstorage.read_only", "aud": "https://oauth2.googleapis.com/token", "exp": 1328554385, "iat": 1328550785 }
مطالبات إضافية
في بعض حالات المؤسسات، يمكن للتطبيق استخدام التفويض على مستوى النطاق للتصرف بالنيابة عن مستخدم معيّن في المؤسسة. ويجب منح الإذن اللازم لهذا النوع من انتحال الهوية قبل أن يتمكن التطبيق من انتحال هوية مستخدم، وعادةً ما يعالجه مشرف متميّز. لمزيد من المعلومات، راجِع التحكُّم في الوصول إلى واجهة برمجة التطبيقات باستخدام التفويض على مستوى النطاق.
للحصول على رمز الدخول الذي يمنح تطبيقًا تفويضًا بالوصول إلى أحد الموارد،
أدرِج عنوان البريد الإلكتروني للمستخدم في مطالبة JWT التي تم تحديدها كقيمة
للحقل sub
.
الاسم | الوصف |
---|---|
sub |
عنوان البريد الإلكتروني للمستخدم الذي يطلب التطبيق الوصول إليه المفوّض. |
إذا لم يكن لدى التطبيق إذن لانتحال هوية مستخدم، ستكون الاستجابة
لطلب رمز الدخول الذي يتضمن الحقل sub
خطأ.
في ما يلي مثال على مجموعة مطالبات JWT تتضمّن الحقل sub
:
{ "iss": "761326798069-r5mljlln1rd4lrbhg75efgigp36m78j5@developer.gserviceaccount.com", "sub": "some.user@example.com", "scope": "https://www.googleapis.com/auth/prediction", "aud": "https://oauth2.googleapis.com/token", "exp": 1328554385, "iat": 1328550785 }
ترميز مجموعة مطالبات JWT
مثل عنوان JWT، يجب أن يتم تسلسل مجموعة المطالبة JWT إلى UTF-8 وBase64url-safe المشفرة. في ما يلي مثال على تمثيل JSON لمجموعة مطالبات JWT:
{ "iss": "761326798069-r5mljlln1rd4lrbhg75efgigp36m78j5@developer.gserviceaccount.com", "scope": "https://www.googleapis.com/auth/prediction", "aud": "https://oauth2.googleapis.com/token", "exp": 1328554385, "iat": 1328550785 }
احتساب التوقيع
توقيع الويب JSON (JWS) هو المواصفات التي تحدد آليات إنشاء التوقيع لـ JWT. إدخال التوقيع هو مصفوفة وحدات البايت للمحتوى التالي:
{Base64url encoded header}.{Base64url encoded claim set}
يجب استخدام خوارزمية التوقيع في عنوان JWT عند احتساب التوقيع. إنّ خوارزمية التوقيع الوحيدة المتوافقة مع خادم تفويض Google OAuth 2.0 هي RSA باستخدام خوارزمية التجزئة SHA-256. ويتم استخدام التعبير RS256
في الحقل alg
ضمن العنوان JWT.
وقِّع تمثيل UTF-8 للإدخال باستخدام SHA256withRSA (المعروف أيضًا باسم RSASSA-PKCS1-V1_5-SIGN مع دالة التجزئة SHA-256) باستخدام المفتاح الخاص الذي تم الحصول عليه من Google API Console. ستكون المخرجات صفيف بايت.
يجب بعد ذلك أن يكون التوقيع بتشفير Base64url. يتم ربط العنوان ومجموعة المطالبات والتوقيع
مع نقطة (.
). والنتيجة هي JWT. ويجب أن يكون على النحو التالي (تمت إضافة فواصل الأسطر للتوضيح):
{Base64url encoded header}. {Base64url encoded claim set}. {Base64url encoded signature}
في ما يلي مثال على JWT قبل ترميز Base64url:
{"alg":"RS256","typ":"JWT"}. { "iss":"761326798069-r5mljlln1rd4lrbhg75efgigp36m78j5@developer.gserviceaccount.com", "scope":"https://www.googleapis.com/auth/prediction", "aud":"https://oauth2.googleapis.com/token", "exp":1328554385, "iat":1328550785 }. [signature bytes]
في ما يلي مثال على JWT تم توقيعها وجاهزة للنقل:
eyJhbGciOiJSUzI1NiIsInR5cCI6IkpXVCJ9.eyJpc3MiOiI3NjEzMjY3OTgwNjktcjVtbGpsbG4xcmQ0bHJiaGc3NWVmZ2lncDM2bTc4ajVAZGV2ZWxvcGVyLmdzZXJ2aWNlYWNjb3VudC5jb20iLCJzY29wZSI6Imh0dHBzOi8vd3d3Lmdvb2dsZWFwaXMuY29tL2F1dGgvcHJlZGljdGlvbiIsImF1ZCI6Imh0dHBzOi8vd3d3Lmdvb2dsZWFwaXMuY29tL29hdXRoMi92NC90b2tlbiIsImV4cCI6MTMyODU1NDM4NSwiaWF0IjoxMzI4NTUwNzg1fQ.UFUt59SUM2_AW4cRU8Y0BYVQsNTo4n7AFsNrqOpYiICDu37vVt-tw38UKzjmUKtcRsLLjrR3gFW3dNDMx_pL9DVjgVHDdYirtrCekUHOYoa1CMR66nxep5q5cBQ4y4u2kIgSvChCTc9pmLLNoIem-ruCecAJYgI9Ks7pTnW1gkOKs0x3YpiLpzplVHAkkHztaXiJdtpBcY1OXyo6jTQCa3Lk2Q3va1dPkh_d--GU2M5flgd8xNBPYw4vxyt0mP59XZlHMpztZt0soSgObf7G3GXArreF_6tpbFsS3z2t5zkEiHuWJXpzcYr5zWTRPDEHsejeBSG8EgpLDce2380ROQ
تقديم طلب رمز الدخول
بعد إنشاء JWT الموقَّع، يمكن للتطبيق استخدامه لطلب رمز الدخول.
طلب الرمز المميّز للدخول هذا هو طلب POST
باستخدام بروتوكول HTTPS، ويكون النص مشفّرًا بعنوان URL. يتم عرض عنوان URL أدناه:
https://oauth2.googleapis.com/token
يجب تضمين المعلَمات التالية في طلب HTTPS POST
:
الاسم | الوصف |
---|---|
grant_type |
استخدِم السلسلة التالية، بترميز عنوان URL حسب الضرورة:
urn:ietf:params:oauth:grant-type:jwt-bearer |
assertion |
JWT، بما في ذلك التوقيع. |
في ما يلي ملف ذاكرة التخزين المؤقت لطلب HTTPS POST
المستخدَم في طلب رمز الدخول:
POST /token HTTP/1.1 Host: oauth2.googleapis.com Content-Type: application/x-www-form-urlencoded grant_type=urn%3Aietf%3Aparams%3Aoauth%3Agrant-type%3Ajwt-bearer&assertion=eyJhbGciOiJSUzI1NiIsInR5cCI6IkpXVCJ9.eyJpc3MiOiI3NjEzMjY3OTgwNjktcjVtbGpsbG4xcmQ0bHJiaGc3NWVmZ2lncDM2bTc4ajVAZGV2ZWxvcGVyLmdzZXJ2aWNlYWNjb3VudC5jb20iLCJzY29wZSI6Imh0dHBzOi8vd3d3Lmdvb2dsZWFwaXMuY29tL2F1dGgvcHJlZGljdGlvbiIsImF1ZCI6Imh0dHBzOi8vYWNjb3VudHMuZ29vZ2xlLmNvbS9vL29hdXRoMi90b2tlbiIsImV4cCI6MTMyODU3MzM4MSwiaWF0IjoxMzI4NTY5NzgxfQ.ixOUGehweEVX_UKXv5BbbwVEdcz6AYS-6uQV6fGorGKrHf3LIJnyREw9evE-gs2bmMaQI5_UbabvI4k-mQE4kBqtmSpTzxYBL1TCd7Kv5nTZoUC1CmwmWCFqT9RE6D7XSgPUh_jF1qskLa2w0rxMSjwruNKbysgRNctZPln7cqQ
في ما يلي الطلب نفسه باستخدام curl
:
curl -d 'grant_type=urn%3Aietf%3Aparams%3Aoauth%3Agrant-type%3Ajwt-bearer&assertion=eyJhbGciOiJSUzI1NiIsInR5cCI6IkpXVCJ9.eyJpc3MiOiI3NjEzMjY3OTgwNjktcjVtbGpsbG4xcmQ0bHJiaGc3NWVmZ2lncDM2bTc4ajVAZGV2ZWxvcGVyLmdzZXJ2aWNlYWNjb3VudC5jb20iLCJzY29wZSI6Imh0dHBzOi8vd3d3Lmdvb2dsZWFwaXMuY29tL2F1dGgvcHJlZGljdGlvbiIsImF1ZCI6Imh0dHBzOi8vYWNjb3VudHMuZ29vZ2xlLmNvbS9vL29hdXRoMi90b2tlbiIsImV4cCI6MTMyODU3MzM4MSwiaWF0IjoxMzI4NTY5NzgxfQ.RZVpzWygMLuL-n3GwjW1_yhQhrqDacyvaXkuf8HcJl8EtXYjGjMaW5oiM5cgAaIorrqgYlp4DPF_GuncFqg9uDZrx7pMmCZ_yHfxhSCXru3gbXrZvAIicNQZMFxrEEn4REVuq7DjkTMyCMGCY1dpMa8aWfTQFt3Eh7smLchaZsU ' https://oauth2.googleapis.com/token
معالجة الاستجابة
إذا تم صياغة طلب JWT ورمز الرمز المميّز بشكل صحيح وكان لحساب الخدمة إذنًا لتنفيذ العملية، تتضمّن استجابة JSON من خادم التفويض رمز دخول. إليك مثال على إجابة:
{ "access_token": "1/8xbJqaOZXSUZbHLl5EOtu1pxz3fmmetKx9W8CV4t79M", "scope": "https://www.googleapis.com/auth/prediction" "token_type": "Bearer", "expires_in": 3600 }
يمكن إعادة استخدام رموز الدخول خلال فترة المهلة التي تحدّدها
القيمة expires_in
.
استدعاء واجهات Google APIs
Java
استخدِم الكائن GoogleCredential
لاستدعاء واجهات Google API من خلال إكمال
الخطوات التالية:
- يمكنك إنشاء كائن خدمة لواجهة برمجة التطبيقات التي تريد طلبها باستخدام العنصر
GoogleCredential
. مثلاً:SQLAdmin sqladmin = new SQLAdmin.Builder(httpTransport, JSON_FACTORY, credential).build();
- يمكنك إرسال طلبات إلى خدمة واجهة برمجة التطبيقات باستخدام
الواجهة التي يوفّرها عنصر الخدمة.
على سبيل المثال، إدراج مثيلات قواعد بيانات Cloud SQL في مشروع Thriller-مثال-123:
SQLAdmin.Instances.List instances = sqladmin.instances().list("exciting-example-123").execute();
Python
يمكنك استخدام الكائن Credentials
المفوَّض لاستدعاء واجهات Google API من خلال إكمال الخطوات التالية:
- يمكنك إنشاء كائن خدمة لواجهة برمجة التطبيقات التي تريد طلبها. يمكنك إنشاء كائن خدمة
من خلال استدعاء الدالة
build
مع اسم إصدار واجهة برمجة التطبيقات وإصداره والكائنCredentials
المصرح به. على سبيل المثال، للاتصال بالإصدار 1 (الإصدار التجريبي) من Cloud SQL Management API:import googleapiclient.discovery sqladmin = googleapiclient.discovery.build('sqladmin', 'v1beta3', credentials=credentials)
- يمكنك إرسال طلبات إلى خدمة واجهة برمجة التطبيقات باستخدام
الواجهة التي يوفّرها عنصر الخدمة.
على سبيل المثال، إدراج مثيلات قواعد بيانات Cloud SQL في مشروع Thriller-مثال-123:
response = sqladmin.instances().list(project='exciting-example-123').execute()
HTTP/REST
بعد حصول تطبيقك على رمز الدخول، يمكنك استخدام الرمز المميز لإجراء طلبات لواجهة برمجة تطبيقات Google نيابةً عن حساب خدمة معيّن أو حساب مستخدم إذا تم منح نطاقات الوصول المطلوبة من خلال واجهة برمجة التطبيقات. ولإجراء ذلك، يمكنك تضمين
رمز الدخول في طلب لواجهة برمجة التطبيقات من خلال تضمين إما معلمة طلب البحث access_token
أو قيمة Authorization
لعنوان HTTP Bearer
. ويُفضّل أن يكون عنوان HTTP إن أمكن، لأن سلاسل طلبات البحث تكون مرئية في سجلّات الخادم. وفي معظم
الحالات، يمكنك استخدام مكتبة برامج لإعداد طلباتك من أجل Google APIs (على سبيل المثال، عند
استدعاء واجهة برمجة تطبيقات ملفات Drive).
يمكنك تجربة جميع واجهات برمجة تطبيقات Google وعرض نطاقاتها على مساحة المرح 2.0 OAuth.
أمثلة على HTTP GET
قد يبدو طلب عرض نقطة نهاية drive.files
(واجهة برمجة تطبيقات الملفات في Drive) باستخدام عنوان HTTP Authorization: Bearer
ما يلي. ملاحظة: عليك تحديد رمز الدخول الخاص بك:
GET /drive/v2/files HTTP/1.1 Host: www.googleapis.com Authorization: Bearer access_token
إليك استدعاء لواجهة برمجة التطبيقات نفسها للمستخدم الذي تمت المصادقة عليه باستخدام معلّمة سلسلة طلب البحث access_token
:
GET https://www.googleapis.com/drive/v2/files?access_token=access_token
أمثلة على curl
يمكنك اختبار هذه الأوامر باستخدام تطبيق سطر الأوامر curl
. إليك مثال على استخدام خيار عنوان HTTP (مفضّل):
curl -H "Authorization: Bearer access_token" https://www.googleapis.com/drive/v2/files
أو بدلاً من ذلك، خيار معلّمة سلسلة طلب البحث:
curl https://www.googleapis.com/drive/v2/files?access_token=access_token
عند انتهاء صلاحية رموز الدخول
تنتهي صلاحية رموز الدخول التي تم إصدارها من خلال خادم تفويض Google OAuth 2.0 بعد المدة
التي تقدِّمها القيمة expires_in
. عند انتهاء صلاحية رمز الدخول، يجب
على التطبيق إنشاء رمز JWT آخر، وتوقيعه، وطلب رمز دخول آخر.
رموز خطأ JWT
حقل error |
حقل error_description |
المعنى | كيفية حلّ المشكلة |
---|---|---|---|
unauthorized_client |
Unauthorized client or scope in request. |
إذا كنت تحاول استخدام التفويض على مستوى النطاق، لن يتم تفويض حساب الخدمة في وحدة تحكّم المشرف لنطاق المستخدم. |
تأكّد من أن حساب الخدمة مفوّض في صفحة
التفويض على مستوى النطاق في "وحدة تحكّم المشرف" للمستخدم في
المطالبة على الرغم من أن هذا التفويض عادةً ما يستغرق بضع دقائق، ما يصل إلى 24 ساعة للوصول إلى جميع المستخدمين في حسابك على Google. |
unauthorized_client |
Client is unauthorized to retrieve access tokens using this method, or client not
authorized for any of the scopes requested. |
تم تفويض حساب الخدمة باستخدام عنوان البريد الإلكتروني للعميل بدلاً من معرِّف العميل (رقمي) في وحدة تحكُّم المشرف. | في صفحة التفويض على مستوى النطاق في وحدة تحكم المشرف، عليك إزالة البرنامج وإعادة إضافته باستخدام المعرّف الرقمي. |
access_denied |
(أي قيمة) | إذا كنت تستخدم التفويض على مستوى النطاق، لن يتم تفويض نطاق واحد أو أكثر من النطاقات المطلوبة في "وحدة تحكُّم المشرف". |
تأكّد من أن حساب الخدمة مفوّض في
صفحة
التفويض على مستوى النطاق في "وحدة تحكّم المشرف" للمستخدم في المطالبة ( على الرغم من أن هذا التفويض عادةً ما يستغرق بضع دقائق، ما يصل إلى 24 ساعة للوصول إلى جميع المستخدمين في حسابك على Google. |
invalid_grant |
Not a valid email. |
المستخدم غير موجود. | تأكّد من أنّ عنوان البريد الإلكتروني في المطالبة (الحقل) sub صحيح. |
invalid_grant |
|
يعني ذلك عادةً أن وقت النظام المحلي غير صحيح. ويمكن أن يحدث ذلك أيضًا إذا كانت قيمة exp تزيد على 65 دقيقة في المستقبل من قيمة iat ، أو إذا كانت قيمة exp أقل من قيمة iat . |
تأكَّد من أنّ الساعة على النظام التي تم إنشاء JWT صحيحة فيها. إذا لزم الأمر، يمكنك مزامنة وقتك مع Google NTP. |
invalid_grant |
Invalid JWT Signature. |
تم توقيع تأكيد JWT باستخدام مفتاح خاص غير مرتبط بحساب الخدمة الذي تم تحديده في البريد الإلكتروني للعميل أو تم حذف المفتاح الذي تم استخدامه أو إيقافه أو انتهت صلاحيته. بدلاً من ذلك، قد يكون ترميز JWT مشفّر بشكل غير صحيح. يجب أن يكون بترميز Base64، بدون أسطر جديدة أو علامات حشو متساوية. |
يمكنك فك تشفير مطالبة JWT والتحقق من أن المفتاح الذي وقّع التأكيد مرتبط بحساب الخدمة. جرِّب استخدام مكتبة OAuth المقدمة من Google للتأكد من إنشاء JWT بشكل صحيح. |
invalid_scope |
Invalid OAuth scope or ID token audience provided. |
لم يتم طلب أي نطاقات (قائمة فارغة من النطاقات)، أو لم يتم العثور على أحد النطاقات المطلوبة (أي غير صالح). |
تأكّد من تعبئة المطالبة يجب فصل قائمة النطاقات في المطالبة |
disabled_client |
The OAuth client was disabled. |
تم إيقاف المفتاح المستخدَم لتوقيع تأكيد JWT. |
انتقِل إلى Google API Console، وضمن IAM & Admin > حسابات الخدمة، فعِّل حساب الخدمة الذي يحتوي على "رقم تعريف المفتاح"، ويُستخدم لتوقيع التأكيد. |
الملحق: تفويض حساب الخدمة بدون OAuth
باستخدام بعض واجهات Google API، يمكنك إجراء طلبات بيانات من واجهة برمجة التطبيقات المصرّح بها باستخدام رمز JWT موقّع مباشرةً كرمز مميّز لحامل بدلاً من رمز الدخول المميّز OAuth 2.0. عندما يكون ذلك ممكنًا، يمكنك تجنب تقديم طلب شبكة إلى خادم تفويض Google قبل إجراء طلب بيانات من واجهة برمجة التطبيقات.
إذا كانت واجهة برمجة التطبيقات التي تريد طلبها لها تعريف خدمة معروض في مستودع GitHub في Google APIs، يمكنك إجراء طلبات بيانات من واجهة برمجة التطبيقات المصرّح بها باستخدام JWT بدلاً من رمز الدخول. ولإجراء ذلك، يُرجى اتّباع الخطوات التالية:
- أنشئ حساب خدمة كما هو موضّح أعلاه. احرص على الاحتفاظ بملف JSON الذي تحصل عليه عند إنشاء الحساب.
- باستخدام أي مكتبة JWT عادية، مثل المكتبة المتوفرة على
jwt.io، يمكنك إنشاء JWT باستخدام عنوان
والحمولة كما هو موضّح في المثال التالي:
{ "alg": "RS256", "typ": "JWT", "kid": "abcdef1234567890" } . { "iss": "123456-compute@developer.gserviceaccount.com", "sub": "123456-compute@developer.gserviceaccount.com", "aud": "https://firestore.googleapis.com/", "iat": 1511900000, "exp": 1511903600 }
- بالنسبة إلى الحقل
kid
في العنوان، حدِّد معرِّف المفتاح الخاص لحساب الخدمة. يمكنك العثور على هذه القيمة في الحقلprivate_key_id
في ملف JSON لحساب الخدمة. - بالنسبة إلى الحقلين
iss
وsub
، حدِّد عنوان البريد الإلكتروني لحساب الخدمة. يمكنك العثور على هذه القيمة في الحقلclient_email
في ملف JSON لحساب الخدمة. - بالنسبة إلى الحقل
aud
، حدِّد نقطة نهاية واجهة برمجة التطبيقات. على سبيل المثال:https://SERVICE.googleapis.com/
. - في الحقل
iat
، حدِّد وقت Unix الحالي، وبالنسبة إلى الحقلexp
، حدِّد الوقت 3600 ثانية بالضبط، عند انتهاء صلاحية JWT.
وقِّع JWT باستخدام RSA-256 باستخدام المفتاح الخاص الموجود في ملف JSON لحساب الخدمة.
مثلاً:
Java
باستخدام google-api-java-client وjava-jwt:
GoogleCredential credential = GoogleCredential.fromStream(new FileInputStream("MyProject-1234.json")); PrivateKey privateKey = credential.getServiceAccountPrivateKey(); String privateKeyId = credential.getServiceAccountPrivateKeyId(); long now = System.currentTimeMillis(); try { Algorithm algorithm = Algorithm.RSA256(null, privateKey); String signedJwt = JWT.create() .withKeyId(privateKeyId) .withIssuer("123456-compute@developer.gserviceaccount.com") .withSubject("123456-compute@developer.gserviceaccount.com") .withAudience("https://firestore.googleapis.com/") .withIssuedAt(new Date(now)) .withExpiresAt(new Date(now + 3600 * 1000L)) .sign(algorithm); } catch ...
Python
باستخدام PyJWT:
iat = time.time() exp = iat + 3600 payload = {'iss': '123456-compute@developer.gserviceaccount.com', 'sub': '123456-compute@developer.gserviceaccount.com', 'aud': 'https://firestore.googleapis.com/', 'iat': iat, 'exp': exp} additional_headers = {'kid': PRIVATE_KEY_ID_FROM_JSON} signed_jwt = jwt.encode(payload, PRIVATE_KEY_FROM_JSON, headers=additional_headers, algorithm='RS256')
- يجب استدعاء واجهة برمجة التطبيقات، باستخدام JWT الموقّع على أنه الرمز المميز للحامل:
GET /v1/projects/abc/databases/123/indexes HTTP/1.1 Authorization: Bearer SIGNED_JWT Host: firestore.googleapis.com