Как пропустить объект в массиве сериализаторов ActiveModel?

Я просмотрел всю документацию по сериализатору активной модели (v 0.9.0) и вопросы SO, которые я могу найти, но не могу понять это.

У меня есть объекты, которые можно пометить как «опубликованные» или «черновики». Когда они не опубликованы, их должен видеть только пользователь, создавший объект. Я, очевидно, могу установить разрешения для «показать» в моем контроллере, но я также хочу удалить эти объекты из json, которое возвращает мое действие «индекс», если это не правильный пользователь. Есть ли способ полностью удалить этот объект из json, возвращаемого сериализатором?

В моем сериализаторе ActiveModel я могу использовать пользовательский фильтр (ключи) и перегруженные атрибуты для удаления данных, как показано с использованием моего кода ниже, но я не могу просто удалить весь объект (мне остается вернуть пустой { } в моем json попытка вернуть nil ломает сериализатор).

Я, наверное, упускаю что-то простое. Любая помощь приветствуется!

class CompleteExampleSerializer < ExampleSerializer

  attributes :id, :title
  has_many :children

  def attributes
     data = super
     (object.published? || object.user == scope || scope.admin?) ? data : {}
  end 

  def filter(keys)
    keys = super
    (object.published? || object.user == scope || scope.admin?) ? keys : {}
  end
end

person scottier    schedule 18.11.2014    source источник
comment
Вы когда-нибудь догадывались об этом? У меня точно такая же проблема! Я думаю, что решение может заключаться в том, чтобы пропустить его в сериализаторе массива. Хотя еще слишком рано, чтобы пачкать руки, я дам еще час, чтобы набраться смелости.   -  person CleoR    schedule 24.11.2014
comment
IDT будет работать, если эта ассоциация включена в другой сериализованный объект. Вам нужно будет указать ему использовать ваш специальный сериализатор в каждом другом сериализаторе. Было бы намного проще, если бы вы могли указать сериализатор массива из сериализатора объекта.   -  person CleoR    schedule 24.11.2014
comment
Не могу заставить фильтр работать. Я могу просто разделить главы на опубликованные и неопубликованные и создать метод для каждой модели. Таким образом, я могу использовать подход «все или ничего» в сериализаторе. Дайте мне знать, если вы нашли лучший подход.   -  person CleoR    schedule 24.11.2014


Ответы (2)


Это выглядит правильно, попробуйте вернуть массив вместо хэша, если вам не нужны никакие ключи. Кроме того, я не думаю, что вызов super необходим, потому что фильтр принимает ключи.

Кроме того, я не думаю, что определение метода атрибутов необходимо.

person Sam    schedule 19.11.2014

У меня есть главы, которые можно либо опубликовать, либо не публиковать. Они принадлежат истории, поэтому я закончил делать что-то вроде ниже.

has_many :unpublished_chapters, -> { where published: false }, :class_name => "Chapter", dependent: :destroy
has_many :published_chapters, -> { where published: true }, :class_name => "Chapter", dependent: :destroy

Внутри моего сериализатора я решил включить unpublished_chapters только в том случае, если current_user является владельцем этих глав. В ams 0.8.0 синтаксис такой.

def include_associations!
  include! :published_chapters if ::Authorization::Story.include_published_chapters?(current_user,object,@options)
  include! :unpublished_chapters if ::Authorization::Story.include_unpublished_chapters?(current_user,object,@options)
end

В моем случае не так уж плохо различать их, и это избавляет меня от необходимости иметь дело с этим на клиенте. У нас похожие ситуации, но скажем, вы хотите получить все главы, посетив индексный маршрут глав. В моем приложении это не имеет особого смысла, но вы можете перейти к этому контроллеру и выполнить запрос к этой таблице.

person CleoR    schedule 24.11.2014