Banyak permintaan kecil vs. beberapa permintaan besar (Desain API)

49

Saat ini saya sedang mengerjakan proyek dengan organisasi sebagai berikut:

  • Klien - Mendapat data dari server utama melalui REST api.
  • Server - Meminta data dari berbagai server lain melalui API pihak ketiga
  • API pihak ketiga - Layanan di luar kendali saya yang menyediakan data ke server (Reddit, Hackernews, Quora, dll.)

Demi argumen, katakanlah klien pertama-tama membutuhkan daftar item dari masing-masing API pihak ketiga. Dari daftar ini, item akan dipilih pada titik mana klien perlu melihat konten lengkap item serta tanggapan (yaitu komentar) terhadap item tersebut. Saya mencoba memutuskan di antara tiga opsi:

A la carte

Dalam pendekatan ini, saya akan memiliki 3 titik akhir yang terpisah di server saya: satu untuk mendapatkan daftar item, satu untuk mendapatkan konten utama untuk suatu item, dan satu untuk mendapatkan tanggapan dari item tersebut.

  • Pro: Saya tidak pernah membuat lebih banyak permintaan daripada yang saya butuhkan, permintaan harus kecil sehingga umumnya harus lebih cepat.
  • Cons: Saya harus membuat banyak permintaan. Setelah memilih item dari daftar, pengguna mungkin harus menunggu sebelum melihat konten utama dan kemudian menunggu lebih lama untuk melihat tanggapannya

Tembolok sisi server

Dalam permintaan ini, saya akan melakukan satu panggilan ke server saya untuk "mengambil" semua data untuk semua sumber. Data kemudian akan di-cache di server. Klien kemudian akan memiliki titik akhir REST yang sama seperti sebelumnya, kecuali tidak akan ada banyak menunggu antara panggilan karena server saya sudah memiliki data dan hanya harus memberi makan kepada klien.

  • Pro: Masih mudah diimplementasikan di sisi klien, tetapi tanpa masalah latensi
  • Cons: Sisi server sedikit lebih terlibat, dan panggilan pertama bisa sangat lama.

Tembolok sisi klien

Skenario ini mirip dengan yang sebelumnya kecuali klien hanya pernah membuat satu permintaan ke server: beri saya semua data. Dari sini, tanggung jawab klien untuk menyimpan data dan menggunakannya dengan tepat.

  • Pro: Implementasi server yang mudah, sangat cepat setelah panggilan pertama
  • Cons: Panggilan pertama akan sangat lambat, implementasi sisi klien lebih rumit

Saya tidak yakin mana yang merupakan pendekatan terbaik, atau jika mungkin saya kehilangan solusi yang jelas. Saran apa pun akan sangat dihargai!

Williamg
sumber
Bagi saya ini adalah pilihan antara kesegaran dan kecepatan. Apa yang lebih disukai oleh para pemangku kepentingan dan pengguna akhir Anda?
Erk

Jawaban:

28

Satu hal yang perlu diingat adalah latensi jaringan yang diharapkan (yaitu waktu ping) antara klien Anda dan server Anda. Dalam situasi tinggi-latency dengan bandwidth yang dinyatakan baik, banyak permintaan kecil akan tampil secara signifikan lebih buruk daripada satu besar.

Saya baru-baru ini berkolaborasi dalam proyek aplikasi web yang didukung database multi-tim di mana salah satu tim berada di India (sisanya berada di AS). Kami memiliki satu instance database yang di-host di kantor kami di AS tempat pengembang menghubungkan instance server web kami. Meja saya mungkin lima puluh kaki dan dua lompatan LAN dari instance database, dan kinerjanya baik-baik saja.

Ketika kami pertama kali memulai dengan pengembang di India, mereka mengalami waktu tunggu yang sangat lama memulai aplikasi dan menavigasi halaman ke halaman. Kita bicara sepuluh menit menunggu di sini. Ternyata ini karena ~ 200 ms waktu ping dari meja mereka ke server database dev kami dikalikan oleh banyak, banyak pertanyaan singkat ke database. Ping 0.5ms lokal saya sangat sepele sehingga obrolan antara server web dan server database tidak pernah berarti. Ini adalah pertama kalinya kami melakukan pemisahan geografis antara server web dan server basis data.

Solusi dalam kasus kami adalah mengkloning server database dan menyimpan salinannya di India, tetapi intinya adalah untuk diingat bahwa jika klien dan server Anda berjauhan, latensi jaringan akan dikalikan dengan jumlah komunikasi di seluruh kawat. Bandwidth setelah koneksi dibuat biasanya tidak terlalu memprihatinkan.

JakeRobb
sumber
2

Ketiga opsi ini tidak eksklusif satu sama lain, Anda dapat menggunakan kombinasi cache sisi-klien dan sisi-server. Namun beberapa data, seperti komentar, mungkin menjadi basi, jika disimpan dalam cache terlalu lama. Mengingat Anda tidak dapat memeriksa apakah itu masalahnya, Anda mungkin sebaiknya tidak menyimpannya sama sekali. Di sisi lain, konten biasanya tidak berubah secara drastis, sehingga tidak ada salahnya menyimpannya di sisi server dan kemudian mengambilnya di sisi klien untuk menurunkan latensi.

wfdctrl
sumber
1

Berdasarkan hanya info yang Anda berikan, opsi 1, karena

  • dengan satu permintaan klien Anda akan mencampurkan apel dan jeruk dan keranjang buah mungkin sangat besar.

  • caching adalah tradeoff di mana Anda mendapatkan kinerja tetapi berpotensi kehilangan konsistensi (data basi). Jika Anda tidak memiliki masalah kinerja yang teridentifikasi, masalah sinkronisasi biasanya tidak layak berisiko.

guillaume31
sumber
0

Saya selalu menemukan beberapa permintaan besar untuk berkinerja lebih baik dan lebih terukur. Tetapi ada pengorbanan dalam semua pendekatan, jadi itu tergantung pada kebutuhan server dan klien. Anda mungkin ingin menggunakan opsi lain, yaitu meminta klien menentukan seluruh rentang atau set data untuk diambil - tidak harus semua data, tetapi beberapa rentang, yang disesuaikan dari waktu ke waktu agar sesuai dengan bandwidth yang tersedia.

Frank Hileman
sumber
0

Saya akan (hampir) opsi diskon 3. Memilih antara 1 dan 2 tergantung pada dua hal:

  • (A) seberapa besar hasil pengambilan tunggal total
  • (B) berapa banyak detail hasil yang biasanya akan digunakan klien / pengguna dalam sesi itu.

Mudah untuk membuat keputusan jika A dan B ekstrem:

  • Jika A besar dan B kecil, pasti pilih opsi 1 (A la Carte).
  • Jika A kecil dan B besar, pilih 2 (cache sisi-server) atau bahkan 3 (cache sisi-klien).

Untuk variasi A / B (besar / kecil) lainnya, Anda harus menerapkan kebijaksanaan. Saya sering menyediakan baik kasar dan halus endpoint untuk cater untuk kasus penggunaan yang berbeda dari klien yang berbeda.

Cornel Masson
sumber
0

Seperti biasa dalam pemrograman, itu tergantung.

Jadi, pertanyaan sebenarnya adalah: apa yang harus Anda pertimbangkan ketika memutuskan untuk A / B / C atau kombinasi dari ketiganya?

Saya akan mengatakan bahwa faktor-faktor yang membedakan sebenarnya adalah detail implementasi API pihak ke-3 yang Anda konsumsi. Sebagai contoh, Anda harus mempertimbangkan: Apakah cepat atau lambat? Apakah data sering berubah dan tidak terduga? Apakah mereka "cerewet" atau Istirahat?

Dalam hal layanan yang cepat dan mudah dipanggil, dengan data yang berubah begitu sering sehingga cache sisi server Anda akan menciptakan masalah basi-cache, tentu saja, pilih opsi 1: lebih banyak permintaan, tidak ada cache, hanya jika diperlukan.

Jika data eksternal Anda akan berubah dengan cara yang dapat diprediksi, atau Anda terbatas dengan penggunaannya, atau hanya Anda bisa mendapatkan pengalaman pengguna yang lebih baik dalam menyimpan data di server Anda, lanjutkan dengan 2. Namun perlu diingat bahwa cache tidak gratis: ada biaya dalam hal debugging dan kadang-kadang pengguna mengeluh mereka tidak melihat pembaruan.

Opsi 3, saya akan mempertimbangkan hanya jika data tidak banyak, tetapi dalam kasus itu bahkan opsi 1 atau 2 dapat bekerja, dan Anda menyimpan lebih banyak logika di server, jadi saya akan tetap untuk 1 atau 2.

Hanya 2c saya.

A. Chiesa
sumber