Pelacakan terdistribusi di aplikasi microservice

Last reviewed 2024-06-26 UTC

Dokumen ini adalah yang keempat dari seri empat bagian tentang mendesain, membangun, dan men-deploy microservice. Seri ini menjelaskan berbagai elemen arsitektur microservice. Seri ini mencakup informasi tentang kelebihan dan kekurangan pola arsitektur microservice, serta cara menerapkannya.

  1. Pengantar microservice
  2. Memfaktorkan ulang monolit menjadi microservice
  3. Komunikasi antarlayanan dalam penyiapan microservice
  4. Pelacakan terdistribusi dalam aplikasi microservice (dokumen ini)

Seri ini ditujukan bagi developer dan arsitek aplikasi yang mendesain dan mengimplementasikan migrasi untuk memfaktorkan ulang aplikasi monolit menjadi aplikasi microservice.

Dalam sistem terdistribusi, penting untuk mengetahui cara permintaan mengalir dari satu layanan ke layanan lainnya, dan berapa lama waktu yang diperlukan untuk melakukan tugas di setiap layanan. Pertimbangkan aplikasi Butik Online berbasis microservice yang Anda deploy di dokumen sebelumnya, Memfaktorkan ulang monolit menjadi microservice. Aplikasi ini terdiri dari beberapa layanan. Contohnya, screenshot berikut menunjukkan halaman detail produk, yang mengambil informasi dari layanan frontend, rekomendasi, dan iklan.

Halaman detail produk.

Untuk merender halaman detail produk, layanan frontend berkomunikasi dengan layanan rekomendasi dan layanan iklan, seperti yang ditunjukkan dalam diagram berikut:

Layanan frontend berkomunikasi dengan layanan rekomendasi, katalog produk, dan layanan iklan.

Gambar 1. Layanan yang ditulis dalam bahasa yang berbeda.

Dalam gambar 1, layanan frontend ditulis dalam Go. Layanan rekomendasi, yang ditulis dalam Python, menggunakan gRPC untuk berkomunikasi dengan layanan frontend. Layanan iklan, yang ditulis dalam Java, juga menggunakan gRPC untuk berkomunikasi dengan layanan frontend. Selain gRPC, metode komunikasi antarlayanan juga dapat menggunakan REST HTTP.

Saat Anda membangun sistem terdistribusi tersebut, Anda ingin alat kemampuan observasi Anda menyediakan insight berikut:

  • Layanan yang dilalui permintaan.
  • Tempat terjadi penundaan jika permintaan lambat.
  • Tempat terjadinya error jika permintaan gagal.
  • Perbedaan eksekusi permintaan dengan perilaku normal sistem.
  • Apakah perbedaan dalam eksekusi permintaan berkaitan dengan performa (apakah beberapa panggilan layanan memerlukan waktu yang lebih lama atau lebih singkat dari biasanya).

Tujuan

  • Gunakan file manifes kustomize untuk menyiapkan infrastruktur.
  • Deploy aplikasi contoh Butik Online ke Google Kubernetes Engine (GKE).
  • Gunakan Cloud Trace untuk meninjau perjalanan pengguna dalam contoh aplikasi.

Biaya

Dalam dokumen ini, Anda akan 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 Anda menyelesaikan dokumen ini, Anda dapat menghindari penagihan berkelanjutan dengan menghapus resource yang Anda buat. Untuk informasi selengkapnya, lihat Pembersihan.

Sebelum memulai

Jika Anda sudah menyiapkan project dengan menyelesaikan dokumen sebelumnya dalam seri ini, Komunikasi antarlayanan dalam penyiapan microservice, Anda dapat menggunakan kembali project tersebut. Selesaikan langkah-langkah berikut untuk mengaktifkan API tambahan dan menetapkan variabel lingkungan.

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

    Go to project selector

  2. Make sure that billing is enabled for your Google Cloud project.

  3. In the Google Cloud console, activate Cloud Shell.

    Activate Cloud Shell

  4. Aktifkan API untuk Compute Engine, GKE, Cloud SQL, Artifact Analysis, Trace, dan Container Registry:

     gcloud services enable \
       compute.googleapis.com \
       sql-component.googleapis.com \
       servicenetworking.googleapis.com\
       container.googleapis.com \
       containeranalysis.googleapis.com \
       containerregistry.googleapis.com \
       sqladmin.googleapis.com
    

Pelacakan terdistribusi

Pelacakan terdistribusi melampirkan metadata kontekstual ke setiap permintaan dan memastikan metadata dibagikan di antara permintaan. Anda menggunakan titik trace untuk menginstrumentasikan pelacakan terdistribusi. Contohnya, Anda dapat menginstrumentasikan layanan Anda (frontend, rekomendasi, dan iklan) dengan dua titik trace untuk menangani permintaan klien guna melihat detail produk: satu titik trace untuk mengirim permintaan dan titik trace lainnya untuk menerima respons. Diagram berikut menunjukkan cara kerja instrumentasi titik trace ini:

Instrumentasi titik trace yang memiliki dua titik trace.

Gambar 2. Setiap panggilan antarlayanan memiliki dua titik trace yang terdiri dari pasangan permintaan respons.

Agar titik trace dapat memahami permintaan yang akan dijalankan saat layanan dipanggil, layanan asal akan meneruskan ID trace di sepanjang alur eksekusi. Proses yang meneruskan ID trace disebut penerapan metadata atau penerapan konteks terdistribusi. Penerapan konteks mentransfer metadata melalui panggilan jaringan saat layanan aplikasi terdistribusi saling berkomunikasi selama eksekusi permintaan tertentu. Diagram berikut menunjukkan penerapan metadata:

Penerapan metadata akan meneruskan ID trace.

Gambar 3. Metadata trace diteruskan antarlayanan. Metadata tersebut mencakup informasi seperti layanan mana yang memanggil dan stempel waktunya.

Pada contoh Butik Online, trace dimulai ketika pengguna mengirim permintaan awal untuk mengambil detail produk. ID trace baru akan dibuat, dan setiap permintaan berturut-turut akan diberi header yang berisi metadata kontekstual yang kembali ke permintaan asli.

Setiap operasi yang dipanggil sebagai bagian dari proses untuk memenuhi permintaan pengguna akhir disebut span. Layanan asal memberi tag pada setiap span dengan ID uniknya sendiri dan ID trace span induk. Diagram berikut menunjukkan visualisasi chart Gantt dari trace:

Operasi individual diberi tag sebagai span.

Gambar 4. Span induk mencakup waktu respons span turunan.

Gambar 4 menunjukkan hierarki trace tempat layanan frontend memanggil layanan rekomendasi dan layanan iklan. Layanan frontend adalah span induk, yang menjelaskan waktu respons seperti yang diamati oleh pengguna akhir. Span turunan menjelaskan cara layanan rekomendasi dan layanan iklan dipanggil dan direspons, termasuk informasi waktu respons.

Mesh layanan seperti Istio memungkinkan pelacakan terdistribusi untuk traffic layanan ke layanan tanpa memerlukan instrumentasi khusus apa pun. Namun, mungkin ada situasi saat Anda ingin memiliki kontrol lebih besar atas trace, atau Anda mungkin perlu melacak kode yang tidak berjalan dalam mesh layanan.

Dokumen ini menggunakan OpenTelemetry untuk mengaktifkan instrumentasi aplikasi microservice terdistribusi guna mengumpulkan trace dan metrik. Dengan OpenTelemetry, Anda dapat mengumpulkan metrik dan trace, lalu mengekspornya ke backend, seperti Prometheus, Cloud Monitoring, Datadog, Graphite, Zipkin, dan Jaeger.

Instrumentasi menggunakan OpenTelemetry

Bagian berikut menunjukkan cara menggunakan penerapan konteks untuk memungkinkan span dari beberapa permintaan agar ditambahkan ke satu trace induk.

Contoh ini menggunakan library Javascript, Python, dan Go OpenTelemetry untuk menginstrumentasikan implementasi trace untuk layanan pembayaran, rekomendasi, dan frontend. Bergantung pada panjang instrumentasi, data pelacakan dapat memengaruhi biaya project (penagihan Cloud Trace). Untuk mengurangi masalah biaya, sebagian besar sistem pelacakan menggunakan berbagai bentuk sampling untuk hanya mengambil persentase tertentu dari trace yang diamati. Di lingkungan produksi, organisasi Anda mungkin memiliki alasan untuk sampel yang ingin diambil dan alasannya. Anda mungkin ingin menyesuaikan strategi sampling berdasarkan pengelolaan biaya, berfokus pada rekaman aktivitas yang menarik, atau memfilter derau. Untuk mempelajari sampling lebih lanjut, lihat Sampling OpenTelemetry.

Dokumen ini menggunakan Trace untuk memvisualisasikan trace terdistribusi. Anda menggunakan pengekspor OpenTelemetry untuk mengirim trace ke Trace.

Mendaftarkan pengekspor trace

Bagian ini menunjukkan cara mendaftarkan pengekspor trace di setiap layanan dengan menambahkan baris ke kode microservice.

Untuk layanan frontend (ditulis dalam Go), contoh kode berikut mendaftarkan pengekspor:

[...]
exporter, err := otlptracegrpc.New(
        ctx,
        otlptracegrpc.WithGRPCConn(svc.collectorConn))
    if err != nil {
        log.Warnf("warn: Failed to create trace exporter: %v", err)
    }
tp := sdktrace.NewTracerProvider(
        sdktrace.WithBatcher(exporter),
        sdktrace.WithSampler(sdktrace.AlwaysSample()))
    otel.SetTracerProvider(tp)

Untuk layanan rekomendasi (ditulis dalam Python), contoh kode berikut mendaftarkan pengekspor:

if os.environ["ENABLE_TRACING"] == "1":
    trace.set_tracer_provider(TracerProvider())
    otel_endpoint = os.getenv("COLLECTOR_SERVICE_ADDR", "localhost:4317")
    trace.get_tracer_provider().add_span_processor(
        BatchSpanProcessor(
            OTLPSpanExporter(
            endpoint = otel_endpoint,
            insecure = True
            )
        )
    )

Untuk layanan pembayaran (ditulis dalam JavaScript), contoh kode berikut mendaftarkan pengekspor:

provider.addSpanProcessor(new SimpleSpanProcessor(new OTLPTraceExporter({url: collectorUrl})));
provider.register();

Menyiapkan penerapan konteks

Sistem pelacakan harus mengikuti spesifikasi konteks trace yang menentukan format untuk menerapkan konteks pelacakan antarlayanan. Contoh format penerapan mencakup format B3 Zipkin dan X-Google-Cloud-Trace.

OpenTelemetry menyebarkan konteks menggunakan TextMapPropagator global. Contoh ini menggunakan propagator Konteks Trace, yang menggunakan format traceparent W3C. Library instrumentasi, seperti library HTTP dan gRPC OpenTelemetry, menggunakan propagator global untuk menambahkan konteks rekaman aktivitas sebagai metadata ke permintaan HTTP atau gRPC. Agar penyebaran konteks berhasil, klien dan server harus menggunakan format penyebaran yang sama.

Penerapan konteks melalui HTTP

Layanan frontend memasukkan konteks rekaman aktivitas ke dalam header permintaan HTTP. Layanan backend mengekstrak konteks rekaman aktivitas. Contoh kode berikut menunjukkan cara layanan frontend diinstrumentasikan untuk mengonfigurasi konteks rekaman aktivitas:

otel.SetTextMapPropagator(
    propagation.NewCompositeTextMapPropagator(
        propagation.TraceContext{}, propagation.Baggage{}))

if os.Getenv("ENABLE_TRACING") == "1" {
    log.Info("Tracing enabled.")
    initTracing(log, ctx, svc)
} else {
    log.Info("Tracing disabled.")
}

...

var handler http.Handler = r
handler = &logHandler{log: log, next: handler}     // add logging
handler = ensureSessionID(handler)                 // add session ID
handler = otelhttp.NewHandler(handler, "frontend") // add OpenTelemetry tracing

Penerapan konteks melalui gRPC

Pertimbangkan alur saat layanan checkout melakukan pemesanan berdasarkan produk yang dipilih pengguna. Layanan ini berkomunikasi melalui gRPC.

Contoh kode berikut menggunakan interseptor panggilan gRPC yang mencegat panggilan keluar dan memasukkan konteks trace:

var srv *grpc.Server

// Propagate trace context always
otel.SetTextMapPropagator(
    propagation.NewCompositeTextMapPropagator(
        propagation.TraceContext{}, propagation.Baggage{}))
srv = grpc.NewServer(
    grpc.UnaryInterceptor(otelgrpc.UnaryServerInterceptor()),
    grpc.StreamInterceptor(otelgrpc.StreamServerInterceptor()),
)

Setelah menerima permintaan, layanan pembayaran atau katalog produk (ListProducts) mengekstrak konteks dari header permintaan dan menggunakan metadata trace induk untuk memunculkan span turunan.

Bagian berikut menyediakan detail tentang cara menyiapkan dan meninjau pelacakan terdistribusi untuk contoh aplikasi Butik Online.

Men-deploy aplikasi

Jika Anda sudah memiliki aplikasi yang berjalan setelah menyelesaikan dokumen sebelumnya dalam seri ini, Komunikasi antarlayanan dalam penyiapan microservice, Anda dapat langsung ke bagian berikutnya, Meninjau trace. Jika tidak, selesaikan langkah berikut untuk men-deploy contoh Butik Online:

  1. Untuk menyiapkan infrastruktur, di Cloud Shell, Anda dapat meng-clone repositori GitHub:

    git clone https://github.com/GoogleCloudPlatform/microservices-demo.git
    
  2. Untuk deployment baru, reset variabel lingkungan:

    PROJECT_ID=PROJECT_ID
    REGION=us-central1
    GSA_NAME=microservices-sa
    GSA_EMAIL=$GSA_NAME@$PROJECT_ID.
    

    Ganti PROJECT_ID dengan project ID Google Cloud yang ingin Anda gunakan.

  3. Opsional: Buat cluster baru atau gunakan kembali cluster yang ada jika ada:

    gcloud container clusters create-auto online-boutique --project=${PROJECT_ID}
      --region=${REGION}
    
  4. Buat akun layanan Google:

    gcloud iam service-accounts create $GSA_NAME \
      --project=$PROJECT_ID
    
  5. Aktifkan API:

    gcloud services enable \
    monitoring.googleapis.com \
    cloudtrace.googleapis.com \
    cloudprofiler.googleapis.com \
      --project ${PROJECT_ID}
    
  6. Berikan peran yang diperlukan untuk Cloud Trace ke akun layanan:

    gcloud projects add-iam-policy-binding ${PROJECT_ID} \
    --member "serviceAccount:${GSA_NAME}@${PROJECT_ID}." \
    --role roles/cloudtrace.agent
    
    gcloud projects add-iam-policy-binding ${PROJECT_ID} \
    --member "serviceAccount:${GSA_NAME}@${PROJECT_ID}." \
    --role roles/monitoring.metricWriter
    
    gcloud projects add-iam-policy-binding ${PROJECT_ID} \
    --member "serviceAccount:${GSA_NAME}@${PROJECT_ID}." \
    --role roles/cloudprofiler.agent
    
    gcloud iam service-accounts add-iam-policy-binding ${GSA_EMAIL} \
    --role roles/iam.workloadIdentityUser \
    --member "serviceAccount:${PROJECT_ID}.svc.id.goog[default/default]"
    
  7. Anotasikan akun layanan Kubernetes Anda (default/default untuk namespace default) agar dapat menggunakan akun layanan Identity and Access Management (IAM):

    kubectl annotate serviceaccount default \
        iam.gke.io/gcp-service-account=${GSA_EMAIL}
    
  8. Aktifkan konfigurasi Google Cloud Observability for GKE, yang mengaktifkan pelacakan:

    cd ~/microservices-demo/kustomize && \
    kustomize edit add component components/google-cloud-operations
    

    Perintah sebelumnya akan memperbarui file kustomize/kustomization.yaml, yang mirip dengan berikut ini:

    apiVersion: kustomize.config.k8s.io/v1beta1
    kind: Kustomization
    resources:
    - base
    components:
    - components/google-cloud-operations
    [...]
    
  9. Men-deploy microservice:

    kubectl apply -k .
    
  10. Periksa status deployment:

    kubectl rollout status deployment/frontend
    kubectl rollout status deployment/paymentservice
    kubectl rollout status deployment/recommendationservice
    kubectl rollout status deployment/adservice
    

    Output untuk setiap perintah terlihat seperti berikut:

    Waiting for deployment "" rollout to finish: 0 of 1 updated replicas are available...
    deployment "" successfully rolled out
    
  11. Dapatkan alamat IP aplikasi yang di-deploy:

    kubectl get service frontend-external | awk '{print $4}'
    

    Tunggu hingga alamat IP load balancer dipublikasikan. Untuk keluar dari perintah, tekan Ctrl+C. Catat alamat IP load balancer, lalu akses aplikasi di URL http://IP_ADDRESS. Mungkin perlu waktu beberapa saat agar load balancer responsif dan mulai meneruskan traffic.

Meninjau rekaman aktivitas menggunakan Cloud Trace

Perjalanan pembelian pengguna di aplikasi Butik Online memiliki alur berikut:

  • Pengguna melihat katalog produk di halaman landing.
  • Untuk melakukan pembelian, pengguna mengklik Beli.
  • Pengguna dialihkan ke halaman detail produk tempat mereka menambahkan item ke keranjang.
  • Pengguna dialihkan ke halaman checkout tempat mereka dapat melakukan pembayaran untuk menyelesaikan pesanan.

Pertimbangkan skenario saat Anda perlu memecahkan masalah waktu respons yang tinggi saat memuat halaman detail produk. Seperti yang dijelaskan sebelumnya, halaman detail produk terdiri dari beberapa microservice. Untuk mengetahui di mana dan mengapa latensi tinggi terjadi, Anda dapat melihat grafik pelacakan terdistribusi untuk meninjau performa seluruh permintaan di berbagai layanan.

Untuk meninjau grafik pelacakan terdistribusi, lakukan tindakan berikut:

  1. Akses aplikasi, lalu klik produk apa pun. Halaman detail produk akan ditampilkan.
  2. Di konsol Google Cloud, buka halaman Daftar trace dan tinjau linimasa.
  3. Untuk melihat hasil trace terdistribusi, klik Frontend di kolom URI.
  4. Tampilan Trace Waterfall menampilkan span yang terkait dengan URI:

    Tampilan Trace Waterfall menampilkan span.

    Dalam screenshot sebelumnya, trace untuk produk berisi span berikut:

    • Span Frontend menangkap latensi menyeluruh (150.349 md) yang diamati klien saat memuat halaman detail produk.
    • Span Layanan Rekomendasi menangkap latensi panggilan backend dalam mengambil rekomendasi (4.246 md) yang terkait dengan produk.
    • Span Layanan Iklan menangkap latensi panggilan backend dalam mengambil iklan (4.511 md) yang relevan dengan halaman produk.

Untuk memecahkan masalah waktu respons yang tinggi, Anda dapat meninjau insight yang mencakup grafik distribusi latensi dari permintaan pencilan apa pun saat dependensi layanan tidak memenuhi tujuan tingkat layanan mereka (SLO). Anda juga dapat menggunakan Cloud Trace untuk mendapatkan insight performa dan membuat laporan analisis dari sampel data.

Pemecahan masalah

Jika rekaman aktivitas di Application Performance Management tidak muncul, periksa Logs Explorer untuk menemukan error izin ditolak. Izin ditolak terjadi saat akun layanan tidak memiliki akses untuk mengekspor rekaman aktivitas. Tinjau langkah-langkah tentang cara memberikan peran yang diperlukan untuk Cloud Trace dan pastikan untuk menganotasi akun layanan dengan namespace yang benar. Setelah itu, mulai ulang opentelemetrycollector:

  kubectl rollout restart deployment opentelemetrycollector

Pembersihan

Agar tidak dikenai biaya pada akun Google Cloud Anda untuk resource yang digunakan dalam tutorial ini, hapus project yang berisi resource tersebut, atau simpan project dan hapus setiap resource.

Menghapus project

  1. In the Google Cloud console, go to the Manage resources page.

    Go to Manage resources

  2. In the project list, select the project that you want to delete, and then click Delete.
  3. In the dialog, type the project ID, and then click Shut down to delete the project.

Menghapus resource

Jika Anda ingin menyimpan project Google Cloud yang Anda gunakan dalam dokumen ini, hapus masing-masing resource:

  • Di Cloud Shell, hapus resource:

    gcloud container clusters delete online-boutique --project=${PROJECT_ID} --region=${REGION}
    

Langkah berikutnya