我怎样才能将字符串呈现为JBuilder视图的JSON表示?
我正在使用JBuilder来返回一些JSON。 我有一个index.json.jbuilder
来生成数据,我需要将它渲染为一个字符串。 但是,我不知道如何做到这一点,因为: @my_object.to_json
和@my_object.as_json
似乎没有通过JBuilder。
我怎么能将JBuilder视图呈现为字符串?
我在控制器中将一组用户呈现为json字符串,如下所示:
#controllers/users_controller.rb def index @users = User.all @users_json = render_to_string( template: 'users.json.jbuilder', locals: { users: @users}) end #views/users/users.json.jbuilder json.array!(users) do |json, user| json.(user, :id, :name) end
如果视图users.json.jbuilder
位于相对于控制器的默认路径并且找不到模板,则可能是由于format
不一致,因为它可能正在尝试查找html
格式文件。 有两种方法可以解决这个问题:
-
让客户端获取
/users/index.json
要么
-
调用
render_to_string
时指定formats
选项(也适用于render
):
#controllers/users_controller.rb def index @users = User.all @users_json = render_to_string( formats: 'json' ) # Yes formats is plural end
这已在Rails 4.1中得到validation。
你也可以这样做,这让你的控制器更清洁。
# controller def new @data = Data.all end # view <% content_for :head do %> <% end %> # path/to/_partial.html.jbuilder json.array!(@data) do |d| json.extract! field1, :field2, :field3, :field4 json.url data_url(d, format: :json) end # layouts/application.html <%= yield :head %> ...
如果您在控制器中执行此操作,则更简单的选择是尝试将代码移动到控制器呈现的视图中。
我在这里描述了这个: https : //github.com/shakacode/react-webpack-rails-tutorial#jbuilder-notes
基本上你可以在视图中调用render
,然后你就完成了。 像这样:
<%= react_component('App', render(template: "/comments/index.json.jbuilder"), generator_function: true, prerender: true) %>
以下是如果要将数据从控制器传递到视图时会发生什么的注释:
class PagesController < ApplicationController def index @comments = Comment.all # NOTE: The below notes apply if you want to set the value of the props in the controller, as # compared to he view. However, it's more convenient to use Jbuilder from the view. See # app/views/pages/index.html.erb:20 # # <%= react_component('App', render(template: "/comments/index.json.jbuilder"), # generator_function: true, prerender: true) %> # # # NOTE: this could be an alternate syntax if you wanted to pass comments as a variable to a partial # @comments_json_sting = render_to_string(partial: "/comments/comments.json.jbuilder", # locals: { comments: Comment.all }, format: :json) # NOTE: @comments is used by the render_to_string call # @comments_json_string = render_to_string("/comments/index.json.jbuilder") # NOTE: It's CRITICAL to call respond_to after calling render_to_string, or else Rails will # not render the HTML version of the index page properly. (not a problem if you do this in the view) # respond_to do |format| # format.html # end end end
查看源代码,看起来你可以这样做:
json_string = Jbuilder.encode do |json| json.partial! 'path/to/index', @my_object end
从控制台:
view = ApplicationController.view_context_class.new("#{Rails.root}/app/views") JbuilderTemplate.encode(view){|json| json.partial!('path/to/index', @my_object) }
通过https://github.com/rails/jbuilder/issues/84#issuecomment-38109709
在控制器中你可以这样做
def index json = JbuilderTemplate.new(view_context) do |json| json.partial! 'index' end.attributes! do_something(json) render json: json end
请注意,您需要“_index.json.jbuilder”,因为它调用了部分渲染器
按照justingordon的提示。
如果您使用的是React组件,则可以执行以下操作。
在你的控制器中:
@users = User.all
在你看来:
<%= react_component("YourComponentName", props: render('your_template.json.jbuilder')) %>
这是在Rails 5.1上测试的。