|
1 | 1 | /* eslint-disable dci-lint/atomic-role-binding */ |
2 | 2 | import type { TaintedFields, SuperFormValidated, SuperValidated } from '$lib/superValidate.js'; |
3 | | -import type { ActionResult, Page, SubmitFunction } from '@sveltejs/kit'; |
| 3 | +import type { ActionResult, BeforeNavigate, Page, SubmitFunction } from '@sveltejs/kit'; |
4 | 4 | import { |
5 | 5 | derived, |
6 | 6 | get, |
@@ -1353,50 +1353,53 @@ export function superForm< |
1353 | 1353 |
|
1354 | 1354 | ///// Store subscriptions /////////////////////////////////////////////////// |
1355 | 1355 |
|
1356 | | - if (browser) { |
1357 | | - // Tainted check |
1358 | | - const defaultMessage = 'Leave page? Changes that you made may not be saved.'; |
1359 | | - let forceRedirection = false; |
1360 | | - beforeNavigate(async (nav) => { |
1361 | | - if (options.taintedMessage && !Data.submitting && !forceRedirection) { |
1362 | | - if (Tainted_isTainted()) { |
1363 | | - const { taintedMessage } = options; |
1364 | | - const isTaintedFunction = typeof taintedMessage === 'function'; |
1365 | | - |
1366 | | - // As beforeNavigate does not support Promise, we cancel the redirection until the promise resolve |
1367 | | - // if it's a custom function |
1368 | | - if (isTaintedFunction) nav.cancel(); |
1369 | | - // Does not display any dialog on page refresh or closing tab, will use default browser behaviour |
1370 | | - if (nav.type === 'leave') return; |
1371 | | - |
1372 | | - const message = |
1373 | | - isTaintedFunction || taintedMessage === true ? defaultMessage : taintedMessage; |
1374 | | - |
1375 | | - let shouldRedirect; |
1376 | | - try { |
1377 | | - // - rejected => shouldRedirect = false |
1378 | | - // - resolved with false => shouldRedirect = false |
1379 | | - // - resolved with true => shouldRedirect = true |
1380 | | - shouldRedirect = isTaintedFunction ? await taintedMessage() : window.confirm(message); |
1381 | | - } catch { |
1382 | | - shouldRedirect = false; |
1383 | | - } |
| 1356 | + // Tainted check |
| 1357 | + const defaultMessage = 'Leave page? Changes that you made may not be saved.'; |
| 1358 | + let forceRedirection = false; |
| 1359 | + |
| 1360 | + async function taintedCheck(nav: BeforeNavigate) { |
| 1361 | + if (options.taintedMessage && !Data.submitting && !forceRedirection) { |
| 1362 | + if (Tainted_isTainted()) { |
| 1363 | + const { taintedMessage } = options; |
| 1364 | + const isTaintedFunction = typeof taintedMessage === 'function'; |
| 1365 | + |
| 1366 | + // As beforeNavigate does not support Promise, we cancel the redirection until the promise resolve |
| 1367 | + // if it's a custom function |
| 1368 | + if (isTaintedFunction) nav.cancel(); |
| 1369 | + // Does not display any dialog on page refresh or closing tab, will use default browser behaviour |
| 1370 | + if (nav.type === 'leave') return; |
| 1371 | + |
| 1372 | + const message = |
| 1373 | + isTaintedFunction || taintedMessage === true ? defaultMessage : taintedMessage; |
| 1374 | + |
| 1375 | + let shouldRedirect; |
| 1376 | + try { |
| 1377 | + // - rejected => shouldRedirect = false |
| 1378 | + // - resolved with false => shouldRedirect = false |
| 1379 | + // - resolved with true => shouldRedirect = true |
| 1380 | + shouldRedirect = isTaintedFunction ? await taintedMessage() : window.confirm(message); |
| 1381 | + } catch { |
| 1382 | + shouldRedirect = false; |
| 1383 | + } |
1384 | 1384 |
|
1385 | | - if (shouldRedirect && nav.to) { |
1386 | | - try { |
1387 | | - forceRedirection = true; |
1388 | | - await goto(nav.to.url, { ...nav.to.params }); |
1389 | | - return; |
1390 | | - } finally { |
1391 | | - // Reset forceRedirection for multiple-tainted purpose |
1392 | | - forceRedirection = false; |
1393 | | - } |
1394 | | - } else if (!shouldRedirect && !isTaintedFunction) { |
1395 | | - nav.cancel(); |
| 1385 | + if (shouldRedirect && nav.to) { |
| 1386 | + try { |
| 1387 | + forceRedirection = true; |
| 1388 | + await goto(nav.to.url, { ...nav.to.params }); |
| 1389 | + return; |
| 1390 | + } finally { |
| 1391 | + // Reset forceRedirection for multiple-tainted purpose |
| 1392 | + forceRedirection = false; |
1396 | 1393 | } |
| 1394 | + } else if (!shouldRedirect && !isTaintedFunction) { |
| 1395 | + nav.cancel(); |
1397 | 1396 | } |
1398 | 1397 | } |
1399 | | - }); |
| 1398 | + } |
| 1399 | + } |
| 1400 | + |
| 1401 | + if (browser) { |
| 1402 | + beforeNavigate(taintedCheck); |
1400 | 1403 |
|
1401 | 1404 | // Need to subscribe to catch page invalidation. |
1402 | 1405 | Unsubscriptions_add( |
|
0 commit comments