Эмбер, передавая модель для перехода ToRoute

Я использую Ember-Cli с Ember 1.11

Я пытаюсь использовать метод transitionToRoute в контроллере для перехода к маршруту и ​​подачи его динамически сгенерированного объекта в качестве модели.

Вот мой контроллер:

import Ember from 'ember';

export default Ember.Controller.extend({
  actions: {      
      launch_scanner: function(){
        console.log('launch_scanner');
        var model = {name: "Edward", phone: "123", email: "email@test.com"};
        //the final app will pull the model variable from a QR scanner

        this.transitionToRoute('addcontact', model);
     }
  }      
});

Когда я запускаю это действие, метод transitionToRoute вызывает эту ошибку:

Uncaught Error: передано больше объектов контекста, чем динамических сегментов для маршрута: addcontact

Если я опускаю параметр модели, он просто переходит на маршрут addcontact. Что я делаю неправильно?

Вот мой файл роутера:

import Ember from 'ember';
import config from './config/environment';

var Router = Ember.Router.extend({
  location: config.locationType
});

Router.map(function() {
  this.route('home', {path: '/'});
  this.resource('addcontact', {path: '/addcontact'});
});

export default Router;

3 ответа

Решение

Вы имеете дело с классической проблемой, возникающей во многих приложениях Ember, которая заключается в том, как обрабатывать "новые"/"создавать" ситуации.

Вы не можете определить маршрут, такой как

this.route('addcontact', { path: /addcontact/:thing_id }

потому что новый контакт не имеет идентификатора, и не будет, пока он не будет сохранен на сервере, после чего он больше не будет новым.

Тем не менее, в вашем приложении есть некоторый момент, в вашем случае, я полагаю, на "домашней" странице, где пользователь нажал кнопку "Новый контакт", и она может содержать полезную информацию о том, что создавать или как ее создавать, и может даже хотите создать объект прямо там, используя this.store.createRecord- как передать эту информацию или новую запись addcontacdt маршрут, который может не иметь динамического отрезка?

Некоторые идеи включают в себя:

  1. Создайте новый контакт в вашем home маршрут или что-то еще, и сохранить его в контроллере. Затем в model крюк нового маршрута, получить его с помощью this.controllerFor('home').get('newContact'),

  2. Передайте необходимые параметры для создания нового объекта, если таковые имеются, addcontact маршрут в качестве параметров запроса, используя transitionTo('newcontact', queryParameters), Затем в model крюк, создайте новый объект, используя this.store.createRecord('contact', transition.queryParameters) или что-то эквивалентное.

Если вы хотите перейти к подгруппе для несохраненной записи, у вас есть 2 варианта

Либо сохраните свою модель перед переходом на маршрут

model.save().then(function(result){
   self.transitionToRoute('route',result.id)
});

или сгенерируйте идентификатор для модели в createRecord, если вы не хотите сохранять модель (возможно, пользователь может отменить, а вы не хотите обрабатывать удаление)

Основная функция для создания идентификатора с низким потенциалом идентичных идентификаторов будет:

generateIdForRecord: function() {
    var d = new Date().getTime();
    var uuid = 'xxxxyyyxxxxxxxxyyxyxxxyyy'.replace(/[xy]/g, function(c){
        var r = (d + Math.random() * 16) % 16 | 0;
        d = Math.floor(d / 16);
        return (c === 'x' ? r : (r & 0x7 | 0x8)).toString(16);
    });
    return uuid;
}

Используя этот подход, еще не сохраненная модель имеет идентификатор для перехода, просто подумайте об обработке переходов с этого маршрута, поскольку текущий идентификатор больше не действителен после сохранения модели (модель получает реальный идентификатор с сервера в ответ).

Это нормально, потому что у вас нет динамического сегмента в вашем маршруте addContact. Вы должны изменить свой маршрутизатор на

Router.map(function() {
  this.route('home', {path: '/'});
  this.resource('addcontact', {path: '/addcontact/:id'});
});

Теперь вы можете передать идентификатор модели вместо всей модели, чтобы вызвать model крюк. В качестве альтернативы вы можете передать всю модель, но это не вызовет model крюк. Хотя вы все еще можете изменить свою модель в afterModel крюк.

Другие вопросы по тегам