Join us in person and online for Firebase Summit on October 18, 2022. Learn how Firebase can help you accelerate app development, release your app with confidence, and scale with ease. Register now

Udostępniaj dynamiczną zawartość i hostuj mikroserwisy za pomocą Cloud Run

Zadbaj o dobrą organizację dzięki kolekcji Zapisuj i kategoryzuj treści zgodnie ze swoimi preferencjami.

Połącz Cloud Run z Hostingiem Firebase, aby generować i udostępniać treści dynamiczne lub tworzyć interfejsy API REST jako mikrousługi.

Za pomocą Cloud Run możesz wdrożyć aplikację spakowaną w obrazie kontenera. Następnie, korzystając z Hostingu Firebase, możesz kierować żądania HTTPS, aby wyzwolić aplikację w kontenerze.

  • Cloud Run obsługuje kilka języków (w tym Go, Node.js, Python i Java), co zapewnia elastyczność w korzystaniu z wybranego języka programowania i struktury.
  • Cloud Run automatycznie i poziomo skaluje obraz kontenera, aby obsłużyć odebrane żądania, a następnie skaluje w dół, gdy zapotrzebowanie spada.
  • Płacisz tylko za procesor, pamięć i sieć zużyte podczas obsługi żądań.

Na przykład przypadki użycia i przykłady dotyczące Cloud Run zintegrowanego z Hostingiem Firebase znajdziesz w naszym omówieniu bezserwerowym .


Ten przewodnik pokazuje, jak:

  1. Napisz prostą aplikację Hello World
  2. Konteneryzuj aplikację i prześlij ją do Container Registry
  3. Wdróż obraz kontenera w Cloud Run
  4. Kieruj żądania hostingu do swojej aplikacji w kontenerach

Pamiętaj, że aby poprawić wydajność udostępniania zawartości dynamicznej, możesz opcjonalnie dostosować ustawienia pamięci podręcznej .

Zanim zaczniesz

Zanim zaczniesz korzystać z Cloud Run, musisz wykonać kilka początkowych zadań, w tym skonfigurować konto rozliczeniowe Cloud, włączyć Cloud Run API i zainstalować narzędzie wiersza poleceń gcloud .

Skonfiguruj rozliczenia za swój projekt

Cloud Run oferuje bezpłatny limit użytkowania , ale nadal musisz mieć konto rozliczeniowe Cloud powiązane z projektem Firebase, aby korzystać lub wypróbować Cloud Run.

Włącz interfejs API i zainstaluj pakiet SDK

  1. Włącz Cloud Run API w konsoli interfejsów Google API:

    1. Otwórz stronę Cloud Run API w konsoli interfejsów Google API.

    2. Po wyświetleniu monitu wybierz projekt Firebase.

    3. Kliknij Włącz na stronie Cloud Run API.

  2. Zainstaluj i zainicjuj pakiet Cloud SDK.

  3. Sprawdź, czy narzędzie gcloud jest skonfigurowane dla prawidłowego projektu:

    gcloud config list

Krok 1 : Napisz przykładową aplikację

Pamiętaj, że Cloud Run obsługuje wiele innych języków oprócz języków pokazanych w poniższym przykładzie.

Iść

  1. Utwórz nowy katalog o nazwie helloworld-go , a następnie zmień na niego katalog:

    mkdir helloworld-go
    cd helloworld-go
  2. Utwórz nowy plik o nazwie helloworld.go , a następnie dodaj następujący kod:

    package main
    
    import (
    	"fmt"
    	"log"
    	"net/http"
    	"os"
    )
    
    func handler(w http.ResponseWriter, r *http.Request) {
    	log.Print("helloworld: received a request")
    	target := os.Getenv("TARGET")
    	if target == "" {
    		target = "World"
    	}
    	fmt.Fprintf(w, "Hello %s!\n", target)
    }
    
    func main() {
    	log.Print("helloworld: starting server...")
    
    	http.HandleFunc("/", handler)
    
    	port := os.Getenv("PORT")
    	if port == "" {
    		port = "8080"
    	}
    
    	log.Printf("helloworld: listening on port %s", port)
    	log.Fatal(http.ListenAndServe(fmt.Sprintf(":%s", port), nil))
    }
    

    Ten kod tworzy podstawowy serwer WWW, który nasłuchuje na porcie zdefiniowanym przez zmienną środowiskową PORT .

Twoja aplikacja jest gotowa i gotowa do konteneryzacji i przesłania do Container Registry.

Node.js

  1. Utwórz nowy katalog o nazwie helloworld-nodejs , a następnie zmień na niego katalog:

    mkdir helloworld-nodejs
    cd helloworld-nodejs
  2. Utwórz plik package.json o następującej zawartości:

    {
      "name": "knative-serving-helloworld",
      "version": "1.0.0",
      "description": "Simple hello world sample in Node",
      "main": "index.js",
      "scripts": {
        "start": "node index.js"
      },
      "author": "",
      "license": "Apache-2.0",
      "dependencies": {
        "express": "^4.16.4"
      }
    }
    
  3. Utwórz nowy plik o nazwie index.js , a następnie dodaj następujący kod:

    const express = require('express');
    const app = express();
    
    app.get('/', (req, res) => {
      console.log('Hello world received a request.');
    
      const target = process.env.TARGET || 'World';
      res.send(`Hello ${target}!\n`);
    });
    
    const port = process.env.PORT || 8080;
    app.listen(port, () => {
      console.log('Hello world listening on port', port);
    });
    

    Ten kod tworzy podstawowy serwer WWW, który nasłuchuje na porcie zdefiniowanym przez zmienną środowiskową PORT .

Twoja aplikacja jest gotowa i gotowa do konteneryzacji i przesłania do Container Registry.

Pyton

  1. Utwórz nowy katalog o nazwie helloworld-python , a następnie zmień na niego katalog:

    mkdir helloworld-python
    cd helloworld-python
  2. Utwórz nowy plik o nazwie app.py , a następnie dodaj następujący kod:

    import os
    
    from flask import Flask
    
    app = Flask(__name__)
    
    @app.route('/')
    def hello_world():
        target = os.environ.get('TARGET', 'World')
        return 'Hello {}!\n'.format(target)
    
    if __name__ == "__main__":
        app.run(debug=True,host='0.0.0.0',port=int(os.environ.get('PORT', 8080)))
    

    Ten kod tworzy podstawowy serwer WWW, który nasłuchuje na porcie zdefiniowanym przez zmienną środowiskową PORT .

Twoja aplikacja jest gotowa i gotowa do konteneryzacji i przesłania do Container Registry.

Jawa

  1. Zainstaluj Java SE 8 lub nowszą wersję JDK i CURL .

    Pamiętaj, że musimy to zrobić tylko po to, aby w następnym kroku utworzyć nowy projekt internetowy. Plik Dockerfile, który jest opisany w dalszej części, załaduje wszystkie zależności do kontenera.

  2. W konsoli utwórz nowy pusty projekt internetowy za pomocą cURL, a następnie rozpakuj polecenia:

    curl https://start.spring.io/starter.zip \
        -d dependencies=web \
        -d name=helloworld \
        -d artifactId=helloworld \
        -o helloworld.zip
    unzip helloworld.zip

    Tworzy to projekt SpringBoot.

  3. Zaktualizuj klasę SpringBootApplication w src/main/java/com/example/helloworld/HelloworldApplication.java , dodając @RestController do obsługi mapowania / oraz dodaj pole @Value , aby zapewnić zmienną środowiskową TARGET :

    package com.example.helloworld;
    
    import org.springframework.beans.factory.annotation.Value;
    import org.springframework.boot.SpringApplication;
    import org.springframework.boot.autoconfigure.SpringBootApplication;
    import org.springframework.web.bind.annotation.GetMapping;
    import org.springframework.web.bind.annotation.RestController;
    
    @SpringBootApplication
    public class HelloworldApplication {
    
      @Value("${TARGET:World}")
      String target;
    
      @RestController
      class HelloworldController {
        @GetMapping("/")
        String hello() {
          return "Hello " + target + "!";
        }
      }
    
      public static void main(String[] args) {
        SpringApplication.run(HelloworldApplication.class, args);
      }
    }
    

    Ten kod tworzy podstawowy serwer WWW, który nasłuchuje na porcie zdefiniowanym przez zmienną środowiskową PORT .

Twoja aplikacja jest gotowa i gotowa do konteneryzacji i przesłania do Container Registry.

Krok 2 : Konteneryzuj aplikację i prześlij ją do Container Registry

  1. Konteneryzuj przykładową aplikację, tworząc nowy plik o nazwie Dockerfile w tym samym katalogu, co pliki źródłowe. Skopiuj następującą zawartość do swojego pliku.

    Iść

    # Use the official Golang image to create a build artifact.
    # This is based on Debian and sets the GOPATH to /go.
    FROM golang:1.13 as builder
    
    # Create and change to the app directory.
    WORKDIR /app
    
    # Retrieve application dependencies using go modules.
    # Allows container builds to reuse downloaded dependencies.
    COPY go.* ./
    RUN go mod download
    
    # Copy local code to the container image.
    COPY . ./
    
    # Build the binary.
    # -mod=readonly ensures immutable go.mod and go.sum in container builds.
    RUN CGO_ENABLED=0 GOOS=linux go build -mod=readonly -v -o server
    
    # Use the official Alpine image for a lean production container.
    # https://hub.docker.com/_/alpine
    # https://docs.docker.com/develop/develop-images/multistage-build/#use-multi-stage-builds
    FROM alpine:3
    RUN apk add --no-cache ca-certificates
    
    # 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"]
    

    Node.js

    # Use the official lightweight Node.js 12 image.
    # https://hub.docker.com/_/node
    FROM node:12-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 production dependencies.
    RUN npm install --only=production
    
    # Copy local code to the container image.
    COPY . ./
    
    # Run the web service on container startup.
    CMD [ "npm", "start" ]
    

    Pyton

    # Use the official lightweight Python image.
    # https://hub.docker.com/_/python
    FROM python:3.7-slim
    
    # Allow statements and log messages to immediately appear in the Knative logs
    ENV PYTHONUNBUFFERED True
    
    # Copy local code to the container image.
    ENV APP_HOME /app
    WORKDIR $APP_HOME
    COPY . ./
    
    # Install production dependencies.
    RUN pip install Flask gunicorn
    
    # Run the web service on container startup. Here we use the 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.
    CMD exec gunicorn --bind :$PORT --workers 1 --threads 8 --timeout 0 app:app
    

    Jawa

    # Use the official maven/Java 8 image to create a build artifact: https://hub.docker.com/_/maven
    FROM maven:3.5-jdk-8-alpine as builder
    
    # Copy local code to the container image.
    WORKDIR /app
    COPY pom.xml .
    COPY src ./src
    
    # Build a release artifact.
    RUN mvn package -DskipTests
    
    # Use the Official OpenJDK image for a lean production stage of our multi-stage build.
    # https://hub.docker.com/_/openjdk
    # https://docs.docker.com/develop/develop-images/multistage-build/#use-multi-stage-builds
    FROM openjdk:8-jre-alpine
    
    # Copy the jar to the production image from the builder stage.
    COPY --from=builder /app/target/helloworld-*.jar /helloworld.jar
    
    # Run the web service on container startup.
    CMD ["java", "-Djava.security.egd=file:/dev/./urandom", "-jar", "/helloworld.jar"]
    

  2. Utwórz obraz kontenera za pomocą Cloud Build, uruchamiając następujące polecenie z katalogu zawierającego plik Dockerfile:

    gcloud builds submit --tag gcr.io/PROJECT_ID/helloworld

    Po sukcesie zobaczysz komunikat SUKCES zawierający nazwę obrazu
    ( gcr.io/ PROJECT_ID /helloworld ).

Obraz kontenera jest teraz przechowywany w Container Registry i w razie potrzeby można go ponownie wykorzystać.

Pamiętaj, że zamiast Cloud Build możesz użyć lokalnie zainstalowanej wersji Dockera do lokalnego skompilowania kontenera .

Krok 3 : Wdróż obraz kontenera w Cloud Run

  1. Wdróż za pomocą następującego polecenia:

    gcloud run deploy --image gcr.io/PROJECT_ID/helloworld

  2. Gdy pojawi się monit:

  3. Poczekaj chwilę na zakończenie wdrażania. Po pomyślnym zakończeniu wiersz poleceń wyświetla adres URL usługi. Na przykład: https://helloworld- RANDOM_HASH -us-central1.a.run.app

  4. Odwiedź wdrożony kontener, otwierając adres URL usługi w przeglądarce internetowej.

W następnym kroku dowiesz się, jak uzyskać dostęp do tej aplikacji znajdującej się w kontenerach z adresu URL w Hostingu Firebase , aby mogła generować zawartość dynamiczną dla Twojej witryny hostowanej przez Firebase.

Krok 4: Kieruj żądania hostingu do swojej aplikacji w kontenerach

Dzięki regułom przepisywania możesz kierować żądania pasujące do określonych wzorców do jednego miejsca docelowego.

Poniższy przykład pokazuje, jak kierować wszystkie żądania ze strony /helloworld w witrynie Hosting, aby wyzwolić uruchamianie i uruchamianie instancji kontenera helloworld .

  1. Upewnić się, że:

    Szczegółowe instrukcje dotyczące instalowania interfejsu wiersza polecenia i inicjowania usługi Hosting znajdują się w przewodniku Wprowadzenie do usługi Hosting .

  2. Otwórz plik firebase.json .

  3. Dodaj następującą konfigurację rewrite w sekcji hosting :

    "hosting": {
      // ...
    
      // Add the "rewrites" attribute within "hosting"
      "rewrites": [ {
        "source": "/helloworld",
        "run": {
          "serviceId": "helloworld",  // "service name" (from when you deployed the container image)
          "region": "us-central1"     // optional (if omitted, default is us-central1)
        }
      } ]
    }
    
  4. Wdróż konfigurację hostingu w witrynie, uruchamiając następujące polecenie z katalogu głównego katalogu projektu:

    firebase deploy

Twój kontener jest teraz dostępny pod następującymi adresami URL:

  • Twoje subdomeny Firebase:
    PROJECT_ID .web.app/ i PROJECT_ID .firebaseapp.com/

  • Wszystkie połączone domeny niestandardowe :
    CUSTOM_DOMAIN /

Odwiedź stronę konfiguracji hostingu, aby uzyskać więcej informacji na temat przepisywania reguł . Możesz też dowiedzieć się o kolejności priorytetów odpowiedzi w różnych konfiguracjach Hostingu.

Przetestuj lokalnie

Podczas programowania możesz uruchomić i przetestować obraz kontenera lokalnie. Szczegółowe instrukcje znajdziesz w dokumentacji Cloud Run .

Następne kroki