Ember js - отношения Hasmany прерываются после обновления других таблиц

Я использую Ember.js с локальным адаптером-хранилищем. У меня есть странная проблема при обновлении записей.

У меня есть модель сообщений и комментариев с hasMany отношениями:

App.Post = DS.Model.extend({
    title: DS.attr('string'),
    comments: DS.hasMany('comment', {
        async: true
    })
});
App.Comment = DS.Model.extend({
    message: DS.attr('string')
});

Это мои контроллеры сообщений и комментариев:

App.PostsController = Ember.ArrayController.extend({
    newTitle: '',
    actions: {
        create: function() {
            var title = this.get('newTitle');
            var post = this.store.createRecord('post', {
                title: title
            });
            this.set('newTitle', '');
            post.save();
        }
    }
});
App.CommentsController = Ember.ArrayController.extend({
    needs: "post",
    post: Ember.computed.alias("controllers.post.model"),
    newMessage: '',
    actions: {
        create: function() {
            var message = this.get('newMessage');
            var comment = this.store.createRecord('comment', {
                message: message
            });
            var post = this.get('post');
            var comments = post.get('comments');
            if (comments.get('content') == null) comments.set('content', []);
            comments.pushObject(comment);
            comment.save();
            post.save();
        }
    }
});

При создании записей hasMany отношения обновляются правильно.

{
    "App.Post": {
        "records": {
            "0v66j": {
                "id": "0v66j",
                "title": "post1",
                "comments": ["p31al", "tgjtj"]
            }
        }
    },
    "App.Comment": {
        "records": {
            "p31al": {
                "id": "p31al",
                "message": "comment 1"
            },
            "tgjtj": {
                "id": "tgjtj",
                "message": "comment 2"
            }
        }
    }
}

Проблема возникла при редактировании сообщения. Отношения после редактирования пост-записи исчезли. Я сделал поиск и нашел этот код:

DS.JSONSerializer.reopen({
    serializeHasMany: function(record, json, relationship) {
        var key = relationship.key;
        var relationshipType = DS.RelationshipChange.determineRelationshipType(record.constructor, relationship);
        //  alert(relationshipType);
        if (relationshipType === 'manyToNone' || relationshipType === 'manyToMany' || relationshipType === 'manyToOne') {
            json[key] = Ember.get(record, key).mapBy('id');
            // TODO support for polymorphic manyToNone and manyToMany
            // relationships
        }
    }
});

Это трюк, и все получилось отлично. Но теперь у меня другая проблема. Если я отредактирую любую другую запись, все ссылки на идентификаторы заменяются целым объектом следующим образом:

{"App.Post":{"records":{"0v66j":{"id":"0v66j","title":"post2","comments":[**{"message":"comment 1"},
{"message":"comment 2"}**]},"8nihs":{"id":"8nihs","title":"post3","comments":["b4v2b","dbki4"]}}},
"App.Comment":{"records":{"p31al":{"id":"p31al","message":"comment 1"},"tgjtj":{"id":"tgjtj","message":"comment 2"},
"b4v2b":{"id":"b4v2b","message":"comments3"},"dbki4":{"id":"dbki4",
"message":"comments4"}}}}

Комментарии refrences должны быть comments ": [" p31al "," tgjtj "], как это, но идентификаторы заменяются как" комментарии ": [ {" сообщение ":" комментарий 1 "}, {" message ":" comment 2 "}]

Ответ 1

При использовании ApplicationSerializer, который расширяет LSSerializer, он работает.

Может быть, он исправлен с тех пор, как спросил?

Ответ 2

Я заметил несколько вещей на своем пути с Ember... и особенно Ember-Data.

Один из них - это когда вы имеете дело с ассоциациями, которые мне приходилось вручную добавлять в ассоциации, сохраняя и перезаписывая, и использовать addObject для ассоциаций в памяти, поскольку вы используете здесь немного.:)

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

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

  if(comments.get('content') == null)
    comments.set('content', []);

В любом случае, следующий код - это то, как я, вероятно, напишу ваше действие для создания. Это может помочь. Надеюсь, это так.

create: function() {
  // get the post for association on the new comment
  var post = this.get('post');

  // get the message to store on the new comment
  var message = this.get('newMessage');

  var comment = this.store.createRecord('comment', {
    message : message,
    post : post
  });

  comment.save().then(function(savedComment) {
    post.get('comments').addObject(savedComment);
  });
}

Обратите внимание, что это намного проще. Как правило, если вы делаете сложные сложные вещи, что-то не так, и пришло время вернуться к основам и добавить одну вещь одновременно, тщательно тестируя между добавлениями.:)

Удачи!