التعرُّف على كيفية استدعاء وظائف Cloud Run التي تمت مصادقتها

1. مقدمة

نظرة عامة

وظائف Cloud Run هي حلّ حوسبة خفيف الوزن يتيح للمطوّرين إنشاء وظائف مستقلة ذات غرض واحد يمكن تشغيلها باستخدام HTTPS أو الاستجابة إلى CloudEvents بدون الحاجة إلى إدارة خادم أو بيئة وقت تشغيل. يمكنك الاطّلاع على مزيد من المعلومات عن دوال Cloud Run في منشور المدوّنة.

هناك طريقتان رئيسيتان للتحكّم في عمليات استدعاء دوال Cloud Run: تأمين الوصول استنادًا إلى الهوية وتأمين الوصول باستخدام عناصر التحكّم في الوصول المستندة إلى الشبكة. يركّز هذا الدرس التطبيقي حول الترميز على الأسلوب الأول، ويشرح لك 3 سيناريوهات لتأمين الوصول استنادًا إلى الهوية من أجل استدعاء دالة:

  1. استخدام رمز هوية gcloud لاستدعاء دالة لأغراض التطوير والاختبار المحليَّين
  2. انتحال هوية حساب خدمة عند التطوير والاختبار محليًا لاستخدام بيانات الاعتماد نفسها المستخدَمة في قناة الإصدار العلني
  3. استخدام مكتبات برامج Google للتعامل مع المصادقة على واجهات Google Cloud API، مثلاً عندما تحتاج خدمة إلى استدعاء دالة

ما ستتعلمه

  • كيفية ضبط المصادقة على إحدى دوال Cloud Run والتأكّد من ضبطها بشكلٍ سليم
  • استدعاء دالة مصادَق عليها من بيئة تطوير محلية من خلال تقديم الرمز المميز لهوية gcloud
  • كيفية إنشاء حساب خدمة ومنحه الدور المناسب لتنفيذ وظيفة
  • كيفية انتحال هوية خدمة من بيئة تطوير محلية تتضمّن الأدوار المناسبة لاستدعاء دالة

2. الإعداد والمتطلبات

المتطلبات الأساسية

تفعيل Cloud Shell

  1. من Cloud Console، انقر على تفعيل Cloud Shell d1264ca30785e435.png.

84688aa223b1c3a2.png

إذا كانت هذه هي المرة الأولى التي تبدأ فيها Cloud Shell، ستظهر لك شاشة وسيطة توضّح ماهيتها. إذا ظهرت لك شاشة وسيطة، انقر على متابعة.

d95252b003979716.png

يستغرق توفير Cloud Shell والاتصال به بضع لحظات فقط.

7833d5e1c5d18f54.png

يتم تحميل هذا الجهاز الافتراضي بجميع أدوات التطوير اللازمة. توفّر هذه الخدمة دليلًا رئيسيًا دائمًا بسعة 5 غيغابايت وتعمل في Google Cloud، ما يؤدي إلى تحسين أداء الشبكة والمصادقة بشكل كبير. يمكن إنجاز معظم عملك في هذا الدرس العملي، إن لم يكن كله، باستخدام متصفح.

بعد الاتصال بـ Cloud Shell، من المفترض أن يظهر لك أنّه تم إثبات هويتك وأنّ المشروع مضبوط على رقم تعريف مشروعك.

  1. نفِّذ الأمر التالي في Cloud Shell للتأكّد من إكمال عملية المصادقة:
gcloud auth list

ناتج الأمر

 Credentialed Accounts
ACTIVE  ACCOUNT
*       <my_account>@<my_domain.com>

To set the active account, run:
    $ gcloud config set account `ACCOUNT`
  1. نفِّذ الأمر التالي في Cloud Shell للتأكّد من أنّ أمر gcloud يعرف مشروعك:
gcloud config list project

ناتج الأمر

[core]
project = <PROJECT_ID>

إذا لم يكن كذلك، يمكنك تعيينه من خلال هذا الأمر:

gcloud config set project <PROJECT_ID>

ناتج الأمر

Updated property [core/project].

3- إنشاء دالة مصادَق عليها في Cloud Run واختبارها

يعني طلب المصادقة أنّ الجهة الأساسية التي تستدعي الدالة يجب أن يكون لديها دور Cloud Run Invoker، وإلا ستعرض الدالة الخطأ "403: إجراء محظور". سيوضّح لك هذا الدرس التطبيقي حول الترميز كيفية منح أدوار المنفّذ المناسبة إلى كيان أساسي.

إعداد متغيرات البيئة المحلية لتبسيط أوامر gcloud

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

REGION=us-central1
PROJECT_ID=$(gcloud config get-value project)

إنشاء رمز المصدر للدالة

على الرغم من أنّ هذا الدرس التطبيقي حول الترميز يستخدم Node.js، يمكنك استخدام أي وقت تشغيل متوافق مع مكتبات برامج Google Auth.

أولاً، أنشئ دليلاً وانتقِل إليه.

mkdir auth-function-codelab && cd $_

بعد ذلك، أنشِئ ملف package.json.

touch package.json

echo '{
  "dependencies": {
    "@google-cloud/functions-framework": "^3.0.0"
  }
}
' > package.json

بعد ذلك، أنشِئ ملف المصدر index.js.

touch index.js

echo 'const functions = require("@google-cloud/functions-framework");

functions.http("helloWorld", (req, res) => {
 res.send(`Hello ${req.query.name || req.body.name || "World"}!`);
});' > index.js

إنشاء الدالة التي تتطلّب المصادقة

في ما يلي خطوات إنشاء دالة مصادَق عليها لوقت التشغيل nodejs20. ومع ذلك، يمكنك استخدام أي وقت تشغيل متوافق مع مكتبات عميل Google Auth.

FUNCTION_NAME=authenticated-function-codelab
ENTRY_POINT=helloWorld

لنشر دالة Cloud Run مباشرةً على Cloud Run، نفِّذ الأمر التالي:

gcloud beta run deploy $FUNCTION_NAME \
      --source . \
      --function helloWorld \
      --region $REGION \
      --no-allow-unauthenticated

بعد ذلك، يمكنك حفظ عنوان URL للدالة كمتغيّر بيئة لاستخدامه لاحقًا.

FUNCTION_URL="$(gcloud run services describe $FUNCTION_NAME --region $REGION --format 'value(status.url)')"

إذا كنت تفضّل النشر كـ "الجيل الثاني من Cloud Functions"، استخدِم الأمر التالي:

gcloud functions deploy nodejs-http-function \
  --gen2 \
  --runtime=nodejs20 \
  --region=$REGION \
  --source=. \
  --entry-point=helloWorld \
  --trigger-http \
  --no-allow-unauthenticated

بعد ذلك، يمكنك حفظ عنوان URL للدالة كمتغيّر بيئة لاستخدامه لاحقًا.

FUNCTION_URL="$(gcloud functions describe $FUNCTION_NAME --gen2 --region us-central1 --format='get(serviceConfig.uri)')"

تأكَّد من أنّ الدالة تتطلّب المصادقة من خلال محاولة استدعائها كمستخدم مجهول

ستستدعي الدالة بدون مصادقة للتحقّق من تلقّي الخطأ المتوقّع 403.

من سطر الأوامر، شغِّل الأمر curl التالي:

curl -i $FUNCTION_URL

ستظهر لك النتيجة التالية:

<html><head>
<meta http-equiv="content-type" content="text/html;charset=utf-8">
<title>403 Forbidden</title>
</head>
<body text=#000000 bgcolor=#ffffff>
<h1>Error: Forbidden</h1>
<h2>Your client does not have permission to get URL <code>/</code> from this server.</h2>
<h2></h2>
</body></html>

أنت الآن جاهز لتجربة 3 سيناريوهات يمكنك فيها استدعاء الدالة من خلال تقديم المصادقة.

4. السيناريو 1: استخدام رمز مميّز لهوية gcloud

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

تأكَّد من مصادقتك باستخدام gcloud من خلال تنفيذ الأمر التالي:

gcloud auth list

من المفترض أن تظهر علامة نجمة بجانب هويتك النشطة، على سبيل المثال:

Credentialed Accounts
ACTIVE  ACCOUNT

*       <my_account>@<my_domain.com>

To set the active account, run:
    $ gcloud config set account `ACCOUNT`

يمكنك العثور على مزيد من المعلومات حول إعداد gcloud init وgcloud auth login في المستندات.

بعد ذلك، استدعِ الدالة ومرِّر إليها رمز التعريف.

curl $FUNCTION_URL -H "Authorization: bearer $(gcloud auth print-identity-token)"

ستظهر لك النتيجة الآن:

Hello World!

تحديد المشاكل وحلّها

إذا تلقّيت الخطأ 403 Forbidden، تأكَّد من أنّ هويتك تتضمّن دور Cloud Run Invoker. يمكنك استخدام وحدة تحكّم إدارة الهوية وإمكانية الوصول للتحقّق من الأدوار الممنوحة لجهة رئيسية.

على الرغم من أنّ استخدام رمز مميّز خاص بهويتك هو طريقة سريعة لاختبار وظيفتك أثناء التطوير، يجب أن يحصل مستدعي الدالة التي تمت مصادقتها على الأدوار المناسبة، وإلا سيتلقّى المستدعي الخطأ 403 Forbidden.

عليك اتّباع مبدأ الحدّ الأدنى من الامتيازات من خلال الحدّ من عدد الهويات وحسابات الخدمة التي لديها أدوار لتنفيذ الوظيفة. في السيناريو التالي، ستتعرّف على كيفية إنشاء حساب خدمة جديد ومنحه الأدوار المناسبة لتنفيذ الدالة.

5- السيناريو 2: انتحال هوية حساب خدمة

في هذا السيناريو، عليك انتحال هوية حساب خدمة (أي الحصول على أذوناته) لاستدعاء إحدى الدوال عند التطوير والاختبار محليًا. من خلال انتحال هوية حساب خدمة، يمكنك اختبار وظيفتك باستخدام بيانات الاعتماد نفسها المستخدَمة في مرحلة الإنتاج.

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

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

إنشاء حساب خدمة جديد

أولاً، عليك إنشاء متغيّري بيئة إضافيين لتمثيل حسابات الخدمة المستخدَمة في أوامر gcloud.

SERVICE_ACCOUNT_NAME="invoke-functions-codelab"
SERVICE_ACCOUNT_ADDRESS=$SERVICE_ACCOUNT_NAME@$PROJECT_ID.iam.gserviceaccount.com

بعد ذلك، عليك إنشاء حساب الخدمة.

gcloud iam service-accounts create $SERVICE_ACCOUNT_NAME \
  --display-name="Cloud Run function Authentication codelab"

وامنح حساب الخدمة دور "مستدعي Cloud Run":

gcloud run services add-iam-policy-binding $FUNCTION_NAME \
  --region=us-central1  \
  --member serviceAccount:$SERVICE_ACCOUNT_ADDRESS \
  --role='roles/run.invoker'

استدعاء الدالة من خلال انتحال هوية حساب الخدمة

لإجراء ذلك، عليك انتحال هوية حساب الخدمة الذي تم إنشاؤه حديثًا من خلال الحصول على رمز التعريف المميز الخاص به.

إضافة الأدوار المطلوبة لانتحال الهوية

لانتحال هوية حساب خدمة، يجب أن يتضمّن حساب المستخدم دور "منشئ الرموز المميزة لحساب الخدمة" (roles/iam.serviceAccountTokenCreator) لإنشاء رمز مميز معرّف لحساب الخدمة.

يمكنك تنفيذ الأوامر التالية لمنح حساب المستخدم النشط هذا الدور:

ACCOUNT_EMAIL=$(gcloud auth list --filter=status:ACTIVE --format="value(account)")

gcloud iam service-accounts add-iam-policy-binding $SERVICE_ACCOUNT_ADDRESS  \
  --member user:$ACCOUNT_EMAIL \
  --role='roles/iam.serviceAccountTokenCreator'

استخدام الرمز المميّز لتعريف حساب الخدمة

انتظِر بضع دقائق حتى يتم نشر الأذونات. يمكنك الآن استدعاء الدالة من خلال تمرير الرمز المميّز لتعريف الهوية الخاص بحساب الخدمة.

curl $FUNCTION_URL -H "Authorization: bearer $(gcloud auth print-identity-token --impersonate-service-account $SERVICE_ACCOUNT_ADDRESS)" 

وسيظهر لك ما يلي:

WARNING: This command is using service account impersonation. All API calls will be executed as [invoke-functions-codelab@<project-id>.iam.gserviceaccount.com].

Hello World!

6. السيناريو 3: استخدام مكتبات برامج Google

في الجزء الأخير من هذا الدرس التطبيقي حول الترميز، ستشغّل خدمة صغيرة محليًا لإنشاء رمز مميّز لتعريف حساب خدمة، ثم ستطلب الدالة آليًا باستخدام مكتبات عميل Google Auth وبيانات الاعتماد التلقائية للتطبيق (ADC). يمكنك الاطّلاع على مزيد من المعلومات حول مكتبات العملاء في Google في قسم "شرح مكتبات العملاء" ضمن المستندات.

يُعدّ استخدام ADC مهمًا بشكل خاص عندما تريد كتابة دالتك واختبارها محليًا (على سبيل المثال، على الكمبيوتر المحمول أو في Cloud Shell أو غير ذلك) أثناء التفاعل مع موارد Google Cloud الأخرى (مثل Cloud Storage وVision API وغير ذلك). في هذا المثال، ستتعرّف على كيفية جعل إحدى الخدمات تستدعي وظيفة أخرى تتطلّب المصادقة. لمزيد من المعلومات عن ADC والتطوير المحلي، يُرجى الاطّلاع على مشاركة المدونة كيفية تطوير واختبار Cloud Functions محليًا | مدونة Google Cloud

تنفيذ أمر gcloud لانتحال هوية حساب خدمة

تعثر بيانات الاعتماد التلقائية للتطبيق تلقائيًا على بيانات الاعتماد استنادًا إلى بيئة التطبيق، وتستخدم هذه البيانات للمصادقة على Google Cloud APIs. يتيح لك الخيار ‎–impersonate-service-account انتحال هوية حساب خدمة من خلال استخدام هويته للمصادقة على واجهات برمجة تطبيقات Google Cloud.

لانتحال هوية حساب خدمة، يمكنك تنفيذ الأمر التالي:

gcloud auth application-default login --impersonate-service-account=$SERVICE_ACCOUNT_ADDRESS

أنت الآن تنفّذ أوامر gcloud بصفتك حساب الخدمة هذا، بدلاً من هويتك.

إنشاء خدمة وتشغيلها لاستدعاء دالة تمت المصادقة عليها

يتضمّن كل وقت تشغيل مكتبة برامج Google Auth يمكنك تثبيتها. يوضّح لك هذا الدرس التطبيقي حول الترميز كيفية إنشاء تطبيق Node.js وتشغيله محليًا.

في ما يلي خطوات استخدام Node.js:

  1. إنشاء دليل جديد
mkdir local-dev && cd $_
  1. إنشاء تطبيق Node.js جديد
npm init -y
  1. تثبيت مكتبة برامج Google Auth
npm install google-auth-library
  1. إنشاء ملف index.js
  2. استرداد عنوان URL لدالة Cloud Run، والذي ستضيفه إلى الرمز في الخطوة التالية
echo $FUNCTION_URL
  1. أضِف الرمز التالي إلى index.js. احرص على تغيير المتغيّر targetAudience إلى عنوان URL لوظيفة Cloud Run.

index.js

// Cloud Functions uses your function's url as the `targetAudience` value

const targetAudience = '<YOUR-CLOUD-RUN-FUNCTION-URL>';

// For Cloud Functions, endpoint(`url`) and `targetAudience` should be equal

const url = targetAudience;

const { GoogleAuth } = require('google-auth-library');
const auth = new GoogleAuth();

async function request() {
    console.info(`request ${url} with target audience ${targetAudience}`);

    // this call retrieves the ID token for the impersonated service account
    const client = await auth.getIdTokenClient(targetAudience);

    const res = await client.request({ url });
    console.info(res.data);
}

request().catch(err => {
    console.error(err.message);
    process.exitCode = 1;
});
  1. تشغيل التطبيق
node index.js

من المفترض أن يظهر لك النص "Hello World!‎" الناتج.

تحديد المشاكل وحلّها

إذا ظهرت لك رسالة الخطأ Permission ‘iam.serviceAccounts.getOpenIdToken' denied on resource (or it may not exist).‎، يُرجى الانتظار بضع دقائق إلى أن يتم نشر دور "منشئ رموز حساب الخدمة".

إذا تلقّيت الخطأ Cannot fetch ID token in this environment, use GCE or set the GOOGLE_APPLICATION_CREDENTIALS environment variable to a service account credentials JSON file، قد تكون نسيت تنفيذ الأمر

gcloud auth application-default login --impersonate-service-account=$SERVICE_ACCOUNT_ADDRESS

7. تهانينا!

تهانينا على إكمال هذا الدرس العملي.

ننصحك بمراجعة المستندات حول كيفية تأمين دوال Cloud Run.

ننصحك أيضًا بقراءة مشاركة المدونة هذه حول التطوير المحلي باستخدام دوال Cloud Run للتعرّف على كيفية تطوير وظيفة Cloud Run واختبارها في بيئة التطوير المحلية.

المواضيع التي تناولناها

  • كيفية ضبط المصادقة على إحدى دوال Cloud Run والتأكّد من ضبطها بشكلٍ سليم
  • استدعاء دالة مصادَق عليها من بيئة تطوير محلية من خلال تقديم الرمز المميز لهوية gcloud
  • كيفية إنشاء حساب خدمة ومنحه الدور المناسب لتنفيذ وظيفة
  • كيفية انتحال هوية خدمة من بيئة تطوير محلية تتضمّن الأدوار المناسبة لاستدعاء دالة

8. تَنظيم

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

لإيقاف انتحال هوية حساب الخدمة، يمكنك إعادة تسجيل الدخول باستخدام هويتك:

gcloud auth application-default login

لحذف وظيفة Cloud Run، انتقِل إلى Cloud Console لوظيفة Cloud Run على https://console.cloud.google.com/functions/. تأكَّد من أنّ المشروع الذي أنشأته في الخطوة 2 هو المشروع المحدّد حاليًا.

اختَر الدالة my-authenticated-function التي نشرتها سابقًا. بعد ذلك، انقر على حذف.

إذا اخترت حذف المشروع بأكمله، يمكنك الانتقال إلى https://console.cloud.google.com/cloud-resource-manager، واختيار المشروع الذي أنشأته في الخطوة 2، ثم النقر على "حذف". إذا حذفت المشروع، عليك تغيير المشاريع في Cloud SDK. يمكنك الاطّلاع على قائمة بجميع المشاريع المتاحة من خلال تنفيذ gcloud projects list.