我在控制器中的帮助方法

我的应用程序应呈现html,以便在用户单击ajax-link时进行回答。

我的控制器:

def create_user @user = User.new(params) if @user.save status = 'success' link = link_to_profile(@user) #it's my custom helper in Application_Helper.rb else status = 'error' link = nil end render :json => {:status => status, :link => link} end 

我的帮手:

  def link_to_profile(user) link = link_to(user.login, {:controller => "users", :action => "profile", :id => user.login}, :class => "profile-link") return(image_tag("/images/users/profile.png") + " " + link) end 

我试过这样的方法:

 ApplicationController.helpers.link_to_profile(@user) # It raises: NoMethodError (undefined method `url_for' for nil:NilClass) 

和:

 class Helper include Singleton include ActionView::Helpers::TextHelper include ActionView::Helpers::UrlHelper include ApplicationHelper end def help Helper.instance end help.link_to_profile(@user) # It also raises: NoMethodError (undefined method `url_for' for nil:NilClass) 

另外,是的,我知道:helper_method,它的工作原理,但我不想用大量的方法重载我的ApplicationController

冲。 让我们回顾一下。 您想要访问某些function/方法,但您不希望将这些方法附加到当前对象。

因此,您希望创建一个代理对象,代理/委托这些方法。

 class Helper class << self #include Singleton - no need to do this, class objects are singletons include ApplicationHelper include ActionView::Helpers::TextHelper include ActionView::Helpers::UrlHelper include ApplicationHelper end end 

而且,在控制器中:

 class UserController < ApplicationController def your_method Helper.link_to_profile end end 

这种方法的主要缺点是从辅助函数你将无法访问控制器上下文(EG你将无法访问参数,会话等)

折衷方案是在辅助模块中将这些函数声明为私有,因此,当您包含模块时,它们在控制器类中也将是私有的。

 module ApplicationHelper private def link_to_profile end end class UserController < ApplicationController include ApplicationHelper end 

正如达米恩指出的那样。

更新 :您收到'url_for'错误的原因是您无法访问控制器的上下文,如上所述。 您可以强制将控制器作为参数(Java样式;))传递,如:

 Helper.link_to_profile(user, :controller => self) 

然后,在你的帮手中:

 def link_to_profile(user, options) options[:controller].url_for(...) end 

或者事件是一个更大的黑客,在这里提出。 但是,我会建议将方法设为私有并将其包含在控制器中的解决方案。

帮助程序只是ruby模块,您可以像任何模块一样包含在任何控制器中。

 module UserHelper def link_to_profile(user) link = link_to(user.login, {:controller => "users", :action => "profile", :id => user.login}, :class => "profile-link") return(image_tag("/images/users/profile.png") + " " + link) end end 

并且,在您的控制器中:

 class UserController < ApplicationController include UserHelper def create redirect_to link_to_profile(User.first) end end 

拿着它! http://apotomo.de/2010/04/activehelper-rails-is-no-pain-in-the-ass/

这正是你要找的,伙计。