我正在使用 Rails,我在預訂中有兩個視圖(客戶和培訓師)。我正在嘗試根據誰是 current_user 從索引路由到客戶端或培訓師。
如果我是客戶,將索引路由給培訓師 如果我是培訓師,將索引路由給客戶
class BookingsController < ApplicationController
def index
end
def clients
@bookings = Booking.where(client: current_user)
@clients = current_user.bookings.map(&:client)
end
def trainers
@trainers = current_user.bookings.map(&:user)
end
end
Rails.application.routes.draw do
resources :bookings do
collection do
get "/clients", to: "bookings#clients", as: "clients"
get "/trainers", to: "bookings#trainers", as: "trainers"
end
resources :shared_training_plans, except: [:new]
end
end
uj5u.com熱心網友回復:
您正在向后嵌套。您的路線的輸出實際上應該更像:
GET /instructors/1/bookings # bookings belonging to instructor 1
GET /instructors/1/clients # clients that are associated with instructor 1
GET /students/3/bookings # bookings belonging to student 3
GET /students/3/instructors # instructors belonging to student 3
這以 RESTful 的方式描述了端點回傳屬于其他資源的內容。這應該由index操作來處理 - 理想情況下是為此目的指定的控制器,因為每個控制器應該只負責一個資源。
您可以將這些路線定義為:
resources :instructors do
resources :bookings, module: :instructors
end
resources :clients do
resources :bookings, module: :clients
end
module Instructors
class ClientsController < ApplicationController
# GET /instructors/1/clients
def index
@instructor = Instructor.find(params[:instructor_id])
@clients = @instructor.clients
end
end
end
module Clients
class InstructorsController < ApplicationController
# GET /clients/1/clients
def index
@client = Client.find(params[:client_id])
@clients = @client.instrucors
end
end
end
您可以通過重新構想該功能來實作這一點,以便鏈接“特定用戶 URL”而不是通用 URL。例如,您可以在 Stackoverflow 的儀表板上看到這一點,它使用https://stackoverflow.com/users/{id}/{username}.
REST 理論上應該是無狀態的,因此無論誰請求,每條路徑都應該回傳相同的資源。但就像所有規則一樣,這可能會被打破,您可以設定如下路線:
GET /user/bookings # GET bookings for the currently signed in user
Which would return different results for the signed in user which is stateful. user here would be consider a singular resource. This is mostly useful if you need to have a significantly different represention of the resource when viewing "your own" vs "others".
To actually be able to use the "current user" from the routes the authentication system must be implemented as Rack middleware (like Devise is) and not on the controller level as almost all the "reinventing the wheel" tutorials are. Routing is Rails is implemented as Rack middeware that is run before your controller is ever instanciated.
Devise has the authenticated routing helper which lets you setup different routes for authenticated/unauthenticated users. For example if instructors are implemented as different warden scopes:
authenticated :instructor do
resource :bookings, controller: 'instructors/bookings', only: [:index]
end
authenticated :student do
resource :bookings, controller: 'students/bookings', only: [:index]
end
But you could also use a lambda if you only have one warden scope (the typical Devise configuration):
authenticate :user, ->{|u| u.instructor? } do
resource :bookings, controller: 'instructors/bookings', only: [:index]
end
authenticate :user, ->{|u| u.student? } do
resource :bookings, controller: 'students/bookings', only: [:index]
end
Both of these would route GET /bookings to Instructors::BookingsController#index and Students::BookingsController#indexdepending on which "role" the user has.
轉載請註明出處,本文鏈接:https://www.uj5u.com/yidong/436023.html
