1 poin oleh GN⁺ 2025-01-24 | 1 komentar | Bagikan ke WhatsApp
  • Titik awal perancangan API adalah perbedaan antara RPC dan REST, dan ketiga pendekatan ini sama-sama dapat terhubung dengan HTTP, tetapi model pembentukan panggilan dan penyusunan kliennya berbeda
  • REST adalah model hiperteks yang mengikuti URL yang disediakan server, sehingga berbeda dari API bergaya OpenAPI, tempat klien menyusun format URL
  • OpenAPI mendefinisikan operasi dengan template path URL dan metode HTTP sehingga praktis dan banyak digunakan, tetapi lebih dekat ke model RPC yang dipetakan ke HTTP daripada ke REST
  • gRPC mendefinisikan API RPC secara langsung melalui IDL, pembuatan kode, payload biner, dan pengelolaan koneksi HTTP/2, sekaligus menyembunyikan detail HTTP
  • gRPC memerlukan perangkat lunak khusus di kedua sisi dan memiliki keterbatasan dalam penguatan proxy, pencegahan pembaruan bersamaan, serta pembaruan parsial, sehingga sangat cocok terutama untuk API internal atau ketika dapat memakai lapisan konversi seperti Cloud Endpoints

Tiga model untuk melihat API berbasis HTTP

  • Pendekatan utama yang menggunakan HTTP sebagai lapisan transport API terbagi menjadi REST, OpenAPI, dan gRPC
  • Salah satu alasan banyak API publik dan API terdistribusi privat menggunakan HTTP adalah karena organisasi sudah terbiasa dengan isu keamanan lalu lintas HTTP di port 80 dan 443
  • Ketiganya sama-sama dapat terhubung dengan HTTP, tetapi berbeda dalam hal apa yang dijadikan alamat dan bagaimana klien membentuk panggilan

REST: mengikuti URL, bukan menyusunnya

  • Dalam REST, klien menggunakan URL yang diberikan server apa adanya, dan tidak memahami atau menyusun format URL sebagai bagian dari spesifikasi API
  • Browser mengikuti halaman saat ini, bookmark, atau URL yang dimasukkan pengguna, dan hanya melakukan hal seperti mengekstrak informasi permintaan HTTP dari URL atau mengubah URL relatif menjadi URL absolut
  • Inti dari API REST adalah penggunaan hiperteks/hipermedia yang mengekspresikan referensi antar resource sebagai URL dari resource lain
  • Dalam pendekatan REST, semua pengenal dipertukarkan sebagai URL
    • POST /accountsaccount_URL
    • kirim account_URL ke POST /subscriptionssubscription_URL
    • GET {account_URL} → mengembalikan pohon data akun
  • Kelebihan REST dekat dengan stabilitas, konsistensi, dan universalitas web itu sendiri, dan model berorientasi entitas pada HTTP/REST dapat membuat API lebih sederhana dan teratur

OpenAPI: lebih dekat ke RPC yang dipetakan langsung ke HTTP

  • OpenAPI mendefinisikan template path URL di bawah paths, dan kombinasi path serta metode HTTP disebut operasi (operation)
  • Path seperti /pets/{petId} mengharuskan klien mengetahui nilai {petId} lalu menyisipkannya ke template URL untuk membuat permintaan HTTP
  • Dalam pendekatan ini, klien harus mengetahui format URL secara rinci, sehingga berlawanan dengan model hiperteks REST
  • Alasan OpenAPI digunakan luas cukup jelas
    • Mirip dengan model RPC tradisional sehingga terasa akrab bagi programmer
    • Konsep RPC dapat dipetakan langsung ke permintaan HTTP
  • Untuk API publik, keuntungannya besar karena dapat diakses dari hampir semua bahasa dan lingkungan hanya dengan teknologi HTTP standar
  • Sebaliknya, karena perlu merancang path URL, metode HTTP, dan pemetaan parameter, detail yang harus dipelajari oleh penyedia maupun pengguna API menjadi lebih banyak

gRPC: teknologi implementasi RPC yang menyembunyikan HTTP/2

  • gRPC menggunakan HTTP/2 sebagai lapisan transport, tetapi tidak mengekspos detail HTTP ke perancang API maupun ke kode klien dan server
  • Alur pemanggilan klien gRPC sederhana
    • Menentukan prosedur yang akan dipanggil
    • Menghitung nilai parameter yang akan digunakan
    • Meneruskan parameter ke stub yang dihasilkan kode untuk melakukan panggilan
  • gRPC mendefinisikan prosedur jarak jauh berbasis interface description language, sehingga tidak perlu seperti OpenAPI yang juga harus menyatakan pemetaan path URL, parameter, dan metode HTTP
  • Melalui pembuatan kode, framework, dan library, pembuatan library klien dan implementasi server bisa menjadi lebih mudah
  • Ada keuntungan performa berkat payload biner dan pengelolaan koneksi HTTP/2, dan teknologi yang sama sebenarnya bisa dipakai tanpa gRPC, tetapi membutuhkan pembelajaran teknis yang lebih banyak

Kapan mempertimbangkan gRPC alih-alih OpenAPI

  • Saat merancang API dengan OpenAPI, operasi dan parameter harus diekspresikan sebagai kombinasi path URL dan metode HTTP, dan banyaknya pilihan dapat membuatnya rumit
  • Jika tetap menggunakan model bergaya RPC, gRPC mengurangi beban merancang pemetaan kustom terhadap HTTP secara manual
  • gRPC dan OpenAPI memiliki model API dasar yang mirip, tetapi cara mengekspos HTTP berbeda
    • OpenAPI mengekspos detail transport HTTP kepada klien dan perancang mengendalikan pemetaannya
    • gRPC menyembunyikan detail HTTP melalui pemetaan yang telah ditentukan sebelumnya dan kode yang dihasilkan
  • Keunggulan besar OpenAPI adalah klien dapat langsung memakai alat dan teknologi HTTP standar, dan bagi banyak perancang API kelebihan ini sepadan dengan biaya desain tambahannya

Menggabungkan model berorientasi entitas ke dalam RPC

  • Walau menggunakan gRPC atau OpenAPI, sebagian kelebihan REST tetap bisa diperoleh jika metode RPC dibatasi agar berpusat pada entitas
  • Caranya adalah mendefinisikan tipe resource terlebih dahulu, bukan memulai dari definisi prosedur, lalu memetakan operasi entitas standar ke tiap tipe
  • Operasi dasarnya adalah Create, Retrieve, Update, Delete, List, yang sering dipandang sebagai CRUD plus List
  • Operasi tambahan bisa ditambahkan bila perlu, tetapi jika konsep berorientasi entitas dan konsep berorientasi prosedur tercampur, sebagian kelebihannya bisa melemah
  • Mengelompokkan prosedur berdasarkan tipe entitas juga merupakan salah satu gagasan inti dalam bahasa berorientasi objek

Keterbatasan dan hal yang perlu diperhatikan pada gRPC

  • gRPC memerlukan perangkat lunak khusus di sisi klien dan server, dan kode yang dihasilkan harus diintegrasikan ke proses build di kedua sisi
  • Bagi pengguna bahasa dinamis seperti JavaScript atau Python, yang lingkungan pengembangannya bisa hampir tidak memiliki proses build, kebutuhan ini dapat menjadi beban
  • Google Cloud Endpoints memungkinkan API gRPC diakses lewat HTTP dan JSON sehingga memulihkan pilihan klien, tetapi tidak semua pengguna dapat memakainya atau membangun fungsi setara
  • API REST memudahkan pembuatan bot yang merayapi keseluruhan sistem tanpa metadata, tetapi API bergaya RPC seperti gRPC atau OpenAPI memerlukan API, metadata, atau perangkat lunak kustom yang berbeda untuk tiap tipe entitas
  • API HTTP sering menambahkan fungsi keamanan, validasi input, pemetaan format data, serta modifikasi header dan body melalui alat manajemen API dan proxy seperti Apigee Edge, tetapi pada gRPC penguatan proxy seperti ini bisa jauh lebih sulit
  • gRPC tidak mendefinisikan mekanisme standar untuk mencegah hilangnya data akibat pembaruan bersamaan
    • HTTP menyediakan header Etag dan If-Match untuk itu
  • gRPC juga tidak mendefinisikan mekanisme pembaruan parsial
    • HTTP memiliki PATCH, dan standar untuk JSON mencakup JSON merge patch dan JSON patch
    • JSON merge patch lebih sederhana tetapi tidak dapat menangani semua kasus seperti pembaruan array
    • JSON patch menangani lebih banyak kasus tetapi lebih rumit digunakan

Kriteria pemilihan

  • Jika Anda sudah bisa merancang model hiperteks REST atau bersedia mempelajarinya, ini bisa menjadi pilihan yang baik untuk menargetkan stabilitas, konsistensi, dan universalitas
  • OpenAPI memungkinkan pembuatan API yang dapat diakses hanya dengan teknologi HTTP standar, tetapi banyaknya pilihan desain untuk memetakan konsep RPC ke HTTP dapat membuat desain, implementasi, dan pembelajaran menjadi lebih sulit
  • Jika suatu API layak dipertimbangkan dengan OpenAPI, gRPC juga patut dievaluasi bersama. Model API dasar keduanya dapat dibandingkan, dan gRPC mengurangi kebutuhan membuat pemetaan HTTP secara manual
  • gRPC sangat menarik terutama dalam kondisi berikut
    • Saat produk seperti Cloud Endpoints memungkinkan klien tidak harus mengadopsi teknologi gRPC secara wajib
    • Saat API bersifat internal dan Anda dapat mengendalikan pilihan teknologi server serta semua klien
  • Saat mengadopsi gRPC alih-alih OpenAPI atau REST, perlu dipertimbangkan bahwa peluang untuk memperkuat atau mengoreksi perilaku API melalui proxy berbasis alat manajemen API seperti Apigee Edge bisa menjadi jauh lebih terbatas

1 komentar

 
GN⁺ 2025-01-24
Pendapat di Hacker News
  • Kalau bisa memutar balik waktu, rasanya saya ingin mencegah diri saya mempelajari gRPC sejak awal
    Awalnya saya terpikat oleh visinya, tetapi setelah beberapa tahun, ternyata terlalu banyak hal yang bikin pusing. Klaim bahwa ia menyembunyikan kompleksitas internal juga hampir seperti lelucon; untuk mencari penyebab permintaan yang gagal 1 dari 10 kali, kita akhirnya membanjiri log debug dan mengutak-atik 10–20 pengaturan timeout/retry yang namanya pun ambigu
    Mulai dari plugin Maven, deadline exceeded yang aneh, load balancer yang tidak suka HTTP/2, situasi ketika firewall memaksa kita akhirnya memakai API standar, dokumentasi yang minim, sampai mendapatkan pesan error yang berguna untuk observabilitas—semuanya menghabiskan waktu

    • Masalah gRPC bukan pada protokol atau protobuf itu sendiri, melainkan setidaknya pada toolchain di sisi Java yang buruk
      Developer experience dari kode yang dihasilkan jelek, stub klien berupa kelas konkret final sehingga sulit di-mock dalam pengujian, dan implementasi server juga harus mewarisi kelas konkret, bukan interface
      Method server memiliki signature asinkron sehingga merusak perilaku berbasis AOP seperti @Transactional, tidak ada dukungan exception, dan meski kelas nilai immutable itu bagus, semuanya harus dibuat lewat builder
      Pada akhirnya, jika ingin memakai gRPC dalam SOA, kita harus menulis banyak kode plumbing untuk menyembunyikan kebisingan gRPC dan mendapatkan kode bersih yang bisa diuji; compiler RPC milik Thrift juga punya masalah serupa ditambah masalah lain
    • Masalah-masalah itu tampaknya lebih dekat ke masalah implementasi tertentu daripada spesifikasi gRPC/protobuf itu sendiri
      Di .NET dan C# modern, pengalaman memakai gRPC cukup baik, sampai-sampai Microsoft juga menghentikan teknologi RPC lama seperti WCF dan berfokus pada gRPC
    • Proyek terbesar yang pernah saya gunakan adalah Java, dan memverifikasi output binding yang dihasilkan protoc ternyata lebih bertele-tele dan lebih rawan error daripada melakukan serialisasi sendiri
      Protokol wire-nya tidak type-safe; memang ada type tag, tetapi tag yang sama digunakan ulang untuk beberapa tipe data. Encoding integer zig-zag juga lambat
      Sebagai library RPC, itu buruk, dan dari yang pernah saya alami, satu-satunya yang lebih buruk hanyalah FlatBuffers
    • Melihat Anda menyebut Maven, sepertinya Anda memakai Java; dari sudut pandang saya yang sudah sekitar 8 tahun terakhir memprogram dengan Go, pengalaman gRPC cukup berbeda
      Saya penasaran apakah perbedaan ini karena Java atau karena teknologi gRPC itu sendiri
    • Saya sudah beberapa tahun memakai gRPC di stack Go+Dart, tetapi belum pernah mengalami masalah seperti ini
      Saya penasaran apakah ini masalah yang spesifik pada Java+gRPC
  • Saya sudah lama membuat API, pernah memakai baik gRPC maupun HTTP/REST, dan juga merilis library https://github.com/oapi-codegen/oapi-codegen yang menghasilkan klien dan server Go dari spesifikasi OpenAPI
    Saya sulit setuju dengan cara tulisan itu membedakan OpenAPI dan REST. OpenAPI adalah cara mendokumentasikan perilaku HTTP API, dan bisa merepresentasikan baik API RESTful maupun API yang sepenuhnya arbitrer. Secara konseptual ia mirip dengan file Protocol Buffer yang menetapkan protokol gRPC, dalam arti keduanya adalah bahasa skema untuk menjelaskan API agar bisa ditafsirkan oleh alat
    gRPC adalah mekanisme RPC yang bertukar proto. Saat Google membuka protobuf, mereka tidak membuka Stubby, lapisan RPC internalnya, dan gRPC tidak sebagus Stubby. Meski begitu, efisiensi transmisinya tinggi dan relatif mudah diperluas
    Namun gRPC tidak memiliki ekosistem sekukuh library HTTP arus utama, sehingga sering kali kita harus mengimplementasikan sendiri middleware seperti logging atau autentikasi; ini terutama terasa pada RPC antarlayanan yang diimplementasikan dalam bahasa berbeda
    Menurut saya masalah sebenarnya pada gRPC adalah file proto. Karena semua klien harus dibangun dengan file .proto yang kompatibel dengan server, protokol ini tidak mudah ditemukan. HTTP API bisa dipanggil dengan curl atau kode yang ditulis sendiri bahkan tanpa deskripsi OpenAPI, sehingga keterikatannya lebih longgar, dan karena itu pengerjaan serta debugging menjadi lebih mudah

    • Ada perbedaan antara apa yang blog ini sebut “OpenAPI” dan REST yang sebenarnya. Namun dalam praktiknya hampir tidak ada yang membuat REST API sungguhan, dan kebanyakan memakai pendekatan ala OpenAPI
      REST seperti yang didefinisikan dalam disertasi doktoral Roy Fielding tahun 2000 mengharuskan ketika melakukan GET ke URL root, respons 200 OK berisi tautan-tautan, dan dengan mengikuti tautan itu kita harus bisa menjelajahi semua resource yang disediakan API. Struktur hierarkis diperbolehkan, tetapi semuanya harus dapat diakses dari suatu tempat dalam pohon tautan itu; tujuannya adalah memberikan discoverability
      Dalam 20 tahun terakhir, hampir semua tempat tempat saya bekerja memakai POST resource_name/resource_id/sub_resource/sub_resource_id/mutation_type atau, bergantung pada cara perusahaan menangani idempotensi, PUT resource_name/resource_id/sub_resource/sub_resource_id, dan klien merakit URL ajaib berdasarkan pengetahuan struktur seperti Swagger/OpenAPI
      Karena itu, orang-orang yang ketat sering menyebut praktik di lapangan sebagai “RESTful”, bukan “REST”, karena tidak mengimplementasikan definisi REST menurut Fielding
    • Bagian yang membedakan OpenAPI dan REST juga membuat saya bingung. Apa yang tulisan itu sebut REST terlihat lebih dekat ke HATEOAS
      Dari sudut pandang mengelola API yang cukup besar dengan klien internal/eksternal, alur menghasilkan kode dari spesifikasi OpenAPI juga sulit saya pahami. Setelah mengisi stub yang dihasilkan lalu mengiterasi spesifikasi API, alat akan membuat stub baru lagi, perlu penggabungan manual, dan makin besar API, makin sulit menemukan perubahan terkait
      Karena itu saya membuat monster yang menghasilkan spesifikasi OpenAPI dari kode dengan go/ast dan sejenisnya. Tidak sempurna, tetapi ini solusi 95% yang berjalan di Echo maupun Gin; jika butuh endpoint baru, saya bisa membuat struct request/response dan handler kosong, lalu menghasilkan dokumentasi dan mengirimkannya ke developer frontend, sehingga prosesnya cepat
      Sebagian besar developer tidak perlu memikirkan bagaimana merepresentasikan API dengan OpenAPI, dan dokumentasinya juga selalu selaras dengan kode
    • Sekarang ada gRPC reflection untuk discovery: https://grpc.io/docs/guides/reflection/
    • Saya juga sedang membuat sintaks query mirip SQL dengan memanfaatkan spesifikasi OpenAPI beserta tipe yang dihasilkan. Dengan begini, API pihak ketiga mana pun bisa ditangani dengan nuansa yang sama
      Apipe.new(GitHun) |> from("search/repositories") |> eq(:language, "elixir") |> order_by(:updated) |> limit(1) |> execute()
      Kita tidak perlu mengetahui fungsi gRPC yang tersedia atau keunikan RESTful pada API pihak ketiga, sambil tetap mempertahankan dokumentasi bawaan dan akses tipe
      https://github.com/cpursley/apipe
      Saya juga sedang mempertimbangkan lapisan adapter TypeScript agar bisa dimasukkan ke proyek JS/TS seperti Supabase
      const { data, error } = await apipe.from('search/repositories').eq('language', 'elixir').order_by('updated').limit(1)
      Panggilan ini bisa dibuat melewati proxy Elixir, yang menangani pekerjaan berat seperti pemrosesan asinkron atau rate limiting
    • Pernyataan bahwa gRPC bukan protokol yang dapat ditemukan tidak sepenuhnya benar
      Berdasarkan serialisasi JSON Protobuf, kita bisa membuat deskripsi OpenAPI dan menyediakannya lewat Swagger, dan gRPC sendiri juga menyediakan reflection bawaan serta utilitas grpcurl yang memakainya
  • Dari sudut pandang pernah bekerja di beberapa perusahaan FAANG, Thrift/gRPC benar-benar berguna untuk routing layanan internal
    Namun sebagian besar kompleksitasnya dikelola oleh tim yang membuat library, lapisan service discovery, routing, dan sebagainya. Dengan protokol RPC, hal-hal seperti ini bisa dilakukan pada skala dan kecepatan yang sulit dicapai dengan layanan JSON/REST biasa
    Saya juga belum pernah melihat REST API yang tidak membiarkan verba “bocor”, dan jika harus membuat mesh layanan backend atau menghubungkan dua layanan lokal melalui stream jaringan, saya akan selalu memilih gRPC
    Tetapi saya tidak akan pernah memakai gRPC untuk penggunaan yang terekspos ke pelanggan atau web. RPC kuat karena mengunci banyak keputusan dan memaksakan “satu cara”. Sebaliknya, jika berbagai klien dari beragam tech stack harus memakai sebuah layanan, REST jauh lebih baik

    • Untuk API publik saya tidak akan melakukannya, tetapi pada API privat saya cukup menangani dengan cara mengirim body JSON ke POST /api/doThingy
      Ini RPC yang mudah, yang memungkinkan siapa pun ikut serta hanya dengan klien HTTP paling dasar, dan bekerja dengan baik di semua OS dan browser. Tidak perlu bergulat soal apakah sesuatu harus dimasukkan ke path URL, parameter query, atau body
      Jika memakai keluarga server seperti Buf atau Connect yang mencoba membuatnya tidak terlalu merepotkan, gRPC pun dengan senang hati menerima JSON lewat HTTP
    • Saya penasaran bagaimana dengan aplikasi client/server yang bukan web
      Saya membayangkan kasus seperti game online atau MMO yang membutuhkan komunikasi jauh lebih real-time daripada REST, tetapi sekarang saya tidak begitu tahu apakah mereka menumpangkan sesuatu di atas koneksi soket
    • Jika Thrift/gRPC adalah berkah dalam routing layanan internal, saya penasaran itu dibandingkan dengan apa
      Saya juga ingin tahu apa saja alternatif lain yang pernah dicoba
    • Saya penasaran apa maksudnya “verba bocor”
  • Jika tidak melakukan streaming dua arah, menurut saya gRPC pada umumnya hanya membuang waktu
    Ada neraka dependensi transitif saat runtime, neraka toolchain, dan bahkan tim-tim di internal Google yang mengelola tiap implementasi tampaknya tidak sepakat secara filosofis tentang bagaimana fitur dasar seharusnya bekerja
    Coba ekspos API gRPC ke tim yang tidak memakai bahasa Anda, terutama jika bukan Go/Python/Java atau bahkan memakai versi lama, atau coba integrasikan dengan produk komersial siap pakai, atau ekspos ke browser; semuanya akan membutuhkan lapisan perantara

    • Saya pernah memakai gRPC di beberapa perusahaan dan tim, dengan ukuran engineering masing-masing kira-kira 100–500 orang, dan tidak mengalami masalah dependensi maupun toolchain
      gRPC umumnya berjalan lancar
    • Menurut saya jangan diekspos langsung ke browser. Itu bukan area yang dikuasai gRPC, dan lebih baik membuat lapisan kustom yang mengonversinya ke JSON
      Memakai REST untuk komunikasi antar-layanan backend juga tidak terlalu masuk akal jika ada kebutuhan performa, dan kecuali itu panggilan yang sesekali mengambil data kecil, alasan untuk memakai protokol/API yang dapat dibaca manusia cukup lemah
    • Saya ingat pernah dipersoalkan karena mencoba mengekspos API gRPC ke browser tetapi tidak membuat antarmuka yang “terasa JSON”
      Saat mengembalikan tipe dari subtipe oneof yang belum memiliki field saat ini, hasil konversi otomatisnya menjadi seperti { "id": "id", "sub_type_two": { } }
      Secara fungsional itu berjalan, dan meskipun nanti field ditambahkan, kode tersebut tetap berjalan. Namun di dunia web, merepresentasikan tipe respons dengan objek kosong terasa aneh, dan masalah seperti ini bisa tidak terlalu terlihat saat menulis protobuf
    • Streaming dua arah pada umumnya adalah ide buruk untuk sesuatu yang ingin dioperasikan “dalam skala besar”
    • Protobuf tidak cocok untuk streaming
      Bahkan dibandingkan dengan hampir semua protokol biner yang bisa dibayangkan, ia cenderung anti-streaming
  • Satu-satunya pengalaman saya memakai gRPC di perusahaan adalah proyek yang didorong oleh developer senior lain dengan alasan “butuh performa”
    Pada akhirnya kami juga membuat JSON API karena harus bisa dikonsumsi frontend, dan selain developer itu tidak ada yang berpengalaman dengan gRPC. Bahkan developer itu sendiri tidak melangkah lebih jauh dari panduan quick start gRPC Python dan tidak membantu memperbaiki bug
    Proyeknya berantakan karena banyak alasan, dan sama sekali tidak pernah mencapai skala yang bisa membenarkan penggunaan gRPC
    Meski begitu, secara pribadi saya menyukai gRPC dari sedikit penggunaan saya, dan terasa bahwa ia membutuhkan jauh lebih banyak pekerjaan dan pertimbangan. Itu mungkin karena saya jauh lebih sering membuat JSON API

    • Itu lebih terdengar seperti kritik terhadap developer “senior” yang bahkan tidak tahu bahwa gRPC tidak kompatibel dengan browser sebelum mengadopsinya, daripada kritik terhadap gRPC itu sendiri
  • Saya sedang cukup menikmati memakai ConnectRPC https://connectrpc.com/
    Ia memperbaiki banyak bagian bermasalah dari gRPC, dan saya berharap ketika Safari menerima WebTransport, ConnectRPC bisa mengembangkan streaming yang lebih baik
    Awalnya saya mengira https://buf.build berlebihan, tetapi kemampuan mengambil file proto pihak ketiga tanpa mengunduhnya satu per satu menjadi faktor penentu
    deps:
    - buf.build/landeed/protopatch
    - buf.build/googleapis/googleapis
    Pembuatan SDK otomatis juga besar pengaruhnya. Dulu saya hendak memujinya karena otomatis membuat SDK untuk sekitar 9 bahasa, tetapi dalam satu-dua hari terakhir ada pembaruan dan sekarang terlihat mendukung 16 bahasa, OpenAPI, serta fitur baru lainnya
    Saya juga sempat tergoda oleh janji palsu streaming gRPC, dan dokumen ini benar-benar sesuai dengan pengalaman saya: https://connectrpc.com/docs/go/streaming/

    • Saya membuat wrapper kecil berbasis WebSocket untuk streaming ConnectRPC agar bisa berjalan di ReactNative
      Berkat itu, streaming dua arah juga bisa digunakan di browser
    • Meski begitu, ia tetap memakai Protocol Buffers, dan banyak masalah yang saya alami dengan gRPC justru berasal dari sana
    • Saya penasaran apakah ada kabar terbaru tentang dukungan WebTransport di Safari
  • Rasanya Google seolah memainkan perang psikologis ke seluruh industri hingga membuat orang memakai gRPC untuk komunikasi layanan internal
    Pengalaman developer gRPC jauh lebih buruk daripada REST
    Anda tidak bisa memberi seseorang satu perintah sederhana untuk memanggil sebuah endpoint, dan butuh alat tambahan yang tidak terstandar. Selain itu, kode sisi klien yang dihasilkan adalah bongkahan buruk rupa yang jarang terlihat dalam bahasa apa pun

    • Dari sudut pandang backend, saya sangat tidak setuju dengan pernyataan bahwa pengalaman developer gRPC lebih buruk daripada REST
      Dengan satu perubahan protokol, Anda bisa tahu secara statis konsumen hilir mana yang perlu diperbarui dan di-deploy ulang, sehingga pekerjaan berminggu-minggu bisa berubah menjadi perubahan satu jam
      Anda juga tahu bahwa pesan yang diterima dan dikirim langsung divalidasi, dan bisa disimpan dengan murah untuk dipulihkan nanti
      Dengan proto, Anda mendapatkan dokumentasi API yang sangat mudah dibaca, tanpa tercampur dengan kode atau logika bisnis. Semantik versioning dan deprecation juga sudah bawaan, dan kecuali map, struktur data yang didukung juga lebih kaya
      Dibandingkan itu, JSON terasa menggelembung dan usang di backend
    • gRPC adalah standar dalam hal-hal penting
      Jika Anda menuliskan tipe data dan signature fungsi, Anda mendapatkan sesuatu yang bisa dipanggil seperti fungsi sungguhan, dan bisa fokus pada logika bisnis alih-alih boilerplate serialisasi/deserialisasi
      Thrift juga jauh lebih baik daripada membuat semuanya sendiri, dan menurut saya GraphQL lebih baik lagi
    • Saya pernah dipaksa memakainya di beberapa perusahaan, tetapi 99%-nya adalah investasi technical debt yang tidak perlu
      Bahkan di Go, memahami regenerasi dan pengelolaan versi proto bersama itu merepotkan, dan makin buruk setiap kali satu bahasa tambahan masuk
      Meski begitu, sepertinya semua startup merasa butuh 100 microservice dan gRPC
  • Kalimat “Jika sebuah API adalah REST API, klien tidak perlu memahami format URL, dan format itu bukan bagian dari spesifikasi API yang diberikan kepada klien” berkaitan dengan definisi REST dari Roy Fielding
    Fielding menulis bahwa REST API harus bisa dimasuki tanpa pengetahuan awal selain URI awal dan sekumpulan media type yang terstandar, dan setelah itu semua transisi state aplikasi harus terjadi dengan cara klien memilih opsi yang disediakan server
    https://roy.gbiv.com/untangled/2008/rest-apis-must-be-hypert...
    Ini sudah sering dibahas, tetapi tetap menarik bahwa dalam sistem yang benar-benar RESTful, “spesifikasi API” yang diberikan kepada klien seharusnya hanya berupa URI/URL entry point awal

    • Gagasan tentang REST yang mendeskripsikan dirinya sendiri kini lebih dikenal sebagai HATEOAS
      Secara pribadi, menurut saya itu berlebihan dan tidak menyelesaikan masalah nyata
      https://en.m.wikipedia.org/wiki/HATEOAS
    • Saya penasaran bagaimana cara menulis klien API untuk REST API yang hanya memublikasikan entry point awal
      Terutama, saya tidak tahu bagaimana klien seharusnya menemukan resource yang bisa dimanipulasi atau model request/response
    • Saya tidak sepenuhnya setuju bahwa dalam sistem yang benar-benar RESTful, spesifikasi API yang diberikan kepada klien seharusnya hanya berupa URI/URL entry point awal
      Konfigurasinya bisa begitu, tetapi spesifikasi API harus jauh lebih banyak daripada URL dan harus menjelaskan media type yang dipakai sistem secara rinci. Dengan kata lain, sebagian besar yang dibutuhkan adalah penjelasan tentang body request/response HTTP
      Di tautan itu juga tertulis bahwa “REST API harus menghabiskan hampir seluruh upaya deskriptifnya untuk mendefinisikan media type yang merepresentasikan resource dan menggerakkan state aplikasi”
      Pada akhirnya, ia bukan sekadar mengembalikan application/json, melainkan sesuatu seperti +json tertentu, dan sebagian besar berisi data bisnis yang harus dipahami aplikasi, bukan JSON biasa
      Dalam diskusi populer, fokusnya hanya pada URL awal, sementara sebagian besar pekerjaan yang dimaksud Fielding sebagai “jelaskan media type” hilang. Jadi wajar jika orang yang mendengar “cukup satu URL” bertanya, “di mana spesifikasi sisanya?”
    • Keduanya sebenarnya menyetujui hal yang sama. Di sini “format URL” benar-benar berarti format URL, bukan format resource
      Saya juga sempat mengira ini blogger lain yang tidak memahami REST, lalu membuka tulisannya, tetapi sepertinya penulis setidaknya memahami konsep dasarnya
      Saya juga suka gRPC dan dalam proyek komersial itu cukup menarik, tetapi untuk proyek pribadi atau idealistis, menurut saya REST lebih baik
    • Ini contoh klasik: setelah sebuah ide bagus menjadi tren, orang-orang terus menyebarkannya sambil salah memahami ide tersebut
  • Saya tidak suka memakai gRPC di dalam datacenter
    Orang memilihnya karena alasan performa, tetapi gRPC sulit disebut berkinerja tinggi, dan kualitas klien publiknya juga sangat rendah, terutama di luar implementasi inti C++/Java. Contohnya implementasi Node.js
    Saya tidak menentang penggunaan protobuf sebagai spesifikasi API, tetapi seharusnya bisa dipakai bersama protokol framing di atas TCP. Namun untuk RPC dengan cara seperti itu, belum ada pilihan dominan yang jelas
    Untuk API berbasis web, saya lebih menyukai payload yang bisa dibaca, tetapi biasanya orang memakai JSON dengan kekhususan tipe yang longgar sehingga muncul masalah interoperabilitas antar bahasa backend. Terutama di Node.js, JSON.parse dipakai seperti implementasi mapping skema
    Untuk melakukannya dengan benar, encoder dan decoder harus dibuat secara eksplisit dari skema, dan itu mengurangi sebagian keuntungan memakai JSON dalam konteks JS

    • Jika Anda sampai mempertimbangkan gRPC karena khawatir soal performa, saya penasaran mengapa pada saat yang sama tidak masalah menempatkan Node.js di dekat stack Anda
    • Setuju, dan untuk masalah skema JS, Zod sangat membantu
      Saya juga memantau proyek TypeSpec dari Microsoft: typespec.io
    • Keunggulan utama proto adalah interoperabilitas di antara beberapa bahasa
      Jika stack teknologinya hanya satu bahasa, kepentingannya berkurang. Dan jika Anda memakai bahasa di luar bahasa utama Google, kemungkinan besar pengalamannya tidak akan sebaik itu
    • Pada 2023 ada presentasi tentang Homa, protokol berbasis non-TCP untuk RPC datacenter: https://youtu.be/xQQT8YUvWg8?si=g3u5TogBe0_QpPpj
  • gRPC terasa tidak perlu sulit diakses bagi orang-orang di luar Google
    Klien gRPC JS terasa terlalu berat dan cukup buram. Idenya bagus, tetapi implementasinya terasa kurang memuaskan dibandingkan bagi mereka yang terbiasa dengan “kesederhanaan” REST

    • Di batas frontend/backend, kubu REST/JSON dan kubu RPC/protobuf/gRPC saling berbenturan
      RPC secara semantik lebih mudah dipelihara karena tidak perlu memaksakan kardinalitas atau relasi model data ke dalam satu pola preskriptif. Di dunia API yang berubah cepat, sulit menyesuaikan entitas RESTful yang indah; dalam tim besar dengan kebutuhan/kepemilikan yang berubah, desain berpusat pada layanan lebih baik
      Sisi frontend tidak memelihara sistem backend. Mereka menginginkan API yang mudah dipahami, dan entitas yang bisa diabstraksikan dengan REST. Merekalah penerima manfaat akhir dari desain semacam itu
      Upaya untuk REST masuk akal bagi perusahaan yang menjual API dan menjadikan developer pihak ketiga sebagai pelanggan utama
      Untuk pengembangan backend, protobuf dan encoding wire biner lebih mudah. API dapat didefinisikan lalu dibagikan antar-layanan dengan cara bertipe statis, dan waktu encoding/decoding pesan juga berkurang. JSON tidak semantik, tidak bertipe, dan overhead-nya besar
      Sebaliknya, frontend secara native menangani teks dan JSON. Mereka tidak ingin mengunduh definisi protobuf atau memperlakukan data biner seperti warga kelas dua, dan itu juga tidak cocok rapi dengan tooling
      gRPC memiliki routing, retry, kanal tambahan, streaming, dan semantik penghentian protokol dengan baik, tetapi hampir tidak terlihat di frontend. Semuanya ditujukan untuk konsumen backend
      Pada akhirnya, ini 100% adalah kesenjangan tooling frontend/backend, serta ketidakselarasan antarmuka dan kegunaan
    • REST mirip dengan HTML
      Pada dasarnya, sumbernya bisa dilihat, bisa dibaca manusia, dan mudah diperiksa
      gRPC ditujukan agar mesin dapat berbicara secara efisien satu sama lain, dan ketika manusia ikut campur—baik saat coding maupun memeriksa request/response—rasanya agak tidak nyaman
      Perbedaan kegunaan ini bisa dimaklumi karena konteks dan tujuannya berbeda
    • Implementasi resmi gRPC JavaScript agak kurang bagus
      Menurut saya, implementasi dari buf.build lebih baik
      https://buf.build/blog/protobuf-es-the-protocol-buffers-type...
    • gRPC adalah ide yang bagus, tetapi menjadi berat oleh solusi untuk masalah ala Google yang tidak saya miliki
      Tampaknya banyak orang memilihnya karena membutuhkan protokol seperti RPC biner dengan kontrak, tetapi semakin jauh dari GoLang, hasilnya makin buruk
    • Ada kegunaan tertentu tempat gRPC bersinar. Streaming adalah salah satunya: ia dapat mengirim stream pesan secara transparan dalam satu “koneksi”
      Untuk layanan CRUD sederhana, REST sudah cukup