2010-09-26 29 views
6

Có cách tiếp cận đồng thuận tốt nhất để triển khai vai trò người dùng khi sử dụng các tuyến tài nguyên RESTful không?Cấu trúc ứng dụng cho các tài nguyên RESTful dựa trên vai trò

Nói rằng tôi có các nguồn sau:

User has_many Tickets 
Event has_many Tickets 
Ticket belongs_to Person, Event 

Và sau đó tiếp tục nói rằng tôi có hai loại người: khách hàng và đại lý. Cả hai sẽ đăng nhập vào hệ thống, nhưng với quyền truy cập tài nguyên và chức năng khác nhau dựa trên vai trò của chúng. Ví dụ:

Khách hàng có thể truy cập vào:

  • index tổ chức sự kiện, cho thấy
  • index Ticket (scoped bởi người sử dụng), show, mua/tạo, trả lại/xóa
  • Person tạo, chương trình, cập nhật

Đại lý có thể truy cập:

  • Chỉ số sự kiện, show, tạo, cập nhật, xóa
  • chỉ số vé, show, bán/tạo, cập nhật, hoàn/xóa
  • Person chỉ mục, chương trình, tạo, cập nhật, xóa

nào của 4 cách tiếp cận chung dưới đây sẽ sạch hơn và linh hoạt hơn?

bộ điều khiển riêng biệt trong vai trò thư mục và các nguồn lực trong không gian tên, ví dụ:

namespace "agent" do 
    resources :events, :tickets, :people 
end 
namespace "customer" do 
    resources :events, :tickets, :people 
end 

riêng biệt điều khiển bằng vai trò, ví dụ:

AgentController 
    def sell_ticket, etc 

CustomerController 
    def buy_ticket, etc 

điều khiển chung với hành động riêng biệt khi cần thiết, ví dụ:

TicketController 
    before_filter :customer_access, :only => :buy 
    before_filter :agent_access, :except => :buy 

    def buy #accessed by customer to create ticket 

    def sell #accessed by agent to create ticket 

Hành động được chia sẻ với câu lệnh có điều kiện, ví dụ:

TicketController 
    def create 
    if @role == :customer 
     #buy ticket 
    elsif @role == :customer 
     #sell ticket 
    end 
    end 

Trả lời

-1

Nếu bạn sử dụng cùng một mô hình cho vé khách hàng và đại lý, sẽ không có sự khác biệt lớn giữa cách chúng được xử lý trong bộ điều khiển. Vì vậy, tạo ra hành động sẽ luôn luôn như thế này:

@ticket = Ticket.new(params[:ticket]) 

if @ticket.save 
    redirect_to @ticket 
else 
    render :action => "new" 
end 

Nhưng quan điểm của bạn có thể được tùy chỉnh đơn giản:

<% if customer? %> 
    Customer area. 
<% else %> 
    Agent area. 
<% end %> 
+0

Mô hình không biết về người dùng đã được xác thực. Điều đó thường được quản lý bởi bộ điều khiển. Ngoài ra, OP đang hỏi về cách tốt nhất để xử lý bảo mật. Điều này không thể được tùy chỉnh trong chế độ xem. Điều gì về các kết nối API? Làm cách nào để bạn thực thi bảo mật cho các vai trò người dùng khác nhau ở đó? Bạn không muốn lặp lại mã, vì vậy nó cần phải được ở một vị trí trung tâm tức là: điều khiển. Vì vậy, câu hỏi là, làm thế nào bạn có thể quản lý một cách an toàn bộ điều khiển của bạn để thêm loại kiểm soát tốt hơn vai trò người dùng và quyền. –

6

tôi sẽ đề nghị sử dụng một sự kết hợp của hai triển khai đề xuất cuối cùng. Họ tuân thủ RESTful đại diện, họ đặt ủy quyền ở cấp độ thích hợp (bộ điều khiển), và nó là một thực hiện khả năng mở rộng.

REST về cơ bản là khoảng accessing nouns with verbs. Vì vậy, bạn muốn Đại lý và Khách hàng thực hiện các hành động (động từ) liên quan đến Vé, Người dùng và Sự kiện (danh từ). Để đại diện chính xác những danh từ này, bạn nên có một bộ điều khiển cho mỗi danh từ. Sau đó, khách hàng có thể xác định tài nguyên họ đang tìm kiếm theo URL, http://example.com/events/22.Từ đây bạn có thể sử dụng định tuyến Rails' để đại diện cho bối cảnh cho các nguồn lực khác nhau, tức là http://example.com/events/22/tickets bằng cách làm một cái gì đó như:

resource :events do 
    resource :tickets 
end 

Bằng cách tôn trọng một kiến ​​trúc RESTful, bạn đang mua vào end to end principle. Mô hình đại diện cho các đối tượng cần phải chịu trách nhiệm cho điều đó. Nó không nên cố gắng xác thực. Đó không phải là công việc của nó. Việc ủy ​​quyền sẽ xảy ra trong các bộ điều khiển. Tôi rất khuyên bạn nên xem xét các loại đá quý như CanCan hoặc Declarative Authorization để thiết lập tất cả điều này cho bạn.

Cuối cùng, mô hình này có thể mở rộng. Bằng cách giữ ủy quyền tách biệt với việc thể hiện tài nguyên của bạn, bạn chỉ phải sử dụng nó nếu bạn cần. Điều này giúp ứng dụng của bạn nhẹ nhàng, linh hoạt và đơn giản.

0

Trong khi cả hai thỏa thuận với việc tạo Vé, việc bán vé Đại lý/Vé so với giao dịch mua/Khách hàng có vẻ đủ khác với tôi rằng họ nên tách biệt nhau. Cuối cùng, họ có thể phân kỳ hơn nữa vì chúng đang được sử dụng rất khác nhau từ đầu.

Có thể đã chia sẻ chức năng điều khiển hoặc với các module hoặc bằng cách kế thừa từ một bộ điều khiển cha mẹ chung:

module TicketsControllersCommom 
    # common helper methods 
end 

class TicketsController < ApplicationController 
    include TicketsControllersCommom 
    # actions 
end 

class AgentTicketsController < ApplicationController 
    include TicketsControllersCommom 
    # actions 
end 

tôi có thể đối xử với những phần đại lý như một loại phần admin, với các bộ phận khách hàng là mặc định:

/events/xx/tickets # collection 
/events/xx/tickets/xx # member 
# etc. 
/events/xx/agent/tickets # collection 
/events/xx/agent/tickets/xx # member 
# etc. 

Hoặc, nếu bạn có rất nhiều admin-loại công cụ, như thế nào nếu các đại lý quản lý các sự kiện là tốt, bạn có thể không gian tên toàn bộ một phần:

/agent/events/xx/tickets 
/agent/events/xx/edit 
# etc. 
Các vấn đề liên quan