Как избежать пропуска сопоставления для двухуровневых глубоких ассоциаций?

У меня есть 3 модели в цепочке hasMany. НАПРИМЕР. Галерея -> Изображение -> Комментарий

Возврат как выбранной галереи, так и изображений в ней в одном ответе json работает, как и ожидалось. Бэкэнд — это приложение Rails, использующее active_model_serializers, кстати.

{"images":[...],"galleries":{"id":1,...,"images":[1,2,3]}}

Но когда я сообщаю сериализатору о комментариях, и они включаются в json, я получаю ошибку отображения от Ember.

{"comments":[...],"images":[...],"galleries":{"id":1,...,"images":[1,2,3]}}

Ошибка: утверждение не удалось: ваш сервер вернул хэш с ключевыми комментариями, но у вас нет для него сопоставления

Я не могу понять, как правильно сказать Эмберу, как с этим справиться. Моя отладка предполагает, что все в ответе json должно быть напрямую указано в модели галереи. Я попытался добавить «сопоставление» в RESTAdapter, используя как формы единственного, так и множественного числа, чтобы быть уверенным. Я не вижу разницы «комментарии: App.Comment» или «комментарий: App.Comment».

Я полагаю, что мог бы сдаться и просто сделать еще несколько запросов, но, поскольку комментарии всегда используются, когда используется данное изображение, это кажется неправильным. Мне бы хотелось, чтобы вам помогли понять, как разрешить данные в одном ответе.

Нужно ли мне полностью перенастраивать сериализаторы и Ember для встраивания данных вместо того, чтобы ссылаться на них с помощью идентификаторов?

Черс, Мартин

(Примечание. Названия моделей вымышлены, чтобы сделать их более понятными по сравнению с забавной областью, которую я моделирую на самом деле)


person Martin Westin    schedule 23.10.2012    source источник
comment
В моем приложении я делаю что-то вроде Store = DS.Store.extend({ adapter: DS.RESTAdapter.create({serializer: DS.RESTSerializer, bulkCommit: false, mappings: {action_words: ActionWord } }) }) и это работает :с   -  person sly7_7    schedule 23.10.2012
comment
Что я сделал до сих пор, так это изменил json, чтобы сделать комментарии, встроенные в изображения. Это сдерживает сетевую болтовню, но менее нормализовано, чем мне хотелось бы.   -  person Martin Westin    schedule 25.10.2012
comment
вы нашли решение своей проблемы? У меня та же проблема, Ember очень строго относится к ожидаемому формату json, и я не могу так легко изменить свой сервер (Symfony)...   -  person George Katsanos    schedule 16.02.2013


Ответы (1)


Спасибо, что побудили меня вернуться к этому.

Вот что у меня есть на данный момент. Я не знаю, смогу ли я удалить что-либо из этого после последних обновлений Ember и Ember Data.

Магазин указывает:

DS.RESTAdapter.configure("plurals", {
  image: 'images',
  gallery: 'galleries',
  comment: 'comments'
});
DS.RESTAdapter.configure('App.Image', {
  sideloadAs: 'images'
});
DS.RESTAdapter.configure('App.Comment', {
  sideloadAs: 'comments'
});
App.store = DS.Store.create({
  revision: 11,
  adapter: DS.RESTAdapter.create({
    mappings: {
      comments: 'App.Comment'
    }
  })
});

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

Мои модели содержат следующее... среди всего прочего обычного.

App.Gallery = DS.Model.extend({
  images: DS.hasMany('App.Image',{key: 'images', embbeded: true})
});

App.Image = DS.Model.extend({
  comments: DS.hasMany('App.Comment',{key: 'comments', embedded: true}),
  gallery: DS.belongsTo('App.Gallery')
});

App.Comment = DS.Model.extend({
  image: DS.belongsTo('App.Image')
});

Это позволяет мне вернуть структуру json, подобную той, что была в моем вопросе:

{"comments":[...],"images":[...],"galleries":{"id":1,...,"images":[1,2,3]}}

Это создается из Rails с использованием ActiveModelSerializers. Мои сериализаторы выглядят так:

class ApplicationSerializer < ActiveModel::Serializer
  embed :ids, :include => true
end
class GallerySerializer < ApplicationSerializer
  attributes :id, ...
  root "gallery"
  has_many :images, key: :images, root: :images
end
class ImageSerializer < ApplicationSerializer
  attributes  :id, ...
  root "image"
  has_many :comments, key: :comments, root: :comments
end
class CommentSerializer < ApplicationSerializer
  attributes  :id, ...
end

Опять таки. Я думаю, что вы можете уйти от того, чтобы быть намного менее многословным. Мои модели рельсов не просто называются "Галерея". Их имена разделены чем-то вроде «BlogGallery», но я не хотел, чтобы Эмберу приходилось иметь дело со всем этим. По этой причине мне нужны key и root вещи.

Я думаю, что это охватывает все, что у меня есть в отношении ассоциаций и их встраивания в один и тот же ответ json.

person Martin Westin    schedule 18.02.2013