2011-03-25 8 views
5

मैं निम्नलिखित मार्गों:रेल मार्ग कार्रवाई है कि कई मार्गों पर उपलब्ध है संभाल करने के लिए

resources :users do 
    # List reviews made by user 
    resources :reviews, :only => [ :index ] 
end 

resources :products do 
    # List reviews by product, and provide :product_id for creation 
    resources :reviews, :only => [ :index, :new, :create ] 
end 

# Other actions don't depend on other resources 
resources :reviews, :except => [ :index, :new, :create ] 

सब कुछ सही लग रहा है, ReviewsController#index को छोड़कर:

def index 
    if params[:user_id] 
    @reviews = Review.find_all_by_user_id params[:user_id] 
    else 
    @reviews = Review.find_all_by_product_id params[:product_id] 
    end 
    respond_with @reviews 
end 

हो, तो एक मानक समाधान मैं सोच रहा था ऊपर की समस्या, या अगर ऐसा करने का एक बेहतर तरीका है।

उत्तर

6

आप क्या वहाँ ठीक है, लेकिन क्या आप के साथ-साथ दो अलग-अलग कार्यों के लिए उपयोग कर सकते चाहते हैं। इस दृष्टिकोण से आप बाद में दृश्य को आसानी से बदल सकते हैं, और थोड़ा सुरक्षित है।

match '/products/:product_id/reviews' => 'reviews#product_index' 
match '/users/:user_id/reviews' => 'reviews#user_index' 

यह भी अपने नियंत्रक कोड एक छोटे से क्लीनर कम /products/10/reviews?user_id=100 की तरह अजीब क्वेरी जिनमें उपयोगकर्ता की समीक्षा परिणाम होगा करने के लिए अतिसंवेदनशील रखेंगे और के बजाय उत्पाद की समीक्षा दिखाया जा रहा है। , मुझे यकीन है कि वहाँ दूसरों रहे हैं हूँ

match '/products/:product_id/reviews' => 'product_reviews#index' 
match '/users/:user_id/reviews' => 'user_reviews#index' 
+1

बहुत अच्छा सुझाव। मुझे लगता है कि मुझे अपनी 'स्टिक को रीस्टफुल एक्शन' मानसिकता से छुटकारा पाना चाहिए। :) –

+1

कभी-कभी यह काम करता है, दूसरी बार यह रास्ते में आता है। यदि आप पूरी तरह से आराम से कार्य करने के लिए चिपकना चाहते हैं, तो आप कंट्रोलर को उनसे संभालने की तुलना में ओवरराइट कर सकते हैं, ताकि आपके पास एक आरामदायक उत्पाद समीक्षा नियंत्रक और एक आरामदायक उपयोगकर्ता समीक्षा नियंत्रक हो। निस्संदेह आप पहले से ही बहुत सारे उपयोग कर रहे हैं और केवल कथन ही स्पष्ट यूआरएल मैचों का उपयोग करके, उदाहरण के लिए, आपके लिए सबसे अच्छा समाधान हो सकता है। –

+1

मैंने सुना है कि कुछ आराम में भी लपेट गए हैं, और मैं मानता हूं कि कभी-कभी आपको तोड़ने की ज़रूरत होती है, लेकिन यह ऐसा समय नहीं दिखता है। असल में, दो नियंत्रकों को बनाकर, आप दो संसाधनों (केवल सूचकांक कार्रवाई) की बाकी शैली में तोड़ रहे हैं। इस मामले में, मैं इसे एक नियंत्रक में रखूंगा और पैराम के लिए उपयुक्त लोड करूंगा। – DGM

0
def index 
    key = [:user_id, :product_id].find{|k| params[k]} 
    @reviews = Review.where(key => params[key]).first 
    respond_with @reviews 
end 
+0

क्यों '.first' है कि आप सिर्फ एक समीक्षा दे देंगे यह पॉलीमोर्फिक एसोसिएशन के लिए भी संभाल नहीं करता है जो समीक्षाओं के पास होनी चाहिए। – Galen

1

कुछ प्लग ऐसे declarative_authorization या कैनकैन के रूप में आप के लिए संसाधनों को लोड करने के तरीके, है:

def product_index 
    @reviews = Review.find_all_by_product_id params[:product_id] 
    respond_with @reviews 
end 

def user_index 
    @reviews = Review.find_all_by_user_id params[:user_id] 
    respond_with @reviews 
end 

अन्य विकल्प के रूप में अच्छी तरह से विभिन्न नियंत्रकों का प्रयोग है।

अन्य समाधान मैंने देखा है कि ऑब्जेक्ट को लोड करने के लिए नियंत्रक में एक निजी विधि बनाना है, और उस विधि में अनिवार्य रूप से वही तर्क है जो आपके पास है; यह सिर्फ इसे इंडेक्स एक्शन से बाहर ले जाता है। मेटोड को तब पहले फिल्टर के रूप में भी बुलाया जा सकता है।

एक अन्य तरीका है अपने तर्क करने के लिए (मूल उद्देश्य के साथ शुरू करने के लिए है अच्छा तुम भी पैरेंट ऑब्जेक्ट की जरूरत है:।

 
before_filter :load_collection, :only => :index 

private 
def load_collection 
    if params[:user_id] 
    @user = @parent = User.find(params[:user_id]) 
    else 
    @product = @parent = Product.find(params[:product_id]) 
    end 
    @reviews = @parent.reviews 
end 
संबंधित मुद्दे