2014-07-08 76 views
3

您好我想實現訂閱按鈕供應商的網站,所以需要呈現vendor_site_id隱藏屬性的訂閱表單。表單在訂閱控制器的範圍內工作正常,但我需要將其作爲partial _new.html.erb在vendor_site/show頁面中呈現。我無法找出解決這個問題的方法,任何機構都可以向我提出這個問題。如何渲染一個控制器的部分視圖到Ruby on Rails的另一個控制器

我的部分觀點訂閱/ _new.html.erb

<%= form_for(@subscription) do |f| %> 
    <div class="field"> 
    <%= f.hidden_field @subscription.vendor_site_id, :value=>"1" %> 
    </div> 
    <%= button_tag(type: 'submit', class: "btn btn-primary") do %> 
    <i class="fa fa-user fa-fw"></i> Subscribe 
    <% end %> 
<% end %> 

現在,當我使這個在vendor_sites/index.html.erb

<h3>This is vendor site with id 1 just for the testing of subscription method</h3> 
<%= render :partial => "subscriptions/new" %> 

它拋出一個說,一個錯誤:

First argument in form cannot contain nil or be empty 

我理解到目前爲止,我需要告訴這個vendor_site控制器關於@subscription f從其他範圍。 但我無法弄清楚如何? 我的訂閱類看起來是這樣的:

class SubscriptionsController < ApplicationController 
    def new 
    @subscription=Subscription.new 
    end 
end 
+1

因爲你沒有定義在vendor_sites控制器的index action'@ subscription',所以' form_for @ subscription'爆炸。 – sevenseacat

回答

3

一些改動,你需要在這裏提出。在進入細節之前我會推薦的一件事是Rails Guides for Layouts and Rendering(和Rails Guides一般,特別是佈局和渲染指南將極大地幫助您使用Rails的VC部分。

現在,詳談。首先,局部變量不是控制器動作,沒有與之相對應的控制器方法,你可以通過兩種方式之一來處理你想要做的事情,這兩種方式都是先從訂閱控制器中刪除new方法。

第一種方式:初始化@subscription在您的供應商現場控制器

最簡單的方法(相對於您已有的更改而言)是在供應商站點控制器的index方法中初始化@subscription。然後,呈現的_new部分將確切知道subscription是什麼。

class VendorSiteController 
    def index 
    @subscription = Subscription.new # add this anywhere in the index method. 
    end 
end 

方式二:@subscription作爲本地的_new部分

這種方式將涉及到改變你的控制器,你的看法,你的部分。在你的控制器中,你仍然需要做出上面給出的改變。

class VendorSiteController 
    def index 
    @subscription = Subscription.new # add this anywhere in the index method. 
    end 
end 

接下來,你需要做@subscription一個局部變量在您的形式,通過簡單地移除@

<%= form_for(@subscription) do |f| %> 
    <div class="field"> 
    <%= f.hidden_field @subscription.vendor_site_id, :value=>"1" %> 
    </div> 
    <!-- no changes to the button tag --> 
<% end %> 

最後,你需要通過@subscriptionsubscription你的部分在你的索引視圖。

<%= render :partial => "subscriptions/new", :locals => { :subscription => @subscription } %> 

雖然這種方式涉及更多的變化,但它比第一種方式更靈活。例如,假設你要呈現多個新的訂閱在一個頁面:

<% Subscription.where(condition: true).find_each do |s| %> 
    <%= render :partial => "subscriptions/new", :locals => { :subscription => s } %> 
<% end %> 

再舉一個例子,也許你想使用@subscription變量名稱不是一個新的訂閱其它的東西,你會使用@new_sub代替新訂閱。

<%= render :partial => "subscriptions/new", :locals => { :subscription => @new_sub } %> 

希望我的回答能幫助你!如果您需要進一步澄清,請隨時發表評論,並務必查看這些Rails指南!

+0

感謝這個令人敬畏的答案,讓我清楚瞭解基礎知識和良好實踐 – surajnew55

2

您可以通過以下方式來實現,您需要在vendor_sites控制器的索引操作中初始化@subscription對象。

class VendorSiteController 
    def index 
    #here your showing list of vendors logic 

    @subscription = Subscription.new #initialize a Subscription object 
    end 
end 

那麼你可以通過下面的方式(對於Rails 3中)

<%= render :partial => "subscriptions/new", :subscription => @subscription } %> 
2

沒有檢查Joe Kennedy的回答傳遞@subscription對象在索引視圖中的部分,所以道歉,如果這倒是在他寫的是什麼:


Partials

partial的全部內容是爲了能夠在應用程序的任何部分使用。他們綁定到特定的控制器,因爲它們主要依靠local variables以豐富他們的數據

這意味着,如果你想呈現的部分之外的控制器的「範圍」,這是尤其如此,你只需要能夠通過其local變量發送正確的數據部分,:

#app/views/controllers/your_view.html.erb 
<%= render partial: "controller/partial", locals: {variable: @value} %> 

一個非常簡單的例子,但希望應該演示如何可以通話諧音任何你想要的。


MVC

你還必須考慮MVC programming pattern,如下所述:

enter image description here

這一點的重要性是Rails的使用MVC模式內置 - 在controller工作來操縱data以顯示您的意見,model是m eant收集/編譯data,視圖僅僅是爲了顯示它

這意味着partial不應「捆綁」到一個特定的控制器 - 它只是需要創建data提供的意見,並作爲這樣,你應該更專注於如何可以顯示此數據,而不是打電話給你的部分與特定controller


數據

到目前爲止總結 - 你需要可以放部分任何地方,並且通過使用MVC編程模式,使用來自您的controller的數據填充它。

現在重要的是填充@subscription價值。這可以在視圖(不推薦)完成,也可能使用的方法在不同的控制器來完成:

#app/views/subscriptions/_new.html.erb 
<%= form_for(subscription) do |f| %> 
    <div class="field"> 
    <%= f.hidden_field @subscription.vendor_site_id, :value=>"1" %> 
    </div> 
    <%= button_tag(type: 'submit', class: "btn btn-primary") do %> 
    <i class="fa fa-user fa-fw"></i> Subscribe 
    <% end %> 
<% end %> 

#app/views/controller/your_action.html.erb 
<%= render partial: "subscriptions/new", partials: {subscription: Subscription.new} %> 
+1

在您的上一個代碼塊中,'f.hidden_​​field @ subscription.vendor_site_id'應該是'f.hidden_​​field subscription.vendor_site_id'。你忘了拿出'@'。 –

相關問題