מדריך לשימוש ב-Pub/Sub עם Cloud Run

במדריך הזה נסביר איך לכתוב, לפרוס ולהפעיל שירות Cloud Run ממינוי דחיפה ב-Pub/Sub.

מטרות

  • כתיבה, פיתוח ופריסה של שירות ב-Cloud Run
  • קוראים לשירות על ידי פרסום הודעה בנושא Pub/Sub.

עלויות

במסמך הזה משתמשים ברכיבים הבאים של Google Cloud, והשימוש בהם כרוך בתשלום:

כדי להעריך את ההוצאות בהתאם לתחזית השימוש שלכם, אתם יכולים להיעזר במחשבון העלויות.

משתמשים חדשים של Google Cloud ? יכול להיות שאתם זכאים לתקופת ניסיון בחינם.

לפני שמתחילים

  1. נכנסים לחשבון Google Cloud . אם אתם משתמשים חדשים ב- Google Cloud, צרו חשבון כדי שתוכלו להעריך את הביצועים של המוצרים שלנו בתרחישים מהעולם האמיתי. לקוחות חדשים מקבלים בחינם גם קרדיט בשווי 300$ להרצה, לבדיקה ולפריסה של עומסי העבודה.
  2. In the Google Cloud console, on the project selector page, select or create a Google Cloud project.

    Roles required to select or create a project

    • Select a project: Selecting a project doesn't require a specific IAM role—you can select any project that you've been granted a role on.
    • Create a project: To create a project, you need the Project Creator role (roles/resourcemanager.projectCreator), which contains the resourcemanager.projects.create permission. Learn how to grant roles.

    Go to project selector

  3. Verify that billing is enabled for your Google Cloud project.

  4. In the Google Cloud console, on the project selector page, select or create a Google Cloud project.

    Roles required to select or create a project

    • Select a project: Selecting a project doesn't require a specific IAM role—you can select any project that you've been granted a role on.
    • Create a project: To create a project, you need the Project Creator role (roles/resourcemanager.projectCreator), which contains the resourcemanager.projects.create permission. Learn how to grant roles.

    Go to project selector

  5. Verify that billing is enabled for your Google Cloud project.

  6. מפעילים את ממשקי ה-API של Artifact Registry, ‏ Cloud Build, ‏ Pub/Sub ו-Cloud Run.

    תפקידים שנדרשים להפעלת ממשקי API

    כדי להפעיל ממשקי API, צריך את תפקיד ה-IAM 'אדמין של Service Usage' (roles/serviceusage.serviceUsageAdmin), שכולל את ההרשאה serviceusage.services.enable. איך מקצים תפקידים

    הפעלת ממשקי ה-API

  7. מתקינים ומפעילים את ה-CLI של gcloud.
  8. עדכון רכיבים:
    gcloud components update

התפקידים הנדרשים

כדי לקבל את ההרשאות שדרושות להשלמת המדריך, צריך לבקש מהאדמין להקצות לכם את תפקידי ה-IAM הבאים בפרויקט:

להסבר על מתן תפקידים, ראו איך מנהלים את הגישה ברמת הפרויקט, התיקייה והארגון.

יכול להיות שאפשר לקבל את ההרשאות הנדרשות גם באמצעות תפקידים בהתאמה אישית או תפקידים מוגדרים מראש.

הגדרת ברירות מחדל ב-gcloud

כדי להגדיר את gcloud עם ערכי ברירת מחדל לשירות Cloud Run:

  1. מגדירים את פרויקט ברירת המחדל:

    gcloud config set project PROJECT_ID

    מחליפים את PROJECT_ID בשם הפרויקט שיצרתם לצורך המדריך הזה.

  2. מגדירים את gcloud לאזור שבחרתם:

    gcloud config set run/region REGION

    מחליפים את REGION באזור נתמך ב-Cloud Run לבחירתכם.

מיקומים של Cloud Run

‫Cloud Run הוא שירות אזורי, כלומר התשתית שמריצה את שירותי Cloud Run ממוקמת באזור ספציפי ומנוהלת על ידי Google כך שתהיה זמינה באופן יתירתי בכל התחומים באותו אזור.

הקריטריונים העיקריים לבחירת האזור שבו יפעלו שירותי Cloud Run הם זמן האחזור, הזמינות או העמידות שנדרשים לכם. בדרך כלל אפשר לבחור את האזור הקרוב ביותר למשתמשים, אבל כדאי לקחת בחשבון את המיקום של מוצרים Google Cloud אחרים שבהם נעשה שימוש בשירות Cloud Run. השימוש במוצרים של Google Cloud Google Cloud יחד בכמה מיקומים יכול להשפיע על זמן האחזור ועל העלות של השירות.

‫Cloud Run זמין באזורים הבאים:

בכפוף לתמחור ברמה 1

בכפוף לתמחור ברמה 2

  • africa-south1 (יוהנסבורג)
  • asia-east2 (הונג קונג)
  • asia-northeast3 (סיאול, קוריאה הדרומית)
  • asia-southeast1 (סינגפור)
  • asia-southeast2 (ג'אקארטה)
  • asia-south2 (דלהי, הודו)
  • australia-southeast1 (סידני)
  • australia-southeast2 (מלבורן)
  • europe-central2 (ורשה, פולין)
  • europe-west10 (Berlin)
  • europe-west12 (טורינו)
  • europe-west2 (לונדון, בריטניה) סמל של עלה רמה נמוכה של CO2
  • europe-west3 (פרנקפורט, גרמניה)
  • europe-west6 (ציריך, שווייץ) סמל של עלה רמה נמוכה של CO2
  • me-central1 (דוחה)
  • me-central2 (דמאם)
  • northamerica-northeast1 (מונטריאול) סמל של עלה רמה נמוכה של CO2
  • northamerica-northeast2 (טורונטו) סמל של עלה רמה נמוכה של CO2
  • southamerica-east1 (סאו פאולו, ברזיל) סמל של עלה רמה נמוכה של CO2
  • southamerica-west1 (סנטיאגו, צ'ילה) סמל של עלה רמה נמוכה של CO2
  • us-west2 (לוס אנג'לס)
  • us-west3 (סולט לייק סיטי)
  • us-west4 (לאס וגאס)

אם כבר יצרתם שירות Cloud Run, תוכלו לראות את האזור בלוח הבקרה של Cloud Run בGoogle Cloud מסוף.

יצירת מאגר רגיל ב-Artifact Registry

יוצרים מאגר רגיל של Artifact Registry לאחסון קובץ האימג' של הקונטיינר:

gcloud artifacts repositories create REPOSITORY \
    --repository-format=docker \
    --location=REGION

מחליפים את:

  • REPOSITORY בשם ייחודי למאגר.
  • REGION עם האזור שבו ישמש מאגר Artifact Registry. Google Cloud

יוצרים נושא Pub/Sub

השירות לדוגמה מופעל על ידי הודעות שמתפרסמות בנושא Pub/Sub, ולכן צריך ליצור נושא ב-Pub/Sub.

gcloud

כדי ליצור נושא Pub/Sub חדש, משתמשים בפקודה:

gcloud pubsub topics create myRunTopic

אפשר להשתמש ב-myRunTopic או להחליף אותו בשם של נושא שהוא ייחודי בפרויקט Google Cloud .

Terraform

כדי ללמוד איך להחיל הגדרות ב-Terraform או להסיר אותן, ראו פקודות בסיסיות ב-Terraform.

כדי ליצור נושא Pub/Sub, מוסיפים לקובץ main.tf הקיים את הנתונים הבאים:

resource "google_pubsub_topic" "default" {
  name = "pubsub_topic"
}

אפשר להשתמש בשם נושא שהוא ייחודי בתוך פרויקט בענן.

אחזור של דוגמת הקוד

כדי לאחזר את דוגמת קוד לשימוש:

  1. משכפלים את מאגר האפליקציה לדוגמה ומעבירים אותו למכונה המקומית:

    Node.js

    git clone https://github.com/GoogleCloudPlatform/nodejs-docs-samples.git

    אפשרות נוספת היא להוריד את הדוגמה כקובץ ZIP ולחלץ אותה.

    Python

    git clone https://github.com/GoogleCloudPlatform/python-docs-samples.git

    אפשרות נוספת היא להוריד את הדוגמה כקובץ ZIP ולחלץ אותה.

    המשך

    git clone https://github.com/GoogleCloudPlatform/golang-samples.git

    אפשרות נוספת היא להוריד את הדוגמה כקובץ ZIP ולחלץ אותה.

    Java

    git clone https://github.com/GoogleCloudPlatform/java-docs-samples.git

    אפשרות נוספת היא להוריד את הדוגמה כקובץ ZIP ולחלץ אותה.

    C#‎

    git clone https://github.com/GoogleCloudPlatform/dotnet-docs-samples.git

    אפשרות נוספת היא להוריד את הדוגמה כקובץ ZIP ולחלץ אותה.

  2. עוברים לספרייה שמכילה את הקוד לדוגמה של Cloud Run:

    Node.js

    cd nodejs-docs-samples/run/pubsub/

    Python

    cd python-docs-samples/run/pubsub/

    Go

    cd golang-samples/run/pubsub/

    Java

    cd java-docs-samples/run/pubsub/

    C#‎

    cd dotnet-docs-samples/run/Run.Samples.Pubsub.MinimalApi/

בדיקת הקוד

הקוד במדריך הזה כולל את הרכיבים הבאים:

  • שרת שמטפל בבקשות נכנסות.

    Node.js

    כדי שיהיה קל לבדוק את שירות Node.js, הגדרת השרת מופרדת מהפעלת השרת.

    שרת האינטרנט של Node.js מוגדר ב-app.js.

    const express = require('express');
    const app = express();
    
    // This middleware is available in Express v4.16.0 onwards
    app.use(express.json());

    שרת האינטרנט מופעל ב-index.js:

    const app = require('./app.js');
    const PORT = parseInt(parseInt(process.env.PORT)) || 8080;
    
    app.listen(PORT, () =>
      console.log(`nodejs-pubsub-tutorial listening on port ${PORT}`)
    );

    Python

    import base64
    
    from flask import Flask, request
    
    
    app = Flask(__name__)
    

    המשך

    
    // Sample run-pubsub is a Cloud Run service which handles Pub/Sub messages.
    package main
    
    import (
    	"encoding/json"
    	"io"
    	"log"
    	"net/http"
    	"os"
    )
    
    func main() {
    	http.HandleFunc("/", HelloPubSub)
    	// Determine port for HTTP service.
    	port := os.Getenv("PORT")
    	if port == "" {
    		port = "8080"
    		log.Printf("Defaulting to port %s", port)
    	}
    	// Start HTTP server.
    	log.Printf("Listening on port %s", port)
    	if err := http.ListenAndServe(":"+port, nil); err != nil {
    		log.Fatal(err)
    	}
    }
    

    Java

    import org.springframework.boot.SpringApplication;
    import org.springframework.boot.autoconfigure.SpringBootApplication;
    
    @SpringBootApplication
    public class PubSubApplication {
      public static void main(String[] args) {
        SpringApplication.run(PubSubApplication.class, args);
      }
    }

    C#‎

    var builder = WebApplication.CreateBuilder(args);
    var app = builder.Build();
    
    var port = Environment.GetEnvironmentVariable("PORT");
    if (port != null)
    {
        app.Urls.Add($"http://0.0.0.0:{port}");
    }
    

  • פונקציית handler שמעבדת את ההודעה ב-Pub/Sub ורושמת ברשומה ברכה.

    Node.js

    app.post('/', (req, res) => {
      if (!req.body) {
        const msg = 'no Pub/Sub message received';
        console.error(`error: ${msg}`);
        res.status(400).send(`Bad Request: ${msg}`);
        return;
      }
      if (!req.body.message) {
        const msg = 'invalid Pub/Sub message format';
        console.error(`error: ${msg}`);
        res.status(400).send(`Bad Request: ${msg}`);
        return;
      }
    
      const pubSubMessage = req.body.message;
      const name = pubSubMessage.data
        ? Buffer.from(pubSubMessage.data, 'base64').toString().trim()
        : 'World';
    
      console.log(`Hello ${name}!`);
      res.status(204).send();
    });

    Python

    @app.route("/", methods=["POST"])
    def index():
        """Receive and parse Pub/Sub messages."""
        envelope = request.get_json()
        if not envelope:
            msg = "no Pub/Sub message received"
            print(f"error: {msg}")
            return f"Bad Request: {msg}", 400
    
        if not isinstance(envelope, dict) or "message" not in envelope:
            msg = "invalid Pub/Sub message format"
            print(f"error: {msg}")
            return f"Bad Request: {msg}", 400
    
        pubsub_message = envelope["message"]
    
        name = "World"
        if isinstance(pubsub_message, dict) and "data" in pubsub_message:
            name = base64.b64decode(pubsub_message["data"]).decode("utf-8").strip()
    
        print(f"Hello {name}!")
    
        return ("", 204)
    
    

    המשך

    
    // WrappedMessage is the payload of a Pub/Sub event.
    //
    // For more information about receiving messages from a Pub/Sub event
    // see: https://cloud.google.com/pubsub/docs/push#receive_push
    type WrappedMessage struct {
    	Message struct {
    		Data []byte `json:"data,omitempty"`
    		ID   string `json:"id"`
    	} `json:"message"`
    	Subscription string `json:"subscription"`
    }
    
    // HelloPubSub receives and processes a Pub/Sub push message.
    func HelloPubSub(w http.ResponseWriter, r *http.Request) {
    	var m WrappedMessage
    	body, err := io.ReadAll(r.Body)
    	defer r.Body.Close()
    	if err != nil {
    		log.Printf("io.ReadAll: %v", err)
    		http.Error(w, "Bad Request", http.StatusBadRequest)
    		return
    	}
    	// byte slice unmarshalling handles base64 decoding.
    	if err := json.Unmarshal(body, &m); err != nil {
    		log.Printf("json.Unmarshal: %v", err)
    		http.Error(w, "Bad Request", http.StatusBadRequest)
    		return
    	}
    
    	name := string(m.Message.Data)
    	if name == "" {
    		name = "World"
    	}
    	log.Printf("Hello %s!", name)
    }
    

    Java

    import com.example.cloudrun.Body;
    import java.util.Base64;
    import org.apache.commons.lang3.StringUtils;
    import org.springframework.http.HttpStatus;
    import org.springframework.http.ResponseEntity;
    import org.springframework.web.bind.annotation.RequestBody;
    import org.springframework.web.bind.annotation.RequestMapping;
    import org.springframework.web.bind.annotation.RequestMethod;
    import org.springframework.web.bind.annotation.RestController;
    
    // PubsubController consumes a Pub/Sub message.
    @RestController
    public class PubSubController {
      @RequestMapping(value = "/", method = RequestMethod.POST)
      public ResponseEntity<String> receiveMessage(@RequestBody Body body) {
        // Get PubSub message from request body.
        Body.Message message = body.getMessage();
        if (message == null) {
          String msg = "Bad Request: invalid Pub/Sub message format";
          System.out.println(msg);
          return new ResponseEntity<>(msg, HttpStatus.BAD_REQUEST);
        }
    
        String data = message.getData();
        String target =
            !StringUtils.isEmpty(data) ? new String(Base64.getDecoder().decode(data)) : "World";
        String msg = "Hello " + target + "!";
    
        System.out.println(msg);
        return new ResponseEntity<>(msg, HttpStatus.OK);
      }
    }

    C#‎

    app.MapPost("/", (Envelope envelope) =>
    {
        if (envelope?.Message?.Data == null)
        {
            app.Logger.LogWarning("Bad Request: Invalid Pub/Sub message format.");
            return Results.BadRequest();
        }
    
        var data = Convert.FromBase64String(envelope.Message.Data);
        var target = System.Text.Encoding.UTF8.GetString(data);
    
        app.Logger.LogInformation($"Hello {target}!");
    
        return Results.NoContent();
    });
    

    צריך לתכנת את השירות כך שיחזיר קוד תגובת HTTP מדויק. קודי הצלחה, כמו HTTP 200 או 204, מאשרים שהעיבוד של הודעת Pub/Sub הושלם. קודי שגיאה, כמו HTTP 400 או 500, מציינים שהמערכת תנסה לשלוח את ההודעה שוב, כמו שמתואר במאמר קבלת הודעות באמצעות מדריך Push. בניגוד לפונקציות שנוצרו באמצעות Cloud Functions v2 API, אי אפשר להשבית ניסיונות חוזרים לפונקציות שנוצרו באמצעות Cloud Run Admin API. מידע נוסף זמין במאמר בנושא הגדרת ניסיונות חוזרים של פונקציות מבוססות-אירועים.

  • Dockerfile שמגדיר את סביבת ההפעלה של השירות. התוכן של Dockerfile משתנה בהתאם לשפה.

    Node.js

    
    # Use the official lightweight Node.js image.
    # https://hub.docker.com/_/node
    FROM node:20-slim
    # Create and change to the app directory.
    WORKDIR /usr/src/app
    
    # Copy application dependency manifests to the container image.
    # A wildcard is used to ensure both package.json AND package-lock.json are copied.
    # Copying this separately prevents re-running npm install on every code change.
    COPY package*.json ./
    
    # Install dependencies.
    # if you need a deterministic and repeatable build create a
    # package-lock.json file and use npm ci:
    # RUN npm ci --omit=dev
    # if you need to include development dependencies during development
    # of your application, use:
    # RUN npm install --dev
    
    RUN npm install --omit=dev
    
    # Copy local code to the container image.
    COPY . .
    
    # Run the web service on container startup.
    CMD [ "npm", "start" ]
    

    Python

    
    # Use the official Python image.
    # https://hub.docker.com/_/python
    FROM python:3.14
    
    # Allow statements and log messages to immediately appear in the Cloud Run logs
    ENV PYTHONUNBUFFERED True
    
    # Copy application dependency manifests to the container image.
    # Copying this separately prevents re-running pip install on every code change.
    COPY requirements.txt ./
    
    # Install production dependencies.
    RUN pip install -r requirements.txt
    
    # Copy local code to the container image.
    ENV APP_HOME /app
    WORKDIR $APP_HOME
    COPY . ./
    
    # Run the web service on container startup.
    # Use gunicorn webserver with one worker process and 8 threads.
    # For environments with multiple CPU cores, increase the number of workers
    # to be equal to the cores available.
    # Timeout is set to 0 to disable the timeouts of the workers to allow Cloud Run to handle instance scaling.
    CMD exec gunicorn --bind :$PORT --workers 1 --threads 8 --timeout 0 main:app
    

    המשך

    
    # Use the official Go image to create a binary.
    # This is based on Debian and sets the GOPATH to /go.
    # https://hub.docker.com/_/golang
    FROM golang:1.25-bookworm as builder
    
    # Create and change to the app directory.
    WORKDIR /app
    
    # Retrieve application dependencies.
    # This allows the container build to reuse cached dependencies.
    # Expecting to copy go.mod and if present go.sum.
    COPY go.* ./
    RUN go mod download
    
    # Copy local code to the container image.
    COPY . ./
    
    # Build the binary.
    RUN go build -v -o server
    
    # Use the official Debian slim image for a lean production container.
    # https://hub.docker.com/_/debian
    # https://docs.docker.com/develop/develop-images/multistage-build/#use-multi-stage-builds
    FROM debian:bookworm-slim
    RUN set -x && apt-get update && DEBIAN_FRONTEND=noninteractive apt-get install -y \
        ca-certificates && \
        rm -rf /var/lib/apt/lists/*
    
    # Copy the binary to the production image from the builder stage.
    COPY --from=builder /app/server /server
    
    # Run the web service on container startup.
    CMD ["/server"]
    

    Java

    בדוגמה הזו נעשה שימוש ב-Jib כדי ליצור תמונות Docker באמצעות כלים נפוצים של Java. ‫Jib מבצע אופטימיזציה של בניית קונטיינרים בלי צורך בקובץ Dockerfile או בהתקנה של Docker. מידע נוסף על יצירת מאגרי Java באמצעות Jib

    <plugin>
      <groupId>com.google.cloud.tools</groupId>
      <artifactId>jib-maven-plugin</artifactId>
      <version>3.4.0</version>
      <configuration>
        <to>
          <image>gcr.io/PROJECT_ID/pubsub</image>
        </to>
      </configuration>
    </plugin>
    

    C#‎

    # Build in SDK base image
    FROM mcr.microsoft.com/dotnet/sdk:6.0 AS build-env
    WORKDIR /app
    
    COPY *.csproj ./
    RUN dotnet restore
    
    COPY . ./
    RUN dotnet publish -r linux-x64 --no-self-contained -p:PublishReadyToRun=true -c Release -o out
    
    # Copy to runtime image
    FROM mcr.microsoft.com/dotnet/aspnet:6.0
    WORKDIR /app
    COPY --from=build-env /app/out .
    
    # Port passed in by Cloud Run via environment variable PORT.  Default 8080.
    ENV PORT=8080
    
    ENTRYPOINT ["dotnet", "Run.Samples.Pubsub.MinimalApi.dll"]

לפרטים על אימות המקור של בקשות Pub/Sub, ראו שילוב עם Pub/Sub.

שליחת הקוד

תהליך שליחת הקוד כולל שלושה שלבים: יצירת קובץ אימג' של קונטיינר באמצעות Cloud Build, העלאת קובץ האימג' של הקונטיינר ל-Artifact Registry ופריסת קובץ האימג' של הקונטיינר ל-Cloud Run.

כדי לשלוח את הקוד:

  1. יוצרים את הקונטיינר ומפרסמים אותו ב-Artifact Registry:

    Node.js

    gcloud builds submit --tag REGION-docker.pkg.dev/PROJECT_ID/REPOSITORY/pubsub
    החלפה:
    • PROJECT_ID במזהה הפרויקט ב- Google Cloud .
    • REPOSITORY בשם המאגר ב-Artifact Registry.
    • REGION עם האזור שבו ישמש מאגר Artifact Registry. Google Cloud

    pubsub הוא שם התמונה.

    אם הפעולה תצליח, תופיע הודעת SUCCESS עם המזהה, זמן היצירה ושם התמונה. התמונה מאוחסנת ב-Artifact Registry ואפשר לעשות בה שימוש חוזר אם צריך.

    Python

    gcloud builds submit --tag REGION-docker.pkg.dev/PROJECT_ID/REPOSITORY/pubsub
    החלפה:
    • PROJECT_ID במזהה הפרויקט ב- Google Cloud .
    • REPOSITORY בשם המאגר ב-Artifact Registry.
    • REGION עם האזור שבו ישמש מאגר Artifact Registry. Google Cloud

    pubsub הוא שם התמונה.

    אם הפעולה תצליח, תופיע הודעת SUCCESS עם המזהה, זמן היצירה ושם התמונה. התמונה מאוחסנת ב-Artifact Registry ואפשר לעשות בה שימוש חוזר אם צריך.

    המשך

    gcloud builds submit --tag REGION-docker.pkg.dev/PROJECT_ID/REPOSITORY/pubsub
    החלפה:
    • PROJECT_ID במזהה הפרויקט ב- Google Cloud .
    • REPOSITORY בשם המאגר ב-Artifact Registry.
    • REGION עם האזור שבו ישמש מאגר Artifact Registry. Google Cloud

    pubsub הוא שם התמונה.

    בסיום מוצלח, אמורה להופיע הודעת SUCCESS עם המזהה, זמן היצירה ושם התמונה. התמונה מאוחסנת ב-Artifact Registry ואפשר לעשות בה שימוש חוזר אם צריך.

    Java

    • משתמשים בכלי העזר של פרטי הכניסה של ה-CLI של gcloud כדי להעניק ל-Docker הרשאה להעביר בדחיפה אל Artifact Registry.
      gcloud auth configure-docker
    • משתמשים בתוסף Jib Maven כדי ליצור את הקונטיינר ולהעביר אותו בדחיפה ל-Artifact Registry.
      mvn compile jib:build -D image=REGION-docker.pkg.dev/PROJECT_ID/REPOSITORY/pubsub
      החלפה:
      • PROJECT_ID במזהה הפרויקט ב- Google Cloud .
      • REPOSITORY בשם המאגר ב-Artifact Registry.
      • REGION עם האזור שבו ישמש מאגר Artifact Registry. Google Cloud

      pubsub הוא שם התמונה.

      אם הפעולה תצליח, תוצג ההודעה BUILD SUCCESS. התמונה מאוחסנת ב-Artifact Registry ואפשר לעשות בה שימוש חוזר אם צריך.

    C#‎

    gcloud builds submit --tag REGION-docker.pkg.dev/PROJECT_ID/REPOSITORY/pubsub
    מחליפים את:
    • PROJECT_ID במזהה הפרויקט ב- Google Cloud .
    • REPOSITORY בשם המאגר ב-Artifact Registry.
    • REGION עם האזור שבו ישמש מאגר Artifact Registry. Google Cloud

    pubsub הוא שם התמונה.

    אם הפעולה תצליח, תופיע הודעת SUCCESS עם המזהה, זמן היצירה ושם התמונה. התמונה מאוחסנת ב-Artifact Registry ואפשר לעשות בה שימוש חוזר אם צריך.

  2. פורסים את האפליקציה:

    שורת הפקודה

    1. מריצים את הפקודה הבאה כדי לפרוס את האפליקציה:

      gcloud run deploy pubsub-tutorial --image REGION-docker.pkg.dev/PROJECT_ID/REPOSITORY/pubsub  --no-allow-unauthenticated
      החלפה:
      • PROJECT_ID במזהה הפרויקט ב- Google Cloud .
      • REPOSITORY בשם המאגר ב-Artifact Registry.
      • REGION עם האזור שבו ישמש מאגר Artifact Registry. Google Cloud

      pubsub הוא שם האימג' ו-pubsub-tutorial הוא שם השירות. שימו לב שקובץ אימג' של הקונטיינר נפרס בשירות ובאזור שהגדרתם קודם בקטע הגדרת gcloud.

      הדגל --no-allow-unauthenticated מגביל את הגישה לשירות ללא אימות. אם השירות פרטי, אפשר להסתמך על השילוב האוטומטי של Cloud Run עם Pub/Sub כדי לאמת בקשות. פרטים נוספים על ההגדרה מופיעים במאמר בנושא שילוב עם Pub/Sub. לפרטים נוספים על אימות שמבוסס על ניהול זהויות והרשאות גישה (IAM), אפשר לעיין במאמר ניהול גישה באמצעות IAM.

      מחכים עד שהפריסה תושלם. התהליך הזה יכול להימשך כחצי דקה. אם הפעולה בוצעה ללא שגיאות, כתובת ה-URL של השירות מוצגת בשורת הפקודה. כתובת ה-URL הזו משמשת להגדרת מינוי ל-Pub/Sub.

    2. אם רוצים לפרוס עדכון קוד בשירות, חוזרים על השלבים הקודמים. כל פריסה לשירות יוצרת גרסה חדשה ומתחילה להציג תנועה באופן אוטומטי כשהיא מוכנה.

    Terraform

    כדי ליצור שירות Cloud Run, מוסיפים את הקוד הבא לקובץ .tf הקיים.

    resource "google_project_service" "cloudrun_api" {
       service            = "run.googleapis.com"
       disable_on_destroy = false
    }
    
    resource "google_cloud_run_v2_service" "default" {
       name     = "pubsub-tutorial"
       location = "REGION"
    
       template {
          containers {
             image = "IMAGE_URL"
         }
       }
       depends_on = [google_project_service.cloudrun_api]
    }
             
    החלפה:
    • IMAGE_URL עם כתובת ה-URL של התמונה: REGION-docker.pkg.dev/PROJECT_ID/REPOSITORY/pubsub
    • REGION עם האזור שבו ישמש מאגר Artifact Registry. Google Cloud

שילוב עם Pub/Sub

כדי לשלב את השירות עם Pub/Sub:

gcloud

  1. יוצרים או בוחרים חשבון שירות שייצג את הזהות של מינוי Pub/Sub.

    gcloud iam service-accounts create cloud-run-pubsub-invoker \
        --display-name "Cloud Run Pub/Sub Invoker"

    אפשר להשתמש ב-cloud-run-pubsub-invoker או להחליף אותו בשם ייחודי בתוך הפרויקט Google Cloud .

  2. יוצרים מינוי ל-Pub/Sub עם חשבון השירות:

    1. נותנים לחשבון השירות של המפעיל הרשאה להפעיל את שירות pubsub-tutorial:

      gcloud run services add-iam-policy-binding pubsub-tutorial \
      --member=serviceAccount:cloud-run-pubsub-invoker@PROJECT_ID.iam.gserviceaccount.com \
      --role=roles/run.invoker

      יכול להיות שיחלפו כמה דקות עד שהשינויים ב-IAM יתעדכנו. בינתיים, יכול להיות שתראו שגיאות HTTP 403 ביומני השירות.

    2. מאפשרים ל-Pub/Sub ליצור טוקנים לאימות בפרויקט:

      gcloud projects add-iam-policy-binding PROJECT_ID \
         --member=serviceAccount:service-PROJECT_NUMBER@gcp-sa-pubsub.iam.gserviceaccount.com \
         --role=roles/iam.serviceAccountTokenCreator

      מחליפים את:

      • PROJECT_ID במזהה הפרויקט ב- Google Cloud .
      • PROJECT_NUMBER במספר הפרויקט. Google Cloud

      מזהה הפרויקט ומספר הפרויקט מופיעים בחלונית Project info בGoogle Cloud מסוף של הפרויקט.

    3. יוצרים מינוי ל-Pub/Sub עם חשבון השירות:

      gcloud pubsub subscriptions create myRunSubscription --topic myRunTopic \
      --ack-deadline=600 \
      --push-endpoint=SERVICE-URL/ \
      --push-auth-service-account=cloud-run-pubsub-invoker@PROJECT_ID.iam.gserviceaccount.com

      מחליפים את:

      • myRunTopic בנושא שיצרתם קודם.
      • SERVICE-URL עם כתובת ה-URL מסוג HTTPS שסופקה כשפרסתם את השירות. כתובת ה-URL הזו פועלת גם אם הוספתם מיפוי דומיין.
      • PROJECT_ID במזהה הפרויקט ב- Google Cloud .

      הדגל --push-auth-service-account מפעיל את הפונקציונליות של Pub/Sub push עבור אימות והרשאה.

      הדומיין של שירות Cloud Run נרשם אוטומטית לשימוש במינויים ל-Pub/Sub.

      ב-Cloud Run בלבד, יש בדיקת אימות מובנית כדי לוודא שהאסימון תקף, ובדיקת הרשאה כדי לוודא שלחשבון השירות יש הרשאה להפעיל את שירות Cloud Run.

השירות משולב עכשיו באופן מלא עם Pub/Sub.

Terraform

  1. יוצרים או בוחרים חשבון שירות שייצג את הזהות של מינוי Pub/Sub.

    resource "google_service_account" "sa" {
      account_id   = "cloud-run-pubsub-invoker"
      display_name = "Cloud Run Pub/Sub Invoker"
    }
  2. יוצרים מינוי ל-Pub/Sub עם חשבון השירות:

    1. נותנים לחשבון השירות של המפעיל הרשאה להפעיל את שירות pubsub-tutorial:

      resource "google_cloud_run_service_iam_binding" "binding" {
        location = google_cloud_run_v2_service.default.location
        service  = google_cloud_run_v2_service.default.name
        role     = "roles/run.invoker"
        members  = ["serviceAccount:${google_service_account.sa.email}"]
      }
    2. מאפשרים ל-Pub/Sub ליצור טוקנים לאימות בפרויקט:

      resource "google_project_service_identity" "pubsub_agent" {
        provider = google-beta
        project  = data.google_project.project.project_id
        service  = "pubsub.googleapis.com"
      }
      
      resource "google_project_iam_binding" "project_token_creator" {
        project = data.google_project.project.project_id
        role    = "roles/iam.serviceAccountTokenCreator"
        members = ["serviceAccount:${google_project_service_identity.pubsub_agent.email}"]
      }
    3. יוצרים מינוי ל-Pub/Sub עם חשבון השירות:

      resource "google_pubsub_subscription" "subscription" {
        name  = "pubsub_subscription"
        topic = google_pubsub_topic.default.name
        push_config {
          push_endpoint = google_cloud_run_v2_service.default.uri
          oidc_token {
            service_account_email = google_service_account.sa.email
          }
          attributes = {
            x-goog-version = "v1"
          }
        }
        depends_on = [google_cloud_run_v2_service.default]
      }

השירות משולב עכשיו באופן מלא עם Pub/Sub.

רוצה לנסות?

כדי לבדוק את הפתרון מקצה לקצה:

  1. שולחים הודעת Pub/Sub לנושא:

    gcloud pubsub topics publish myRunTopic --message "Runner"

    אפשר גם לפרסם הודעות באופן פרוגרמטי במקום להשתמש בשורת הפקודה, כמו שמוצג במדריך הזה. מידע נוסף זמין במאמר בנושא פרסום הודעות.

  2. עוברים ליומני השירות:

    1. ניווט אל מסוףGoogle Cloud
    2. לוחצים על השירות pubsub-tutorial.
    3. לוחצים על הכרטיסייה יומנים.

      יכול להיות שייקח ליומנים כמה דקות להופיע. אם הם לא מופיעים מיד, כדאי לבדוק שוב אחרי כמה רגעים.

  3. מחפשים את ההודעה Hello Runner!‎.

הסרת המשאבים

כדי לעיין בתרחיש שימוש מפורט יותר של Cloud Run עם Pub/Sub, אפשר לדלג על שלב הניקוי בשלב הזה ולהמשיך אל המדריך לעיבוד תמונות באמצעות Cloud Run.

כדי להימנע מחיובים נוספים בחשבון Google Cloud , מוחקים את כל המשאבים שהצבתם באמצעות המדריך הזה.

מחיקת הפרויקט

אם יצרתם פרויקט חדש בשביל המדריך הזה, מוחקים את הפרויקט. אם השתמשתם בפרויקט קיים ואתם רוצים לשמור אותו בלי השינויים שהוספתם במדריך הזה, תצטרכו למחוק את המשאבים שיצרתם לצורך המדריך.

הדרך הקלה ביותר לבטל את החיוב היא למחוק את הפרויקט שיצרתם בשביל המדריך.

כדי למחוק את הפרויקט:

  1. במסוף Google Cloud , נכנסים לדף Manage resources.

    כניסה לדף Manage resources

  2. ברשימת הפרויקטים, בוחרים את הפרויקט שרוצים למחוק ולוחצים על Delete.
  3. כדי למחוק את הפרויקט, כותבים את מזהה הפרויקט בתיבת הדו-שיח ולוחצים על Shut down.

מחיקת משאבי הדרכה

  1. מוחקים את שירות Cloud Run שפרסתם במדריך הזה. שירותי Cloud Run לא צוברים עלויות עד שהם מקבלים בקשות.

    כדי למחוק את שירות Cloud Run, מריצים את הפקודה הבאה:

    gcloud run services delete SERVICE-NAME

    מחליפים את SERVICE-NAME בשם השירות.

    אפשר גם למחוק שירותים של Cloud Run מGoogle Cloud המסוף.

  2. מסירים את הגדרת ברירת המחדל של האזור gcloud שהוספתם במהלך ההגדרה של המדריך:

     gcloud config unset run/region
    
  3. מסירים את הגדרות הפרויקט:

     gcloud config unset project
    
  4. מחיקת משאבים אחרים Google Cloud שנוצרו במדריך הזה:

המאמרים הבאים