title: “59. Integrasi gRPC dengan OAuth2: Panduan Lengkap dan Praktis” date: 2024-07-08 author: Senior Software Engineer tags: [gRPC, OAuth2, Security, Golang, Microservices, Authentication]
Pendahuluan
Pada era di mana microservices menjadi arsitektur primadona, keamanan komunikasi antar layanan menjadi prioritas utama. Salah satu protokol RPC modern, yaitu gRPC, semakin populer karena efisiensi dan fleksibilitasnya. Namun, bagaimana Anda memastikan komunikasi di antara layanan gRPC tetap aman? Di sinilah OAuth2 berperan sebagai mekanisme otentikasi yang kokoh dan teruji.
Artikel ini membahas end-to-end integrasi gRPC dengan OAuth2 — mulai dari konsep dasar, arsitektur, hingga implementasi lengkap beserta simulasi dan contoh kode menggunakan Golang. Cocok bagi Anda yang ingin membangun microservices yang secure by design.
Konsep Dasar gRPC dan OAuth2
gRPC adalah framework RPC (Remote Procedure Call) open-source dari Google, berbasis protokol HTTP/2 dan Protobuf. Keunggulannya ada pada efisiensi, language-agnostic, serta streaming data.
OAuth2 adalah standar otorisasi modern yang banyak dipakai untuk mengelola akses terhadap REST API, serta kini juga diadopsi pada komunikasi API modern seperti gRPC.
Mengapa OAuth2 untuk gRPC?
- Single Sign-On (SSO) untuk service-to-service.
- Mendukung scopes dan roles based access.
- Skala distribusi, audit, dan pengelolaan token sentral.
Arsitektur Integrasi gRPC + OAuth2
Secara umum, flow integrasi OAuth2 pada skenario gRPC service-to-service adalah sebagai berikut:
sequenceDiagram
participant Client as gRPC Client
participant AuthServer as OAuth2 Server
participant Service as gRPC Server
Client->>AuthServer: Request Access Token (client_credentials)
AuthServer-->>Client: Access Token
Client->>Service: gRPC Request with Bearer Token (metadata)
Service-->>Client: Response / Error (Unauthorized if expired/invalid)
Penjelasan Alur
- Client melakukan request token ke OAuth2 server menggunakan grant type
client_credentials. - Mendapatkan access token (JWT) dari OAuth2 server.
- Setiap request gRPC menyisipkan token pada metadata (mirip header HTTP).
- gRPC Server melakukan verifikasi token setiap request dan memutuskan apakah request boleh dilayani.
Implementasi Integrasi: Studi Kasus di Golang
Kita akan membangun simulasi minimum viable:
- gRPC Client (berperan sebagai microservice client)
- OAuth2 Server (dummy)
- gRPC Server (API provider, validasi token)
Catatan: Untuk lingkungan real-world, Anda dapat menggunakan OIDC Provider seperti Keycloak, Auth0, dsb. Namun di sini kita gunakan pendekatan dummy agar mudah dipahami.
1. Mendefinisikan Protobuf
Buat file greet.proto:
syntax = "proto3";
package greet;
service Greeter {
rpc SayHello (HelloRequest) returns (HelloReply) {}
}
message HelloRequest {
string name = 1;
}
message HelloReply {
string message = 1;
}
2. Implementasi Dummy OAuth2 Server
// oauth2_server.go
package main
import (
"net/http"
"encoding/json"
"time"
)
func main() {
http.HandleFunc("/token", func(w http.ResponseWriter, r *http.Request) {
// Validasi client_id dan secret, grant_type, dsb
// Di dunia nyata, jangan seperti ini!
token := map[string]interface{}{
"access_token": "dummy-access-token",
"token_type": "bearer",
"expires_in": 3600,
}
w.Header().Set("Content-Type", "application/json")
json.NewEncoder(w).Encode(token)
})
http.ListenAndServe(":8081", nil)
}
3. Server gRPC dengan Interceptor OAuth2
Interceptor untuk Validasi Bearer Token
import (
"context"
"google.golang.org/grpc"
"google.golang.org/grpc/metadata"
"google.golang.org/grpc/codes"
"google.golang.org/grpc/status"
)
func authUnaryInterceptor(
ctx context.Context,
req interface{},
info *grpc.UnaryServerInfo,
handler grpc.UnaryHandler,
) (interface{}, error) {
md, ok := metadata.FromIncomingContext(ctx)
if !ok {
return nil, status.Errorf(codes.Unauthenticated, "metadata tidak ditemukan")
}
tokens := md["authorization"]
if len(tokens) < 1 || tokens[0] != "Bearer dummy-access-token" {
return nil, status.Errorf(codes.Unauthenticated, "akses ditolak, token tidak valid")
}
return handler(ctx, req)
}
Setup Server
s := grpc.NewServer(grpc.UnaryInterceptor(authUnaryInterceptor))
// Daftarkan service Greeter
pb.RegisterGreeterServer(s, &GreeterServer{})
4. Client: Ambil Token & Lakukan Panggilan RPC
func getAccessToken() (string, error) {
resp, err := http.PostForm("http://localhost:8081/token", url.Values{
"grant_type": {"client_credentials"},
"client_id": {"test"},
"client_secret": {"test123"},
})
// parsing response JSON, return access_token
}
func main() {
conn, _ := grpc.Dial("localhost:50051", grpc.WithInsecure())
client := pb.NewGreeterClient(conn)
// Dapatkan access token
token, _ := getAccessToken()
// Kirim metadata dengan token
md := metadata.Pairs("authorization", fmt.Sprintf("Bearer %s", token))
ctx := metadata.NewOutgoingContext(context.Background(), md)
resp, err := client.SayHello(ctx, &pb.HelloRequest{Name: "OAuth2"})
}
Tabel Komparasi: Integrasi gRPC tanpa dan dengan OAuth2
| Fitur | Tanpa OAuth2 | Dengan OAuth2 |
|---|---|---|
| Otentikasi | Tidak ada | Access Token JWT |
| Otorisasi | Tidak ada | Scope/role-based |
| Audit Log | Tidak tersedia | Tersedia (token claim) |
| Single Sign-On | Tidak bisa | Bisa |
| Manajemen Token Expiry | Manual / Tidak ada | Otomatis (expires_in) |
Best Practice & Simulasi Attack
Simulasi: Client mencoba request ke gRPC server TANPA menyematkan token.
Hasil:
Server menolak dengan status Unauthenticated.
Ini memastikan bahwa hanya client yang memiliki access-token valid dari OAuth2 server yang dapat mengakses resource di RPC server.
Tips Production:
- Gunakan token proper (misal JWT) dan library jwt-go untuk parsing dan validasi.
- Gunakan TLS (gRPC mendukung TLS secara natif).
- Pastikan token tidak hardcoded!
Kesimpulan
Integrasi gRPC dengan OAuth2 sangat penting untuk menjaga keamanan arsitektur microservices Anda. Dengan menerapkan interceptor pada gRPC server, kita bisa memastikan semua permintaan terverifikasi — sekaligus menyiapkan jalur untuk future enhancement seperti role-based access control.
Ingat: Untuk lingkungan production gunakan OAuth2 provider populer (Keycloak, Auth0) serta JWT verification yang komprehensif. Integrasi ini scalable baik untuk B2B, SaaS, maupun internal systems.
Masih banyak pengembangan lanjutan (scope, policy, dynamic permission) yang bisa diintegrasikan. Namun semoga artikel ini memberi pondasi kuat dan praktikal untuk perjalanan adopsi OAuth2 dengan gRPC di sistem Anda.
Selamat mencoba, dan tetap utamakan keamanan! 🚀