ember-source 4.3.0-alpha.1 → 4.3.0-beta.1
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/CHANGELOG.md +6 -2
- package/blueprints/component-addon/index.js +2 -3
- package/blueprints/component-class-addon/index.js +2 -3
- package/blueprints/controller/files/__root__/__path__/__name__.js +2 -2
- package/blueprints/controller/index.js +2 -4
- package/blueprints/route/files/__root__/__path__/__name__.js +3 -3
- package/blueprints/route/index.js +2 -3
- package/blueprints/service/files/__root__/__path__/__name__.js +2 -2
- package/blueprints/service/index.js +2 -4
- package/build-metadata.json +3 -3
- package/dist/dependencies/router_js.js +66 -31
- package/dist/ember-template-compiler.js +1250 -861
- package/dist/ember-template-compiler.map +1 -1
- package/dist/ember-testing.js +88 -56
- package/dist/ember-testing.map +1 -1
- package/dist/ember.debug.js +3712 -3159
- package/dist/ember.debug.map +1 -1
- package/dist/header/license.js +1 -1
- package/dist/header/loader.js +0 -1
- package/dist/packages/@ember/-internals/bootstrap/index.js +0 -2
- package/dist/packages/@ember/-internals/container/index.js +16 -11
- package/dist/packages/@ember/-internals/extension-support/lib/container_debug_adapter.js +3 -3
- package/dist/packages/@ember/-internals/extension-support/lib/data_adapter.js +52 -52
- package/dist/packages/@ember/-internals/glimmer/index.js +161 -125
- package/dist/packages/@ember/-internals/meta/lib/meta.js +67 -11
- package/dist/packages/@ember/-internals/metal/index.js +95 -121
- package/dist/packages/@ember/-internals/routing/lib/ext/controller.js +24 -12
- package/dist/packages/@ember/-internals/routing/lib/location/api.js +1 -0
- package/dist/packages/@ember/-internals/routing/lib/location/auto_location.js +3 -1
- package/dist/packages/@ember/-internals/routing/lib/services/router.js +117 -197
- package/dist/packages/@ember/-internals/routing/lib/services/routing.js +3 -1
- package/dist/packages/@ember/-internals/routing/lib/system/route-info.js +2 -2
- package/dist/packages/@ember/-internals/routing/lib/system/route.js +147 -402
- package/dist/packages/@ember/-internals/routing/lib/system/router.js +82 -40
- package/dist/packages/@ember/-internals/routing/lib/utils.js +48 -25
- package/dist/packages/@ember/-internals/runtime/lib/mixins/-proxy.js +1 -1
- package/dist/packages/@ember/-internals/runtime/lib/mixins/array.js +1 -0
- package/dist/packages/@ember/-internals/runtime/lib/mixins/comparable.js +4 -4
- package/dist/packages/@ember/-internals/runtime/lib/mixins/container_proxy.js +29 -29
- package/dist/packages/@ember/-internals/runtime/lib/mixins/promise_proxy.js +16 -16
- package/dist/packages/@ember/-internals/runtime/lib/mixins/registry_proxy.js +48 -48
- package/dist/packages/@ember/-internals/runtime/lib/mixins/target_action_support.js +8 -8
- package/dist/packages/@ember/-internals/runtime/lib/system/namespace.js +1 -2
- package/dist/packages/@ember/-internals/runtime/lib/type-of.js +1 -1
- package/dist/packages/@ember/-internals/utils/index.js +11 -9
- package/dist/packages/@ember/-internals/views/lib/mixins/view_support.js +2 -4
- package/dist/packages/@ember/-internals/views/lib/system/utils.js +2 -0
- package/dist/packages/@ember/application/lib/application.js +0 -2
- package/dist/packages/@ember/array/index.js +1 -1
- package/dist/packages/@ember/canary-features/index.js +2 -2
- package/dist/packages/@ember/controller/index.js +3 -54
- package/dist/packages/@ember/debug/index.js +1 -1
- package/dist/packages/@ember/debug/lib/deprecate.js +12 -10
- package/dist/packages/@ember/instrumentation/index.js +9 -13
- package/dist/packages/@ember/object/compat.js +16 -7
- package/dist/packages/@ember/polyfills/lib/assign.js +1 -0
- package/dist/packages/@ember/routing/router-service.js +1 -0
- package/dist/packages/@ember/runloop/index.js +9 -9
- package/dist/packages/@ember/service/index.js +6 -73
- package/dist/packages/@ember/string/index.js +1 -0
- package/dist/packages/ember/index.js +1 -2
- package/dist/packages/ember/version.js +1 -1
- package/docs/data.json +2588 -1839
- package/package.json +27 -27
- package/blueprints/component-addon/native-files/__root__/__path__/__name__.js +0 -1
- package/blueprints/component-class-addon/native-files/__root__/__path__/__name__.js +0 -1
- package/blueprints/controller/native-files/__root__/__path__/__name__.js +0 -4
- package/blueprints/edition-detector.js +0 -13
- package/blueprints/route/native-files/__root__/__path__/__name__.js +0 -11
- package/blueprints/route/native-files/__root__/__templatepath__/__templatename__.hbs +0 -2
- package/blueprints/service/native-files/__root__/__path__/__name__.js +0 -4
|
@@ -20,47 +20,6 @@ import { calculateCacheKey, deprecateTransitionMethods, normalizeControllerQuery
|
|
|
20
20
|
import generateController from './generate_controller';
|
|
21
21
|
export const ROUTE_CONNECTIONS = new WeakMap();
|
|
22
22
|
const RENDER = symbol('render');
|
|
23
|
-
export function defaultSerialize(model, params) {
|
|
24
|
-
if (params.length < 1 || !model) {
|
|
25
|
-
return;
|
|
26
|
-
}
|
|
27
|
-
|
|
28
|
-
let object = {};
|
|
29
|
-
|
|
30
|
-
if (params.length === 1) {
|
|
31
|
-
let [name] = params;
|
|
32
|
-
|
|
33
|
-
if (name in model) {
|
|
34
|
-
object[name] = get(model, name);
|
|
35
|
-
} else if (/_id$/.test(name)) {
|
|
36
|
-
object[name] = get(model, 'id');
|
|
37
|
-
} else if (isProxy(model)) {
|
|
38
|
-
object[name] = get(model, name);
|
|
39
|
-
}
|
|
40
|
-
} else {
|
|
41
|
-
object = getProperties(model, params);
|
|
42
|
-
}
|
|
43
|
-
|
|
44
|
-
return object;
|
|
45
|
-
}
|
|
46
|
-
export function hasDefaultSerialize(route) {
|
|
47
|
-
return route.serialize === defaultSerialize;
|
|
48
|
-
}
|
|
49
|
-
/**
|
|
50
|
-
@module @ember/routing
|
|
51
|
-
*/
|
|
52
|
-
|
|
53
|
-
/**
|
|
54
|
-
The `Route` class is used to define individual routes. Refer to
|
|
55
|
-
the [routing guide](https://guides.emberjs.com/release/routing/) for documentation.
|
|
56
|
-
|
|
57
|
-
@class Route
|
|
58
|
-
@extends EmberObject
|
|
59
|
-
@uses ActionHandler
|
|
60
|
-
@uses Evented
|
|
61
|
-
@since 1.0.0
|
|
62
|
-
@public
|
|
63
|
-
*/
|
|
64
23
|
|
|
65
24
|
class Route extends EmberObject.extend(ActionHandler, Evented) {
|
|
66
25
|
constructor(owner) {
|
|
@@ -77,6 +36,68 @@ class Route extends EmberObject.extend(ActionHandler, Evented) {
|
|
|
77
36
|
this._environment = owner.lookup('-environment:main');
|
|
78
37
|
}
|
|
79
38
|
}
|
|
39
|
+
/**
|
|
40
|
+
A hook you can implement to convert the route's model into parameters
|
|
41
|
+
for the URL.
|
|
42
|
+
```app/router.js
|
|
43
|
+
// ...
|
|
44
|
+
Router.map(function() {
|
|
45
|
+
this.route('post', { path: '/posts/:post_id' });
|
|
46
|
+
});
|
|
47
|
+
```
|
|
48
|
+
```app/routes/post.js
|
|
49
|
+
import Route from '@ember/routing/route';
|
|
50
|
+
export default class PostRoute extends Route {
|
|
51
|
+
model({ post_id }) {
|
|
52
|
+
// the server returns `{ id: 12 }`
|
|
53
|
+
return fetch(`/posts/${post_id}`;
|
|
54
|
+
}
|
|
55
|
+
serialize(model) {
|
|
56
|
+
// this will make the URL `/posts/12`
|
|
57
|
+
return { post_id: model.id };
|
|
58
|
+
}
|
|
59
|
+
}
|
|
60
|
+
```
|
|
61
|
+
The default `serialize` method will insert the model's `id` into the
|
|
62
|
+
route's dynamic segment (in this case, `:post_id`) if the segment contains '_id'.
|
|
63
|
+
If the route has multiple dynamic segments or does not contain '_id', `serialize`
|
|
64
|
+
will return `getProperties(model, params)`
|
|
65
|
+
This method is called when `transitionTo` is called with a context
|
|
66
|
+
in order to populate the URL.
|
|
67
|
+
@method serialize
|
|
68
|
+
@param {Object} model the routes model
|
|
69
|
+
@param {Array} params an Array of parameter names for the current
|
|
70
|
+
route (in the example, `['post_id']`.
|
|
71
|
+
@return {Object} the serialized parameters
|
|
72
|
+
@since 1.0.0
|
|
73
|
+
@public
|
|
74
|
+
*/
|
|
75
|
+
|
|
76
|
+
|
|
77
|
+
serialize(model, params) {
|
|
78
|
+
if (params.length < 1 || !model) {
|
|
79
|
+
return;
|
|
80
|
+
}
|
|
81
|
+
|
|
82
|
+
let object = {};
|
|
83
|
+
|
|
84
|
+
if (params.length === 1) {
|
|
85
|
+
let [name] = params;
|
|
86
|
+
assert('has name', name);
|
|
87
|
+
|
|
88
|
+
if (name in model) {
|
|
89
|
+
object[name] = get(model, name);
|
|
90
|
+
} else if (/_id$/.test(name)) {
|
|
91
|
+
object[name] = get(model, 'id');
|
|
92
|
+
} else if (isProxy(model)) {
|
|
93
|
+
object[name] = get(model, name);
|
|
94
|
+
}
|
|
95
|
+
} else {
|
|
96
|
+
object = getProperties(model, params);
|
|
97
|
+
}
|
|
98
|
+
|
|
99
|
+
return object;
|
|
100
|
+
}
|
|
80
101
|
/**
|
|
81
102
|
Sets the name for this route, including a fully resolved name for routes
|
|
82
103
|
inside engines.
|
|
@@ -88,7 +109,9 @@ class Route extends EmberObject.extend(ActionHandler, Evented) {
|
|
|
88
109
|
|
|
89
110
|
_setRouteName(name) {
|
|
90
111
|
this.routeName = name;
|
|
91
|
-
|
|
112
|
+
let owner = getOwner(this);
|
|
113
|
+
assert('Route is unexpectedly missing an owner', owner);
|
|
114
|
+
this.fullRouteName = getEngineRouteName(owner, name);
|
|
92
115
|
}
|
|
93
116
|
/**
|
|
94
117
|
@private
|
|
@@ -106,18 +129,17 @@ class Route extends EmberObject.extend(ActionHandler, Evented) {
|
|
|
106
129
|
if (!names.length) {
|
|
107
130
|
routeInfo = dynamicParent;
|
|
108
131
|
names = routeInfo && routeInfo['_names'] || [];
|
|
109
|
-
}
|
|
132
|
+
} // SAFETY: Since `_qp` is protected we can't infer the type
|
|
133
|
+
|
|
110
134
|
|
|
111
|
-
let qps = get(this, '_qp.qps
|
|
135
|
+
let qps = get(this, '_qp').qps;
|
|
112
136
|
let namePaths = new Array(names.length);
|
|
113
137
|
|
|
114
138
|
for (let a = 0; a < names.length; ++a) {
|
|
115
139
|
namePaths[a] = `${routeInfo.name}.${names[a]}`;
|
|
116
140
|
}
|
|
117
141
|
|
|
118
|
-
for (let
|
|
119
|
-
let qp = qps[i];
|
|
120
|
-
|
|
142
|
+
for (let qp of qps) {
|
|
121
143
|
if (qp.scope === 'model') {
|
|
122
144
|
qp.parts = namePaths;
|
|
123
145
|
}
|
|
@@ -187,7 +209,9 @@ class Route extends EmberObject.extend(ActionHandler, Evented) {
|
|
|
187
209
|
|
|
188
210
|
|
|
189
211
|
paramsFor(name) {
|
|
190
|
-
let
|
|
212
|
+
let owner = getOwner(this);
|
|
213
|
+
assert('Route is unexpectedly missing an owner', owner);
|
|
214
|
+
let route = owner.lookup(`route:${name}`);
|
|
191
215
|
|
|
192
216
|
if (route === undefined) {
|
|
193
217
|
return {};
|
|
@@ -198,9 +222,9 @@ class Route extends EmberObject.extend(ActionHandler, Evented) {
|
|
|
198
222
|
let fullName = route.fullRouteName;
|
|
199
223
|
let params = Object.assign({}, state.params[fullName]);
|
|
200
224
|
let queryParams = getQueryParamsFor(route, state);
|
|
201
|
-
return Object.
|
|
225
|
+
return Object.entries(queryParams).reduce((params, [key, value]) => {
|
|
202
226
|
assert(`The route '${this.routeName}' has both a dynamic segment and query param with name '${key}'. Please rename one to avoid collisions.`, !params[key]);
|
|
203
|
-
params[key] =
|
|
227
|
+
params[key] = value;
|
|
204
228
|
return params;
|
|
205
229
|
}, params);
|
|
206
230
|
}
|
|
@@ -301,8 +325,9 @@ class Route extends EmberObject.extend(ActionHandler, Evented) {
|
|
|
301
325
|
|
|
302
326
|
|
|
303
327
|
_internalReset(isExiting, transition) {
|
|
304
|
-
let controller = this.controller;
|
|
305
|
-
|
|
328
|
+
let controller = this.controller; // SAFETY: Since `_qp` is protected we can't infer the type
|
|
329
|
+
|
|
330
|
+
controller['_qpDelegate'] = get(this, '_qp').states.inactive;
|
|
306
331
|
this.resetController(controller, isExiting, transition);
|
|
307
332
|
}
|
|
308
333
|
/**
|
|
@@ -316,148 +341,6 @@ class Route extends EmberObject.extend(ActionHandler, Evented) {
|
|
|
316
341
|
this.activate(transition);
|
|
317
342
|
this.trigger('activate', transition);
|
|
318
343
|
}
|
|
319
|
-
/**
|
|
320
|
-
The `willTransition` action is fired at the beginning of any
|
|
321
|
-
attempted transition with a `Transition` object as the sole
|
|
322
|
-
argument. This action can be used for aborting, redirecting,
|
|
323
|
-
or decorating the transition from the currently active routes.
|
|
324
|
-
A good example is preventing navigation when a form is
|
|
325
|
-
half-filled out:
|
|
326
|
-
```app/routes/contact-form.js
|
|
327
|
-
import Route from '@ember/routing/route';
|
|
328
|
-
import { action } from '@ember/object';
|
|
329
|
-
export default class ContactFormRoute extends Route {
|
|
330
|
-
@action
|
|
331
|
-
willTransition(transition) {
|
|
332
|
-
if (this.controller.get('userHasEnteredData')) {
|
|
333
|
-
this.controller.displayNavigationConfirm();
|
|
334
|
-
transition.abort();
|
|
335
|
-
}
|
|
336
|
-
}
|
|
337
|
-
}
|
|
338
|
-
```
|
|
339
|
-
You can also redirect elsewhere by calling
|
|
340
|
-
`this.transitionTo('elsewhere')` from within `willTransition`.
|
|
341
|
-
Note that `willTransition` will not be fired for the
|
|
342
|
-
redirecting `transitionTo`, since `willTransition` doesn't
|
|
343
|
-
fire when there is already a transition underway. If you want
|
|
344
|
-
subsequent `willTransition` actions to fire for the redirecting
|
|
345
|
-
transition, you must first explicitly call
|
|
346
|
-
`transition.abort()`.
|
|
347
|
-
To allow the `willTransition` event to continue bubbling to the parent
|
|
348
|
-
route, use `return true;`. When the `willTransition` method has a
|
|
349
|
-
return value of `true` then the parent route's `willTransition` method
|
|
350
|
-
will be fired, enabling "bubbling" behavior for the event.
|
|
351
|
-
@event willTransition
|
|
352
|
-
@param {Transition} transition
|
|
353
|
-
@since 1.0.0
|
|
354
|
-
@public
|
|
355
|
-
*/
|
|
356
|
-
|
|
357
|
-
/**
|
|
358
|
-
The `didTransition` action is fired after a transition has
|
|
359
|
-
successfully been completed. This occurs after the normal model
|
|
360
|
-
hooks (`beforeModel`, `model`, `afterModel`, `setupController`)
|
|
361
|
-
have resolved. The `didTransition` action has no arguments,
|
|
362
|
-
however, it can be useful for tracking page views or resetting
|
|
363
|
-
state on the controller.
|
|
364
|
-
```app/routes/login.js
|
|
365
|
-
import Route from '@ember/routing/route';
|
|
366
|
-
import { action } from '@ember/object';
|
|
367
|
-
export default class LoginRoute extends Route {
|
|
368
|
-
@action
|
|
369
|
-
didTransition() {
|
|
370
|
-
this.controller.get('errors.base').clear();
|
|
371
|
-
return true; // Bubble the didTransition event
|
|
372
|
-
}
|
|
373
|
-
}
|
|
374
|
-
```
|
|
375
|
-
@event didTransition
|
|
376
|
-
@since 1.2.0
|
|
377
|
-
@public
|
|
378
|
-
*/
|
|
379
|
-
|
|
380
|
-
/**
|
|
381
|
-
The `loading` action is fired on the route when a route's `model`
|
|
382
|
-
hook returns a promise that is not already resolved. The current
|
|
383
|
-
`Transition` object is the first parameter and the route that
|
|
384
|
-
triggered the loading event is the second parameter.
|
|
385
|
-
```app/routes/application.js
|
|
386
|
-
import Route from '@ember/routing/route';
|
|
387
|
-
import { action } from '@ember/object';
|
|
388
|
-
export default class ApplicationRoute extends Route {
|
|
389
|
-
@action
|
|
390
|
-
loading(transition, route) {
|
|
391
|
-
let controller = this.controllerFor('foo');
|
|
392
|
-
// The controller may not be instantiated when initially loading
|
|
393
|
-
if (controller) {
|
|
394
|
-
controller.currentlyLoading = true;
|
|
395
|
-
transition.finally(function() {
|
|
396
|
-
controller.currentlyLoading = false;
|
|
397
|
-
});
|
|
398
|
-
}
|
|
399
|
-
}
|
|
400
|
-
}
|
|
401
|
-
```
|
|
402
|
-
@event loading
|
|
403
|
-
@param {Transition} transition
|
|
404
|
-
@param {Route} route The route that triggered the loading event
|
|
405
|
-
@since 1.2.0
|
|
406
|
-
@public
|
|
407
|
-
*/
|
|
408
|
-
|
|
409
|
-
/**
|
|
410
|
-
When attempting to transition into a route, any of the hooks
|
|
411
|
-
may return a promise that rejects, at which point an `error`
|
|
412
|
-
action will be fired on the partially-entered routes, allowing
|
|
413
|
-
for per-route error handling logic, or shared error handling
|
|
414
|
-
logic defined on a parent route.
|
|
415
|
-
Here is an example of an error handler that will be invoked
|
|
416
|
-
for rejected promises from the various hooks on the route,
|
|
417
|
-
as well as any unhandled errors from child routes:
|
|
418
|
-
```app/routes/admin.js
|
|
419
|
-
import { reject } from 'rsvp';
|
|
420
|
-
import Route from '@ember/routing/route';
|
|
421
|
-
import { action } from '@ember/object';
|
|
422
|
-
export default class AdminRoute extends Route {
|
|
423
|
-
beforeModel() {
|
|
424
|
-
return reject('bad things!');
|
|
425
|
-
}
|
|
426
|
-
@action
|
|
427
|
-
error(error, transition) {
|
|
428
|
-
// Assuming we got here due to the error in `beforeModel`,
|
|
429
|
-
// we can expect that error === "bad things!",
|
|
430
|
-
// but a promise model rejecting would also
|
|
431
|
-
// call this hook, as would any errors encountered
|
|
432
|
-
// in `afterModel`.
|
|
433
|
-
// The `error` hook is also provided the failed
|
|
434
|
-
// `transition`, which can be stored and later
|
|
435
|
-
// `.retry()`d if desired.
|
|
436
|
-
this.transitionTo('login');
|
|
437
|
-
}
|
|
438
|
-
}
|
|
439
|
-
```
|
|
440
|
-
`error` actions that bubble up all the way to `ApplicationRoute`
|
|
441
|
-
will fire a default error handler that logs the error. You can
|
|
442
|
-
specify your own global default error handler by overriding the
|
|
443
|
-
`error` handler on `ApplicationRoute`:
|
|
444
|
-
```app/routes/application.js
|
|
445
|
-
import Route from '@ember/routing/route';
|
|
446
|
-
import { action } from '@ember/object';
|
|
447
|
-
export default class ApplicationRoute extends Route {
|
|
448
|
-
@action
|
|
449
|
-
error(error, transition) {
|
|
450
|
-
this.controllerFor('banner').displayError(error.message);
|
|
451
|
-
}
|
|
452
|
-
}
|
|
453
|
-
```
|
|
454
|
-
@event error
|
|
455
|
-
@param {Error} error
|
|
456
|
-
@param {Transition} transition
|
|
457
|
-
@since 1.0.0
|
|
458
|
-
@public
|
|
459
|
-
*/
|
|
460
|
-
|
|
461
344
|
/**
|
|
462
345
|
This event is triggered when the router enters the route. It is
|
|
463
346
|
not executed when the model for the route changes.
|
|
@@ -768,24 +651,17 @@ class Route extends EmberObject.extend(ActionHandler, Evented) {
|
|
|
768
651
|
setup(context, transition) {
|
|
769
652
|
let controllerName = this.controllerName || this.routeName;
|
|
770
653
|
let definedController = this.controllerFor(controllerName, true);
|
|
771
|
-
let controller;
|
|
654
|
+
let controller = definedController !== null && definedController !== void 0 ? definedController : this.generateController(controllerName); // SAFETY: Since `_qp` is protected we can't infer the type
|
|
772
655
|
|
|
773
|
-
|
|
774
|
-
controller = definedController;
|
|
775
|
-
} else {
|
|
776
|
-
controller = this.generateController(controllerName);
|
|
777
|
-
} // Assign the route's controller so that it can more easily be
|
|
656
|
+
let queryParams = get(this, '_qp'); // Assign the route's controller so that it can more easily be
|
|
778
657
|
// referenced in action handlers. Side effects. Side effects everywhere.
|
|
779
658
|
|
|
780
|
-
|
|
781
659
|
if (!this.controller) {
|
|
782
|
-
let
|
|
783
|
-
let propNames = qp !== undefined ? get(qp, 'propertyNames') : [];
|
|
660
|
+
let propNames = queryParams.propertyNames;
|
|
784
661
|
addQueryParamsObservers(controller, propNames);
|
|
785
662
|
this.controller = controller;
|
|
786
663
|
}
|
|
787
664
|
|
|
788
|
-
let queryParams = get(this, '_qp');
|
|
789
665
|
let states = queryParams.states;
|
|
790
666
|
controller._qpDelegate = states.allowOverrides;
|
|
791
667
|
|
|
@@ -797,6 +673,7 @@ class Route extends EmberObject.extend(ActionHandler, Evented) {
|
|
|
797
673
|
let allParams = queryParams.propertyNames;
|
|
798
674
|
allParams.forEach(prop => {
|
|
799
675
|
let aQp = queryParams.map[prop];
|
|
676
|
+
assert('expected aQp', aQp);
|
|
800
677
|
aQp.values = params;
|
|
801
678
|
let cacheKey = calculateCacheKey(aQp.route.fullRouteName, aQp.parts, aQp.values);
|
|
802
679
|
let value = cache.lookup(cacheKey, prop, aQp.undecoratedDefaultValue);
|
|
@@ -833,71 +710,10 @@ class Route extends EmberObject.extend(ActionHandler, Evented) {
|
|
|
833
710
|
let cacheKey = calculateCacheKey(qp.route.fullRouteName, qp.parts, qp.values);
|
|
834
711
|
cache.stash(cacheKey, prop, value);
|
|
835
712
|
}
|
|
836
|
-
/**
|
|
837
|
-
This hook is the first of the route entry validation hooks
|
|
838
|
-
called when an attempt is made to transition into a route
|
|
839
|
-
or one of its children. It is called before `model` and
|
|
840
|
-
`afterModel`, and is appropriate for cases when:
|
|
841
|
-
1) A decision can be made to redirect elsewhere without
|
|
842
|
-
needing to resolve the model first.
|
|
843
|
-
2) Any async operations need to occur first before the
|
|
844
|
-
model is attempted to be resolved.
|
|
845
|
-
This hook is provided the current `transition` attempt
|
|
846
|
-
as a parameter, which can be used to `.abort()` the transition,
|
|
847
|
-
save it for a later `.retry()`, or retrieve values set
|
|
848
|
-
on it from a previous hook. You can also just call
|
|
849
|
-
`this.transitionTo` to another route to implicitly
|
|
850
|
-
abort the `transition`.
|
|
851
|
-
You can return a promise from this hook to pause the
|
|
852
|
-
transition until the promise resolves (or rejects). This could
|
|
853
|
-
be useful, for instance, for retrieving async code from
|
|
854
|
-
the server that is required to enter a route.
|
|
855
|
-
@method beforeModel
|
|
856
|
-
@param {Transition} transition
|
|
857
|
-
@return {any | Promise<any>} if the value returned from this hook is
|
|
858
|
-
a promise, the transition will pause until the transition
|
|
859
|
-
resolves. Otherwise, non-promise return values are not
|
|
860
|
-
utilized in any way.
|
|
861
|
-
@since 1.0.0
|
|
862
|
-
@public
|
|
863
|
-
*/
|
|
864
|
-
|
|
865
|
-
|
|
866
|
-
beforeModel() {}
|
|
867
|
-
/**
|
|
868
|
-
This hook is called after this route's model has resolved.
|
|
869
|
-
It follows identical async/promise semantics to `beforeModel`
|
|
870
|
-
but is provided the route's resolved model in addition to
|
|
871
|
-
the `transition`, and is therefore suited to performing
|
|
872
|
-
logic that can only take place after the model has already
|
|
873
|
-
resolved.
|
|
874
|
-
```app/routes/posts.js
|
|
875
|
-
import Route from '@ember/routing/route';
|
|
876
|
-
export default class PostsRoute extends Route {
|
|
877
|
-
afterModel(posts, transition) {
|
|
878
|
-
if (posts.get('length') === 1) {
|
|
879
|
-
this.transitionTo('post.show', posts.get('firstObject'));
|
|
880
|
-
}
|
|
881
|
-
}
|
|
882
|
-
}
|
|
883
|
-
```
|
|
884
|
-
Refer to documentation for `beforeModel` for a description
|
|
885
|
-
of transition-pausing semantics when a promise is returned
|
|
886
|
-
from this hook.
|
|
887
|
-
@method afterModel
|
|
888
|
-
@param {Object} resolvedModel the value returned from `model`,
|
|
889
|
-
or its resolved value if it was a promise
|
|
890
|
-
@param {Transition} transition
|
|
891
|
-
@return {any | Promise<any>} if the value returned from this hook is
|
|
892
|
-
a promise, the transition will pause until the transition
|
|
893
|
-
resolves. Otherwise, non-promise return values are not
|
|
894
|
-
utilized in any way.
|
|
895
|
-
@since 1.0.0
|
|
896
|
-
@public
|
|
897
|
-
*/
|
|
898
713
|
|
|
714
|
+
beforeModel(_transition) {}
|
|
899
715
|
|
|
900
|
-
afterModel() {}
|
|
716
|
+
afterModel(_resolvedModel, _transition) {}
|
|
901
717
|
/**
|
|
902
718
|
A hook you can implement to optionally redirect to another route.
|
|
903
719
|
Calling `this.transitionTo` from inside of the `redirect` hook will
|
|
@@ -920,7 +736,7 @@ class Route extends EmberObject.extend(ActionHandler, Evented) {
|
|
|
920
736
|
*/
|
|
921
737
|
|
|
922
738
|
|
|
923
|
-
redirect() {}
|
|
739
|
+
redirect(_model, _transition) {}
|
|
924
740
|
/**
|
|
925
741
|
Called when the context is changed by router.js.
|
|
926
742
|
@private
|
|
@@ -994,8 +810,9 @@ class Route extends EmberObject.extend(ActionHandler, Evented) {
|
|
|
994
810
|
|
|
995
811
|
|
|
996
812
|
model(params, transition) {
|
|
997
|
-
let name, sawParams, value;
|
|
998
|
-
|
|
813
|
+
let name, sawParams, value; // SAFETY: Since `_qp` is protected we can't infer the type
|
|
814
|
+
|
|
815
|
+
let queryParams = get(this, '_qp').map;
|
|
999
816
|
|
|
1000
817
|
for (let prop in params) {
|
|
1001
818
|
if (prop === 'queryParams' || queryParams && prop in queryParams) {
|
|
@@ -1014,11 +831,14 @@ class Route extends EmberObject.extend(ActionHandler, Evented) {
|
|
|
1014
831
|
|
|
1015
832
|
if (!name) {
|
|
1016
833
|
if (sawParams) {
|
|
834
|
+
// SAFETY: This should be equivalent
|
|
1017
835
|
return Object.assign({}, params);
|
|
1018
836
|
} else {
|
|
1019
837
|
if (transition.resolveIndex < 1) {
|
|
1020
838
|
return;
|
|
1021
|
-
}
|
|
839
|
+
} // SAFETY: These return types should be equivalent but router.js doesn't have enough
|
|
840
|
+
// generics to infer it.
|
|
841
|
+
|
|
1022
842
|
|
|
1023
843
|
return transition[STATE_SYMBOL].routeInfos[transition.resolveIndex - 1].context;
|
|
1024
844
|
}
|
|
@@ -1105,35 +925,14 @@ class Route extends EmberObject.extend(ActionHandler, Evented) {
|
|
|
1105
925
|
|
|
1106
926
|
|
|
1107
927
|
setupController(controller, context, _transition) {
|
|
1108
|
-
// eslint-disable-line no-unused-vars
|
|
1109
928
|
if (controller && context !== undefined) {
|
|
1110
929
|
set(controller, 'model', context);
|
|
1111
930
|
}
|
|
1112
931
|
}
|
|
1113
|
-
/**
|
|
1114
|
-
Returns the controller of the current route, or a parent (or any ancestor)
|
|
1115
|
-
route in a route hierarchy.
|
|
1116
|
-
The controller instance must already have been created, either through entering the
|
|
1117
|
-
associated route or using `generateController`.
|
|
1118
|
-
```app/routes/post.js
|
|
1119
|
-
import Route from '@ember/routing/route';
|
|
1120
|
-
export default class PostRoute extends Route {
|
|
1121
|
-
setupController(controller, post) {
|
|
1122
|
-
super.setupController(controller, post);
|
|
1123
|
-
this.controllerFor('posts').set('currentPost', post);
|
|
1124
|
-
}
|
|
1125
|
-
}
|
|
1126
|
-
```
|
|
1127
|
-
@method controllerFor
|
|
1128
|
-
@param {String} name the name of the route or controller
|
|
1129
|
-
@return {Controller}
|
|
1130
|
-
@since 1.0.0
|
|
1131
|
-
@public
|
|
1132
|
-
*/
|
|
1133
932
|
|
|
1134
|
-
|
|
1135
|
-
controllerFor(name, _skipAssert) {
|
|
933
|
+
controllerFor(name, _skipAssert = false) {
|
|
1136
934
|
let owner = getOwner(this);
|
|
935
|
+
assert('Route is unexpectedly missing an owner', owner);
|
|
1137
936
|
let route = owner.lookup(`route:${name}`);
|
|
1138
937
|
|
|
1139
938
|
if (route && route.controllerName) {
|
|
@@ -1167,6 +966,7 @@ class Route extends EmberObject.extend(ActionHandler, Evented) {
|
|
|
1167
966
|
|
|
1168
967
|
generateController(name) {
|
|
1169
968
|
let owner = getOwner(this);
|
|
969
|
+
assert('Route is unexpectedly missing an owner', owner);
|
|
1170
970
|
return generateController(owner, name);
|
|
1171
971
|
}
|
|
1172
972
|
/**
|
|
@@ -1208,6 +1008,7 @@ class Route extends EmberObject.extend(ActionHandler, Evented) {
|
|
|
1208
1008
|
modelFor(_name) {
|
|
1209
1009
|
let name;
|
|
1210
1010
|
let owner = getOwner(this);
|
|
1011
|
+
assert('Route is unexpectedly missing an owner', owner);
|
|
1211
1012
|
let transition = this._router && this._router._routerMicrolib ? this._router._routerMicrolib.activeTransition : undefined; // Only change the route name when there is an active transition.
|
|
1212
1013
|
// Otherwise, use the passed in route name.
|
|
1213
1014
|
|
|
@@ -1228,7 +1029,7 @@ class Route extends EmberObject.extend(ActionHandler, Evented) {
|
|
|
1228
1029
|
}
|
|
1229
1030
|
}
|
|
1230
1031
|
|
|
1231
|
-
return route
|
|
1032
|
+
return route === null || route === void 0 ? void 0 : route.currentModel;
|
|
1232
1033
|
}
|
|
1233
1034
|
/**
|
|
1234
1035
|
`this[RENDER]` is used to render a template into a region of another template
|
|
@@ -1271,39 +1072,6 @@ class Route extends EmberObject.extend(ActionHandler, Evented) {
|
|
|
1271
1072
|
once(this._router, '_setOutlets');
|
|
1272
1073
|
}
|
|
1273
1074
|
}
|
|
1274
|
-
/**
|
|
1275
|
-
Allows you to produce custom metadata for the route.
|
|
1276
|
-
The return value of this method will be attached to
|
|
1277
|
-
its corresponding RouteInfoWithAttributes object.
|
|
1278
|
-
Example
|
|
1279
|
-
```app/routes/posts/index.js
|
|
1280
|
-
import Route from '@ember/routing/route';
|
|
1281
|
-
export default class PostsIndexRoute extends Route {
|
|
1282
|
-
buildRouteInfoMetadata() {
|
|
1283
|
-
return { title: 'Posts Page' }
|
|
1284
|
-
}
|
|
1285
|
-
}
|
|
1286
|
-
```
|
|
1287
|
-
```app/routes/application.js
|
|
1288
|
-
import Route from '@ember/routing/route';
|
|
1289
|
-
import { service } from '@ember/service';
|
|
1290
|
-
export default class ApplicationRoute extends Route {
|
|
1291
|
-
@service router
|
|
1292
|
-
constructor() {
|
|
1293
|
-
super(...arguments);
|
|
1294
|
-
this.router.on('routeDidChange', transition => {
|
|
1295
|
-
document.title = transition.to.metadata.title;
|
|
1296
|
-
// would update document's title to "Posts Page"
|
|
1297
|
-
});
|
|
1298
|
-
}
|
|
1299
|
-
}
|
|
1300
|
-
```
|
|
1301
|
-
@method buildRouteInfoMetadata
|
|
1302
|
-
@return any
|
|
1303
|
-
@since 3.10.0
|
|
1304
|
-
@public
|
|
1305
|
-
*/
|
|
1306
|
-
|
|
1307
1075
|
|
|
1308
1076
|
buildRouteInfoMetadata() {}
|
|
1309
1077
|
|
|
@@ -1329,7 +1097,8 @@ class Route extends EmberObject.extend(ActionHandler, Evented) {
|
|
|
1329
1097
|
|
|
1330
1098
|
|
|
1331
1099
|
get store() {
|
|
1332
|
-
|
|
1100
|
+
const owner = getOwner(this);
|
|
1101
|
+
assert('Route is unexpectedly missing an owner', owner);
|
|
1333
1102
|
let routeName = this.routeName;
|
|
1334
1103
|
return {
|
|
1335
1104
|
find(name, value) {
|
|
@@ -1361,6 +1130,7 @@ class Route extends EmberObject.extend(ActionHandler, Evented) {
|
|
|
1361
1130
|
let combinedQueryParameterConfiguration;
|
|
1362
1131
|
let controllerName = this.controllerName || this.routeName;
|
|
1363
1132
|
let owner = getOwner(this);
|
|
1133
|
+
assert('Route is unexpectedly missing an owner', owner);
|
|
1364
1134
|
let controller = owner.lookup(`controller:${controllerName}`);
|
|
1365
1135
|
let queryParameterConfiguraton = get(this, 'queryParams');
|
|
1366
1136
|
let hasRouterDefinedQueryParams = Object.keys(queryParameterConfiguraton).length > 0;
|
|
@@ -1370,7 +1140,7 @@ class Route extends EmberObject.extend(ActionHandler, Evented) {
|
|
|
1370
1140
|
// this route find its query params and normalize their object shape them
|
|
1371
1141
|
// merge in the query params for the route. As a mergedProperty,
|
|
1372
1142
|
// Route#queryParams is always at least `{}`
|
|
1373
|
-
let controllerDefinedQueryParameterConfiguration = get(controller, 'queryParams') ||
|
|
1143
|
+
let controllerDefinedQueryParameterConfiguration = get(controller, 'queryParams') || [];
|
|
1374
1144
|
let normalizedControllerQueryParameterConfiguration = normalizeControllerQueryParams(controllerDefinedQueryParameterConfiguration);
|
|
1375
1145
|
combinedQueryParameterConfiguration = mergeEachQueryParams(normalizedControllerQueryParameterConfiguration, queryParameterConfiguraton);
|
|
1376
1146
|
} else if (hasRouterDefinedQueryParams) {
|
|
@@ -1398,7 +1168,7 @@ class Route extends EmberObject.extend(ActionHandler, Evented) {
|
|
|
1398
1168
|
|
|
1399
1169
|
let desc = combinedQueryParameterConfiguration[propName];
|
|
1400
1170
|
let scope = desc.scope || 'model';
|
|
1401
|
-
let parts;
|
|
1171
|
+
let parts = undefined;
|
|
1402
1172
|
|
|
1403
1173
|
if (scope === 'controller') {
|
|
1404
1174
|
parts = [];
|
|
@@ -1442,6 +1212,7 @@ class Route extends EmberObject.extend(ActionHandler, Evented) {
|
|
|
1442
1212
|
*/
|
|
1443
1213
|
inactive: (prop, value) => {
|
|
1444
1214
|
let qp = map[prop];
|
|
1215
|
+
assert('expected inactive callback to only be called for registered qps', qp);
|
|
1445
1216
|
|
|
1446
1217
|
this._qpChanged(prop, value, qp);
|
|
1447
1218
|
},
|
|
@@ -1453,6 +1224,7 @@ class Route extends EmberObject.extend(ActionHandler, Evented) {
|
|
|
1453
1224
|
*/
|
|
1454
1225
|
active: (prop, value) => {
|
|
1455
1226
|
let qp = map[prop];
|
|
1227
|
+
assert('expected active callback to only be called for registered qps', qp);
|
|
1456
1228
|
|
|
1457
1229
|
this._qpChanged(prop, value, qp);
|
|
1458
1230
|
|
|
@@ -1465,6 +1237,7 @@ class Route extends EmberObject.extend(ActionHandler, Evented) {
|
|
|
1465
1237
|
*/
|
|
1466
1238
|
allowOverrides: (prop, value) => {
|
|
1467
1239
|
let qp = map[prop];
|
|
1240
|
+
assert('expected allowOverrides callback to only be called for registered qps', qp);
|
|
1468
1241
|
|
|
1469
1242
|
this._qpChanged(prop, value, qp);
|
|
1470
1243
|
|
|
@@ -1495,7 +1268,9 @@ function routeInfoFor(route, routeInfos, offset = 0) {
|
|
|
1495
1268
|
let current;
|
|
1496
1269
|
|
|
1497
1270
|
for (let i = 0; i < routeInfos.length; i++) {
|
|
1498
|
-
|
|
1271
|
+
let routeInfo = routeInfos[i];
|
|
1272
|
+
assert('has current routeInfo', routeInfo);
|
|
1273
|
+
current = routeInfo.route;
|
|
1499
1274
|
|
|
1500
1275
|
if (current === route) {
|
|
1501
1276
|
return routeInfos[i + offset];
|
|
@@ -1522,6 +1297,7 @@ function buildRenderOptions(route, nameOrOptions, options) {
|
|
|
1522
1297
|
|
|
1523
1298
|
assert('You passed undefined as the outlet name.', isDefaultRender || !(options && 'outlet' in options && options.outlet === undefined));
|
|
1524
1299
|
let owner = getOwner(route);
|
|
1300
|
+
assert('Route is unexpectedly missing an owner', owner);
|
|
1525
1301
|
let name, templateName, into, outlet, model;
|
|
1526
1302
|
let controller = undefined;
|
|
1527
1303
|
|
|
@@ -1594,13 +1370,12 @@ function buildRenderOptions(route, nameOrOptions, options) {
|
|
|
1594
1370
|
}
|
|
1595
1371
|
|
|
1596
1372
|
export function getFullQueryParams(router, state) {
|
|
1597
|
-
if (state
|
|
1598
|
-
return state
|
|
1373
|
+
if (state.fullQueryParams) {
|
|
1374
|
+
return state.fullQueryParams;
|
|
1599
1375
|
}
|
|
1600
1376
|
|
|
1601
|
-
let fullQueryParamsState = {};
|
|
1602
1377
|
let haveAllRouteInfosResolved = state.routeInfos.every(routeInfo => routeInfo.route);
|
|
1603
|
-
Object.assign(
|
|
1378
|
+
let fullQueryParamsState = Object.assign({}, state.queryParams);
|
|
1604
1379
|
|
|
1605
1380
|
router._deserializeQueryParams(state.routeInfos, fullQueryParamsState); // only cache query params state if all routeinfos have resolved; it's possible
|
|
1606
1381
|
// for lazy routes to not have resolved when `getFullQueryParams` is called, so
|
|
@@ -1608,37 +1383,40 @@ export function getFullQueryParams(router, state) {
|
|
|
1608
1383
|
|
|
1609
1384
|
|
|
1610
1385
|
if (haveAllRouteInfosResolved) {
|
|
1611
|
-
state
|
|
1386
|
+
state.fullQueryParams = fullQueryParamsState;
|
|
1612
1387
|
}
|
|
1613
1388
|
|
|
1614
1389
|
return fullQueryParamsState;
|
|
1615
1390
|
}
|
|
1616
1391
|
|
|
1617
1392
|
function getQueryParamsFor(route, state) {
|
|
1618
|
-
state
|
|
1393
|
+
state.queryParamsFor = state.queryParamsFor || {};
|
|
1619
1394
|
let name = route.fullRouteName;
|
|
1395
|
+
let existing = state.queryParamsFor[name];
|
|
1620
1396
|
|
|
1621
|
-
if (
|
|
1622
|
-
return
|
|
1397
|
+
if (existing) {
|
|
1398
|
+
return existing;
|
|
1623
1399
|
}
|
|
1624
1400
|
|
|
1625
1401
|
let fullQueryParams = getFullQueryParams(route._router, state);
|
|
1626
|
-
let params = state
|
|
1402
|
+
let params = state.queryParamsFor[name] = {}; // Copy over all the query params for this route/controller into params hash.
|
|
1403
|
+
// SAFETY: Since `_qp` is protected we can't infer the type
|
|
1627
1404
|
|
|
1628
|
-
let qps = get(route, '_qp.qps
|
|
1405
|
+
let qps = get(route, '_qp').qps;
|
|
1629
1406
|
|
|
1630
|
-
for (let
|
|
1407
|
+
for (let qp of qps) {
|
|
1631
1408
|
// Put deserialized qp on params hash.
|
|
1632
|
-
let qp = qps[i];
|
|
1633
1409
|
let qpValueWasPassedIn = (qp.prop in fullQueryParams);
|
|
1634
1410
|
params[qp.prop] = qpValueWasPassedIn ? fullQueryParams[qp.prop] : copyDefaultValue(qp.defaultValue);
|
|
1635
1411
|
}
|
|
1636
1412
|
|
|
1637
1413
|
return params;
|
|
1638
|
-
}
|
|
1414
|
+
} // FIXME: This should probably actually return a `NativeArray` if the passed in value is an Array.
|
|
1415
|
+
|
|
1639
1416
|
|
|
1640
1417
|
function copyDefaultValue(value) {
|
|
1641
1418
|
if (Array.isArray(value)) {
|
|
1419
|
+
// SAFETY: We lost the type data about the array if we don't cast.
|
|
1642
1420
|
return emberA(value.slice());
|
|
1643
1421
|
}
|
|
1644
1422
|
|
|
@@ -1718,54 +1496,12 @@ function getEngineRouteName(engine, routeName) {
|
|
|
1718
1496
|
|
|
1719
1497
|
return routeName;
|
|
1720
1498
|
}
|
|
1721
|
-
/**
|
|
1722
|
-
A hook you can implement to convert the route's model into parameters
|
|
1723
|
-
for the URL.
|
|
1724
|
-
|
|
1725
|
-
```app/router.js
|
|
1726
|
-
// ...
|
|
1727
|
-
|
|
1728
|
-
Router.map(function() {
|
|
1729
|
-
this.route('post', { path: '/posts/:post_id' });
|
|
1730
|
-
});
|
|
1731
|
-
|
|
1732
|
-
```
|
|
1733
|
-
|
|
1734
|
-
```app/routes/post.js
|
|
1735
|
-
import Route from '@ember/routing/route';
|
|
1736
1499
|
|
|
1737
|
-
|
|
1738
|
-
|
|
1739
|
-
|
|
1740
|
-
|
|
1741
|
-
|
|
1742
|
-
|
|
1743
|
-
serialize(model) {
|
|
1744
|
-
// this will make the URL `/posts/12`
|
|
1745
|
-
return { post_id: model.id };
|
|
1746
|
-
}
|
|
1747
|
-
}
|
|
1748
|
-
```
|
|
1749
|
-
|
|
1750
|
-
The default `serialize` method will insert the model's `id` into the
|
|
1751
|
-
route's dynamic segment (in this case, `:post_id`) if the segment contains '_id'.
|
|
1752
|
-
If the route has multiple dynamic segments or does not contain '_id', `serialize`
|
|
1753
|
-
will return `getProperties(model, params)`
|
|
1754
|
-
|
|
1755
|
-
This method is called when `transitionTo` is called with a context
|
|
1756
|
-
in order to populate the URL.
|
|
1757
|
-
|
|
1758
|
-
@method serialize
|
|
1759
|
-
@param {Object} model the routes model
|
|
1760
|
-
@param {Array} params an Array of parameter names for the current
|
|
1761
|
-
route (in the example, `['post_id']`.
|
|
1762
|
-
@return {Object} the serialized parameters
|
|
1763
|
-
@since 1.0.0
|
|
1764
|
-
@public
|
|
1765
|
-
*/
|
|
1766
|
-
|
|
1767
|
-
|
|
1768
|
-
Route.prototype.serialize = defaultSerialize; // Set these here so they can be overridden with extend
|
|
1500
|
+
const defaultSerialize = Route.prototype.serialize;
|
|
1501
|
+
export { defaultSerialize };
|
|
1502
|
+
export function hasDefaultSerialize(route) {
|
|
1503
|
+
return route.serialize === defaultSerialize;
|
|
1504
|
+
} // Set these here so they can be overridden with extend
|
|
1769
1505
|
|
|
1770
1506
|
Route.reopen({
|
|
1771
1507
|
mergedProperties: ['queryParams'],
|
|
@@ -1824,15 +1560,22 @@ Route.reopen({
|
|
|
1824
1560
|
@private
|
|
1825
1561
|
*/
|
|
1826
1562
|
queryParamsDidChange(changed, _totalPresent, removed) {
|
|
1563
|
+
// SAFETY: Since `_qp` is protected we can't infer the type
|
|
1827
1564
|
let qpMap = get(this, '_qp').map;
|
|
1828
1565
|
let totalChanged = Object.keys(changed).concat(Object.keys(removed));
|
|
1829
1566
|
|
|
1830
|
-
for (let
|
|
1831
|
-
let qp = qpMap[
|
|
1567
|
+
for (let change of totalChanged) {
|
|
1568
|
+
let qp = qpMap[change];
|
|
1569
|
+
|
|
1570
|
+
if (qp) {
|
|
1571
|
+
let options = this._optionsForQueryParam(qp);
|
|
1572
|
+
|
|
1573
|
+
assert('options exists', options && typeof options === 'object');
|
|
1832
1574
|
|
|
1833
|
-
|
|
1834
|
-
|
|
1835
|
-
|
|
1575
|
+
if (get(options, 'refreshModel') && this._router.currentState) {
|
|
1576
|
+
this.refresh();
|
|
1577
|
+
break;
|
|
1578
|
+
}
|
|
1836
1579
|
}
|
|
1837
1580
|
}
|
|
1838
1581
|
|
|
@@ -1859,15 +1602,15 @@ Route.reopen({
|
|
|
1859
1602
|
let replaceUrl;
|
|
1860
1603
|
stashParamNames(router, routeInfos);
|
|
1861
1604
|
|
|
1862
|
-
for (let
|
|
1863
|
-
let qp = qpMeta.qps[i];
|
|
1605
|
+
for (let qp of qpMeta.qps) {
|
|
1864
1606
|
let route = qp.route;
|
|
1865
1607
|
let controller = route.controller;
|
|
1866
1608
|
let presentKey = qp.urlKey in params && qp.urlKey; // Do a reverse lookup to see if the changed query
|
|
1867
1609
|
// param URL key corresponds to a QP property on
|
|
1868
1610
|
// this controller.
|
|
1869
1611
|
|
|
1870
|
-
let value
|
|
1612
|
+
let value;
|
|
1613
|
+
let svalue;
|
|
1871
1614
|
|
|
1872
1615
|
if (changes.has(qp.urlKey)) {
|
|
1873
1616
|
// Value updated in/before setupController
|
|
@@ -1885,9 +1628,10 @@ Route.reopen({
|
|
|
1885
1628
|
svalue = qp.serializedDefaultValue;
|
|
1886
1629
|
value = copyDefaultValue(qp.defaultValue);
|
|
1887
1630
|
}
|
|
1888
|
-
}
|
|
1631
|
+
} // SAFETY: Since `_qp` is protected we can't infer the type
|
|
1632
|
+
|
|
1889
1633
|
|
|
1890
|
-
controller._qpDelegate = get(route, '_qp.states.inactive
|
|
1634
|
+
controller._qpDelegate = get(route, '_qp').states.inactive;
|
|
1891
1635
|
let thisQueryParamChanged = svalue !== qp.serializedValue;
|
|
1892
1636
|
|
|
1893
1637
|
if (thisQueryParamChanged) {
|
|
@@ -1932,6 +1676,7 @@ Route.reopen({
|
|
|
1932
1676
|
}
|
|
1933
1677
|
|
|
1934
1678
|
qpMeta.qps.forEach(qp => {
|
|
1679
|
+
// SAFETY: Since `_qp` is protected we can't infer the type
|
|
1935
1680
|
let routeQpMeta = get(qp.route, '_qp');
|
|
1936
1681
|
let finalizedController = qp.route.controller;
|
|
1937
1682
|
finalizedController['_qpDelegate'] = get(routeQpMeta, 'states.active');
|