From 69312f5133734237edaea6ca29e2de9bf3203050 Mon Sep 17 00:00:00 2001 From: polwex Date: Sun, 15 Jun 2025 01:44:45 +0700 Subject: checkpoint here... --- bs5/universal/native/shared/Router.re | 117 ++++++++++++++++++++++++++++++++++ 1 file changed, 117 insertions(+) create mode 100644 bs5/universal/native/shared/Router.re (limited to 'bs5/universal/native/shared/Router.re') diff --git a/bs5/universal/native/shared/Router.re b/bs5/universal/native/shared/Router.re new file mode 100644 index 0000000..7b814a6 --- /dev/null +++ b/bs5/universal/native/shared/Router.re @@ -0,0 +1,117 @@ +let home = "/"; +let demoRenderToStaticMarkup = "/demo/render-to-static-markup"; +let demoRenderToString = "/demo/render-to-string"; +let demoRenderToStream = "/demo/render-to-stream"; +let demoServerOnlyRSC = "/demo/server-only-rsc"; +let demoSinglePageRSC = "/demo/single-page-rsc"; +let demoRouterRSC = "/demo/router-rsc"; + +let links = [| + ("Server side render to string (renderToString)", demoRenderToString), + ( + "Server side render to static markup (renderToStaticMarkup)", + demoRenderToStaticMarkup, + ), + ("Server side render to stream (renderToStream)", demoRenderToStream), + ( + "React Server components without client (createFromFetch)", + demoServerOnlyRSC, + ), + ( + "React Server components with createFromReadableStream (RSC + SSR)", + demoSinglePageRSC, + ), + ( + "React Server components with single page router (createFromFetch + createFromReadableStream)", + demoRouterRSC, + ), +|]; + +module Menu = { + [@react.component] + let make = () => { + ; + }; +}; +type location = { + selectedId: option(int), + isEditing: bool, + searchText: option(string), +}; + +let locationToString = location => + [ + switch (location.selectedId) { + | Some(id) => "selectedId=" ++ Int.to_string(id) + | None => "" + }, + "isEditing=" ++ (location.isEditing ? "true" : "false"), + switch (location.searchText) { + | Some(text) => "searchText=" ++ text + | None => "" + }, + ] + |> List.filter(s => s != "") + |> String.concat("&"); + +let initialLocation = { + selectedId: None, + isEditing: false, + searchText: None, +}; + +let locationFromString = str => { + switch (URL.make(str)) { + | Some(url) => + let searchParams = URL.searchParams(url); + let selectedId = + URL.SearchParams.get(searchParams, "selectedId") + |> Option.map(id => int_of_string(id)); + let searchText = URL.SearchParams.get(searchParams, "searchText"); + + let isEditing = + URL.SearchParams.get(searchParams, "isEditing") + |> Option.map(v => + switch (v) { + | "true" => true + | "false" => false + | _ => false + } + ) + |> Option.value(~default=false); + + { + selectedId, + isEditing, + searchText, + }; + + | None => initialLocation + }; +}; + +type payload = { + body: string, + title: string, +}; + +/* 'a is melange-fetch's response in melange */ +type t('a) = { + location, + navigate: location => unit, + useAction: (string, string) => ((payload, location, unit) => unit, bool), + refresh: option('a) => unit, +}; + +let useRouter = () => { + location: initialLocation, + navigate: _ => (), + useAction: (_, _) => ((_, _, _) => (), false), + refresh: _ => (), +}; -- cgit v1.2.3