crelte 0.1.3 → 0.2.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.
Files changed (53) hide show
  1. package/dist/CrelteRequest.d.ts +11 -6
  2. package/dist/CrelteRequest.d.ts.map +1 -1
  3. package/dist/CrelteRequest.js +14 -14
  4. package/dist/graphql/GraphQl.d.ts +1 -1
  5. package/dist/graphql/GraphQl.d.ts.map +1 -1
  6. package/dist/graphql/GraphQl.js +1 -1
  7. package/dist/index.d.ts +3 -1
  8. package/dist/index.d.ts.map +1 -1
  9. package/dist/index.js +10 -3
  10. package/dist/init/client.d.ts.map +1 -1
  11. package/dist/init/client.js +11 -5
  12. package/dist/init/server.d.ts +2 -0
  13. package/dist/init/server.d.ts.map +1 -1
  14. package/dist/init/server.js +24 -10
  15. package/dist/init/shared.d.ts +3 -3
  16. package/dist/init/shared.d.ts.map +1 -1
  17. package/dist/init/shared.js +1 -1
  18. package/dist/loadData/index.d.ts +11 -5
  19. package/dist/loadData/index.d.ts.map +1 -1
  20. package/dist/loadData/index.js +15 -6
  21. package/dist/routing/History.d.ts +5 -3
  22. package/dist/routing/History.d.ts.map +1 -1
  23. package/dist/routing/History.js +9 -4
  24. package/dist/routing/InnerRouter.d.ts +31 -21
  25. package/dist/routing/InnerRouter.d.ts.map +1 -1
  26. package/dist/routing/InnerRouter.js +98 -76
  27. package/dist/routing/PageLoader.d.ts +4 -5
  28. package/dist/routing/PageLoader.d.ts.map +1 -1
  29. package/dist/routing/PageLoader.js +5 -5
  30. package/dist/routing/Request.d.ts +15 -2
  31. package/dist/routing/Request.d.ts.map +1 -1
  32. package/dist/routing/Request.js +22 -1
  33. package/dist/routing/Route.d.ts +61 -25
  34. package/dist/routing/Route.d.ts.map +1 -1
  35. package/dist/routing/Route.js +90 -41
  36. package/dist/routing/Router.d.ts +34 -13
  37. package/dist/routing/Router.d.ts.map +1 -1
  38. package/dist/routing/Router.js +102 -49
  39. package/package.json +3 -2
  40. package/src/CrelteRequest.ts +14 -19
  41. package/src/graphql/GraphQl.ts +5 -2
  42. package/src/index.ts +26 -3
  43. package/src/init/client.ts +14 -10
  44. package/src/init/server.ts +31 -11
  45. package/src/init/shared.ts +4 -4
  46. package/src/loadData/index.ts +47 -15
  47. package/src/routing/History.ts +12 -5
  48. package/src/routing/InnerRouter.ts +109 -82
  49. package/src/routing/PageLoader.ts +7 -17
  50. package/src/routing/Request.ts +28 -6
  51. package/src/routing/Route.ts +115 -52
  52. package/src/routing/Router.ts +123 -59
  53. package/LICENSE.md +0 -41
@@ -1,6 +1,6 @@
1
1
  import Site, { SiteFromGraphQl } from './Site.js';
2
2
  import History from './History.js';
3
- import Request from './Request.js';
3
+ import Request, { RequestOptions } from './Request.js';
4
4
  import Route from './Route.js';
5
5
  export type InnerRouterOpts = {
6
6
  preloadOnMouseOver: boolean;
@@ -10,16 +10,21 @@ export type InnerRouterOpts = {
10
10
  */
11
11
  export default class InnerRouter {
12
12
  sites: Site[];
13
+ /**
14
+ * The current route
15
+ *
16
+ * ## Null
17
+ * It might be null on the first targetToRequest, open, and routeFromUrl call
18
+ */
13
19
  route: Route | null;
14
- site: Site;
15
20
  history: History;
16
21
  preloadOnMouseOver: boolean;
17
22
  /**
18
23
  * @param changeHistory returns a function you need to call when you are ready to
19
24
  update the window history (note do not call this after another onRoute call was made)
20
25
  */
21
- onRoute: (route: Request, site: Site, changeHistory: () => void) => void;
22
- onPreload: (route: Request, site: Site) => void;
26
+ onRoute: (route: Request, changeHistory: () => void) => void;
27
+ onPreload: (route: Request) => void;
23
28
  private scrollDebounceTimeout;
24
29
  /**
25
30
  * Creates a new Router
@@ -39,8 +44,7 @@ export default class InnerRouter {
39
44
  /**
40
45
  * Get a site and if possible use the accept lang header.
41
46
  *
42
- * @param {(string|null)} [acceptLang=null] Accept Language header.
43
- * @return {Site}
47
+ * @param acceptLang Accept Language header.
44
48
  */
45
49
  siteByAcceptLang(acceptLang?: string | null): Site;
46
50
  /**
@@ -52,12 +56,13 @@ export default class InnerRouter {
52
56
  */
53
57
  siteById(id: number): Site | null;
54
58
  /**
55
- * Resolve a url or Route and convert it to a Route
59
+ * Resolve a url or Route and convert it to a Request
56
60
  *
57
61
  * @param target
62
+ * @param opts, any option present will override the value in target
58
63
  * @return Returns null if the url does not match our host (the protocol get's ignored)
59
64
  */
60
- targetToRequest(target: string | URL | Route | Request): Request;
65
+ targetToRequest(target: string | URL | Route | Request, opts?: RequestOptions): Request;
61
66
  /**
62
67
  * Resolve a url and convert it to a Route
63
68
  *
@@ -67,12 +72,16 @@ export default class InnerRouter {
67
72
  routeFromUrl(fullUrl: URL): Route;
68
73
  listen(): void;
69
74
  /**
70
- * Open's a route
75
+ * Open a new route
71
76
  *
72
77
  * @param route a route object or an url or uri, never input the same route object again
73
78
  * @param pushState if true pushed the state to the window.history
79
+ *
80
+ * ## Important
81
+ * Make sure a req always has the correct origin,
82
+ * `push` and `replace` will cause this function to throw an error
74
83
  */
75
- open(target: string | URL | Route | Request, pushState?: boolean): void;
84
+ open(req: Request): void;
76
85
  /**
77
86
  * Sets a route
78
87
  *
@@ -81,24 +90,25 @@ export default class InnerRouter {
81
90
  *
82
91
  * @param req
83
92
  */
84
- setRoute(req: Request): void;
93
+ setRoute(req: Request, preventOnRoute?: boolean): void;
85
94
  /**
86
- * This pushes the state of the route without triggering a currentRoute
87
- * or currentSiteId change
95
+ * This pushes a new route to the history
88
96
  *
89
- * You can use when using pagination for example change the route object
90
- * (search argument) and then call pushState
97
+ * @param req, never input the same route object again
91
98
  *
92
- * @param route, never input the same route object again
99
+ * ## Important
100
+ * Make sure the route has the correct origin
93
101
  */
94
- pushState(route: Route): void;
102
+ push(req: Request, preventOnRoute?: boolean): void;
95
103
  /**
96
- * This replaces the state of the route without triggering a currentRoute
97
- * or currentSiteId change
104
+ * This replaces the current route
105
+ *
106
+ * @param req, never input the same route object again
98
107
  *
99
- * @param route, never input the same route object again
108
+ * ## Important
109
+ * Make sure the route has the correct origin
100
110
  */
101
- replaceState(route: Route): void;
111
+ replace(req: Request): void;
102
112
  /**
103
113
  * Preload a url
104
114
  *
@@ -1 +1 @@
1
- {"version":3,"file":"InnerRouter.d.ts","sourceRoot":"","sources":["../../../../src/routing/InnerRouter.ts"],"names":[],"mappings":"AAAA,OAAO,IAAI,EAAE,EAAE,eAAe,EAAE,MAAM,WAAW,CAAC;AAClD,OAAO,OAAO,MAAM,cAAc,CAAC;AAEnC,OAAO,OAAsB,MAAM,cAAc,CAAC;AAClD,OAAO,KAAK,MAAM,YAAY,CAAC;AAE/B,MAAM,MAAM,eAAe,GAAG;IAC7B,kBAAkB,EAAE,OAAO,CAAC;CAC5B,CAAC;AAEF;;GAEG;AACH,MAAM,CAAC,OAAO,OAAO,WAAW;IAC/B,KAAK,EAAE,IAAI,EAAE,CAAC;IACd,KAAK,EAAE,KAAK,GAAG,IAAI,CAAC;IACpB,IAAI,EAAE,IAAI,CAAC;IACX,OAAO,EAAE,OAAO,CAAC;IACjB,kBAAkB,EAAE,OAAO,CAAC;IAC5B;;;OAGG;IACH,OAAO,EAAE,CAAC,KAAK,EAAE,OAAO,EAAE,IAAI,EAAE,IAAI,EAAE,aAAa,EAAE,MAAM,IAAI,KAAK,IAAI,CAAC;IACzE,SAAS,EAAE,CAAC,KAAK,EAAE,OAAO,EAAE,IAAI,EAAE,IAAI,KAAK,IAAI,CAAC;IAEhD,OAAO,CAAC,qBAAqB,CAAa;IAE1C;;;;;OAKG;gBACS,KAAK,EAAE,eAAe,EAAE,EAAE,IAAI,EAAE,eAAe;IAmB3D;;OAEG;IACH,UAAU;IAkBV;;OAEG;IACH,UAAU;IAEV;;;;;OAKG;IACH,gBAAgB,CAAC,UAAU,GAAE,MAAM,GAAG,IAAW,GAAG,IAAI;IAsCxD;;OAEG;IACH,WAAW,IAAI,IAAI;IAInB;;OAEG;IACH,QAAQ,CAAC,EAAE,EAAE,MAAM,GAAG,IAAI,GAAG,IAAI;IAIjC;;;;;OAKG;IACH,eAAe,CAAC,MAAM,EAAE,MAAM,GAAG,GAAG,GAAG,KAAK,GAAG,OAAO,GAAG,OAAO;IAqBhE;;;;;OAKG;IACH,YAAY,CAAC,OAAO,EAAE,GAAG,GAAG,KAAK;IA8BjC,MAAM;IA0FN;;;;;OAKG;IACH,IAAI,CAAC,MAAM,EAAE,MAAM,GAAG,GAAG,GAAG,KAAK,GAAG,OAAO,EAAE,SAAS,GAAE,OAAc;IAyCtE;;;;;;;OAOG;IACH,QAAQ,CAAC,GAAG,EAAE,OAAO;IAOrB;;;;;;;;OAQG;IACH,SAAS,CAAC,KAAK,EAAE,KAAK;IAYtB;;;;;OAKG;IACH,YAAY,CAAC,KAAK,EAAE,KAAK;IAYzB;;;;;;OAMG;IACH,OAAO,CAAC,MAAM,EAAE,MAAM,GAAG,GAAG,GAAG,KAAK,GAAG,OAAO;IAoB9C,QAAQ,CAAC,GAAG,EAAE,OAAO;CAkErB"}
1
+ {"version":3,"file":"InnerRouter.d.ts","sourceRoot":"","sources":["../../../../src/routing/InnerRouter.ts"],"names":[],"mappings":"AAAA,OAAO,IAAI,EAAE,EAAE,eAAe,EAAE,MAAM,WAAW,CAAC;AAClD,OAAO,OAAO,MAAM,cAAc,CAAC;AAEnC,OAAO,OAAO,EAAE,EAAa,cAAc,EAAE,MAAM,cAAc,CAAC;AAClE,OAAO,KAAK,MAAM,YAAY,CAAC;AAE/B,MAAM,MAAM,eAAe,GAAG;IAC7B,kBAAkB,EAAE,OAAO,CAAC;CAC5B,CAAC;AAEF;;GAEG;AACH,MAAM,CAAC,OAAO,OAAO,WAAW;IAC/B,KAAK,EAAE,IAAI,EAAE,CAAC;IACd;;;;;OAKG;IACH,KAAK,EAAE,KAAK,GAAG,IAAI,CAAC;IACpB,OAAO,EAAE,OAAO,CAAC;IACjB,kBAAkB,EAAE,OAAO,CAAC;IAC5B;;;OAGG;IACH,OAAO,EAAE,CAAC,KAAK,EAAE,OAAO,EAAE,aAAa,EAAE,MAAM,IAAI,KAAK,IAAI,CAAC;IAC7D,SAAS,EAAE,CAAC,KAAK,EAAE,OAAO,KAAK,IAAI,CAAC;IAEpC,OAAO,CAAC,qBAAqB,CAAa;IAE1C;;;;;OAKG;gBACS,KAAK,EAAE,eAAe,EAAE,EAAE,IAAI,EAAE,eAAe;IAkB3D;;OAEG;IACH,UAAU;IAaV;;OAEG;IACH,UAAU;IAEV;;;;OAIG;IACH,gBAAgB,CAAC,UAAU,GAAE,MAAM,GAAG,IAAW,GAAG,IAAI;IAsCxD;;OAEG;IACH,WAAW,IAAI,IAAI;IAInB;;OAEG;IACH,QAAQ,CAAC,EAAE,EAAE,MAAM,GAAG,IAAI,GAAG,IAAI;IAIjC;;;;;;OAMG;IACH,eAAe,CACd,MAAM,EAAE,MAAM,GAAG,GAAG,GAAG,KAAK,GAAG,OAAO,EACtC,IAAI,GAAE,cAAmB,GACvB,OAAO;IAwBV;;;;;OAKG;IACH,YAAY,CAAC,OAAO,EAAE,GAAG,GAAG,KAAK;IAgCjC,MAAM;IA6FN;;;;;;;;;OASG;IACH,IAAI,CAAC,GAAG,EAAE,OAAO;IAuCjB;;;;;;;OAOG;IACH,QAAQ,CAAC,GAAG,EAAE,OAAO,EAAE,cAAc,UAAQ;IAM7C;;;;;;;OAOG;IACH,IAAI,CAAC,GAAG,EAAE,OAAO,EAAE,cAAc,UAAQ;IAsBzC;;;;;;;OAOG;IACH,OAAO,CAAC,GAAG,EAAE,OAAO;IAsBpB;;;;;;OAMG;IACH,OAAO,CAAC,MAAM,EAAE,MAAM,GAAG,GAAG,GAAG,KAAK,GAAG,OAAO;IAW9C,QAAQ,CAAC,GAAG,EAAE,OAAO;CAsErB"}
@@ -7,8 +7,13 @@ import Route from './Route.js';
7
7
  */
8
8
  export default class InnerRouter {
9
9
  sites;
10
+ /**
11
+ * The current route
12
+ *
13
+ * ## Null
14
+ * It might be null on the first targetToRequest, open, and routeFromUrl call
15
+ */
10
16
  route;
11
- site;
12
17
  history;
13
18
  preloadOnMouseOver;
14
19
  /**
@@ -27,7 +32,6 @@ export default class InnerRouter {
27
32
  constructor(sites, opts) {
28
33
  this.sites = sites.map(s => new Site(s));
29
34
  this.route = null;
30
- this.site = this.defaultSite();
31
35
  // @ts-ignore
32
36
  this.history = import.meta.env.SSR
33
37
  ? new ServerHistory()
@@ -44,14 +48,11 @@ export default class InnerRouter {
44
48
  initClient() {
45
49
  this.listen();
46
50
  // let's first try to load from the state
47
- const route = this.targetToRequest(window.location.href);
48
- route._fillFromState(window.history.state);
49
- route.origin = 'init';
50
- if (route.search.get('x-craft-live-preview')) {
51
- route.origin = 'live-preview-init';
52
- }
51
+ const req = this.targetToRequest(window.location.href);
52
+ req._fillFromState(window.history.state);
53
+ req.origin = 'init';
53
54
  window.history.scrollRestoration = 'manual';
54
- this.open(route, false);
55
+ this.setRoute(req);
55
56
  }
56
57
  /**
57
58
  * Initializes the router when running on the server.
@@ -60,8 +61,7 @@ export default class InnerRouter {
60
61
  /**
61
62
  * Get a site and if possible use the accept lang header.
62
63
  *
63
- * @param {(string|null)} [acceptLang=null] Accept Language header.
64
- * @return {Site}
64
+ * @param acceptLang Accept Language header.
65
65
  */
66
66
  siteByAcceptLang(acceptLang = null) {
67
67
  if (!acceptLang)
@@ -102,7 +102,7 @@ export default class InnerRouter {
102
102
  * Get the default site
103
103
  */
104
104
  defaultSite() {
105
- return this.sites[0];
105
+ return this.sites.find(s => s.primary) ?? this.sites[0];
106
106
  }
107
107
  /**
108
108
  * Tries to get a site by it's id
@@ -111,15 +111,18 @@ export default class InnerRouter {
111
111
  return this.sites.find(s => s.id === id) ?? null;
112
112
  }
113
113
  /**
114
- * Resolve a url or Route and convert it to a Route
114
+ * Resolve a url or Route and convert it to a Request
115
115
  *
116
116
  * @param target
117
+ * @param opts, any option present will override the value in target
117
118
  * @return Returns null if the url does not match our host (the protocol get's ignored)
118
119
  */
119
- targetToRequest(target) {
120
+ targetToRequest(target, opts = {}) {
120
121
  if (typeof target === 'string') {
121
122
  if (target.startsWith('/')) {
122
- const site = this.site;
123
+ // todo should we use the language matching or throw if the route does not
124
+ // exists
125
+ const site = this.route?.site ?? this.defaultSite();
123
126
  target = new URL(site.uri + target, site.url);
124
127
  }
125
128
  else {
@@ -130,8 +133,9 @@ export default class InnerRouter {
130
133
  target = this.routeFromUrl(target);
131
134
  }
132
135
  if (!isRequest(target)) {
133
- return Request.fromRoute(target);
136
+ return Request.fromRoute(target, opts);
134
137
  }
138
+ target._updateOpts(opts);
135
139
  return target;
136
140
  }
137
141
  /**
@@ -161,7 +165,9 @@ export default class InnerRouter {
161
165
  continue;
162
166
  site = s;
163
167
  }
164
- route.site = site;
168
+ // todo should we throw if we can't find a site
169
+ // or use the site which matches the language
170
+ route.site = site ?? this.defaultSite();
165
171
  return route;
166
172
  }
167
173
  listen() {
@@ -177,11 +183,18 @@ export default class InnerRouter {
177
183
  if (!link.href.startsWith('http'))
178
184
  return;
179
185
  e.preventDefault();
180
- const route = this.routeFromUrl(link.href);
181
- if (this.route?.eq(route))
186
+ const req = this.targetToRequest(link.href, { origin: 'click' });
187
+ const routeEq = this.route && this.route.eqUrl(req) && this.route.eqSearch(req);
188
+ // the route is the same don't do anything
189
+ // or maybe scroll the page to the hash? todo
190
+ if (routeEq && this.route?.eqHash(req))
182
191
  return;
183
- route.origin = 'click';
184
- this.open(route);
192
+ // this means the hash did not match, so we wan't to just scroll but not load
193
+ // data
194
+ if (routeEq) {
195
+ req.disableLoadData = true;
196
+ }
197
+ this.open(req);
185
198
  });
186
199
  if (this.preloadOnMouseOver) {
187
200
  let currentMouseOver = null;
@@ -220,7 +233,7 @@ export default class InnerRouter {
220
233
  return;
221
234
  // use the latest state
222
235
  this.history.replaceState(this.route._toState());
223
- if (current.origin === 'live-preview-init') {
236
+ if (current.inLivePreview()) {
224
237
  sessionStorage.setItem('live-preview-scroll',
225
238
  // use the latest scrollY
226
239
  this.route.scrollY + '');
@@ -232,24 +245,26 @@ export default class InnerRouter {
232
245
  window.addEventListener('popstate', async (e) => {
233
246
  if (!('route' in e.state))
234
247
  return;
235
- const route = this.targetToRequest(window.location.href);
236
- route._fillFromState(e.state);
237
- route.origin = 'pop';
238
- // since the pop event replaced our state we can't replace the state
239
- // for the scrollY in our open call so we just clear the current
240
- // route since it is now already the new route
241
- this.route = null;
242
- this.open(route, false);
248
+ const req = this.targetToRequest(window.location.href);
249
+ req._fillFromState(e.state);
250
+ req.origin = 'pop';
251
+ this.setRoute(req);
243
252
  });
244
253
  }
245
254
  /**
246
- * Open's a route
255
+ * Open a new route
247
256
  *
248
257
  * @param route a route object or an url or uri, never input the same route object again
249
258
  * @param pushState if true pushed the state to the window.history
259
+ *
260
+ * ## Important
261
+ * Make sure a req always has the correct origin,
262
+ * `push` and `replace` will cause this function to throw an error
250
263
  */
251
- open(target, pushState = true) {
252
- const req = this.targetToRequest(target);
264
+ open(req) {
265
+ if (['push', 'replace'].includes(req.origin)) {
266
+ throw new Error('Do not use open with push or replace');
267
+ }
253
268
  const current = this.route;
254
269
  if (current) {
255
270
  // if the scrollY would still be updated we clear the timeout
@@ -270,18 +285,13 @@ export default class InnerRouter {
270
285
  if ((current && current.url.origin !== req.url.origin) ||
271
286
  // @ts-ignore
272
287
  import.meta.env.SSR) {
273
- this.history.open(req.url.href);
288
+ this.history.open(req);
274
289
  return;
275
290
  }
276
- if (pushState) {
277
- req.index = (current?.index ?? 0) + 1;
278
- this.onRoute(req, req.site ?? this.site, () => {
279
- this.pushState(req.toRoute());
280
- });
281
- }
282
- else {
283
- this.setRoute(req);
284
- }
291
+ req.index = (current?.index ?? 0) + 1;
292
+ this.onRoute(req, () => {
293
+ this.push(req, true);
294
+ });
285
295
  }
286
296
  /**
287
297
  * Sets a route
@@ -291,40 +301,56 @@ export default class InnerRouter {
291
301
  *
292
302
  * @param req
293
303
  */
294
- setRoute(req) {
304
+ setRoute(req, preventOnRoute = false) {
295
305
  this.route = req.toRoute();
296
- if (req.site)
297
- this.site = req.site;
298
- this.onRoute(req, this.site, () => { });
306
+ if (!preventOnRoute)
307
+ this.onRoute(req, () => { });
299
308
  }
300
309
  /**
301
- * This pushes the state of the route without triggering a currentRoute
302
- * or currentSiteId change
310
+ * This pushes a new route to the history
303
311
  *
304
- * You can use when using pagination for example change the route object
305
- * (search argument) and then call pushState
312
+ * @param req, never input the same route object again
306
313
  *
307
- * @param route, never input the same route object again
314
+ * ## Important
315
+ * Make sure the route has the correct origin
308
316
  */
309
- pushState(route) {
310
- const url = route.url;
311
- this.history.pushState(route._toState(), url.pathname + url.search + url.hash);
312
- this.route = route;
313
- if (route.site)
314
- this.site = route.site;
317
+ push(req, preventOnRoute = false) {
318
+ const url = req.url;
319
+ // todo a push should also store the previous scrollY
320
+ let nReq = req;
321
+ if (req.scrollY === null) {
322
+ // if there is no scrollY stored we store the current scrollY
323
+ // since a push does not cause a scroll top
324
+ // todo: probably should refactor something probably
325
+ // should not be here
326
+ nReq = req.clone();
327
+ nReq.scrollY = this.history.scrollY();
328
+ }
329
+ this.history.pushState(nReq._toState(), url.pathname + url.search + url.hash);
330
+ this.setRoute(req, preventOnRoute);
315
331
  }
316
332
  /**
317
- * This replaces the state of the route without triggering a currentRoute
318
- * or currentSiteId change
333
+ * This replaces the current route
334
+ *
335
+ * @param req, never input the same route object again
319
336
  *
320
- * @param route, never input the same route object again
337
+ * ## Important
338
+ * Make sure the route has the correct origin
321
339
  */
322
- replaceState(route) {
323
- const url = route.url;
324
- this.history.replaceState(route._toState(), url.pathname + url.search + url.hash);
325
- this.route = route;
326
- if (route.site)
327
- this.site = route.site;
340
+ replace(req) {
341
+ const url = req.url;
342
+ let nReq = req;
343
+ if (req.scrollY === null) {
344
+ // if there is no scrollY stored we store the current scrollY
345
+ // since a replace does not cause a scrollTo and we wan't
346
+ // history back to work as intended
347
+ // todo: probably should refactor something probably
348
+ // should not be here
349
+ nReq = req.clone();
350
+ nReq.scrollY = this.history.scrollY();
351
+ }
352
+ this.history.replaceState(nReq._toState(), url.pathname + url.search + url.hash);
353
+ this.setRoute(req);
328
354
  }
329
355
  /**
330
356
  * Preload a url
@@ -335,18 +361,11 @@ export default class InnerRouter {
335
361
  */
336
362
  preload(target) {
337
363
  const req = this.targetToRequest(target);
338
- // todo, don't think this makes any sense
339
- // if the domain of the current site is different than the domain of the
340
- // new site id does not make sense to preload
341
- if (this.site.url.origin !== req.url.origin) {
342
- return;
343
- }
344
364
  const current = this.route;
345
- const site = req.site ?? this.site;
346
365
  // if the origin matches, the route will be able to be load
347
366
  // so let's preload it
348
367
  if (current && current.url.origin === req.url.origin) {
349
- this.onPreload(req, site);
368
+ this.onPreload(req);
350
369
  }
351
370
  }
352
371
  domReady(req) {
@@ -356,7 +375,7 @@ export default class InnerRouter {
356
375
  let scrollTo = null;
357
376
  // if the route is a live preview init and we have a scrollY stored
358
377
  // scroll to that
359
- if (req.origin === 'live-preview-init') {
378
+ if (req.inLivePreview()) {
360
379
  const scrollY = sessionStorage.getItem('live-preview-scroll');
361
380
  if (scrollY) {
362
381
  scrollTo = {
@@ -386,6 +405,9 @@ export default class InnerRouter {
386
405
  behavior: 'instant',
387
406
  };
388
407
  }
408
+ // make sure push and replace don't cause a scroll if it is not intended
409
+ if (!scrollTo && (req.origin === 'push' || req.origin === 'replace'))
410
+ return;
389
411
  // scroll to the top if nothing else matches
390
412
  if (!scrollTo) {
391
413
  scrollTo = {
@@ -1,5 +1,4 @@
1
1
  import Request from './Request.js';
2
- import Site from './Site.js';
3
2
  export type PageLoaderOptions = {
4
3
  debugTiming: boolean;
5
4
  };
@@ -7,7 +6,7 @@ export type LoadResponse = {
7
6
  success: boolean;
8
7
  data: any;
9
8
  };
10
- export type LoadFn = (req: Request, site: Site, opts: LoadOptions) => Promise<any> | any;
9
+ export type LoadFn = (req: Request, opts: LoadOptions) => Promise<any> | any;
11
10
  export type LoadOptions = {
12
11
  setProgress: (num: number) => void;
13
12
  };
@@ -18,7 +17,7 @@ export default class PageLoader<More> {
18
17
  private debugTiming;
19
18
  private preloadedUrls;
20
19
  private loadingVersion;
21
- onLoaded: (resp: LoadResponse, req: Request, site: Site, more: More) => void;
20
+ onLoaded: (resp: LoadResponse, req: Request, more: More) => void;
22
21
  onProgress: (loading: boolean, progress?: number) => void;
23
22
  loadFn: LoadFn;
24
23
  /**
@@ -31,7 +30,7 @@ export default class PageLoader<More> {
31
30
  * Discard the current page load if one is happening
32
31
  */
33
32
  discard(): void;
34
- load(req: Request, site: Site, more: More): Promise<void>;
35
- preload(req: Request, site: Site): Promise<void>;
33
+ load(req: Request, more: More): Promise<void>;
34
+ preload(req: Request): Promise<void>;
36
35
  }
37
36
  //# sourceMappingURL=PageLoader.d.ts.map
@@ -1 +1 @@
1
- {"version":3,"file":"PageLoader.d.ts","sourceRoot":"","sources":["../../../../src/routing/PageLoader.ts"],"names":[],"mappings":"AAAA,OAAO,OAAO,MAAM,cAAc,CAAC;AACnC,OAAO,IAAI,MAAM,WAAW,CAAC;AAE7B,MAAM,MAAM,iBAAiB,GAAG;IAC/B,WAAW,EAAE,OAAO,CAAC;CACrB,CAAC;AAEF,MAAM,MAAM,YAAY,GAAG;IAC1B,OAAO,EAAE,OAAO,CAAC;IACjB,IAAI,EAAE,GAAG,CAAC;CACV,CAAC;AAEF,MAAM,MAAM,MAAM,GAAG,CACpB,GAAG,EAAE,OAAO,EACZ,IAAI,EAAE,IAAI,EACV,IAAI,EAAE,WAAW,KACb,OAAO,CAAC,GAAG,CAAC,GAAG,GAAG,CAAC;AAExB,MAAM,MAAM,WAAW,GAAG;IACzB,WAAW,EAAE,CAAC,GAAG,EAAE,MAAM,KAAK,IAAI,CAAC;CACnC,CAAC;AAEF;;GAEG;AACH,MAAM,CAAC,OAAO,OAAO,UAAU,CAAC,IAAI;IACnC,OAAO,CAAC,WAAW,CAAU;IAC7B,OAAO,CAAC,aAAa,CAAc;IAEnC,OAAO,CAAC,cAAc,CAAS;IAE/B,QAAQ,EAAE,CACT,IAAI,EAAE,YAAY,EAClB,GAAG,EAAE,OAAO,EACZ,IAAI,EAAE,IAAI,EACV,IAAI,EAAE,IAAI,KACN,IAAI,CAAC;IACV,UAAU,EAAE,CAAC,OAAO,EAAE,OAAO,EAAE,QAAQ,CAAC,EAAE,MAAM,KAAK,IAAI,CAAC;IAC1D,MAAM,EAAE,MAAM,CAAC;IAEf;;;;OAIG;gBACS,OAAO,EAAE,iBAAiB;IAWtC;;OAEG;IACH,OAAO;IAKD,IAAI,CAAC,GAAG,EAAE,OAAO,EAAE,IAAI,EAAE,IAAI,EAAE,IAAI,EAAE,IAAI;IAiCzC,OAAO,CAAC,GAAG,EAAE,OAAO,EAAE,IAAI,EAAE,IAAI;CActC"}
1
+ {"version":3,"file":"PageLoader.d.ts","sourceRoot":"","sources":["../../../../src/routing/PageLoader.ts"],"names":[],"mappings":"AAAA,OAAO,OAAO,MAAM,cAAc,CAAC;AAEnC,MAAM,MAAM,iBAAiB,GAAG;IAC/B,WAAW,EAAE,OAAO,CAAC;CACrB,CAAC;AAEF,MAAM,MAAM,YAAY,GAAG;IAC1B,OAAO,EAAE,OAAO,CAAC;IACjB,IAAI,EAAE,GAAG,CAAC;CACV,CAAC;AAEF,MAAM,MAAM,MAAM,GAAG,CAAC,GAAG,EAAE,OAAO,EAAE,IAAI,EAAE,WAAW,KAAK,OAAO,CAAC,GAAG,CAAC,GAAG,GAAG,CAAC;AAE7E,MAAM,MAAM,WAAW,GAAG;IACzB,WAAW,EAAE,CAAC,GAAG,EAAE,MAAM,KAAK,IAAI,CAAC;CACnC,CAAC;AAEF;;GAEG;AACH,MAAM,CAAC,OAAO,OAAO,UAAU,CAAC,IAAI;IACnC,OAAO,CAAC,WAAW,CAAU;IAC7B,OAAO,CAAC,aAAa,CAAc;IAEnC,OAAO,CAAC,cAAc,CAAS;IAE/B,QAAQ,EAAE,CAAC,IAAI,EAAE,YAAY,EAAE,GAAG,EAAE,OAAO,EAAE,IAAI,EAAE,IAAI,KAAK,IAAI,CAAC;IACjE,UAAU,EAAE,CAAC,OAAO,EAAE,OAAO,EAAE,QAAQ,CAAC,EAAE,MAAM,KAAK,IAAI,CAAC;IAC1D,MAAM,EAAE,MAAM,CAAC;IAEf;;;;OAIG;gBACS,OAAO,EAAE,iBAAiB;IAWtC;;OAEG;IACH,OAAO;IAKD,IAAI,CAAC,GAAG,EAAE,OAAO,EAAE,IAAI,EAAE,IAAI;IAiC7B,OAAO,CAAC,GAAG,EAAE,OAAO;CAc1B"}
@@ -28,7 +28,7 @@ export default class PageLoader {
28
28
  this.loadingVersion++;
29
29
  this.onProgress(false);
30
30
  }
31
- async load(req, site, more) {
31
+ async load(req, more) {
32
32
  this.onProgress(true);
33
33
  const version = ++this.loadingVersion;
34
34
  const startTime = this.debugTiming ? Date.now() : null;
@@ -39,7 +39,7 @@ export default class PageLoader {
39
39
  };
40
40
  const resp = { success: false, data: null };
41
41
  try {
42
- resp.data = await this.loadFn(req, site, { setProgress });
42
+ resp.data = await this.loadFn(req, { setProgress });
43
43
  resp.success = true;
44
44
  }
45
45
  catch (e) {
@@ -52,16 +52,16 @@ export default class PageLoader {
52
52
  if (this.loadingVersion !== version)
53
53
  return console.log('route changed quickly, ignoring response');
54
54
  this.onProgress(false);
55
- this.onLoaded(resp, req, site, more);
55
+ this.onLoaded(resp, req, more);
56
56
  }
57
57
  // you don't need to wait on this call
58
- async preload(req, site) {
58
+ async preload(req) {
59
59
  const url = req.url.origin + req.url.pathname;
60
60
  if (this.preloadedUrls.has(url))
61
61
  return;
62
62
  this.preloadedUrls.add(url);
63
63
  try {
64
- await this.loadFn(req, site, { setProgress: () => null });
64
+ await this.loadFn(req, { setProgress: () => null });
65
65
  }
66
66
  catch (_e) {
67
67
  console.log('preload failed');
@@ -9,6 +9,8 @@ export type RequestOptions = {
9
9
  index?: number;
10
10
  origin?: RouteOrigin;
11
11
  disableScroll?: boolean;
12
+ disableLoadData?: boolean;
13
+ statusCode?: number;
12
14
  };
13
15
  /**
14
16
  * A Request is a Route with some extra options
@@ -21,16 +23,25 @@ export default class Request extends Route {
21
23
  * @default false
22
24
  */
23
25
  disableScroll: boolean;
26
+ /**
27
+ * Disable loading data
28
+ * @default false
29
+ */
30
+ disableLoadData: boolean;
31
+ /**
32
+ * The Status code that should be returned for a redirect
33
+ */
34
+ statusCode: number | null;
24
35
  /** @hidden */
25
36
  _renderBarrier: RenderBarrier;
26
37
  /**
27
38
  * Create a new Request
28
39
  */
29
- constructor(url: string | URL, site: Site | null, opts?: RequestOptions);
40
+ constructor(url: string | URL, site: Site, opts?: RequestOptions);
30
41
  /**
31
42
  * Create a Request from a Route
32
43
  */
33
- static fromRoute(route: Route): Request;
44
+ static fromRoute(route: Route, opts?: RequestOptions): Request;
34
45
  /**
35
46
  * With delayRender you can make sure that the render waits
36
47
  * until you are ready. This is useful for building page transitions.
@@ -68,6 +79,8 @@ export default class Request extends Route {
68
79
  * Create a Route from the Request
69
80
  */
70
81
  toRoute(): Route;
82
+ /** @hidden */
83
+ _updateOpts(opts?: RequestOptions): void;
71
84
  }
72
85
  export declare function isRequest(req: any): req is Request;
73
86
  declare class RenderBarrier {
@@ -1 +1 @@
1
- {"version":3,"file":"Request.d.ts","sourceRoot":"","sources":["../../../../src/routing/Request.ts"],"names":[],"mappings":"AAAA,OAAO,EAAE,OAAO,EAAE,MAAM,iBAAiB,CAAC;AAC1C,OAAO,KAAK,EAAE,EAAE,WAAW,EAAE,MAAM,YAAY,CAAC;AAChD,OAAO,IAAI,MAAM,WAAW,CAAC;AAE7B;;GAEG;AACH,MAAM,MAAM,cAAc,GAAG;IAC5B,OAAO,CAAC,EAAE,MAAM,CAAC;IACjB,KAAK,CAAC,EAAE,MAAM,CAAC;IACf,MAAM,CAAC,EAAE,WAAW,CAAC;IACrB,aAAa,CAAC,EAAE,OAAO,CAAC;CACxB,CAAC;AAEF;;;;GAIG;AACH,MAAM,CAAC,OAAO,OAAO,OAAQ,SAAQ,KAAK;IACzC;;;OAGG;IACH,aAAa,EAAE,OAAO,CAAC;IAEvB,cAAc;IACd,cAAc,EAAE,aAAa,CAAC;IAE9B;;OAEG;gBAEF,GAAG,EAAE,MAAM,GAAG,GAAG,EACjB,IAAI,EAAE,IAAI,GAAG,IAAI,EACjB,IAAI,GAAE,cAAmB;IAQ1B;;OAEG;IACH,MAAM,CAAC,SAAS,CAAC,KAAK,EAAE,KAAK;IAQ7B;;;;;;;;;;;;;;;;;;;;;;;;;;;OA2BG;IACH,WAAW,IAAI,WAAW;IAI1B;;OAEG;IACH,KAAK;IASL;;OAEG;IACH,OAAO;CAOP;AAED,wBAAgB,SAAS,CAAC,GAAG,EAAE,GAAG,GAAG,GAAG,IAAI,OAAO,CAElD;AAED,cAAM,aAAa;IAClB,KAAK,EAAE,OAAO,CAAC,OAAO,CAAC,CAAC;IACxB,SAAS,EAAE,OAAO,CAAC;IACnB,IAAI,EAAE,WAAW,CAAC;;IAQlB,MAAM,IAAI,OAAO;IAIjB,GAAG,IAAI,WAAW;IAclB,cAAc;IACd,MAAM;IAQN,cAAc;IACd,KAAK,IAAI,OAAO,CAAC,OAAO,CAAC;CAGzB;AAED;;GAEG;AACH,MAAM,MAAM,WAAW,GAAG;IACzB;;;;;OAKG;IACH,KAAK,EAAE,MAAM,OAAO,CAAC,OAAO,CAAC,CAAC;IAE9B;;OAEG;IACH,MAAM,EAAE,MAAM,IAAI,CAAC;CACnB,CAAC"}
1
+ {"version":3,"file":"Request.d.ts","sourceRoot":"","sources":["../../../../src/routing/Request.ts"],"names":[],"mappings":"AAAA,OAAO,EAAE,OAAO,EAAE,MAAM,iBAAiB,CAAC;AAC1C,OAAO,KAAK,EAAE,EAAE,WAAW,EAAE,MAAM,YAAY,CAAC;AAChD,OAAO,IAAI,MAAM,WAAW,CAAC;AAE7B;;GAEG;AACH,MAAM,MAAM,cAAc,GAAG;IAC5B,OAAO,CAAC,EAAE,MAAM,CAAC;IACjB,KAAK,CAAC,EAAE,MAAM,CAAC;IACf,MAAM,CAAC,EAAE,WAAW,CAAC;IACrB,aAAa,CAAC,EAAE,OAAO,CAAC;IACxB,eAAe,CAAC,EAAE,OAAO,CAAC;IAC1B,UAAU,CAAC,EAAE,MAAM,CAAC;CACpB,CAAC;AAEF;;;;GAIG;AACH,MAAM,CAAC,OAAO,OAAO,OAAQ,SAAQ,KAAK;IACzC;;;OAGG;IACH,aAAa,EAAE,OAAO,CAAC;IAEvB;;;OAGG;IACH,eAAe,EAAE,OAAO,CAAC;IAEzB;;OAEG;IACH,UAAU,EAAE,MAAM,GAAG,IAAI,CAAC;IAE1B,cAAc;IACd,cAAc,EAAE,aAAa,CAAC;IAE9B;;OAEG;gBACS,GAAG,EAAE,MAAM,GAAG,GAAG,EAAE,IAAI,EAAE,IAAI,EAAE,IAAI,GAAE,cAAmB;IASpE;;OAEG;IACH,MAAM,CAAC,SAAS,CAAC,KAAK,EAAE,KAAK,EAAE,IAAI,GAAE,cAAmB;IASxD;;;;;;;;;;;;;;;;;;;;;;;;;;;OA2BG;IACH,WAAW,IAAI,WAAW;IAI1B;;OAEG;IACH,KAAK;IAUL;;OAEG;IACH,OAAO;IAQP,cAAc;IACd,WAAW,CAAC,IAAI,GAAE,cAAmB;CAOrC;AAED,wBAAgB,SAAS,CAAC,GAAG,EAAE,GAAG,GAAG,GAAG,IAAI,OAAO,CAElD;AAED,cAAM,aAAa;IAClB,KAAK,EAAE,OAAO,CAAC,OAAO,CAAC,CAAC;IACxB,SAAS,EAAE,OAAO,CAAC;IACnB,IAAI,EAAE,WAAW,CAAC;;IAQlB,MAAM,IAAI,OAAO;IAIjB,GAAG,IAAI,WAAW;IAclB,cAAc;IACd,MAAM;IAQN,cAAc;IACd,KAAK,IAAI,OAAO,CAAC,OAAO,CAAC;CAGzB;AAED;;GAEG;AACH,MAAM,MAAM,WAAW,GAAG;IACzB;;;;;OAKG;IACH,KAAK,EAAE,MAAM,OAAO,CAAC,OAAO,CAAC,CAAC;IAE9B;;OAEG;IACH,MAAM,EAAE,MAAM,IAAI,CAAC;CACnB,CAAC"}
@@ -11,6 +11,15 @@ export default class Request extends Route {
11
11
  * @default false
12
12
  */
13
13
  disableScroll;
14
+ /**
15
+ * Disable loading data
16
+ * @default false
17
+ */
18
+ disableLoadData;
19
+ /**
20
+ * The Status code that should be returned for a redirect
21
+ */
22
+ statusCode;
14
23
  /** @hidden */
15
24
  _renderBarrier;
16
25
  /**
@@ -19,16 +28,19 @@ export default class Request extends Route {
19
28
  constructor(url, site, opts = {}) {
20
29
  super(url, site, opts);
21
30
  this.disableScroll = opts.disableScroll ?? false;
31
+ this.disableLoadData = opts.disableLoadData ?? false;
32
+ this.statusCode = opts.statusCode ?? null;
22
33
  this._renderBarrier = new RenderBarrier();
23
34
  }
24
35
  /**
25
36
  * Create a Request from a Route
26
37
  */
27
- static fromRoute(route) {
38
+ static fromRoute(route, opts = {}) {
28
39
  return new Request(route.url.href, route.site, {
29
40
  scrollY: route.scrollY ?? undefined,
30
41
  index: route.index,
31
42
  origin: route.origin,
43
+ ...opts,
32
44
  });
33
45
  }
34
46
  /**
@@ -71,6 +83,7 @@ export default class Request extends Route {
71
83
  index: this.index,
72
84
  origin: this.origin,
73
85
  disableScroll: this.disableScroll,
86
+ statusCode: this.statusCode ?? undefined,
74
87
  });
75
88
  }
76
89
  /**
@@ -83,6 +96,14 @@ export default class Request extends Route {
83
96
  origin: this.origin,
84
97
  });
85
98
  }
99
+ /** @hidden */
100
+ _updateOpts(opts = {}) {
101
+ this.scrollY = opts.scrollY ?? this.scrollY;
102
+ this.index = opts.index ?? this.index;
103
+ this.origin = opts.origin ?? this.origin;
104
+ this.disableScroll = opts.disableScroll ?? this.disableScroll;
105
+ this.statusCode = opts.statusCode ?? this.statusCode;
106
+ }
86
107
  }
87
108
  export function isRequest(req) {
88
109
  return typeof req === 'object' && req !== null && req instanceof Request;