Bagaimana merancang titik akhir API untuk memposting objek anak dan untuk mendapatkan semua anak dari semua orang tua?

12

Misalnya saya punya entitas: Klien, Laporan. Klien mungkin memiliki banyak Laporan dan saya pikir titik akhir untuk satu manajemen Laporan harus disarangkan seperti ini:

/clients/{client_id}/reports/{report_id}

Adapun semua laporan dari satu klien titik diharapkan:

/clients/{client_id}/reports

Tetapi bagaimana seharusnya terlihat titik akhir untuk mendapatkan semua Laporan dari semua Klien agar API konsisten dan dirancang dengan baik.

Pendekatan saya:

  1. (Saya melihatnya di beberapa google api) gunakan "-" sebagai ganti dan parsing sebagai "semua":

/clients/-/reports

Ini membuat format endpoint tetap sama, tetapi terlihat agak tidak biasa, tidak dapat menemukan rfc yang menyarankan cara ini.

  1. Buat titik akhir yang terpisah hanya untuk semua laporan:

/reports

Tetapi untuk mendapatkan Laporan Klien itu masih:

/clients/{client_id}/reports

  1. Refactor titik akhir untuk membuat "klien" bukan orangtua, tetapi hanya parameter filter:

/reports?client={client_id} - laporan satu klien

/reports - laporan semua klien

Dalam hal menambahkan titik akhir baru untuk memposting laporan untuk klien tertentu, itu mungkin terlihat jelek, karena itu akan menjadi permintaan POST dengan parameter di URL.

Apakah ada saran ide lain?

Yann
sumber
2
Anda mungkin tertarik pertanyaan
Laiv

Jawaban:

3

Tetapi bagaimana seharusnya terlihat titik akhir untuk mendapatkan semua Laporan dari semua Klien agar API konsisten dan dirancang dengan baik.

Sebelum hal lain, ingatlah bahwa tidak ada aturan emas untuk memodelkan API ISTIRAHAT. Yang kami miliki hanyalah praktik dan konvensi terbaik. Yang sedang berkata, kemungkinan jawabannya adalah -seperti biasa- pilih salah satu yang paling memenuhi persyaratan Anda dan dalam hal ini yang paling mengekspresikan model Anda.

Jadi, periksa tiga opsi dari ekspresif.

# 1 Notasi "-"

Ini ide yang cemerlang. Ini memungkinkan kita untuk mengekspresikan kondisi semua reportsmilikclients . Ini mempersempit "kueri" ke set laporan tertentu (yang terletak di dalam clientsbatas).

Itu menjaga gagasan hierarki (milik) sepanjang waktu, jadi jika reportsdapat ditemukan di lokasi yang berbeda, notasi ini membuat masalah besar. Sebagai contoh:

  • Semua laporan itu milik klien /clients/-/reports
  • Semua laporan milik departemen /departments/-/reports
  • Semua laporan itu milik karyawan /employees/-/reports

Namun, untuk mengambil semua laporan yang tersedia dalam sistem, menjaga hierarki tidak memberikan keuntungan yang berharga atas opsi berikutnya.

# 2 URI yang berbeda

Jika kita tidak perlu mengungkapkan batasan / konteks / hierarki pada saat mengambil semua laporan yang tersedia , pendekatan ini tampaknya lebih masuk akal bagi saya.

URI baru ( /reports) juga membuka kemungkinan untuk manajemen laporan . Namun, kami tidak harus menyediakannya dengan dukungan RESTful lengkap jika kami tidak menganggapnya perlu. Misalnya, Anda telah menyatakan Make a separate endpoint just for all the reports. Tidak apa-apa, Anda hanya perlu menerapkan GETdan mungkin beberapa filter untuk permintaan dan hanya itu.

Perhatikan bahwa Anda masih bisa melakukan ini /reports?client={client_id}. Memiliki URI berbeda untuk sumber daya yang sama baik-baik saja. Beberapa artikel yang saya baca akan menyebut ketahanan ini .

# 3 Mengembalikan hierarki

Saya merasa bahwa pendekatan ini tidak memenuhi harapan Anda. Plus, saya pikir, ini akan membawa Anda pada akhirnya ke titik awal.

Kesimpulan

Perhatikan bahwa # 1 dan # 2 tidak saling eksklusif. Kita bisa menerapkan keduanya. Mengingat situasi aktual dan menurut premis OP, saya hanya akan mengimplementasikan # 2.


1: itu setara dengan /clients/-/reportskurasa

Laiv
sumber
0

Pola desain API Google menyarankan penggunaan '-' dalam skenario ini.

GET /clients/-/reports

Sumber:

https://cloud.google.com/apis/design/design_patterns#list_sub-collections

wfg4
sumber
2
Sejauh ini bagi saya untuk tidak setuju dengan Google yang maha kuasa, tapi saya pikir saya lebih suka sesuatu seperti /client/{client_id}/report/{report_id}dan/clients/report/{report_id}
Robert Harvey
2
@RobertHarvey mengapa tidak adil /reports?
Laiv
@Laiv: Itu akan menyiratkan semua laporan. Perbarui halaman Anda; Saya membuat edit ninja.
Robert Harvey
@ RobertTarvey Maksudku, mengapa tidak 2 titik akhir /clients...dan berbeda /reports.
Laiv
1
@Laiv: Oke, tapi itu hanya menimbulkan pertanyaan "Parameter mana yang harus saya masukkan ke badan permintaan?"
Robert Harvey