Rails response_with:它是如何工作的? [英] Rails respond_with: how does it work?

查看:82
本文介绍了Rails response_with:它是如何工作的?的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

我一直在阅读有关 Rails 3 中 respond_with 方法有多酷的文章.但我什至无法在 Rails API 中或通过搜索源找到对它的引用.任何人都可以向我解释它是如何工作的(您可以使用哪些选项等)或将我指向它实际实现的地方,以便我可以自己仔细阅读代码?

I've been reading here and there about how cool the respond_with method is in Rails 3. But I can't even find a reference to it in either the Rails APIs or by searching the source. Can anyone either explain to me how it works (what options you can use, etc) or point me to the place it's actually implemented so I can peruse the code on my own?

推荐答案

Rails 4.2+ 更新

#respond_with::respond_to(n.b. 类方法)不再是 Rails 的一部分.从 Rails 4.2 开始,它们被迁移到第三方 responders gem (发行说明/commit 日期为 2014 年 8 月).虽然默认情况下响应器不包含在 Rails 中,但它是 Devise 的依赖项,因此在许多 Rails 应用程序中可用.

Update for Rails 4.2+

#respond_with and ::respond_to (n.b. class method) are no longer a part of Rails. They were migrated into the third-party responders gem as of Rails 4.2 (release notes / commit dated Aug 2014). While responders is not included in Rails by default, it is a dependency of Devise, and thus available in many Rails applications.

#respond_to 实例方法仍然是 Rails 的一部分(撰写本文时为 5.2rc1).

The #respond_to instance method, however, is still a part of Rails (5.2rc1 as of this writing).

ActionController::MimeResponds<的官方 Rails API 文档/a> 解释了 #respond_to 的工作原理.#respond_with::respond_to 的原始 Rails 指南文档注释仍然可以在 响应者 gem 源代码.

The official Rails API documentation for ActionController::MimeResponds explains how #respond_to works. The original Rails Guides documentation comments for #respond_with and ::respond_to can still be found in the responders gem source code.

响应者的代码基于一个类和一个模块.MimeResponds 包含在ActionController::Base,ApplicationController 继承的类.然后是 ActionController::Responder 提供了使用 response_with 时的默认行为.

The code for the responders is based in a class and a module. MimeResponds which is included into ActionController::Base, the class your ApplicationController inherits from. Then there is ActionController::Responder which provides the default behavior when using respond_with.

默认情况下,rails 在响应中提供的唯一行为是隐式尝试呈现名称与操作匹配的模板.除此之外的任何操作都需要在操作中使用更多指令,或者使用块的自定义响应调用调用来处理多种格式的响应.

By default, the only behavior rails provides in the response is an implicit attempt to render a template with a name matching the action. Anything beyond that requires more instructions within the action, or a custom respond_to call with a block to handle multiple format responses.

由于大多数控制器使用相当常见的自定义模式,响应者通过引入更多默认行为来提供额外的抽象级别.读取为特定格式调用 to_xml/to_json 的操作,以及为成功的 mutator 操作提供相同和重定向的 mutator 操作.

As most controllers use a fairly common pattern of customization, responders provide an extra level of abstraction by introducing more default behavior. Read actions calling to_xml/to_json for specific formats, and mutator actions providing the same as well as redirects for successful mutator actions.

有一些机会可以自定义响应者的行为方式,从细微的调整到完全覆盖或扩展行为.

There are a few opportunities to customize how responders behave, from subtle tweaks to completly overriding or extending the behavior.

在此指定响应程序应处理的格式.可以自定义格式以了解它们将应用于哪些操作.可以使用单独的调用指定每种格式,从而可以完全自定义每种格式的操作.

Here you specify the formats that the Responder should handle. The formats can be customized as to which actions they will apply to. Each format can be specified with separate calls, allowing complete customization of the actions for each format.

# Responds to html and json on all actions
respond_to :html, :json

# Responds to html and json on index and show actions only.
respond_to :html, :json, :only => [:index,:show]

# Responds to html for everything except show, and json only for index, create and update
respond_to :html, :except => [:show]
respond_to :json, :only => [:index, :create, :update]

班级:responder

这是一个包含响应者的类属性.这可以是响应调用的任何东西,这意味着您可以使用 proc/lambda 或响应调用的类.另一种选择是将一个或多个模块混合到现有响应器中,以重载现有方法,增强默认行为.

Class Level: responder

This is a class attribute that holds the responder. This can be anything that responds to call, which means you can use a proc/lambda or a class that responds to call. Another alternative is to mixin one or modules to the existing responder to overload existing methods, augmenting the default behavior.

class SomeController < ApplicationController
  respond_to :json

  self.responder = proc do |controller, resources, options|
    resource = resources.last
    request = controller.request
    if request.get?
      controller.render json: resource
    elsif request.post? or request.put?
      if resource.errors.any?
        render json: {:status => 'failed', :errors => resource.errors}
      else
        render json: {:status => 'created', :object => resource}
      end
    end
  end
end

虽然可能有一些有趣的边缘用例,但将模块扩展或混合到默认响应器中更有可能是更常见的模式.在任何情况下,相关的选项是资源和选项,因为它们是从 response_with 传递过来的.

While there may be some interesting edge use cases, it's more likely that extending or mixing modules into the default responder would be more common patterns. In any case, the options that are relevant are the resources and options, as they are passed through from the from respond_with.

此处的选项是将传递给控制器​​中的 render 或 redirect_to 的选项,但它们仅包含在成功场景中.对于 GET 操作,这些将是渲染调用,对于其他操作,这将是重定向的选项.其中最有用的可能是 :location 选项,它可用于覆盖该重定向路径,以防 respond_with 的参数不足以构建正确的 URL.

The options here are those that would be passed to render or redirect_to in your controller, but they are only included for success scenarios. For GET actions these would be the render calls, for other actions this would be the options for redirect. Probably the most useful of these is the :location option, which can be used to override that redirect path in case the arguments for respond_with are not sufficient to build the right URL.

# These two are essentially equal
respond_with(:admin, @user, @post)
respond_with(@post, :location => admin_user_post(@user, @post)

# Respond with a 201 instead of a 200 HTTP status code, and also
# redirect to the collection path instead of the resource path
respond_with(@post, :status => :created, :location => posts_path)

# Note that if you want to pass a URL with a query string
# then the location option would be needed.
# /users?scope=active
respond_with(@user, :location => users_path(:scope => 'active'))

<小时>

作为替代方案,responders gem 不仅提供了一些模块来覆盖一些默认行为.它使用扩展默认响应器的匿名类覆盖默认响应器,并提供类级方法用于将自定义模块混合到此类中.这里最有用的是 flash 响应器,它提供一组默认的 flash,将自定义委托给 I18n 系统,默认情况下 config/locales/en.yml.


As an alternative, the responders gem not only provides some modules for overriding some of the default behavior. It overrides the default responder with an anonymous class that extends the default responder, and provides a class level method for mixing in custom modules to this class. The most useful here is the flash responder, which provides a default set of flashes, delegating customization to the I18n system, config/locales/en.yml by default.

我在之前的项目中使用过的一些自定义响应程序示例包括一个自动装饰我的资源的响应程序,并提供一组默认的页面标题和一个界面,用于轻松自定义或覆盖页面标题.

Some examples of custom responders I've used in previous projects include a responder that automatically decorated my resources, and provided a default set of page titles with an interface for easily customizing or overriding the page title.

这篇关于Rails response_with:它是如何工作的?的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆