Menyiapkan proxy Pub/Sub untuk klien seluler di GKE


Tutorial ini menunjukkan cara memublikasikan pesan dari aplikasi seluler atau sisi klien ke Pub/Sub dengan menggunakan proxy yang menangani autentikasi dan logika otorisasi, bukan kredensial sisi klien.

Meskipun Anda dapat mengautentikasi pesan dari klien ke Pub/Sub menggunakan Identity and Access Management (IAM), kredensial yang berumur panjang seperti itu tidak pernah kedaluwarsa. Di aplikasi sisi klien, kredensial ini dapat ditemukan melalui teknik seperti dekompilasi aplikasi dan rekayasa balik.

Sebagai gantinya, Anda dapat memindahkan logika autentikasi dan otorisasi ke proxy yang melakukan tugas-tugas berikut:

  • Mengautentikasi permintaan masuk untuk memvalidasi pengguna.
  • Meneruskan permintaan ke Pub/Sub beserta izin IAM yang sesuai.

Tutorial ini menunjukkan cara menerapkan proxy Pub/Sub di Google Kubernetes Engine (GKE). Tutorial ini ditujukan bagi developer aplikasi dan arsitek sistem yang menentukan dan menerapkan desain untuk aplikasi seluler atau aplikasi sisi klien. Hal ini mengasumsikan bahwa Anda memahami konsep dasar Kubernetes dan sudah memahami Cloud Endpoints.

Alur permintaan untuk tutorial ini

Untuk memahami kecocokan Pub/Sub dengan pipeline streaming, pertimbangkan analisis clickstream. Dalam kasus penggunaan ini, Anda mungkin ingin memahami bagaimana pengguna berinteraksi dengan aplikasi seluler. Untuk mendapatkan analisis ini, Anda menangkap aktivitas pengguna secara real time. Diagram berikut menunjukkan aliran data.

Proxy Pub/Sub menerima pesan dari klien sebelum data digabungkan.

Data yang diambil oleh aplikasi akan dikirimkan ke Pub/Sub melalui proxy. Pub/Sub dapat memiliki pelanggan downstream, seperti Dataflow atau Dataproc, yang menggabungkan data sehingga Anda dapat melakukan analisis yang bermakna.

Diagram berikut menunjukkan tampilan mendetail dari alur permintaan yang diikuti tutorial ini.

Cara komponen pipeline berinteraksi dalam permintaan pengguna.

Bagian berikutnya menjelaskan cara berbagai komponen dalam diagram ini berinteraksi.

Autentikasi pengguna

Aplikasi seluler dapat menggunakan berbagai metode untuk mengautentikasi pengguna. Alur autentikasi bersifat khusus untuk aplikasi Anda. Tutorial ini menunjukkan salah satu solusi untuk mengautentikasi pengguna. Sebuah Implementasi solusi ini menyertai tutorial ini.

Permintaan dari aplikasi klien ke proxy Pub/Sub

Backend aplikasi membuat token autentikasi berdurasi singkat yang disimpan klien secara lokal (misalnya, menggunakan sistem Android Keystore atau layanan keychain iOS). Tutorial ini menggunakan token ID OpenID Connect (OIDC) untuk mengautentikasi aplikasi klien. Google mengeluarkan dan menandatangani token ID OIDC.

Aplikasi sisi klien mengirimkan permintaan ke proxy Pub/Sub menggunakan token ID OIDC. Proxy Pub/Sub memvalidasi token dan meneruskan permintaan ke Pub/Sub dengan kredensial IAM yang sesuai.

Memublikasikan pesan

Setelah aplikasi klien berhasil diautentikasi, proxy Pub/Sub mengirimkan permintaan publikasi ke Pub/Sub. Dengan menggunakan IAM, Pub/Sub membantu memastikan pemanggil (proxy Pub/Sub) memiliki izin yang tepat untuk mengirim permintaan publikasi. Dalam tutorial ini, proxy Pub/Sub menggunakan akun layanan default Compute Engine untuk melakukan autentikasi dengan Pub/Sub. Akun layanan default Compute Engine memiliki Editor Peran IAM (roles/editor ), yang menyediakan akses penayang ke proxy Pub/Sub.

Tujuan

  • Buat cluster GKE untuk menjalankan proxy Pub/Sub.
  • Buat topik Pub/Sub.
  • Deploy proxy Pub/Sub.
  • Konfigurasi Endpoint untuk mengautentikasi permintaan ke proxy Pub/Sub.
  • Pastikan bahwa pesan dipublikasikan ke Pub/Sub.

Biaya

Dalam dokumen ini, Anda menggunakan komponen Google Cloud yang dapat ditagih berikut:

Untuk membuat perkiraan biaya berdasarkan proyeksi penggunaan Anda, gunakan kalkulator harga. Pengguna baru Google Cloud mungkin memenuhi syarat untuk mendapatkan uji coba gratis.

Setelah menyelesaikan tugas yang dijelaskan dalam dokumen ini, Anda dapat menghindari penagihan berkelanjutan dengan menghapus resource yang Anda buat. Untuk mengetahui informasi selengkapnya, lihat Pembersihan.

Sebelum memulai

  1. Di konsol Google Cloud, buka halaman Pemilih project.

    Buka pemilih project

  2. Pilih atau buat project Google Cloud.

  3. Pastikan penagihan telah diaktifkan untuk project Google Cloud Anda.

  4. Di konsol Google Cloud, aktifkan Cloud Shell.

    Aktifkan Cloud Shell

    Di bagian bawah Google Cloud Console, Cloud Shell sesi akan terbuka dan menampilkan perintah command line. Cloud Shell adalah lingkungan shell dengan Google Cloud CLI yang sudah terinstal, dan dengan nilai yang sudah ditetapkan untuk project Anda saat ini. Diperlukan waktu beberapa detik untuk melakukan inisialisasi sesi.

  5. Tentukan variabel lingkungan yang Anda perlukan untuk tutorial ini:
        export PROJECT=$(gcloud config get-value project)
        export REGION=us-central1
        export ZONE=${REGION}-b
        export CLUSTER=pubsub-proxy
        export TOPIC=proxy-test
        export SERVICE_ACCOUNT=publish-test
        export ENDPOINTS_SERVICE="pubtest.endpoints.${PROJECT}.cloud.goog"
        export GENERATE_TOKEN="https://iamcredentials.googleapis.com/v1/projects/-/serviceAccounts"
  6. Aktifkan API untuk Cloud Build, Compute Engine, Google Kubernetes Engine, Artifact Analysis, Container Registry, Endpoint, Pengelolaan Layanan, Kontrol Layanan, dan Pub/Sub:
        gcloud services enable \
            cloudbuild.googleapis.com \
            compute.googleapis.com \
            container.googleapis.com \
            containeranalysis.googleapis.com \
            containerregistry.googleapis.com \
            endpoints.googleapis.com \
            servicemanagement.googleapis.com \
            servicecontrol.googleapis.com \
            pubsub.googleapis.com

Membuat topik Pub/Sub

  • Di Cloud Shell, buat topik Pub/Sub di tempat Anda memublikasikan pesan:

    gcloud pubsub topics create $TOPIC
    

Membuat cluster GKE

  1. Di Cloud Shell, buat cluster GKE:

    gcloud container clusters create $CLUSTER \
        --zone $ZONE \
        --scopes "https://www.googleapis.com/auth/cloud-platform"
    
  2. Dapatkan kredensial untuk cluster yang sedang berjalan:

    gcloud container clusters get-credentials $CLUSTER \
        --zone $ZONE \
        --project $PROJECT
    

Membuat gambar container

  1. Di Cloud Shell, clone repositori kode:

    git clone https://github.com/GoogleCloudPlatform/solutions-pubsub-proxy-rest
    
  2. Gunakan Cloud Build untuk membangun image container dari sumber, lalu simpan di Container Registry:

    cd solutions-pubsub-proxy-rest && \
        gcloud builds submit --tag gcr.io/$PROJECT/pubsub-proxy:v1
    

Membuat alamat IP eksternal statis

  1. Di Cloud Shell, buat alamat IP eksternal statis yang nantinya ditetapkan ke load balancer proxy Pub/Sub:

    gcloud compute addresses create service-ip --region $REGION
    
  2. Simpan alamat IP statis dalam variabel lingkungan, PROXY_IP:

    PROXY_IP=$(gcloud compute addresses describe service-ip \
        --region $REGION --format='value(address)')
    

Men-deploy Endpoints

Proxy Pub/Sub menggunakan Endpoint untuk mengautentikasi permintaan dari pengguna. Endpoint menggunakan Extensible Service Proxy (ESP) untuk menyediakan fitur pengelolaan API seperti autentikasi, monitoring, pelacakan, dan pengelolaan siklus proses API. Tutorial ini hanya menggunakan Endpoint untuk mengautentikasi permintaan masuk ke proxy Pub/Sub.

Dalam tutorial ini, Anda akan men-deploy ESP sebagai file bantuan dengan proxy Pub/Sub. ESP mencegat dan mengautentikasi permintaan masuk sebelum meneruskannya ke proxy Pub/Sub proxy.

  1. Di Cloud Shell, ganti [PROJECT_ID]placeholder dengan project ID Google Cloud Anda di file openapi.yaml:

    sed -i -e "s/\[PROJECT_ID\]/$PROJECT/g" openapi.yaml
    
  2. Dalam file manifes OpenAPI, ganti [IP_ADDRESS] placeholder dengan nilai PROXY_IP:

    sed -i -e "s/\[IP_ADDRESS\]/$PROXY_IP/g" openapi.yaml
    
  3. Deploy definisi layanan OpenAPI ke Endpoint:

    gcloud endpoints services deploy openapi.yaml
    

    Perintah sebelumnya membuat hal berikut:

    • A layanan terkelola dengan nama yang telah Anda tetapkan di kolom host openapi.yaml file (pubtest.endpoints.project-id.cloud.goog ), dengan project-id adalah ID proyek Google Cloud Anda.
    • DNS Sebuah catatan yang menggunakan nama layanan dan Pub/Sub load balancer proxy alamat IP pemetaan yang didefinisikan dalamx-google-endpointsekstensi di openapi.yaml file.

    Selama deployment, Anda akan melihat peringatan yang dapat diabaikan karena tutorial ini menggunakan token ID OIDC untuk autentikasi, bukan kunci API.

    WARNING: openapi.yaml: Operation 'post' in path '/publish': Operation does
    not require an API key; callers may invoke the method without specifying an
    associated API-consuming project. To enable API key all the
    SecurityRequirement Objects
    (https://github.com/OAI/OpenAPI-Specification/blob/master/versions/2.0.md#security-requirement-object)
    inside security definition must reference at least one SecurityDefinition
    of type : 'apiKey'.
    
  4. Periksa apakah layanan telah di-deploy dengan benar:

    gcloud endpoints services describe ${ENDPOINTS_SERVICE}
    

    Outputnya serupa dengan yang berikut ini:

    [...]
    producerProjectId: project-id
    serviceConfig:
      documentation:
        summary: Pub/Sub proxy exposed as an Endpoint API
    [...]
      name: pubtest.endpoints.project-id.cloud.goog
      title: PubSub Proxy
      usage: {}
    serviceName: pubtest.endpoints.project-id.cloud.goog
    

    Pada output:

    • project-id: ID project Google Cloud Anda.

Men-deploy proxy

  1. Di Cloud Shell, buat sertifikat SSL yang ditandatangani sendiri untuk mengizinkan koneksi HTTPS ke proxy.

    openssl req -x509 -nodes -days 365 \
        -newkey rsa:2048 -keyout ./nginx.key \
        -out ./nginx.crt \
        -subj "/CN=${ENDPOINTS_SERVICE}"
    
  2. Buat secret Kubernetes menggunakan sertifikat SSL dan kunci pribadi:

    kubectl create secret generic nginx-ssl \
        --from-file=./nginx.crt \
        --from-file=./nginx.key
    
  3. Ganti [PROJECT_ID] placeholder di file manifes deployment dengan ID project Google Cloud Anda:

    sed -i -e "s/\[PROJECT_ID\]/$PROJECT/g" kube/deployment.yaml
    
  4. Ganti [IP_ADDRESS] placeholder dalam file manifes layanan dengan nilai PROXY_IP:

    sed -i -e "s/\[IP_ADDRESS\]/$PROXY_IP/g" kube/service.yaml
    
  5. Men-deploy proxy:

    kubectl apply -f kube/
    
  6. Verifikasi bahwa deployment berhasil:

    kubectl rollout status deployment/pubsub-proxy
    

    Outputnya mirip dengan hal berikut ini:

    [...]
    deployment "pubsub-proxy" successfully rolled out
    
  7. Pastikan dua container (proxy ESP dan Pub/Sub) berjalan di Pod:

    kubectl get pods $(kubectl get pod \
        -l app=pubsub-proxy \
        -o jsonpath="{.items[0].metadata.name}") \
        -o jsonpath={.spec.containers[*].name}
    

    Outputnya mirip dengan hal berikut ini:

    esp  pubsub-proxy
    
  8. Perhatikan nilai EXTERNAL-IP agar berubah dari <pending> menjadi alamat IP eksternal statis yang Anda buat sebelumnya:

    kubectl get svc pubsub-proxy -w
    

    Outputnya mirip dengan hal berikut ini:

    NAME          TYPE          CLUSTER-IP    EXTERNAL-IP   PORT(S)        AGE
    pubsub-proxy  LoadBalancer  10.7.247.212  <pending>     443:31104/TCP  6m32s
    pubsub-proxy  LoadBalancer  10.7.247.212  <PROXY_IP>    443:31104/TCP  6m5s
    

    Untuk berhenti melihat, tekan CTRL+C.

    Setelah berhasil di-deploy, proxy Pub/Sub akan diekspos di https://${ENDPOINTS_SERVICE}/publish. Mungkin memerlukan waktu beberapa menit agar konfigurasi DNS baru diterapkan.

  9. Memverifikasi konfigurasi DNS:

    watch nslookup ${ENDPOINTS_SERVICE}
    

    Outputnya mirip dengan hal berikut ini:

    Server:   169.254.169.254
    Address:  169.254.169.254#53
    
    Non-authoritative answer:
    Name: pubtest.endpoints.project-id.cloud.goog
    Address: gke-load-balancer-ip
    

    Pada output:

    • gke-load-balancer-ip: Alamat IP load balancer GKE (IP proxy) Anda.

    Untuk berhenti melihat, tekan CTRL+C.

Jika salah satu langkah sebelumnya menghasilkan error, lihat langkah pemecahan masalah.

Membuat token autentikasi

Prosedur berikut ini dimaksudkan sebagai contoh untuk membuat token autentikasi. Untuk lingkungan produksi, Anda memerlukan cara bagi pengguna untuk membuat token autentikasi mereka sendiri. Misalnya, Anda dapat menemukan kode contoh untuk mendapatkan token ID OIDC secara terprogram dalam dokumentasi Identity-Aware Proxy.

Untuk membuat token autentikasi, lakukan langkah berikut:

  1. Buat akun layanan Google Cloud untuk membuat token ID OIDC:

    gcloud iam service-accounts create \
        $SERVICE_ACCOUNT \
        --display-name $SERVICE_ACCOUNT
    
  2. Dapatkan identitas email akun layanan:

    SA_EMAIL=${SERVICE_ACCOUNT}@${PROJECT}.iam.gserviceaccount.com
    
  3. Berikan Service Account Token Creator peran IAM(roles/iam.serviceAccountTokenCreator) untuk akun layanan:

    gcloud iam service-accounts add-iam-policy-binding $SA_EMAIL \
        --member user:$(gcloud config get-value account) \
        --role roles/iam.serviceAccountTokenCreator
    
  4. Menggunakan Kredensial IAM API, buatlah token ID OIDC.

    TOKEN=$(curl -s ${GENERATE_TOKEN}/${SA_EMAIL}:generateIdToken \
        -H "Content-Type: application/json" \
        -H "Authorization: Bearer $(gcloud auth application-default print-access-token)" \
        -d '{"audience": "'${ENDPOINTS_SERVICE}'", "includeEmail": "true"}' | jq -r ".token")
    

    Nama layanan Endpoint ditentukan di kolom audience. Klaim audience mengidentifikasi penerima yang dituju oleh token.

  5. Verifikasi bahwa token berhasil dibuat:

    echo $TOKEN
    

    Token Web JSON (JWT) sama dengan yang berikut ini:

    eyJhbGciOiJSUzI1NiIsImtpZCI6IjY4NjQyODlm[...].eyJhdWQiOiJwdWJ0ZXN0LmVuZHBvaW50cy52aXR
    hbC1vY3RhZ29uLTEwOTYxMi5jbG91ZC5nb[...].SjBI4TZjZAlYo6lFKkrvfAcVUp_AJzFKoSsjNbmD_n[...]
    

Memanggil Pub/Sub menggunakan proxy

  1. Di Cloud Shell, publikasikan pesan pengujian:

    curl -i -k -X POST https://${ENDPOINTS_SERVICE}/publish \
        -H "Authorization: Bearer $TOKEN" \
        -H "Content-Type: application/json" \
        -d '{"topic": "'$TOPIC'", "messages": [ {"attributes": {"key1": "value1", "key2" : "value2"}, "data": "test data"}]}'
    

    Outputnya mirip dengan hal berikut ini:

    HTTP/2 200
    server: nginx
    date: Sun, 02 Jun 2019 03:53:46 GMT
    ...
    
  2. Periksa apakah pesan berhasil dipublikasikan ke topik Pub/Sub:

    kubectl logs -f --tail=5 deployment/pubsub-proxy -c pubsub-proxy
    

    Log deployment proxy Pub/Sub menampilkan pesan Successfully published:

    2019-06-02 03:49:39.723:INFO:oejs.Server:main: Started @2554ms
    Jun 02, 2019 3:53:44 AM com.google.pubsub.proxy.publish.PublishMessage
    getPublisher
    INFO: Creating new publisher for: proxy-test
    Jun 02, 2019 3:53:47 AM
    com.google.pubsub.proxy.publish.PublishMessage$1 onSuccess
    INFO: Successfully published: 569006136173844
    

Pemecahan masalah

  1. Di Cloud Shell, periksa status kedua container pada Pod proxy Pub/Sub:

    kubectl describe pods $(kubectl get pod -l app=pubsub-proxy \
        -o jsonpath="{.items[0].metadata.name}")
    

    Dalam output log, status container adalah Running:

    [...]
    Containers:
      esp:
    [...]
      State:  Running
        Started:  Fri, 21 Jun 2019 16:41:30 +0530
      Ready:  True
      Restart Count:  0
    [...]
      pubsub-proxy:
        State:  Running
          Started:  Fri, 21 Jun 2019 16:41:42 +0530
        Ready:  True
        Restart Count:  0
    [...]
    
  2. (Opsional) Periksa log container untuk melihat apakah ada error lain. Misalnya, untuk memeriksa log proxy Pub/Sub, jalankan perintah berikut:

    kubectl logs -f --tail=10 deployment/pubsub-proxy -c pubsub-proxy
    

Untuk mendapatkan bantuan terkait pemecahan masalah, lihat dokumen berikut:

Pembersihan

Agar tidak menimbulkan biaya pada akun Google Cloud Anda untuk resource yang digunakan dalam tutorial ini, Anda dapat menghapus project Google Cloud yang Anda buat untuk tutorial ini, atau menghapus resource yang berkaitan dengan tutorial ini.

Menghapus project Google Cloud

Cara termudah untuk menghilangkan penagihan adalah dengan menghapus project yang Anda buat untuk tutorial.

  1. Di konsol Google Cloud, buka halaman Manage resource.

    Buka Manage resource

  2. Pada daftar project, pilih project yang ingin Anda hapus, lalu klik Delete.
  3. Pada dialog, ketik project ID, lalu klik Shut down untuk menghapus project.

Menghapus resource

Jika ingin menyimpan project Google Cloud yang digunakan dalam tutorial ini, hapus masing-masing resource:

  1. Di Cloud Shell, hapus cluster GKE:

    gcloud container clusters delete $CLUSTER --zone $ZONE --async
    
  2. Hapus kode, artefak, dan dependensi lainnya yang didownload:

    cd .. && rm -rf solutions-pubsub-proxy-rest
    
  3. Hapus image di Container Registry:

    gcloud container images list-tags \
        gcr.io/$PROJECT/pubsub-proxy \
        --format 'value(digest)' | \
        xargs -I {} gcloud container images delete \
        --force-delete-tags --quiet \
        gcr.io/${PROJECT}/pubsub-proxy@sha256:{}
    
  4. Menghapus topik Pub/Sub

    gcloud pubsub topics delete $TOPIC
    
  5. Hapus akun layanan:

    gcloud iam service-accounts delete $SA_EMAIL
    
  6. Menghapus endpoint

    gcloud endpoints services delete ${ENDPOINTS_SERVICE}
    
  7. Hapus alamat IP statis:

    gcloud compute addresses delete service-ip --region $REGION
    

Langkah selanjutnya