1
1
import { writable } from 'svelte/store' ;
2
2
import App from '@sapper/internal/App.svelte' ;
3
- import { Query } from '@sapper/internal/shared' ;
3
+ import {
4
+ extract_query ,
5
+ init ,
6
+ load_current_page ,
7
+ select_target
8
+ } from './router' ;
4
9
import {
5
10
DOMComponentLoader ,
6
11
DOMComponentModule ,
7
12
ErrorComponent ,
8
- ignore ,
9
13
components ,
10
- root_comp ,
11
- routes
14
+ root_comp
12
15
} from '@sapper/internal/manifest-client' ;
13
16
import {
14
17
HydratedTarget ,
15
18
Target ,
16
- ScrollPosition ,
17
19
Redirect ,
18
20
Page
19
21
} from './types' ;
@@ -71,69 +73,23 @@ export function set_target(element) {
71
73
target = element ;
72
74
}
73
75
74
- export let uid = 1 ;
75
- export function set_uid ( n ) {
76
- uid = n ;
77
- }
76
+ export default function start ( opts : {
77
+ target : Node
78
+ } ) : Promise < void > {
79
+ set_target ( opts . target ) ;
78
80
79
- export let cid : number ;
80
- export function set_cid ( n ) {
81
- cid = n ;
82
- }
81
+ init ( initial_data . baseUrl , handle_target ) ;
83
82
84
- const _history = typeof history !== 'undefined' ? history : {
85
- pushState : ( state : any , title : string , href : string ) => { } ,
86
- replaceState : ( state : any , title : string , href : string ) => { } ,
87
- scrollRestoration : ''
88
- } ;
89
- export { _history as history } ;
90
-
91
- export const scroll_history : Record < string , ScrollPosition > = { } ;
92
-
93
- export function extract_query ( search : string ) {
94
- const query = Object . create ( null ) ;
95
- if ( search . length > 0 ) {
96
- search . slice ( 1 ) . split ( '&' ) . forEach ( searchParam => {
97
- const [ , key , value = '' ] = / ( [ ^ = ] * ) (?: = ( .* ) ) ? / . exec ( decodeURIComponent ( searchParam . replace ( / \+ / g, ' ' ) ) ) ;
98
- if ( typeof query [ key ] === 'string' ) query [ key ] = [ < string > query [ key ] ] ;
99
- if ( typeof query [ key ] === 'object' ) ( query [ key ] as string [ ] ) . push ( value ) ;
100
- else query [ key ] = value ;
83
+ if ( initial_data . error ) {
84
+ return Promise . resolve ( ) . then ( ( ) => {
85
+ return handle_error ( new URL ( location . href ) ) ;
101
86
} ) ;
102
87
}
103
- return query ;
104
- }
105
-
106
- export function select_target ( url : URL ) : Target {
107
- if ( url . origin !== location . origin ) return null ;
108
- if ( ! url . pathname . startsWith ( initial_data . baseUrl ) ) return null ;
109
-
110
- let path = url . pathname . slice ( initial_data . baseUrl . length ) ;
111
-
112
- if ( path === '' ) {
113
- path = '/' ;
114
- }
115
88
116
- // avoid accidental clashes between server routes and page routes
117
- if ( ignore . some ( pattern => pattern . test ( path ) ) ) return ;
118
-
119
- for ( let i = 0 ; i < routes . length ; i += 1 ) {
120
- const route = routes [ i ] ;
121
-
122
- const match = route . pattern . exec ( path ) ;
123
-
124
- if ( match ) {
125
- const query : Query = extract_query ( url . search ) ;
126
- const part = route . parts [ route . parts . length - 1 ] ;
127
- const params = part . params ? part . params ( match ) : { } ;
128
-
129
- const page = { host : location . host , path, query, params } ;
130
-
131
- return { href : url . href , route, match, page } ;
132
- }
133
- }
89
+ return load_current_page ( ) ;
134
90
}
135
91
136
- export function handle_error ( url : URL ) {
92
+ function handle_error ( url : URL ) {
137
93
const { host, pathname, search } = location ;
138
94
const { session, preloaded, status, error } = initial_data ;
139
95
@@ -162,29 +118,7 @@ export function handle_error(url: URL) {
162
118
render ( [ ] , props , { host, path : pathname , query, params : { } } ) ;
163
119
}
164
120
165
- export function scroll_state ( ) {
166
- return {
167
- x : pageXOffset ,
168
- y : pageYOffset
169
- } ;
170
- }
171
-
172
- export async function navigate ( dest : Target , id : number , noscroll ?: boolean , hash ?: string ) : Promise < any > {
173
- if ( id ) {
174
- // popstate or initial navigation
175
- cid = id ;
176
- } else {
177
- const current_scroll = scroll_state ( ) ;
178
-
179
- // clicked on a link. preserve scroll state
180
- scroll_history [ cid ] = current_scroll ;
181
-
182
- id = cid = ++ uid ;
183
- scroll_history [ cid ] = noscroll ? current_scroll : { x : 0 , y : 0 } ;
184
- }
185
-
186
- cid = id ;
187
-
121
+ async function handle_target ( dest : Target ) : Promise < void > {
188
122
if ( root_component ) stores . preloading . set ( true ) ;
189
123
190
124
const loaded = prefetching && prefetching . href === dest . href ?
@@ -204,28 +138,6 @@ export async function navigate(dest: Target, id: number, noscroll?: boolean, has
204
138
const { props, branch } = loaded_result ;
205
139
await render ( branch , props , dest . page ) ;
206
140
}
207
- if ( document . activeElement && ( document . activeElement instanceof HTMLElement ) ) document . activeElement . blur ( ) ;
208
-
209
- if ( ! noscroll ) {
210
- let scroll = scroll_history [ id ] ;
211
-
212
- if ( hash ) {
213
- // scroll is an element id (from a hash), we need to compute y.
214
- const deep_linked = document . getElementById ( hash . slice ( 1 ) ) ;
215
-
216
- if ( deep_linked ) {
217
- scroll = {
218
- x : 0 ,
219
- y : deep_linked . getBoundingClientRect ( ) . top + scrollY
220
- } ;
221
- }
222
- }
223
-
224
- scroll_history [ cid ] = scroll ;
225
- if ( scroll ) {
226
- redirect ? scrollTo ( 0 , 0 ) : scrollTo ( scroll . x , scroll . y ) ;
227
- }
228
- }
229
141
}
230
142
231
143
async function render ( branch : any [ ] , props : any , page : Page ) {
0 commit comments