elm-pages 3.0.0-beta.3 → 3.0.0-beta.31
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/README.md +10 -1
- package/codegen/{elm-pages-codegen.js → elm-pages-codegen.cjs} +2864 -2589
- package/generator/dead-code-review/elm-stuff/tests-0.19.1/elm-stuff/0.19.1/Pages-Review-DeadCodeEliminateData.elmi +0 -0
- package/generator/dead-code-review/elm-stuff/tests-0.19.1/elm-stuff/0.19.1/Pages-Review-DeadCodeEliminateData.elmo +0 -0
- package/generator/dead-code-review/elm-stuff/tests-0.19.1/elm-stuff/0.19.1/Pages-Review-DeadCodeEliminateDataTest.elmo +0 -0
- package/generator/dead-code-review/elm-stuff/tests-0.19.1/elm-stuff/0.19.1/d.dat +0 -0
- package/generator/dead-code-review/elm-stuff/tests-0.19.1/elm-stuff/0.19.1/i.dat +0 -0
- package/generator/dead-code-review/elm-stuff/tests-0.19.1/elm-stuff/0.19.1/o.dat +0 -0
- package/generator/dead-code-review/elm-stuff/tests-0.19.1/elm.json +1 -1
- package/generator/dead-code-review/elm-stuff/tests-0.19.1/js/Reporter.elm.js +1447 -342
- package/generator/dead-code-review/elm-stuff/tests-0.19.1/js/Runner.elm.js +16458 -13724
- package/generator/dead-code-review/elm-stuff/tests-0.19.1/js/node_runner.js +1 -1
- package/generator/dead-code-review/elm-stuff/tests-0.19.1/js/node_supervisor.js +4 -4
- package/generator/dead-code-review/elm.json +9 -7
- package/generator/dead-code-review/src/Pages/Review/DeadCodeEliminateData.elm +59 -10
- package/generator/dead-code-review/tests/Pages/Review/DeadCodeEliminateDataTest.elm +52 -36
- package/generator/review/elm-stuff/tests-0.19.1/elm-stuff/0.19.1/Pages-Internal-RoutePattern.elmi +0 -0
- package/generator/review/elm-stuff/tests-0.19.1/elm-stuff/0.19.1/Pages-Internal-RoutePattern.elmo +0 -0
- package/generator/review/elm-stuff/tests-0.19.1/elm-stuff/0.19.1/Pages-Review-NoContractViolations.elmi +0 -0
- package/generator/review/elm-stuff/tests-0.19.1/elm-stuff/0.19.1/Pages-Review-NoContractViolations.elmo +0 -0
- package/generator/review/elm-stuff/tests-0.19.1/elm-stuff/0.19.1/d.dat +0 -0
- package/generator/review/elm-stuff/tests-0.19.1/elm-stuff/0.19.1/i.dat +0 -0
- package/generator/review/elm-stuff/tests-0.19.1/elm-stuff/0.19.1/o.dat +0 -0
- package/generator/review/elm-stuff/tests-0.19.1/elm.json +1 -1
- package/generator/review/elm-stuff/tests-0.19.1/js/Reporter.elm.js +1447 -342
- package/generator/review/elm-stuff/tests-0.19.1/js/Runner.elm.js +24542 -21748
- package/generator/review/elm-stuff/tests-0.19.1/js/node_runner.js +1 -1
- package/generator/review/elm-stuff/tests-0.19.1/js/node_supervisor.js +4 -4
- package/generator/review/elm.json +10 -10
- package/generator/src/RouteBuilder.elm +113 -107
- package/generator/src/SharedTemplate.elm +3 -2
- package/generator/src/SiteConfig.elm +3 -2
- package/generator/src/basepath-middleware.js +3 -3
- package/generator/src/build.js +125 -88
- package/generator/src/cli.js +273 -88
- package/generator/src/codegen.js +29 -27
- package/generator/src/compatibility-key.js +3 -0
- package/generator/src/compile-elm.js +43 -26
- package/generator/src/config.js +39 -0
- package/generator/src/copy-dir.js +2 -2
- package/generator/src/dev-server.js +150 -133
- package/generator/src/dir-helpers.js +9 -26
- package/generator/src/elm-codegen.js +5 -4
- package/generator/src/elm-file-constants.js +2 -3
- package/generator/src/error-formatter.js +12 -11
- package/generator/src/file-helpers.js +3 -4
- package/generator/src/generate-template-module-connector.js +23 -22
- package/generator/src/init.js +9 -8
- package/generator/src/pre-render-html.js +39 -28
- package/generator/src/render-test.js +109 -0
- package/generator/src/render-worker.js +25 -28
- package/generator/src/render.js +320 -142
- package/generator/src/request-cache.js +252 -163
- package/generator/src/resolve-elm-module.js +63 -0
- package/generator/src/rewrite-client-elm-json.js +6 -5
- package/generator/src/rewrite-elm-json-help.js +56 -0
- package/generator/src/rewrite-elm-json.js +17 -7
- package/generator/src/route-codegen-helpers.js +16 -31
- package/generator/src/seo-renderer.js +12 -7
- package/generator/src/vite-utils.js +77 -0
- package/generator/static-code/hmr.js +79 -13
- package/generator/template/app/Api.elm +6 -5
- package/generator/template/app/Effect.elm +123 -0
- package/generator/template/app/ErrorPage.elm +37 -6
- package/generator/template/app/Route/Index.elm +17 -10
- package/generator/template/app/Shared.elm +24 -47
- package/generator/template/app/Site.elm +19 -6
- package/generator/template/app/View.elm +1 -8
- package/generator/template/elm-tooling.json +0 -3
- package/generator/template/elm.json +32 -24
- package/generator/template/package.json +10 -4
- package/package.json +29 -27
- package/src/ApiRoute.elm +199 -61
- package/src/BackendTask/Custom.elm +325 -0
- package/src/BackendTask/Env.elm +90 -0
- package/src/{DataSource → BackendTask}/File.elm +128 -43
- package/src/{DataSource → BackendTask}/Glob.elm +136 -125
- package/src/BackendTask/Http.elm +673 -0
- package/src/{DataSource → BackendTask}/Internal/Glob.elm +1 -1
- package/src/BackendTask/Internal/Request.elm +28 -0
- package/src/BackendTask/Random.elm +79 -0
- package/src/BackendTask/Time.elm +47 -0
- package/src/BackendTask.elm +537 -0
- package/src/FatalError.elm +89 -0
- package/src/Form/Field.elm +21 -9
- package/src/Form/FieldView.elm +94 -14
- package/src/Form.elm +275 -400
- package/src/Head.elm +237 -7
- package/src/HtmlPrinter.elm +7 -3
- package/src/Internal/ApiRoute.elm +7 -5
- package/src/PageServerResponse.elm +6 -1
- package/src/Pages/FormState.elm +6 -5
- package/src/Pages/GeneratorProgramConfig.elm +15 -0
- package/src/Pages/Internal/FatalError.elm +5 -0
- package/src/Pages/Internal/Form.elm +21 -1
- package/src/Pages/{Msg.elm → Internal/Msg.elm} +26 -16
- package/src/Pages/Internal/Platform/Cli.elm +598 -763
- package/src/Pages/Internal/Platform/CompatibilityKey.elm +6 -0
- package/src/Pages/Internal/Platform/Effect.elm +1 -2
- package/src/Pages/Internal/Platform/GeneratorApplication.elm +373 -0
- package/src/Pages/Internal/Platform/StaticResponses.elm +73 -270
- package/src/Pages/Internal/Platform/ToJsPayload.elm +4 -7
- package/src/Pages/Internal/Platform.elm +216 -102
- package/src/Pages/Internal/Script.elm +17 -0
- package/src/Pages/Internal/StaticHttpBody.elm +35 -1
- package/src/Pages/Manifest.elm +29 -4
- package/src/Pages/PageUrl.elm +23 -9
- package/src/Pages/ProgramConfig.elm +14 -10
- package/src/Pages/Script.elm +109 -0
- package/src/Pages/SiteConfig.elm +3 -2
- package/src/Pages/StaticHttp/Request.elm +2 -2
- package/src/Pages/StaticHttpRequest.elm +23 -98
- package/src/PagesMsg.elm +92 -0
- package/src/Path.elm +16 -19
- package/src/QueryParams.elm +21 -172
- package/src/RequestsAndPending.elm +8 -19
- package/src/Result/Extra.elm +26 -0
- package/src/Scaffold/Form.elm +560 -0
- package/src/Scaffold/Route.elm +1388 -0
- package/src/Server/Request.elm +43 -37
- package/src/Server/Session.elm +62 -42
- package/src/Server/SetCookie.elm +12 -4
- package/src/Test/Html/Internal/ElmHtml/ToString.elm +8 -9
- package/src/DataSource/Env.elm +0 -38
- package/src/DataSource/Http.elm +0 -446
- package/src/DataSource/Internal/Request.elm +0 -20
- package/src/DataSource/Port.elm +0 -90
- package/src/DataSource.elm +0 -538
- package/src/Pages/Generate.elm +0 -800
|
@@ -31,13 +31,14 @@ import Pages.ContentCache as ContentCache
|
|
|
31
31
|
import Pages.Fetcher
|
|
32
32
|
import Pages.Flags
|
|
33
33
|
import Pages.FormState
|
|
34
|
+
import Pages.Internal.Msg
|
|
34
35
|
import Pages.Internal.NotFoundReason exposing (NotFoundReason)
|
|
35
36
|
import Pages.Internal.ResponseSketch as ResponseSketch exposing (ResponseSketch)
|
|
36
37
|
import Pages.Internal.String as String
|
|
37
|
-
import Pages.Msg
|
|
38
38
|
import Pages.ProgramConfig exposing (ProgramConfig)
|
|
39
39
|
import Pages.StaticHttpRequest as StaticHttpRequest
|
|
40
40
|
import Pages.Transition
|
|
41
|
+
import PagesMsg exposing (PagesMsg)
|
|
41
42
|
import Path exposing (Path)
|
|
42
43
|
import QueryParams
|
|
43
44
|
import Task
|
|
@@ -45,11 +46,6 @@ import Time
|
|
|
45
46
|
import Url exposing (Url)
|
|
46
47
|
|
|
47
48
|
|
|
48
|
-
type Transition
|
|
49
|
-
= Loading Int Path
|
|
50
|
-
| Submitting FormData
|
|
51
|
-
|
|
52
|
-
|
|
53
49
|
{-| -}
|
|
54
50
|
type alias Program userModel userMsg pageData actionData sharedData errorPage =
|
|
55
51
|
Platform.Program Flags (Model userModel pageData actionData sharedData) (Msg userMsg pageData actionData sharedData errorPage)
|
|
@@ -58,7 +54,7 @@ type alias Program userModel userMsg pageData actionData sharedData errorPage =
|
|
|
58
54
|
mainView :
|
|
59
55
|
ProgramConfig userMsg userModel route pageData actionData sharedData effect (Msg userMsg pageData actionData sharedData errorPage) errorPage
|
|
60
56
|
-> Model userModel pageData actionData sharedData
|
|
61
|
-
-> { title : String, body : List (Html (
|
|
57
|
+
-> { title : String, body : List (Html (PagesMsg userMsg)) }
|
|
62
58
|
mainView config model =
|
|
63
59
|
case model.notFound of
|
|
64
60
|
Just info ->
|
|
@@ -230,7 +226,7 @@ init config flags url key =
|
|
|
230
226
|
, host = url.host
|
|
231
227
|
, port_ = url.port_
|
|
232
228
|
, path = pagePath
|
|
233
|
-
, query = url.query |> Maybe.map QueryParams.fromString
|
|
229
|
+
, query = url.query |> Maybe.map QueryParams.fromString |> Maybe.withDefault Dict.empty
|
|
234
230
|
, fragment = url.fragment
|
|
235
231
|
}
|
|
236
232
|
}
|
|
@@ -274,7 +270,7 @@ init config flags url key =
|
|
|
274
270
|
, url = url
|
|
275
271
|
, currentPath = url.path
|
|
276
272
|
, pageData = Err "Not found"
|
|
277
|
-
, ariaNavigationAnnouncement = "
|
|
273
|
+
, ariaNavigationAnnouncement = "Page Not Found" -- TODO use error page title for announcement?
|
|
278
274
|
, userFlags = flags
|
|
279
275
|
, notFound = Just info
|
|
280
276
|
, transition = Nothing
|
|
@@ -313,16 +309,22 @@ init config flags url key =
|
|
|
313
309
|
type Msg userMsg pageData actionData sharedData errorPage
|
|
314
310
|
= LinkClicked Browser.UrlRequest
|
|
315
311
|
| UrlChanged Url
|
|
316
|
-
|
|
312
|
+
-- TODO rename to PagesMsg
|
|
313
|
+
| UserMsg (PagesMsg userMsg)
|
|
317
314
|
| SetField { formId : String, name : String, value : String }
|
|
318
315
|
| UpdateCacheAndUrlNew Bool Url (Maybe userMsg) (Result Http.Error ( Url, ResponseSketch pageData actionData sharedData ))
|
|
319
|
-
| FetcherComplete Bool String Int (Result Http.Error ( Maybe userMsg,
|
|
316
|
+
| FetcherComplete Bool String Int (Result Http.Error ( Maybe userMsg, ActionDataOrRedirect actionData ))
|
|
320
317
|
| FetcherStarted String Int FormData Time.Posix
|
|
321
318
|
| PageScrollComplete
|
|
322
319
|
| HotReloadCompleteNew Bytes
|
|
323
320
|
| ProcessFetchResponse Int (Result Http.Error ( Url, ResponseSketch pageData actionData sharedData )) (Result Http.Error ( Url, ResponseSketch pageData actionData sharedData ) -> Msg userMsg pageData actionData sharedData errorPage)
|
|
324
321
|
|
|
325
322
|
|
|
323
|
+
type ActionDataOrRedirect action
|
|
324
|
+
= ActionResponse (Maybe action)
|
|
325
|
+
| RedirectResponse String
|
|
326
|
+
|
|
327
|
+
|
|
326
328
|
{-| -}
|
|
327
329
|
type alias Model userModel pageData actionData sharedData =
|
|
328
330
|
{ key : Maybe Browser.Navigation.Key
|
|
@@ -414,7 +416,7 @@ update config appMsg model =
|
|
|
414
416
|
model
|
|
415
417
|
|
|
416
418
|
Nothing ->
|
|
417
|
-
if model.url.path == url.path then
|
|
419
|
+
if model.url.path == url.path && model.url.query == url.query then
|
|
418
420
|
( { model
|
|
419
421
|
| -- update the URL in case query params or fragment changed
|
|
420
422
|
url = url
|
|
@@ -423,46 +425,57 @@ update config appMsg model =
|
|
|
423
425
|
)
|
|
424
426
|
|
|
425
427
|
else
|
|
426
|
-
(
|
|
427
|
-
| url = url
|
|
428
|
-
}
|
|
428
|
+
( model
|
|
429
429
|
, NoEffect
|
|
430
430
|
)
|
|
431
431
|
-- TODO is it reasonable to always re-fetch route data if you re-navigate to the current route? Might be a good
|
|
432
432
|
-- parallel to the browser behavior
|
|
433
433
|
|> startNewGetLoad url (UpdateCacheAndUrlNew True url Nothing)
|
|
434
434
|
|
|
435
|
-
FetcherComplete
|
|
435
|
+
FetcherComplete _ fetcherKey _ userMsgResult ->
|
|
436
436
|
case userMsgResult of
|
|
437
|
-
Ok ( userMsg,
|
|
438
|
-
|
|
439
|
-
|
|
440
|
-
model
|
|
441
|
-
|
|
442
|
-
|
|
443
|
-
|
|
444
|
-
(
|
|
445
|
-
|
|
446
|
-
|
|
447
|
-
|
|
448
|
-
|
|
449
|
-
|
|
450
|
-
|
|
451
|
-
|
|
437
|
+
Ok ( userMsg, actionOrRedirect ) ->
|
|
438
|
+
case actionOrRedirect of
|
|
439
|
+
ActionResponse maybeFetcherDoneActionData ->
|
|
440
|
+
( { model
|
|
441
|
+
| inFlightFetchers =
|
|
442
|
+
model.inFlightFetchers
|
|
443
|
+
|> Dict.update fetcherKey
|
|
444
|
+
(Maybe.map
|
|
445
|
+
(\( transitionId, fetcherState ) ->
|
|
446
|
+
( transitionId
|
|
447
|
+
, { fetcherState
|
|
448
|
+
| status =
|
|
449
|
+
maybeFetcherDoneActionData
|
|
450
|
+
|> Maybe.map Pages.Transition.FetcherReloading
|
|
451
|
+
-- TODO remove this bad default, FetcherSubmitting is incorrect
|
|
452
|
+
|> Maybe.withDefault Pages.Transition.FetcherSubmitting
|
|
453
|
+
}
|
|
454
|
+
)
|
|
455
|
+
)
|
|
452
456
|
)
|
|
453
|
-
|
|
454
|
-
|
|
455
|
-
|
|
456
|
-
|
|
457
|
-
|
|
458
|
-
|
|
459
|
-
|
|
460
|
-
|
|
461
|
-
|
|
462
|
-
|
|
463
|
-
|
|
464
|
-
|
|
465
|
-
|
|
457
|
+
}
|
|
458
|
+
, NoEffect
|
|
459
|
+
)
|
|
460
|
+
|> (case userMsg of
|
|
461
|
+
Just justUserMsg ->
|
|
462
|
+
performUserMsg justUserMsg config
|
|
463
|
+
|
|
464
|
+
Nothing ->
|
|
465
|
+
identity
|
|
466
|
+
)
|
|
467
|
+
|> startNewGetLoad (currentUrlWithPath model.url.path model) (UpdateCacheAndUrlNew False model.url Nothing)
|
|
468
|
+
|
|
469
|
+
RedirectResponse redirectTo ->
|
|
470
|
+
( { model
|
|
471
|
+
| inFlightFetchers =
|
|
472
|
+
model.inFlightFetchers
|
|
473
|
+
|> Dict.remove fetcherKey
|
|
474
|
+
, pendingRedirect = True
|
|
475
|
+
}
|
|
476
|
+
, NoEffect
|
|
477
|
+
)
|
|
478
|
+
|> startNewGetLoad (currentUrlWithPath redirectTo model) (UpdateCacheAndUrlNew False model.url Nothing)
|
|
466
479
|
|
|
467
480
|
Err _ ->
|
|
468
481
|
-- TODO how to handle error?
|
|
@@ -480,11 +493,11 @@ update config appMsg model =
|
|
|
480
493
|
|
|
481
494
|
UserMsg userMsg_ ->
|
|
482
495
|
case userMsg_ of
|
|
483
|
-
Pages.Msg.UserMsg userMsg ->
|
|
496
|
+
Pages.Internal.Msg.UserMsg userMsg ->
|
|
484
497
|
( model, NoEffect )
|
|
485
498
|
|> performUserMsg userMsg config
|
|
486
499
|
|
|
487
|
-
Pages.Msg.Submit fields ->
|
|
500
|
+
Pages.Internal.Msg.Submit fields ->
|
|
488
501
|
( { model
|
|
489
502
|
| transition =
|
|
490
503
|
Just
|
|
@@ -496,7 +509,7 @@ update config appMsg model =
|
|
|
496
509
|
, Submit fields
|
|
497
510
|
)
|
|
498
511
|
|
|
499
|
-
Pages.Msg.SubmitIfValid formId fields isValid ->
|
|
512
|
+
Pages.Internal.Msg.SubmitIfValid formId fields isValid maybeUserMsg ->
|
|
500
513
|
if isValid then
|
|
501
514
|
( { model
|
|
502
515
|
-- TODO should I setSubmitAttempted here, too?
|
|
@@ -509,6 +522,13 @@ update config appMsg model =
|
|
|
509
522
|
}
|
|
510
523
|
, Submit fields
|
|
511
524
|
)
|
|
525
|
+
|> (case maybeUserMsg of
|
|
526
|
+
Just justUserMsg ->
|
|
527
|
+
performUserMsg justUserMsg config
|
|
528
|
+
|
|
529
|
+
Nothing ->
|
|
530
|
+
identity
|
|
531
|
+
)
|
|
512
532
|
|
|
513
533
|
else
|
|
514
534
|
( { model
|
|
@@ -519,7 +539,7 @@ update config appMsg model =
|
|
|
519
539
|
, NoEffect
|
|
520
540
|
)
|
|
521
541
|
|
|
522
|
-
Pages.Msg.SubmitFetcher fetcherKey fields isValid maybeUserMsg ->
|
|
542
|
+
Pages.Internal.Msg.SubmitFetcher fetcherKey fields isValid maybeUserMsg ->
|
|
523
543
|
if isValid then
|
|
524
544
|
-- TODO should I setSubmitAttempted here, too?
|
|
525
545
|
( { model | nextTransitionKey = model.nextTransitionKey + 1 }
|
|
@@ -542,12 +562,15 @@ update config appMsg model =
|
|
|
542
562
|
, NoEffect
|
|
543
563
|
)
|
|
544
564
|
|
|
545
|
-
Pages.Msg.FormFieldEvent value ->
|
|
565
|
+
Pages.Internal.Msg.FormFieldEvent value ->
|
|
546
566
|
-- TODO when init is called for a new page, also need to clear out client-side `pageFormState`
|
|
547
567
|
( { model | pageFormState = Pages.FormState.update value model.pageFormState }
|
|
548
568
|
, NoEffect
|
|
549
569
|
)
|
|
550
570
|
|
|
571
|
+
Pages.Internal.Msg.NoOp ->
|
|
572
|
+
( model, NoEffect )
|
|
573
|
+
|
|
551
574
|
UpdateCacheAndUrlNew scrollToTopWhenDone urlWithoutRedirectResolution maybeUserMsg updateResult ->
|
|
552
575
|
-- TODO remove all fetchers that are in the state `FetcherReloading` here -- I think that's the right logic?
|
|
553
576
|
case
|
|
@@ -605,27 +628,32 @@ update config appMsg model =
|
|
|
605
628
|
, actionData = newActionData
|
|
606
629
|
}
|
|
607
630
|
|
|
608
|
-
( userModel,
|
|
631
|
+
( userModel, userEffect ) =
|
|
609
632
|
-- TODO if urlWithoutRedirectResolution is different from the url with redirect resolution, then
|
|
610
633
|
-- instead of calling update, call pushUrl (I think?)
|
|
611
634
|
-- TODO include user Cmd
|
|
612
|
-
|
|
613
|
-
(
|
|
614
|
-
|
|
615
|
-
|
|
616
|
-
|
|
617
|
-
|
|
618
|
-
|
|
619
|
-
|
|
620
|
-
|
|
621
|
-
|
|
622
|
-
|
|
623
|
-
|
|
624
|
-
|
|
625
|
-
|
|
626
|
-
|
|
627
|
-
|
|
628
|
-
|
|
635
|
+
if stayingOnSamePath then
|
|
636
|
+
( previousPageData.userModel, NoEffect )
|
|
637
|
+
|
|
638
|
+
else
|
|
639
|
+
config.update model.pageFormState
|
|
640
|
+
(model.inFlightFetchers |> toFetcherState)
|
|
641
|
+
(model.transition |> Maybe.map Tuple.second)
|
|
642
|
+
newSharedData
|
|
643
|
+
newPageData
|
|
644
|
+
model.key
|
|
645
|
+
(config.onPageChange
|
|
646
|
+
{ protocol = model.url.protocol
|
|
647
|
+
, host = model.url.host
|
|
648
|
+
, port_ = model.url.port_
|
|
649
|
+
, path = urlPathToPath urlWithoutRedirectResolution
|
|
650
|
+
, query = urlWithoutRedirectResolution.query
|
|
651
|
+
, fragment = urlWithoutRedirectResolution.fragment
|
|
652
|
+
, metadata = config.urlToRoute urlWithoutRedirectResolution
|
|
653
|
+
}
|
|
654
|
+
)
|
|
655
|
+
previousPageData.userModel
|
|
656
|
+
|> Tuple.mapSecond UserCmd
|
|
629
657
|
|
|
630
658
|
updatedModel : Model userModel pageData actionData sharedData
|
|
631
659
|
updatedModel =
|
|
@@ -656,10 +684,13 @@ update config appMsg model =
|
|
|
656
684
|
, currentPath = newUrl.path
|
|
657
685
|
}
|
|
658
686
|
, if not stayingOnSamePath && scrollToTopWhenDone then
|
|
659
|
-
|
|
687
|
+
Batch
|
|
688
|
+
[ ScrollToTop
|
|
689
|
+
, userEffect
|
|
690
|
+
]
|
|
660
691
|
|
|
661
692
|
else
|
|
662
|
-
|
|
693
|
+
userEffect
|
|
663
694
|
)
|
|
664
695
|
|> (case maybeUserMsg of
|
|
665
696
|
Just userMsg ->
|
|
@@ -679,10 +710,10 @@ update config appMsg model =
|
|
|
679
710
|
Err _ ->
|
|
680
711
|
{-
|
|
681
712
|
When there is an error loading the content.dat, we are either
|
|
682
|
-
1) in the dev server, and should show the relevant
|
|
713
|
+
1) in the dev server, and should show the relevant BackendTask error for the page
|
|
683
714
|
we're navigating to. This could be done more cleanly, but it's simplest to just
|
|
684
715
|
do a fresh page load and use the code path for presenting an error for a fresh page.
|
|
685
|
-
2) In a production app. That means we had a successful build, so there were no
|
|
716
|
+
2) In a production app. That means we had a successful build, so there were no BackendTask failures,
|
|
686
717
|
so the app must be stale (unless it's in some unexpected state from a bug). In the future,
|
|
687
718
|
it probably makes sense to include some sort of hash of the app version we are fetching, match
|
|
688
719
|
it with the current version that's running, and perform this logic when we see there is a mismatch.
|
|
@@ -745,7 +776,86 @@ update config appMsg model =
|
|
|
745
776
|
_ ->
|
|
746
777
|
( model, NoEffect )
|
|
747
778
|
)
|
|
748
|
-
|> Result.withDefault
|
|
779
|
+
|> Result.withDefault
|
|
780
|
+
(let
|
|
781
|
+
pageDataResult : Maybe (InitKind sharedData pageData actionData errorPage)
|
|
782
|
+
pageDataResult =
|
|
783
|
+
case Bytes.Decode.decode config.decodeResponse pageDataBytes of
|
|
784
|
+
Just (ResponseSketch.RenderPage _ _) ->
|
|
785
|
+
Nothing
|
|
786
|
+
|
|
787
|
+
Just (ResponseSketch.HotUpdate pageData shared actionData) ->
|
|
788
|
+
OkPage shared pageData actionData
|
|
789
|
+
|> Just
|
|
790
|
+
|
|
791
|
+
Just (ResponseSketch.NotFound notFound) ->
|
|
792
|
+
NotFound notFound
|
|
793
|
+
|> Just
|
|
794
|
+
|
|
795
|
+
_ ->
|
|
796
|
+
Nothing
|
|
797
|
+
in
|
|
798
|
+
case pageDataResult of
|
|
799
|
+
Just (OkPage sharedData pageData actionData) ->
|
|
800
|
+
let
|
|
801
|
+
urls : { currentUrl : Url, basePath : List String }
|
|
802
|
+
urls =
|
|
803
|
+
{ currentUrl = model.url
|
|
804
|
+
, basePath = config.basePath
|
|
805
|
+
}
|
|
806
|
+
|
|
807
|
+
pagePath : Path
|
|
808
|
+
pagePath =
|
|
809
|
+
urlsToPagePath urls
|
|
810
|
+
|
|
811
|
+
userFlags : Pages.Flags.Flags
|
|
812
|
+
userFlags =
|
|
813
|
+
model.userFlags
|
|
814
|
+
|> Decode.decodeValue
|
|
815
|
+
(Decode.field "userFlags" Decode.value)
|
|
816
|
+
|> Result.withDefault Json.Encode.null
|
|
817
|
+
|> Pages.Flags.BrowserFlags
|
|
818
|
+
|
|
819
|
+
( userModel, userCmd ) =
|
|
820
|
+
Just
|
|
821
|
+
{ path =
|
|
822
|
+
{ path = pagePath
|
|
823
|
+
, query = model.url.query
|
|
824
|
+
, fragment = model.url.fragment
|
|
825
|
+
}
|
|
826
|
+
, metadata = config.urlToRoute model.url
|
|
827
|
+
, pageUrl =
|
|
828
|
+
Just
|
|
829
|
+
{ protocol = model.url.protocol
|
|
830
|
+
, host = model.url.host
|
|
831
|
+
, port_ = model.url.port_
|
|
832
|
+
, path = pagePath
|
|
833
|
+
, query = model.url.query |> Maybe.map QueryParams.fromString |> Maybe.withDefault Dict.empty
|
|
834
|
+
, fragment = model.url.fragment
|
|
835
|
+
}
|
|
836
|
+
}
|
|
837
|
+
|> config.init userFlags sharedData pageData actionData
|
|
838
|
+
|
|
839
|
+
cmd : Effect userMsg pageData actionData sharedData userEffect errorPage
|
|
840
|
+
cmd =
|
|
841
|
+
UserCmd userCmd
|
|
842
|
+
in
|
|
843
|
+
( { model
|
|
844
|
+
| pageData =
|
|
845
|
+
Ok
|
|
846
|
+
{ userModel = userModel
|
|
847
|
+
, sharedData = sharedData
|
|
848
|
+
, pageData = pageData
|
|
849
|
+
, actionData = actionData
|
|
850
|
+
}
|
|
851
|
+
, notFound = Nothing
|
|
852
|
+
}
|
|
853
|
+
, cmd
|
|
854
|
+
)
|
|
855
|
+
|
|
856
|
+
_ ->
|
|
857
|
+
( model, NoEffect )
|
|
858
|
+
)
|
|
749
859
|
|
|
750
860
|
FetcherStarted fetcherKey transitionId fetcherData initiatedAt ->
|
|
751
861
|
( { model
|
|
@@ -766,7 +876,7 @@ update config appMsg model =
|
|
|
766
876
|
toFetcherState : Dict String ( Int, Pages.Transition.FetcherState actionData ) -> Dict String (Pages.Transition.FetcherState actionData)
|
|
767
877
|
toFetcherState inFlightFetchers =
|
|
768
878
|
inFlightFetchers
|
|
769
|
-
|> Dict.map (\_ (
|
|
879
|
+
|> Dict.map (\_ ( _, fetcherState ) -> fetcherState)
|
|
770
880
|
|
|
771
881
|
|
|
772
882
|
performUserMsg :
|
|
@@ -828,7 +938,7 @@ perform config model effect =
|
|
|
828
938
|
|> Maybe.withDefault Cmd.none
|
|
829
939
|
|
|
830
940
|
FetchPageData transitionKey maybeRequestInfo url toMsg ->
|
|
831
|
-
fetchRouteData
|
|
941
|
+
fetchRouteData transitionKey toMsg config url maybeRequestInfo
|
|
832
942
|
|
|
833
943
|
Submit fields ->
|
|
834
944
|
if fields.method == Get then
|
|
@@ -843,7 +953,7 @@ perform config model effect =
|
|
|
843
953
|
-- TODO add optional path parameter to Submit variant to allow submitting to other routes
|
|
844
954
|
model.url
|
|
845
955
|
in
|
|
846
|
-
fetchRouteData
|
|
956
|
+
fetchRouteData -1 (UpdateCacheAndUrlNew False model.url Nothing) config urlToSubmitTo (Just fields)
|
|
847
957
|
|
|
848
958
|
SubmitFetcher fetcherKey transitionId formData ->
|
|
849
959
|
startFetcher2 config False fetcherKey transitionId formData model
|
|
@@ -863,7 +973,7 @@ perform config model effect =
|
|
|
863
973
|
|> config.perform
|
|
864
974
|
{ fetchRouteData =
|
|
865
975
|
\fetchInfo ->
|
|
866
|
-
fetchRouteData
|
|
976
|
+
fetchRouteData
|
|
867
977
|
-1
|
|
868
978
|
(prepare fetchInfo.toMsg)
|
|
869
979
|
config
|
|
@@ -873,13 +983,13 @@ perform config model effect =
|
|
|
873
983
|
---- TODO map the Msg with the wrapper type (like in the PR branch)
|
|
874
984
|
, submit =
|
|
875
985
|
\fetchInfo ->
|
|
876
|
-
fetchRouteData
|
|
986
|
+
fetchRouteData -1 (prepare fetchInfo.toMsg) config (fetchInfo.values.action |> Url.fromString |> Maybe.withDefault model.url) (Just fetchInfo.values)
|
|
877
987
|
, runFetcher =
|
|
878
988
|
\(Pages.Fetcher.Fetcher options) ->
|
|
879
989
|
-- TODO need to get the fetcherId here
|
|
880
990
|
-- TODO need to increment and pass in the transitionId
|
|
881
991
|
startFetcher "TODO" -1 options model
|
|
882
|
-
, fromPageMsg = Pages.Msg.UserMsg >> UserMsg
|
|
992
|
+
, fromPageMsg = Pages.Internal.Msg.UserMsg >> UserMsg
|
|
883
993
|
, key = key
|
|
884
994
|
, setField = \info -> Task.succeed (SetField info) |> Task.perform identity
|
|
885
995
|
}
|
|
@@ -927,10 +1037,10 @@ startFetcher fetcherKey transitionId options model =
|
|
|
927
1037
|
Http.expectBytesResponse (FetcherComplete False fetcherKey model.nextTransitionKey)
|
|
928
1038
|
(\bytes ->
|
|
929
1039
|
case bytes of
|
|
930
|
-
Http.GoodStatus_
|
|
1040
|
+
Http.GoodStatus_ _ bytesBody ->
|
|
931
1041
|
( options.decoder (Ok bytesBody)
|
|
932
1042
|
|> Just
|
|
933
|
-
, Nothing
|
|
1043
|
+
, ActionResponse Nothing
|
|
934
1044
|
)
|
|
935
1045
|
|> Ok
|
|
936
1046
|
|
|
@@ -943,7 +1053,7 @@ startFetcher fetcherKey transitionId options model =
|
|
|
943
1053
|
Http.NetworkError_ ->
|
|
944
1054
|
Err <| Http.NetworkError
|
|
945
1055
|
|
|
946
|
-
Http.BadStatus_ metadata
|
|
1056
|
+
Http.BadStatus_ metadata _ ->
|
|
947
1057
|
Err <| Http.BadStatus metadata.statusCode
|
|
948
1058
|
)
|
|
949
1059
|
, tracker = Nothing
|
|
@@ -974,7 +1084,7 @@ startFetcher2 config fromPageReload fetcherKey transitionId formData model =
|
|
|
974
1084
|
Cmd.batch
|
|
975
1085
|
[ cancelStaleFetchers model
|
|
976
1086
|
, case Dict.get fetcherKey model.inFlightFetchers of
|
|
977
|
-
Just ( inFlightId,
|
|
1087
|
+
Just ( inFlightId, _ ) ->
|
|
978
1088
|
Http.cancel (String.fromInt inFlightId)
|
|
979
1089
|
|
|
980
1090
|
Nothing ->
|
|
@@ -985,22 +1095,26 @@ startFetcher2 config fromPageReload fetcherKey transitionId formData model =
|
|
|
985
1095
|
Http.expectBytesResponse (FetcherComplete fromPageReload fetcherKey model.nextTransitionKey)
|
|
986
1096
|
(\bytes ->
|
|
987
1097
|
case bytes of
|
|
988
|
-
Http.GoodStatus_
|
|
1098
|
+
Http.GoodStatus_ _ bytesBody ->
|
|
989
1099
|
let
|
|
990
|
-
decodedAction :
|
|
1100
|
+
decodedAction : ActionDataOrRedirect actionData
|
|
991
1101
|
decodedAction =
|
|
992
1102
|
case Bytes.Decode.decode config.decodeResponse bytesBody of
|
|
1103
|
+
-- @@@
|
|
1104
|
+
Just (ResponseSketch.Redirect redirectTo) ->
|
|
1105
|
+
RedirectResponse redirectTo
|
|
1106
|
+
|
|
993
1107
|
Just (ResponseSketch.RenderPage _ maybeAction) ->
|
|
994
|
-
maybeAction
|
|
1108
|
+
ActionResponse maybeAction
|
|
995
1109
|
|
|
996
|
-
Just (ResponseSketch.HotUpdate
|
|
997
|
-
maybeAction
|
|
1110
|
+
Just (ResponseSketch.HotUpdate _ _ maybeAction) ->
|
|
1111
|
+
ActionResponse maybeAction
|
|
998
1112
|
|
|
999
|
-
Just (ResponseSketch.NotFound
|
|
1000
|
-
Nothing
|
|
1113
|
+
Just (ResponseSketch.NotFound _) ->
|
|
1114
|
+
ActionResponse Nothing
|
|
1001
1115
|
|
|
1002
1116
|
_ ->
|
|
1003
|
-
Nothing
|
|
1117
|
+
ActionResponse Nothing
|
|
1004
1118
|
in
|
|
1005
1119
|
-- TODO maybe have an optional way to pass the bytes through?
|
|
1006
1120
|
Ok ( Nothing, decodedAction )
|
|
@@ -1014,7 +1128,7 @@ startFetcher2 config fromPageReload fetcherKey transitionId formData model =
|
|
|
1014
1128
|
Http.NetworkError_ ->
|
|
1015
1129
|
Err <| Http.NetworkError
|
|
1016
1130
|
|
|
1017
|
-
Http.BadStatus_ metadata
|
|
1131
|
+
Http.BadStatus_ metadata _ ->
|
|
1018
1132
|
Err <| Http.BadStatus metadata.statusCode
|
|
1019
1133
|
)
|
|
1020
1134
|
, tracker = Just (String.fromInt transitionId)
|
|
@@ -1036,7 +1150,7 @@ cancelStaleFetchers model =
|
|
|
1036
1150
|
model.inFlightFetchers
|
|
1037
1151
|
|> Dict.toList
|
|
1038
1152
|
|> List.filterMap
|
|
1039
|
-
(\(
|
|
1153
|
+
(\( _, ( id, fetcher ) ) ->
|
|
1040
1154
|
case fetcher.status of
|
|
1041
1155
|
Pages.Transition.FetcherReloading _ ->
|
|
1042
1156
|
Http.cancel (String.fromInt id)
|
|
@@ -1104,7 +1218,7 @@ application config =
|
|
|
1104
1218
|
[ config.subscriptions (model.url |> config.urlToRoute)
|
|
1105
1219
|
(urls.currentUrl |> config.urlToRoute |> config.routeToPath |> Path.join)
|
|
1106
1220
|
pageData.userModel
|
|
1107
|
-
|> Sub.map (Pages.Msg.UserMsg >> UserMsg)
|
|
1221
|
+
|> Sub.map (Pages.Internal.Msg.UserMsg >> UserMsg)
|
|
1108
1222
|
, config.hotReloadData
|
|
1109
1223
|
|> Sub.map HotReloadCompleteNew
|
|
1110
1224
|
]
|
|
@@ -1157,14 +1271,13 @@ urlPathToPath urls =
|
|
|
1157
1271
|
|
|
1158
1272
|
|
|
1159
1273
|
fetchRouteData :
|
|
1160
|
-
|
|
1161
|
-
-> Int
|
|
1274
|
+
Int
|
|
1162
1275
|
-> (Result Http.Error ( Url, ResponseSketch pageData actionData sharedData ) -> Msg userMsg pageData actionData sharedData errorPage)
|
|
1163
1276
|
-> ProgramConfig userMsg userModel route pageData actionData sharedData effect (Msg userMsg pageData actionData sharedData errorPage) errorPage
|
|
1164
1277
|
-> Url
|
|
1165
1278
|
-> Maybe FormData
|
|
1166
1279
|
-> Cmd (Msg userMsg pageData actionData sharedData errorPage)
|
|
1167
|
-
fetchRouteData
|
|
1280
|
+
fetchRouteData transitionKey toMsg config url details =
|
|
1168
1281
|
{-
|
|
1169
1282
|
TODO:
|
|
1170
1283
|
- [X] `toMsg` needs a parameter for the callback Msg so it can pass it on if there is a Redirect response
|
|
@@ -1251,7 +1364,7 @@ fetchRouteData forPageDataReload transitionKey toMsg config url details =
|
|
|
1251
1364
|
Http.NetworkError_ ->
|
|
1252
1365
|
Err Http.NetworkError
|
|
1253
1366
|
|
|
1254
|
-
Http.BadStatus_
|
|
1367
|
+
Http.BadStatus_ _ body ->
|
|
1255
1368
|
body
|
|
1256
1369
|
|> Bytes.Decode.decode config.decodeResponse
|
|
1257
1370
|
|> Result.fromMaybe "Decoding error"
|
|
@@ -1303,7 +1416,7 @@ startNewGetLoad urlToGet toMsg ( model, effect ) =
|
|
|
1303
1416
|
cancelIfStale : Effect userMsg pageData actionData sharedData userEffect errorPage
|
|
1304
1417
|
cancelIfStale =
|
|
1305
1418
|
case model.transition of
|
|
1306
|
-
Just ( transitionKey, Pages.Transition.Loading
|
|
1419
|
+
Just ( transitionKey, Pages.Transition.Loading _ _ ) ->
|
|
1307
1420
|
CancelRequest transitionKey
|
|
1308
1421
|
|
|
1309
1422
|
_ ->
|
|
@@ -1314,13 +1427,13 @@ startNewGetLoad urlToGet toMsg ( model, effect ) =
|
|
|
1314
1427
|
, transition =
|
|
1315
1428
|
( model.nextTransitionKey
|
|
1316
1429
|
, case model.transition of
|
|
1317
|
-
Just (
|
|
1430
|
+
Just ( _, Pages.Transition.LoadAfterSubmit submitData _ _ ) ->
|
|
1318
1431
|
Pages.Transition.LoadAfterSubmit
|
|
1319
1432
|
submitData
|
|
1320
1433
|
(urlToGet.path |> Path.fromString)
|
|
1321
1434
|
Pages.Transition.Load
|
|
1322
1435
|
|
|
1323
|
-
Just (
|
|
1436
|
+
Just ( _, Pages.Transition.Submitting submitData ) ->
|
|
1324
1437
|
Pages.Transition.LoadAfterSubmit
|
|
1325
1438
|
submitData
|
|
1326
1439
|
(urlToGet.path |> Path.fromString)
|
|
@@ -1392,6 +1505,7 @@ loadDataAndUpdateUrl ( newPageData, newSharedData, newActionData ) maybeUserMsg
|
|
|
1392
1505
|
, actionData = newActionData
|
|
1393
1506
|
}
|
|
1394
1507
|
|
|
1508
|
+
-- TODO use userEffect here?
|
|
1395
1509
|
( userModel, _ ) =
|
|
1396
1510
|
-- TODO if urlWithoutRedirectResolution is different from the url with redirect resolution, then
|
|
1397
1511
|
-- instead of calling update, call pushUrl (I think?)
|
|
@@ -1467,10 +1581,10 @@ loadDataAndUpdateUrl ( newPageData, newSharedData, newActionData ) maybeUserMsg
|
|
|
1467
1581
|
Err _ ->
|
|
1468
1582
|
{-
|
|
1469
1583
|
When there is an error loading the content.dat, we are either
|
|
1470
|
-
1) in the dev server, and should show the relevant
|
|
1584
|
+
1) in the dev server, and should show the relevant BackendTask error for the page
|
|
1471
1585
|
we're navigating to. This could be done more cleanly, but it's simplest to just
|
|
1472
1586
|
do a fresh page load and use the code path for presenting an error for a fresh page.
|
|
1473
|
-
2) In a production app. That means we had a successful build, so there were no
|
|
1587
|
+
2) In a production app. That means we had a successful build, so there were no BackendTask failures,
|
|
1474
1588
|
so the app must be stale (unless it's in some unexpected state from a bug). In the future,
|
|
1475
1589
|
it probably makes sense to include some sort of hash of the app version we are fetching, match
|
|
1476
1590
|
it with the current version that's running, and perform this logic when we see there is a mismatch.
|
|
@@ -0,0 +1,17 @@
|
|
|
1
|
+
module Pages.Internal.Script exposing (Script(..))
|
|
2
|
+
|
|
3
|
+
import BackendTask exposing (BackendTask)
|
|
4
|
+
import Cli.Program as Program
|
|
5
|
+
import FatalError exposing (FatalError)
|
|
6
|
+
import Html exposing (Html)
|
|
7
|
+
|
|
8
|
+
|
|
9
|
+
{-| -}
|
|
10
|
+
type Script
|
|
11
|
+
= Script
|
|
12
|
+
((Maybe { indent : Int, newLines : Bool }
|
|
13
|
+
-> Html Never
|
|
14
|
+
-> String
|
|
15
|
+
)
|
|
16
|
+
-> Program.Config (BackendTask FatalError ())
|
|
17
|
+
)
|