elm-pages 3.0.0-beta.9 → 3.0.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 (208) hide show
  1. package/README.md +2 -2
  2. package/adapter/netlify.js +207 -0
  3. package/codegen/{elm-pages-codegen.js → elm-pages-codegen.cjs} +2730 -2938
  4. package/generator/dead-code-review/elm-stuff/generated-code/elm-community/elm-test/0.19.1-revision9/dependencies.c59ecaf7fa8379e3a2d0f793fe9784e3060cb64a6d1fe22b8f6a054502021dbe.json +1 -0
  5. package/generator/dead-code-review/elm-stuff/generated-code/elm-community/elm-test/0.19.1-revision9/elm-stuff/0.19.1/Console-Text.elmi +0 -0
  6. package/generator/dead-code-review/elm-stuff/generated-code/elm-community/elm-test/0.19.1-revision9/elm-stuff/0.19.1/Console-Text.elmo +0 -0
  7. package/generator/dead-code-review/elm-stuff/generated-code/elm-community/elm-test/0.19.1-revision9/elm-stuff/0.19.1/Pages-Review-DeadCodeEliminateData.elmi +0 -0
  8. package/generator/dead-code-review/elm-stuff/generated-code/elm-community/elm-test/0.19.1-revision9/elm-stuff/0.19.1/Pages-Review-DeadCodeEliminateData.elmo +0 -0
  9. package/generator/dead-code-review/elm-stuff/generated-code/elm-community/elm-test/0.19.1-revision9/elm-stuff/0.19.1/Pages-Review-DeadCodeEliminateDataTest.elmi +0 -0
  10. package/generator/dead-code-review/elm-stuff/generated-code/elm-community/elm-test/0.19.1-revision9/elm-stuff/0.19.1/Pages-Review-DeadCodeEliminateDataTest.elmo +0 -0
  11. package/generator/dead-code-review/elm-stuff/generated-code/elm-community/elm-test/0.19.1-revision9/elm-stuff/0.19.1/Test-Generated-Main.elmi +0 -0
  12. package/generator/dead-code-review/elm-stuff/generated-code/elm-community/elm-test/0.19.1-revision9/elm-stuff/0.19.1/Test-Generated-Main.elmo +0 -0
  13. package/generator/dead-code-review/elm-stuff/generated-code/elm-community/elm-test/0.19.1-revision9/elm-stuff/0.19.1/Test-Reporter-Console-Format-Color.elmi +0 -0
  14. package/generator/dead-code-review/elm-stuff/generated-code/elm-community/elm-test/0.19.1-revision9/elm-stuff/0.19.1/Test-Reporter-Console-Format-Color.elmo +0 -0
  15. package/generator/dead-code-review/elm-stuff/generated-code/elm-community/elm-test/0.19.1-revision9/elm-stuff/0.19.1/Test-Reporter-Console-Format-Monochrome.elmi +0 -0
  16. package/generator/dead-code-review/elm-stuff/generated-code/elm-community/elm-test/0.19.1-revision9/elm-stuff/0.19.1/Test-Reporter-Console-Format-Monochrome.elmo +0 -0
  17. package/generator/dead-code-review/elm-stuff/generated-code/elm-community/elm-test/0.19.1-revision9/elm-stuff/0.19.1/Test-Reporter-Console-Format.elmi +0 -0
  18. package/generator/dead-code-review/elm-stuff/generated-code/elm-community/elm-test/0.19.1-revision9/elm-stuff/0.19.1/Test-Reporter-Console-Format.elmo +0 -0
  19. package/generator/dead-code-review/elm-stuff/generated-code/elm-community/elm-test/0.19.1-revision9/elm-stuff/0.19.1/Test-Reporter-Console.elmi +0 -0
  20. package/generator/dead-code-review/elm-stuff/generated-code/elm-community/elm-test/0.19.1-revision9/elm-stuff/0.19.1/Test-Reporter-Console.elmo +0 -0
  21. package/generator/dead-code-review/elm-stuff/generated-code/elm-community/elm-test/0.19.1-revision9/elm-stuff/0.19.1/Test-Reporter-Highlightable.elmi +0 -0
  22. package/generator/dead-code-review/elm-stuff/generated-code/elm-community/elm-test/0.19.1-revision9/elm-stuff/0.19.1/Test-Reporter-Highlightable.elmo +0 -0
  23. package/generator/dead-code-review/elm-stuff/generated-code/elm-community/elm-test/0.19.1-revision9/elm-stuff/0.19.1/Test-Reporter-JUnit.elmi +0 -0
  24. package/generator/dead-code-review/elm-stuff/generated-code/elm-community/elm-test/0.19.1-revision9/elm-stuff/0.19.1/Test-Reporter-JUnit.elmo +0 -0
  25. package/generator/dead-code-review/elm-stuff/generated-code/elm-community/elm-test/0.19.1-revision9/elm-stuff/0.19.1/Test-Reporter-Json.elmi +0 -0
  26. package/generator/dead-code-review/elm-stuff/generated-code/elm-community/elm-test/0.19.1-revision9/elm-stuff/0.19.1/Test-Reporter-Json.elmo +0 -0
  27. package/generator/dead-code-review/elm-stuff/generated-code/elm-community/elm-test/0.19.1-revision9/elm-stuff/0.19.1/Test-Reporter-Reporter.elmi +0 -0
  28. package/generator/dead-code-review/elm-stuff/generated-code/elm-community/elm-test/0.19.1-revision9/elm-stuff/0.19.1/Test-Reporter-Reporter.elmo +0 -0
  29. package/generator/dead-code-review/elm-stuff/generated-code/elm-community/elm-test/0.19.1-revision9/elm-stuff/0.19.1/Test-Reporter-TestResults.elmi +0 -0
  30. package/generator/dead-code-review/elm-stuff/generated-code/elm-community/elm-test/0.19.1-revision9/elm-stuff/0.19.1/Test-Reporter-TestResults.elmo +0 -0
  31. package/generator/dead-code-review/elm-stuff/generated-code/elm-community/elm-test/0.19.1-revision9/elm-stuff/0.19.1/Test-Runner-JsMessage.elmi +0 -0
  32. package/generator/dead-code-review/elm-stuff/generated-code/elm-community/elm-test/0.19.1-revision9/elm-stuff/0.19.1/Test-Runner-JsMessage.elmo +0 -0
  33. package/generator/dead-code-review/elm-stuff/generated-code/elm-community/elm-test/0.19.1-revision9/elm-stuff/0.19.1/Test-Runner-Node-Vendor-Console.elmi +0 -0
  34. package/generator/dead-code-review/elm-stuff/generated-code/elm-community/elm-test/0.19.1-revision9/elm-stuff/0.19.1/Test-Runner-Node-Vendor-Console.elmo +0 -0
  35. package/generator/dead-code-review/elm-stuff/generated-code/elm-community/elm-test/0.19.1-revision9/elm-stuff/0.19.1/Test-Runner-Node-Vendor-Diff.elmi +0 -0
  36. package/generator/dead-code-review/elm-stuff/generated-code/elm-community/elm-test/0.19.1-revision9/elm-stuff/0.19.1/Test-Runner-Node-Vendor-Diff.elmo +0 -0
  37. package/generator/dead-code-review/elm-stuff/generated-code/elm-community/elm-test/0.19.1-revision9/elm-stuff/0.19.1/Test-Runner-Node.elmi +0 -0
  38. package/generator/dead-code-review/elm-stuff/generated-code/elm-community/elm-test/0.19.1-revision9/elm-stuff/0.19.1/Test-Runner-Node.elmo +0 -0
  39. package/generator/dead-code-review/elm-stuff/generated-code/elm-community/elm-test/0.19.1-revision9/elm-stuff/0.19.1/d.dat +0 -0
  40. package/generator/dead-code-review/elm-stuff/generated-code/elm-community/elm-test/0.19.1-revision9/elm-stuff/0.19.1/i.dat +0 -0
  41. package/generator/dead-code-review/elm-stuff/generated-code/elm-community/elm-test/0.19.1-revision9/elm-stuff/0.19.1/lock +0 -0
  42. package/generator/dead-code-review/elm-stuff/generated-code/elm-community/elm-test/0.19.1-revision9/elm-stuff/0.19.1/o.dat +0 -0
  43. package/generator/dead-code-review/elm-stuff/generated-code/elm-community/elm-test/0.19.1-revision9/elm.json +38 -0
  44. package/generator/dead-code-review/elm-stuff/generated-code/elm-community/elm-test/0.19.1-revision9/elmTestOutput.js +30883 -0
  45. package/generator/dead-code-review/elm-stuff/generated-code/elm-community/elm-test/0.19.1-revision9/package.json +1 -0
  46. package/generator/dead-code-review/elm-stuff/generated-code/elm-community/elm-test/0.19.1-revision9/src/Test/Generated/Main.elm +27 -0
  47. package/generator/dead-code-review/elm-stuff/tests-0.19.1/elm-stuff/0.19.1/Pages-Review-DeadCodeEliminateData.elmi +0 -0
  48. package/generator/dead-code-review/elm-stuff/tests-0.19.1/elm-stuff/0.19.1/Pages-Review-DeadCodeEliminateData.elmo +0 -0
  49. package/generator/dead-code-review/elm-stuff/tests-0.19.1/elm-stuff/0.19.1/Pages-Review-DeadCodeEliminateDataTest.elmo +0 -0
  50. package/generator/dead-code-review/elm-stuff/tests-0.19.1/elm-stuff/0.19.1/d.dat +0 -0
  51. package/generator/dead-code-review/elm-stuff/tests-0.19.1/elm-stuff/0.19.1/i.dat +0 -0
  52. package/generator/dead-code-review/elm-stuff/tests-0.19.1/elm-stuff/0.19.1/o.dat +0 -0
  53. package/generator/dead-code-review/elm-stuff/tests-0.19.1/elm.json +1 -1
  54. package/generator/dead-code-review/elm-stuff/tests-0.19.1/js/Reporter.elm.js +1527 -422
  55. package/generator/dead-code-review/elm-stuff/tests-0.19.1/js/Runner.elm.js +17042 -13855
  56. package/generator/dead-code-review/elm-stuff/tests-0.19.1/js/node_runner.js +1 -1
  57. package/generator/dead-code-review/elm-stuff/tests-0.19.1/js/node_supervisor.js +2 -2
  58. package/generator/dead-code-review/elm.json +9 -7
  59. package/generator/dead-code-review/src/Pages/Review/DeadCodeEliminateData.elm +64 -13
  60. package/generator/dead-code-review/tests/Pages/Review/DeadCodeEliminateDataTest.elm +66 -50
  61. package/generator/review/elm-stuff/tests-0.19.1/elm-stuff/0.19.1/Pages-Internal-RoutePattern.elmi +0 -0
  62. package/generator/review/elm-stuff/tests-0.19.1/elm-stuff/0.19.1/Pages-Internal-RoutePattern.elmo +0 -0
  63. package/generator/review/elm-stuff/tests-0.19.1/elm-stuff/0.19.1/Pages-Review-NoContractViolations.elmi +0 -0
  64. package/generator/review/elm-stuff/tests-0.19.1/elm-stuff/0.19.1/Pages-Review-NoContractViolations.elmo +0 -0
  65. package/generator/review/elm-stuff/tests-0.19.1/elm-stuff/0.19.1/d.dat +0 -0
  66. package/generator/review/elm-stuff/tests-0.19.1/elm-stuff/0.19.1/i.dat +0 -0
  67. package/generator/review/elm-stuff/tests-0.19.1/elm-stuff/0.19.1/o.dat +0 -0
  68. package/generator/review/elm-stuff/tests-0.19.1/elm.json +1 -1
  69. package/generator/review/elm-stuff/tests-0.19.1/js/Reporter.elm.js +1527 -422
  70. package/generator/review/elm-stuff/tests-0.19.1/js/Runner.elm.js +25118 -21832
  71. package/generator/review/elm-stuff/tests-0.19.1/js/node_runner.js +1 -1
  72. package/generator/review/elm-stuff/tests-0.19.1/js/node_supervisor.js +2 -2
  73. package/generator/review/elm.json +10 -10
  74. package/generator/src/RouteBuilder.elm +93 -128
  75. package/generator/src/SharedTemplate.elm +8 -7
  76. package/generator/src/SiteConfig.elm +3 -2
  77. package/generator/src/basepath-middleware.js +3 -3
  78. package/generator/src/build.js +143 -59
  79. package/generator/src/cli.js +292 -88
  80. package/generator/src/codegen.js +29 -27
  81. package/generator/src/compatibility-key.js +3 -0
  82. package/generator/src/compile-elm.js +43 -26
  83. package/generator/src/config.js +2 -4
  84. package/generator/src/copy-dir.js +2 -2
  85. package/generator/src/dev-server.js +160 -102
  86. package/generator/src/dir-helpers.js +9 -26
  87. package/generator/src/elm-codegen.js +5 -4
  88. package/generator/src/elm-file-constants.js +2 -3
  89. package/generator/src/error-formatter.js +12 -11
  90. package/generator/src/file-helpers.js +3 -4
  91. package/generator/src/generate-template-module-connector.js +23 -23
  92. package/generator/src/init.js +9 -8
  93. package/generator/src/pre-render-html.js +10 -13
  94. package/generator/src/render-test.js +109 -0
  95. package/generator/src/render-worker.js +25 -28
  96. package/generator/src/render.js +320 -143
  97. package/generator/src/request-cache.js +265 -162
  98. package/generator/src/resolve-elm-module.js +64 -0
  99. package/generator/src/rewrite-client-elm-json.js +6 -5
  100. package/generator/src/rewrite-elm-json-help.js +56 -0
  101. package/generator/src/rewrite-elm-json.js +17 -7
  102. package/generator/src/route-codegen-helpers.js +16 -31
  103. package/generator/src/seo-renderer.js +1 -3
  104. package/generator/src/vite-utils.js +1 -2
  105. package/generator/static-code/elm-pages.js +10 -0
  106. package/generator/static-code/hmr.js +79 -13
  107. package/generator/template/app/Api.elm +3 -2
  108. package/generator/template/app/Effect.elm +155 -0
  109. package/generator/template/app/ErrorPage.elm +49 -6
  110. package/generator/template/app/Route/Blog/Slug_.elm +86 -0
  111. package/generator/template/app/Route/Greet.elm +107 -0
  112. package/generator/template/app/Route/Hello.elm +119 -0
  113. package/generator/template/app/Route/Index.elm +26 -25
  114. package/generator/template/app/Shared.elm +38 -39
  115. package/generator/template/app/Site.elm +4 -7
  116. package/generator/template/app/View.elm +9 -8
  117. package/generator/template/codegen/elm.codegen.json +18 -0
  118. package/generator/template/custom-backend-task.ts +3 -0
  119. package/generator/template/elm-pages.config.mjs +13 -0
  120. package/generator/template/elm-tooling.json +0 -3
  121. package/generator/template/elm.json +34 -25
  122. package/generator/template/index.ts +1 -2
  123. package/generator/template/netlify.toml +4 -1
  124. package/generator/template/package.json +10 -4
  125. package/generator/template/script/.elm-pages/compiled-ports/custom-backend-task.mjs +7 -0
  126. package/generator/template/script/custom-backend-task.ts +3 -0
  127. package/generator/template/script/elm.json +61 -0
  128. package/generator/template/script/src/AddRoute.elm +312 -0
  129. package/generator/template/script/src/Stars.elm +42 -0
  130. package/package.json +30 -27
  131. package/src/ApiRoute.elm +249 -82
  132. package/src/BackendTask/Custom.elm +325 -0
  133. package/src/BackendTask/Env.elm +90 -0
  134. package/src/{DataSource → BackendTask}/File.elm +171 -56
  135. package/src/{DataSource → BackendTask}/Glob.elm +136 -125
  136. package/src/BackendTask/Http.elm +679 -0
  137. package/src/{DataSource → BackendTask}/Internal/Glob.elm +1 -1
  138. package/src/BackendTask/Internal/Request.elm +69 -0
  139. package/src/BackendTask/Random.elm +79 -0
  140. package/src/BackendTask/Time.elm +47 -0
  141. package/src/BackendTask.elm +531 -0
  142. package/src/FatalError.elm +90 -0
  143. package/src/FormData.elm +21 -18
  144. package/src/Head/Seo.elm +4 -4
  145. package/src/Head.elm +112 -8
  146. package/src/Internal/ApiRoute.elm +7 -5
  147. package/src/Internal/Request.elm +84 -4
  148. package/src/PageServerResponse.elm +6 -1
  149. package/src/Pages/ConcurrentSubmission.elm +127 -0
  150. package/src/Pages/Form.elm +340 -0
  151. package/src/Pages/FormData.elm +19 -0
  152. package/src/Pages/GeneratorProgramConfig.elm +15 -0
  153. package/src/Pages/Internal/FatalError.elm +5 -0
  154. package/src/Pages/Internal/Msg.elm +93 -0
  155. package/src/Pages/Internal/NotFoundReason.elm +4 -4
  156. package/src/Pages/Internal/Platform/Cli.elm +586 -768
  157. package/src/Pages/Internal/Platform/CompatibilityKey.elm +1 -1
  158. package/src/Pages/Internal/Platform/Effect.elm +1 -2
  159. package/src/Pages/Internal/Platform/GeneratorApplication.elm +379 -0
  160. package/src/Pages/Internal/Platform/StaticResponses.elm +65 -276
  161. package/src/Pages/Internal/Platform/ToJsPayload.elm +6 -9
  162. package/src/Pages/Internal/Platform.elm +330 -203
  163. package/src/Pages/Internal/ResponseSketch.elm +2 -2
  164. package/src/Pages/Internal/Script.elm +17 -0
  165. package/src/Pages/Internal/StaticHttpBody.elm +35 -1
  166. package/src/Pages/Manifest.elm +52 -11
  167. package/src/Pages/Navigation.elm +85 -0
  168. package/src/Pages/PageUrl.elm +26 -12
  169. package/src/Pages/ProgramConfig.elm +32 -22
  170. package/src/Pages/Script.elm +166 -0
  171. package/src/Pages/SiteConfig.elm +3 -2
  172. package/src/Pages/StaticHttp/Request.elm +2 -2
  173. package/src/Pages/StaticHttpRequest.elm +23 -99
  174. package/src/Pages/Url.elm +3 -3
  175. package/src/PagesMsg.elm +88 -0
  176. package/src/QueryParams.elm +21 -172
  177. package/src/RenderRequest.elm +7 -7
  178. package/src/RequestsAndPending.elm +37 -20
  179. package/src/Result/Extra.elm +26 -0
  180. package/src/Scaffold/Form.elm +569 -0
  181. package/src/Scaffold/Route.elm +1431 -0
  182. package/src/Server/Request.elm +476 -1001
  183. package/src/Server/Response.elm +130 -36
  184. package/src/Server/Session.elm +181 -111
  185. package/src/Server/SetCookie.elm +80 -32
  186. package/src/Stub.elm +53 -0
  187. package/src/Test/Html/Internal/ElmHtml/ToString.elm +8 -9
  188. package/src/{Path.elm → UrlPath.elm} +33 -36
  189. package/generator/template/public/images/icon-png.png +0 -0
  190. package/src/DataSource/Env.elm +0 -38
  191. package/src/DataSource/Http.elm +0 -446
  192. package/src/DataSource/Internal/Request.elm +0 -20
  193. package/src/DataSource/Port.elm +0 -90
  194. package/src/DataSource.elm +0 -546
  195. package/src/Form/Field.elm +0 -717
  196. package/src/Form/FieldStatus.elm +0 -36
  197. package/src/Form/FieldView.elm +0 -417
  198. package/src/Form/FormData.elm +0 -22
  199. package/src/Form/Validation.elm +0 -391
  200. package/src/Form/Value.elm +0 -118
  201. package/src/Form.elm +0 -1683
  202. package/src/FormDecoder.elm +0 -102
  203. package/src/Pages/FormState.elm +0 -256
  204. package/src/Pages/Generate.elm +0 -1242
  205. package/src/Pages/Internal/Form.elm +0 -17
  206. package/src/Pages/Internal/Platform/Cli.elm.bak +0 -1276
  207. package/src/Pages/Msg.elm +0 -79
  208. package/src/Pages/Transition.elm +0 -70
@@ -1,20 +0,0 @@
1
- module DataSource.Internal.Request exposing (request)
2
-
3
- import DataSource exposing (DataSource)
4
- import DataSource.Http exposing (Body, Expect)
5
-
6
-
7
- request :
8
- { name : String
9
- , body : Body
10
- , expect : Expect a
11
- }
12
- -> DataSource a
13
- request { name, body, expect } =
14
- DataSource.Http.request
15
- { url = "elm-pages-internal://" ++ name
16
- , method = "GET"
17
- , headers = []
18
- , body = body
19
- }
20
- expect
@@ -1,90 +0,0 @@
1
- module DataSource.Port exposing (get)
2
-
3
- {-|
4
-
5
- @docs get
6
-
7
- -}
8
-
9
- import DataSource
10
- import DataSource.Http
11
- import DataSource.Internal.Request
12
- import Json.Decode exposing (Decoder)
13
- import Json.Encode as Encode
14
-
15
-
16
- {-| In a vanilla Elm application, ports let you either send or receive JSON data between your Elm application and the JavaScript context in the user's browser at runtime.
17
-
18
- With `DataSource.Port`, you send and receive JSON to JavaScript running in NodeJS during build-time. This means that you can call shell scripts, or run NPM packages that are installed, or anything else you could do with NodeJS.
19
-
20
- A `DataSource.Port` will call an async JavaScript function with the given name. The function receives the input JSON value, and the Decoder is used to decode the return value of the async function.
21
-
22
- Here is the Elm code and corresponding JavaScript definition for getting an environment variable (or a build error if it isn't found).
23
-
24
- import DataSource exposing (DataSource)
25
- import DataSource.Port
26
- import Json.Encode
27
- import OptimizedDecoder as Decode
28
-
29
- data : DataSource String
30
- data =
31
- DataSource.Port.get "environmentVariable"
32
- (Json.Encode.string "EDITOR")
33
- Decode.string
34
-
35
- -- will resolve to "VIM" if you run `EDITOR=vim elm-pages dev`
36
-
37
- ```javascript
38
- const kleur = require("kleur");
39
-
40
-
41
- module.exports =
42
- /**
43
- * @param { unknown } fromElm
44
- * @returns { Promise<unknown> }
45
- */
46
- {
47
- environmentVariable: async function (name) {
48
- const result = process.env[name];
49
- if (result) {
50
- return result;
51
- } else {
52
- throw `No environment variable called ${kleur
53
- .yellow()
54
- .underline(name)}\n\nAvailable:\n\n${Object.keys(process.env).join(
55
- "\n"
56
- )}`;
57
- }
58
- },
59
- }
60
- ```
61
-
62
-
63
- ## Error Handling
64
-
65
- `port-data-source.js`
66
-
67
- Any time you throw an exception from a DataSource.Port definition, it will result in a build error in your `elm-pages build` or dev server. In the example above, if the environment variable
68
- is not found it will result in a build failure. Notice that the NPM package `kleur` is being used in this example to add color to the output for that build error. You can use any tool you
69
- prefer to add ANSI color codes within the error string in an exception and it will show up with color output in the build output and dev server.
70
-
71
-
72
- ## Performance
73
-
74
- As with any JavaScript or NodeJS code, avoid doing blocking IO operations. For example, avoid using `fs.readFileSync`, because blocking IO can slow down your elm-pages builds and dev server.
75
-
76
- -}
77
- get : String -> Encode.Value -> Decoder b -> DataSource.DataSource b
78
- get portName input decoder =
79
- DataSource.Internal.Request.request
80
- { name = "port"
81
- , body =
82
- Encode.object
83
- [ ( "input", input )
84
- , ( "portName", Encode.string portName )
85
- ]
86
- |> DataSource.Http.jsonBody
87
- , expect =
88
- decoder
89
- |> DataSource.Http.expectJson
90
- }
@@ -1,546 +0,0 @@
1
- module DataSource exposing
2
- ( DataSource
3
- , map, succeed, fail
4
- , fromResult
5
- , andThen, resolve, combine
6
- , andMap
7
- , map2, map3, map4, map5, map6, map7, map8, map9
8
- )
9
-
10
- {-| In an `elm-pages` app, each Route Module can define a value `data` which is a `DataSource` that will be resolved **before** `init` is called. That means it is also available
11
- when the page's HTML is pre-rendered during the build step. You can also access the resolved data in `head` to use it for the page's SEO meta tags.
12
-
13
- A `DataSource` lets you pull in data from:
14
-
15
- - Local files ([`DataSource.File`](DataSource-File))
16
- - HTTP requests ([`DataSource.Http`](DataSource-Http))
17
- - Globs, i.e. listing out local files based on a pattern like `content/*.txt` ([`DataSource.Glob`](DataSource-Glob))
18
- - Ports, i.e. getting JSON data from running custom NodeJS, similar to a port in a vanilla Elm app except run at build-time in NodeJS, rather than at run-time in the browser ([`DataSource.Port`](DataSource-Port))
19
- - Hardcoded data (`DataSource.succeed "Hello!"`)
20
- - Or any combination of the above, using `DataSource.map2`, `DataSource.andThen`, or other combining/continuing helpers from this module
21
-
22
-
23
- ## DataSource's vs. Effect's/Cmd's
24
-
25
- DataSource's are always resolved before the page is rendered and sent to the browser. A DataSource is never executed
26
- in the Browser. Instead, the resolved data from the DataSource is passed down to the Browser - it has been resolved
27
- before any client-side JavaScript ever executes. In the case of a pre-rendered route, this is during the CLI build phase,
28
- and for server-rendered routes its DataSource is resolved on the server.
29
-
30
- Effect's/Cmd's are never executed on the CLI or server, they are only executed in the Browser. The data from a Route Module's
31
- `init` function is used to render the initial HTML on the server or build step, but the Effect isn't executed and `update` is never called
32
- before the page is hydrated in the Browser. This gives a deterministic mental model of what the first render will look like,
33
- and a nicely typed way to define the initial `Data` you have to render your initial view.
34
-
35
- Because `elm-pages` hydrates into a full Elm single-page app, it does need the data in order to initialize the Elm app.
36
- So why not just get the data the old-fashioned way, with `elm/http`, for example?
37
-
38
- A few reasons:
39
-
40
- 1. DataSource's allow you to pull in data that you wouldn't normally be able to access from an Elm app, like local files, or listings of files in a folder. Not only that, but the dev server knows to automatically hot reload the data when the files it depends on change, so you can edit the files you used in your DataSource and see the page hot reload as you save!
41
- 2. Because `elm-pages` has a build step, you know that your `DataSource.Http` requests succeeded, your decoders succeeded, your custom DataSource validations succeeded, and everything went smoothly. If something went wrong, you get a build failure and can deal with the issues before the site goes live. That means your users won't see those errors, and as a developer you don't need to handle those error cases in your code! Think of it as "parse, don't validate", but for your entire build.
42
- 3. You don't have to worry about an API being down, or hitting it repeatedly. You can build in data and it will end up as JSON files served up with all the other assets of your site. If your CDN (static site host) is down, then the rest of your site is probably down anyway. If your site host is up, then so is all of your `DataSource` data. Also, it will be served up extremely quickly without needing to wait for any database queries to be performed, `andThen` requests to be resolved, etc., because all of that work and waiting was done at build-time!
43
- 4. You can pre-render pages, including the SEO meta tags, with all that rich, well-typed Elm data available! That's something you can't accomplish with a vanilla Elm app, and it's one of the main use cases for elm-pages.
44
-
45
-
46
- ## Mental Model
47
-
48
- You can think of a DataSource as a declarative (not imperative) definition of data. It represents where to get the data from, and how to transform it (map, combine with other DataSources, etc.).
49
-
50
- Even though an HTTP request is non-deterministic, you should think of it that way as much as possible with a DataSource because elm-pages will only perform a given DataSource.Http request once, and
51
- it will share the result between any other DataSource.Http requests that have the exact same URL, Method, Body, and Headers.
52
-
53
- So calling a function to increment a counter on a server through an HTTP request would not be a good fit for a `DataSource`. Let's imagine we have an HTTP endpoint that gives these stateful results when called repeatedly:
54
-
55
- <https://my-api.example.com/increment-counter>
56
- -> Returns 1
57
- <https://my-api.example.com/increment-counter>
58
- -> Returns 2
59
- <https://my-api.example.com/increment-counter>
60
- -> Returns 3
61
-
62
- If we define a `DataSource` that hits that endpoint:
63
-
64
- data =
65
- DataSource.Http.get
66
- "https://my-api.example.com/increment-counter"
67
- Decode.int
68
-
69
- No matter how many places we use that `DataSource`, its response will be "locked in" (let's say the response was `3`, then every page would have the same value of `3` for that request).
70
-
71
- So even though HTTP requests, JavaScript code, etc. can be non-deterministic, a `DataSource` always represents a single snapshot of a resource, and those values will be re-used as if they were a deterministic, declarative resource.
72
- So it's best to use that mental model to avoid confusion.
73
-
74
-
75
- ## Basics
76
-
77
- @docs DataSource
78
-
79
- @docs map, succeed, fail
80
-
81
- @docs fromResult
82
-
83
-
84
- ## Chaining Requests
85
-
86
- @docs andThen, resolve, combine
87
-
88
- @docs andMap
89
-
90
- @docs map2, map3, map4, map5, map6, map7, map8, map9
91
-
92
- -}
93
-
94
- import Pages.Internal.StaticHttpBody as Body
95
- import Pages.StaticHttp.Request as HashRequest
96
- import Pages.StaticHttpRequest exposing (RawRequest(..))
97
- import RequestsAndPending exposing (RequestsAndPending)
98
-
99
-
100
- {-| A DataSource represents data that will be gathered at build time. Multiple `DataSource`s can be combined together using the `mapN` functions,
101
- very similar to how you can manipulate values with Json Decoders in Elm.
102
- -}
103
- type alias DataSource value =
104
- RawRequest value
105
-
106
-
107
- {-| Transform a request into an arbitrary value. The same underlying HTTP requests will be performed during the build
108
- step, but mapping allows you to change the resulting values by applying functions to the results.
109
-
110
- A common use for this is to map your data into your elm-pages view:
111
-
112
- import DataSource
113
- import Json.Decode as Decode exposing (Decoder)
114
-
115
- view =
116
- DataSource.Http.get
117
- (Secrets.succeed "https://api.github.com/repos/dillonkearns/elm-pages")
118
- (Decode.field "stargazers_count" Decode.int)
119
- |> DataSource.map
120
- (\stars ->
121
- { view =
122
- \model viewForPage ->
123
- { title = "Current stars: " ++ String.fromInt stars
124
- , body = Html.text <| "⭐️ " ++ String.fromInt stars
125
- , head = []
126
- }
127
- }
128
- )
129
-
130
- -}
131
- map : (a -> b) -> DataSource a -> DataSource b
132
- map fn requestInfo =
133
- case requestInfo of
134
- ApiRoute value ->
135
- ApiRoute (fn value)
136
-
137
- Request urls lookupFn ->
138
- Request
139
- urls
140
- (mapLookupFn fn lookupFn)
141
-
142
- RequestError error ->
143
- RequestError error
144
-
145
-
146
- mapLookupFn : (a -> b) -> (d -> c -> DataSource a) -> d -> c -> DataSource b
147
- mapLookupFn fn lookupFn maybeMock requests =
148
- map fn (lookupFn maybeMock requests)
149
-
150
-
151
- {-| Helper to remove an inner layer of Request wrapping.
152
- -}
153
- resolve : DataSource (List (DataSource value)) -> DataSource (List value)
154
- resolve =
155
- andThen combine
156
-
157
-
158
- {-| Turn a list of `StaticHttp.Request`s into a single one.
159
-
160
- import DataSource
161
- import Json.Decode as Decode exposing (Decoder)
162
-
163
- type alias Pokemon =
164
- { name : String
165
- , sprite : String
166
- }
167
-
168
- pokemonDetailRequest : StaticHttp.Request (List Pokemon)
169
- pokemonDetailRequest =
170
- StaticHttp.get
171
- (Secrets.succeed "https://pokeapi.co/api/v2/pokemon/?limit=3")
172
- (Decode.field "results"
173
- (Decode.list
174
- (Decode.map2 Tuple.pair
175
- (Decode.field "name" Decode.string)
176
- (Decode.field "url" Decode.string)
177
- |> Decode.map
178
- (\( name, url ) ->
179
- StaticHttp.get (Secrets.succeed url)
180
- (Decode.at
181
- [ "sprites", "front_default" ]
182
- Decode.string
183
- |> Decode.map (Pokemon name)
184
- )
185
- )
186
- )
187
- )
188
- )
189
- |> StaticHttp.andThen StaticHttp.combine
190
-
191
- -}
192
- combine : List (DataSource value) -> DataSource (List value)
193
- combine items =
194
- List.foldl (map2 (::)) (succeed []) items |> map List.reverse
195
-
196
-
197
- {-| Like map, but it takes in two `Request`s.
198
-
199
- view siteMetadata page =
200
- StaticHttp.map2
201
- (\elmPagesStars elmMarkdownStars ->
202
- { view =
203
- \model viewForPage ->
204
- { title = "Repo Stargazers"
205
- , body = starsView elmPagesStars elmMarkdownStars
206
- }
207
- , head = head elmPagesStars elmMarkdownStars
208
- }
209
- )
210
- (get
211
- (Secrets.succeed "https://api.github.com/repos/dillonkearns/elm-pages")
212
- (Decode.field "stargazers_count" Decode.int)
213
- )
214
- (get
215
- (Secrets.succeed "https://api.github.com/repos/dillonkearns/elm-markdown")
216
- (Decode.field "stargazers_count" Decode.int)
217
- )
218
-
219
- -}
220
- map2 : (a -> b -> c) -> DataSource a -> DataSource b -> DataSource c
221
- map2 fn request1 request2 =
222
- case ( request1, request2 ) of
223
- ( ApiRoute value1, ApiRoute value2 ) ->
224
- ApiRoute (fn value1 value2)
225
-
226
- ( Request urls1 lookupFn1, Request urls2 lookupFn2 ) ->
227
- Request
228
- (urls1 ++ urls2)
229
- (mapReq fn lookupFn1 lookupFn2)
230
-
231
- ( Request urls1 lookupFn1, ApiRoute value2 ) ->
232
- Request
233
- urls1
234
- (mapReq fn lookupFn1 (\_ _ -> ApiRoute value2))
235
-
236
- ( ApiRoute value2, Request urls1 lookupFn1 ) ->
237
- Request
238
- urls1
239
- (mapReq fn (\_ _ -> ApiRoute value2) lookupFn1)
240
-
241
- ( RequestError error, _ ) ->
242
- RequestError error
243
-
244
- ( _, RequestError error ) ->
245
- RequestError error
246
-
247
-
248
- mapReq : (a -> b -> c) -> (e -> d -> DataSource a) -> (e -> d -> DataSource b) -> e -> d -> DataSource c
249
- mapReq fn lookupFn1 lookupFn2 maybeMock rawResponses =
250
- map2 fn
251
- (lookupFn1 maybeMock rawResponses)
252
- (lookupFn2 maybeMock rawResponses)
253
-
254
-
255
- lookup : Maybe Pages.StaticHttpRequest.MockResolver -> DataSource value -> RequestsAndPending -> Result Pages.StaticHttpRequest.Error value
256
- lookup maybeMockResolver requestInfo rawResponses =
257
- case requestInfo of
258
- Request urls lookupFn ->
259
- lookup maybeMockResolver
260
- (addUrls urls (lookupFn maybeMockResolver rawResponses))
261
- rawResponses
262
-
263
- ApiRoute value ->
264
- Ok value
265
-
266
- RequestError error ->
267
- Err error
268
-
269
-
270
- addUrls : List HashRequest.Request -> DataSource value -> DataSource value
271
- addUrls urlsToAdd requestInfo =
272
- case requestInfo of
273
- ApiRoute value ->
274
- ApiRoute value
275
-
276
- Request initialUrls function ->
277
- Request (initialUrls ++ urlsToAdd) function
278
-
279
- RequestError error ->
280
- RequestError error
281
-
282
-
283
- {-| The full details to perform a StaticHttp request.
284
- -}
285
- type alias RequestDetails =
286
- { url : String
287
- , method : String
288
- , headers : List ( String, String )
289
- , body : Body.Body
290
- , useCache : Bool
291
- }
292
-
293
-
294
- lookupUrls : DataSource value -> List RequestDetails
295
- lookupUrls requestInfo =
296
- case requestInfo of
297
- ApiRoute _ ->
298
- []
299
-
300
- Request urls _ ->
301
- urls
302
-
303
- RequestError _ ->
304
- -- TODO should this have URLs passed through?
305
- []
306
-
307
-
308
- {-| Build off of the response from a previous `DataSource` request to build a follow-up request. You can use the data
309
- from the previous response to build up the URL, headers, etc. that you send to the subsequent request.
310
-
311
- import DataSource
312
- import Json.Decode as Decode exposing (Decoder)
313
-
314
- licenseData : DataSource String
315
- licenseData =
316
- DataSource.Http.get
317
- (Secrets.succeed "https://api.github.com/repos/dillonkearns/elm-pages")
318
- (Decode.at [ "license", "url" ] Decode.string)
319
- |> DataSource.andThen
320
- (\licenseUrl ->
321
- DataSource.Http.get (Secrets.succeed licenseUrl) (Decode.field "description" Decode.string)
322
- )
323
-
324
- -}
325
- andThen : (a -> DataSource b) -> DataSource a -> DataSource b
326
- andThen fn requestInfo =
327
- Request
328
- (lookupUrls requestInfo)
329
- (\maybeMockResolver rawResponses ->
330
- lookup maybeMockResolver
331
- requestInfo
332
- rawResponses
333
- |> (\result ->
334
- case result of
335
- Ok value ->
336
- case fn value of
337
- ApiRoute finalValue ->
338
- ApiRoute finalValue
339
-
340
- Request values function ->
341
- Request values function
342
-
343
- RequestError error ->
344
- RequestError error
345
-
346
- Err error ->
347
- RequestError error
348
- )
349
- )
350
-
351
-
352
- {-| A helper for combining `DataSource`s in pipelines.
353
- -}
354
- andMap : DataSource a -> DataSource (a -> b) -> DataSource b
355
- andMap =
356
- map2 (|>)
357
-
358
-
359
- {-| This is useful for prototyping with some hardcoded data, or for having a view that doesn't have any StaticHttp data.
360
-
361
- import DataSource
362
-
363
- view :
364
- List ( PagePath, Metadata )
365
- ->
366
- { path : PagePath
367
- , frontmatter : Metadata
368
- }
369
- ->
370
- StaticHttp.Request
371
- { view : Model -> View -> { title : String, body : Html Msg }
372
- , head : List (Head.Tag Pages.PathKey)
373
- }
374
- view siteMetadata page =
375
- StaticHttp.succeed
376
- { view =
377
- \model viewForPage ->
378
- mainView model viewForPage
379
- , head = head page.frontmatter
380
- }
381
-
382
- -}
383
- succeed : a -> DataSource a
384
- succeed value =
385
- ApiRoute value
386
-
387
-
388
- {-| Stop the StaticHttp chain with the given error message. If you reach a `fail` in your request,
389
- you will get a build error. Or in the dev server, you will see the error message in an overlay in your browser (and in
390
- the terminal).
391
- -}
392
- fail : String -> DataSource a
393
- fail errorMessage =
394
- RequestError (Pages.StaticHttpRequest.UserCalledStaticHttpFail errorMessage)
395
-
396
-
397
- {-| Turn an Err into a DataSource failure.
398
- -}
399
- fromResult : Result String value -> DataSource value
400
- fromResult result =
401
- case result of
402
- Ok okValue ->
403
- succeed okValue
404
-
405
- Err error ->
406
- fail error
407
-
408
-
409
- {-| -}
410
- map3 :
411
- (value1 -> value2 -> value3 -> valueCombined)
412
- -> DataSource value1
413
- -> DataSource value2
414
- -> DataSource value3
415
- -> DataSource valueCombined
416
- map3 combineFn request1 request2 request3 =
417
- succeed combineFn
418
- |> map2 (|>) request1
419
- |> map2 (|>) request2
420
- |> map2 (|>) request3
421
-
422
-
423
- {-| -}
424
- map4 :
425
- (value1 -> value2 -> value3 -> value4 -> valueCombined)
426
- -> DataSource value1
427
- -> DataSource value2
428
- -> DataSource value3
429
- -> DataSource value4
430
- -> DataSource valueCombined
431
- map4 combineFn request1 request2 request3 request4 =
432
- succeed combineFn
433
- |> map2 (|>) request1
434
- |> map2 (|>) request2
435
- |> map2 (|>) request3
436
- |> map2 (|>) request4
437
-
438
-
439
- {-| -}
440
- map5 :
441
- (value1 -> value2 -> value3 -> value4 -> value5 -> valueCombined)
442
- -> DataSource value1
443
- -> DataSource value2
444
- -> DataSource value3
445
- -> DataSource value4
446
- -> DataSource value5
447
- -> DataSource valueCombined
448
- map5 combineFn request1 request2 request3 request4 request5 =
449
- succeed combineFn
450
- |> map2 (|>) request1
451
- |> map2 (|>) request2
452
- |> map2 (|>) request3
453
- |> map2 (|>) request4
454
- |> map2 (|>) request5
455
-
456
-
457
- {-| -}
458
- map6 :
459
- (value1 -> value2 -> value3 -> value4 -> value5 -> value6 -> valueCombined)
460
- -> DataSource value1
461
- -> DataSource value2
462
- -> DataSource value3
463
- -> DataSource value4
464
- -> DataSource value5
465
- -> DataSource value6
466
- -> DataSource valueCombined
467
- map6 combineFn request1 request2 request3 request4 request5 request6 =
468
- succeed combineFn
469
- |> map2 (|>) request1
470
- |> map2 (|>) request2
471
- |> map2 (|>) request3
472
- |> map2 (|>) request4
473
- |> map2 (|>) request5
474
- |> map2 (|>) request6
475
-
476
-
477
- {-| -}
478
- map7 :
479
- (value1 -> value2 -> value3 -> value4 -> value5 -> value6 -> value7 -> valueCombined)
480
- -> DataSource value1
481
- -> DataSource value2
482
- -> DataSource value3
483
- -> DataSource value4
484
- -> DataSource value5
485
- -> DataSource value6
486
- -> DataSource value7
487
- -> DataSource valueCombined
488
- map7 combineFn request1 request2 request3 request4 request5 request6 request7 =
489
- succeed combineFn
490
- |> map2 (|>) request1
491
- |> map2 (|>) request2
492
- |> map2 (|>) request3
493
- |> map2 (|>) request4
494
- |> map2 (|>) request5
495
- |> map2 (|>) request6
496
- |> map2 (|>) request7
497
-
498
-
499
- {-| -}
500
- map8 :
501
- (value1 -> value2 -> value3 -> value4 -> value5 -> value6 -> value7 -> value8 -> valueCombined)
502
- -> DataSource value1
503
- -> DataSource value2
504
- -> DataSource value3
505
- -> DataSource value4
506
- -> DataSource value5
507
- -> DataSource value6
508
- -> DataSource value7
509
- -> DataSource value8
510
- -> DataSource valueCombined
511
- map8 combineFn request1 request2 request3 request4 request5 request6 request7 request8 =
512
- succeed combineFn
513
- |> map2 (|>) request1
514
- |> map2 (|>) request2
515
- |> map2 (|>) request3
516
- |> map2 (|>) request4
517
- |> map2 (|>) request5
518
- |> map2 (|>) request6
519
- |> map2 (|>) request7
520
- |> map2 (|>) request8
521
-
522
-
523
- {-| -}
524
- map9 :
525
- (value1 -> value2 -> value3 -> value4 -> value5 -> value6 -> value7 -> value8 -> value9 -> valueCombined)
526
- -> DataSource value1
527
- -> DataSource value2
528
- -> DataSource value3
529
- -> DataSource value4
530
- -> DataSource value5
531
- -> DataSource value6
532
- -> DataSource value7
533
- -> DataSource value8
534
- -> DataSource value9
535
- -> DataSource valueCombined
536
- map9 combineFn request1 request2 request3 request4 request5 request6 request7 request8 request9 =
537
- succeed combineFn
538
- |> map2 (|>) request1
539
- |> map2 (|>) request2
540
- |> map2 (|>) request3
541
- |> map2 (|>) request4
542
- |> map2 (|>) request5
543
- |> map2 (|>) request6
544
- |> map2 (|>) request7
545
- |> map2 (|>) request8
546
- |> map2 (|>) request9