Rails рендеринг частичного JSON в модели - PullRequest
2 голосов
/ 10 февраля 2012

В нашем приложении rails 3.2 мы используем Jbuilder для рендеринга наших ответов json (здесь ничего особенного).Представление json может быть таким простым:

_model_name.json.jbuilder

json.extract!(page, :id, :name, :url_name)

Нам часто нужно возвращать глубоко вложенный объект json, и для этого прекрасно работают партиалы Jbuilder:

_page.json.jbuilder

json.extract!(page, :id, :name, :url_name)
json.page_images (page_images) do |json, page_image|
    json.partial! page_image
end

В последнем примере будут извлечены страница и вложенные page_images, представление json ... опять ничего особенного.

Часто одинpart будет вызывать другой и может возвращать вложенный объект json глубиной 2 или 3 уровня.

ПРОБЛЕМА

Как я уже говорил выше, мы используем партиалы Jbuilder для быстрой связи несколькихЧастицы вместе, чтобы сформировать глубоко вложенный объект JSON для представления.Нам также необходимо собрать эти точно такие же вложенные объекты как хэш (а не json) и сделать их доступными для модели.

Получить объект Jbuilder для вывода хеша с помощью .attributes просто!метода, но у нас есть некоторые серьезные трудности, связанные с предоставлением Jbuilder доступа к частичным представлениям из модели.

Если посмотреть на источник Jbuilder, то класс JbuilderTemplate должен иметь доступ к контексту контроллера, чтобы все работало.

Мы можем попробовать что-то вроде этого:

class SomeClass

  def initialize pages
    @pages = pages
    @context = ActionController::Base.new
  end

  def to_hash
     builder = JbuilderTemplate.new(@context)
     builder.pages(@pages) do |json, page|
        json.partial! page
     end
     builder.attributes!
  end
end

Приведенный выше пример, очевидно, неверен, но он иллюстрирует, что нужно сделать.Я просто не уверен, как пройти инициализацию контроллера из модели, а затем передать контекст контроллера.

Некоторые выводы, которые мы следуем:

Может кто-нибудь помочь направить нас в правильном направлении?

Ответы [ 4 ]

2 голосов
/ 22 июня 2016

Я почти уверен, что вы были на правильном пути.Вы должны быть в состоянии вызвать json.array! и построить частичное нормально, если вы передадите блок непосредственно в инициализаторе.

def to_hash
  builder = JbuilderTemplate.new(@context) do |json|
    json.array! @pages, partial: 'path/to/partial'
  end
  builder.attributes!
end
1 голос
/ 11 февраля 2012

Не удалось найти решение.Мы вернулись к использованию as_json для настройки вывода нашей модели json.

0 голосов
/ 15 января 2014

Если вам действительно нужен этот функционал, я могу показать вам некоторые шиммы:

c = ActionController::Base.new
c.instance_variable_set '@item', Item.find(5)
JSON.parse c.render_to_string('items/show')
0 голосов
/ 21 июня 2013

Я использую ActiveModel :: Serializer, чтобы сделать то же самое.Вы можете визуализировать json в модели или в любом другом месте - мы делаем это для предварительного заполнения кэша.

Синтаксис для этого изначально не был очевиден, поэтому я публикую здесь:

ItemSerializer.new(item).to_json
...