Bentuk asli dari jawaban ini sangat berbeda, dan dapat ditemukan di sini . Buktinya ada lebih dari satu cara menguliti kucing.
Saya telah memperbarui jawaban sejak menggunakan ruang nama dan menggunakan pengalihan 301 - daripada default 302. Terima kasih kepada pixeltrix dan Bo Jeanes untuk dorongan pada hal-hal itu.
Anda mungkin ingin mengenakan helm yang benar - benar kuat karena ini akan membuat Anda berpikir .
API perutean Rails 3 sangat jahat. Untuk menulis rute untuk API Anda, sesuai kebutuhan Anda di atas, Anda hanya perlu ini:
namespace :api do
namespace :v1 do
resources :users
end
namespace :v2 do
resources :users
end
match 'v:api/*path', :to => redirect("/api/v2/%{path}")
match '*path', :to => redirect("/api/v2/%{path}")
end
Jika pikiran Anda masih utuh setelah titik ini, izinkan saya menjelaskannya.
Pertama, kami memanggil namespaceyang sangat berguna ketika Anda ingin banyak rute dicakup ke jalur dan modul tertentu yang diberi nama serupa. Dalam hal ini, kami ingin semua rute di dalam blok untuk kami namespacescoping ke controller di dalam Apimodul dan semua permintaan untuk jalur di dalam rute ini akan diawali dengan api. Permintaan seperti /api/v2/users, Anda tahu?
Di dalam namespace, kami mendefinisikan dua ruang nama lagi (woah!). Kali ini kita mendefinisikan "v1" namespace, sehingga semua rute untuk kontroler sini akan berada di dalam V1modul di dalam Apimodul: Api::V1. Dengan mendefinisikan resources :usersdi dalam rute ini, pengontrol akan berlokasi di Api::V1::UsersController. Ini adalah versi 1, dan Anda sampai di sana dengan membuat permintaan seperti /api/v1/users.
Versi 2 hanya kecil sedikit berbeda. Alih-alih controller yang menyajikannya berada Api::V1::UsersController, sekarang di Api::V2::UsersController. Anda sampai di sana dengan membuat permintaan seperti /api/v2/users.
Selanjutnya, a matchdigunakan. Ini akan cocok dengan semua rute API yang menuju ke hal-hal seperti /api/v3/users.
Ini adalah bagian yang harus saya cari. The :to =>pilihan memungkinkan Anda untuk menentukan bahwa permintaan khusus harus diarahkan di tempat lain - saya tahu bahwa banyak - tapi aku tidak tahu bagaimana untuk mendapatkannya untuk mengarahkan ke tempat lain dan lulus dalam sepotong permintaan asli bersama dengan itu .
Untuk melakukan ini, kita memanggil redirectmetode dan meneruskannya string dengan %{path}parameter interpolasi khusus . Ketika permintaan masuk yang cocok dengan matchtugas akhir ini , itu akan menginterpolasi pathparameter ke lokasi %{path}di dalam string dan mengarahkan pengguna ke tempat yang mereka tuju.
Akhirnya, kami menggunakan yang lain matchuntuk merutekan semua jalur yang tersisa yang diawali /apidan mengarahkannya ke /api/v2/%{path}. Ini berarti permintaan seperti /api/usersakan dituju /api/v2/users.
Saya tidak tahu bagaimana cara /api/asdf/usersmencocokkan, karena bagaimana Anda menentukan apakah itu seharusnya menjadi permintaan /api/<resource>/<identifier>atau /api/<version>/<resource>?
Bagaimanapun, ini menyenangkan untuk diteliti dan saya harap ini membantu Anda!