如何在RoR中调用方法并发送新参数?

假设我有方法A.

def methodA note = Note.find(params[:id]) note.link = params[:link] note.linktype = params[:linktype] note.save redirect_to(notes_url) end 

当我从这样的视图调用此方法时,它工作正常

 0), methodA_path(:linktype => w.linktype, :link => w.link, :id => @note.id) %> 

但是,如果我从同一控制器中的另一个方法调用该方法,如下所示:

 def methodB ... methodA(:id => params[:id], :link => link, :linktype => "image") end 

我收到此错误:

 wrong number of arguments (1 for 0) 

methodA获取的参数仍然与methodB获得的参数相同,而不是我从methodB发送的参数。 我该如何解决这个问题? 感谢阅读。

几件事:

  • Ruby和Ruby on Rails的命名约定是使用下划线表示法而不是camelcase。 所以它应该是method_a而不是method_a
  • 看起来methodA是一个控制器动作。 如果查看方法签名,则实际上并未定义任何方法参数。 这是一件好事:行动不会采取任何行动。
  • 方法中的params调用操作不是访问方法参数,而是访问Rails请求params hash。
  • 在您看来,您实际上并没有调用该方法。 相反,您将链接到该操作,该操作在单击时会启动路由到该操作的请求。 您调用的实际方法是methodA_path ,它生成URL。 这是url_for的快捷方式,可以自动为您填写一些参数(其他参数位于您传递的哈希值中)。 您的路线会自动为您生成此方法。 从应用程序的根目录执行rake routes以获取更多信息。
  • 如果你想从methodB调用action方法,这可能是不明智的,你不需要传递参数。 因为methodB也是一个在它自己的请求周期中被调用的动作,所以params哈希仍然可用于methodA ,它会发现所有这些事情都很好。 但是,我建议将任何常用function提取到第三个辅助方法中并从每个操作中调用它; 从其他动作调用动作对我来说感觉就像代码味道。

总结一下: methodA_pathmethodA_path不同的方法。 前者不使用参数但访问Rails请求参数哈希,而后者则将参数传递给url_for

这一切都非常基础,所以我强烈建议你阅读Rails的敏捷Web开发 (Rails 2第3版,Rails 3第4版)。

method_a_pathmethod_a调用不一样。

  • method_a不接受参数。 它在动作调用期间访问从params哈希集到控制器实例的参数。

  • method_a_path不调用method_a ,它只生成用于调用方法的URL。 当用户单击链接并且rails服务器处理请求时,会发生实际调用。

如果要在不同的上下文中重用该方法,请将操作的代码提取到新方法,如下所示:

 class PostsController < ApplicationController def add_media add_media_with_para(params) end def action2 add_media_with_para(:id => params[:id], :link => link, :linktype => "image") end private def add_media_with_para p = {} note = Note.find(p[:id]) note.link = p[:link] note.linktype = p[:linktype] note.save redirect_to(notes_url) end end 

现在在您的视图中,您可以获取add_media操作的路径,如下所示:

 posts_add_media_path(:linktype => w.linktype, :link => w.link, :id => @note.id) 

我假设addMedia你的意思是methodA

注意,方法methodA_pathmethodA_path methodA 。 第一个是自动生成的,因为您有一个名为methodA的路由,并返回访问该路由所需的url。 因此,它返回字符串。 而methodA通常呈现html模板。

如果要将渲染委托给另一个动作,可以执行redirect_to :action => :methodA, :id => 1, :otherParam => 2redirect_to :action => :methodA, :id => 1, :otherParam => 2