summaryrefslogtreecommitdiff
path: root/bs5/server/Claude.md
diff options
context:
space:
mode:
authorpolwex <polwex@sortug.com>2025-06-14 23:30:34 +0700
committerpolwex <polwex@sortug.com>2025-06-14 23:30:34 +0700
commitd8b3e15bec60f58defad13e961f80354d250235d (patch)
tree6a6f9158141bf40ea452a5913d72160362e0c472 /bs5/server/Claude.md
aaaaaa
Diffstat (limited to 'bs5/server/Claude.md')
-rw-r--r--bs5/server/Claude.md69
1 files changed, 69 insertions, 0 deletions
diff --git a/bs5/server/Claude.md b/bs5/server/Claude.md
new file mode 100644
index 0000000..cbf70d7
--- /dev/null
+++ b/bs5/server/Claude.md
@@ -0,0 +1,69 @@
+
+Core Architecture
+
+ server.re - Main entry point:
+ - Uses Dream web framework (OCaml's web server)
+ - Sets up routing with getAndPost helper for progressive enhancement
+ - Serves static assets (CSS, JS) and handles React rendering
+
+ Key Libraries (from dune file):
+
+ - dream - Web framework
+ - react/reactDOM - Native React implementation
+ - demo_shared_native - Shared components
+ - lwt.unix - Async I/O
+ - yojson - JSON handling
+
+ Rendering Pipeline
+
+ Three rendering modes:
+ 1. renderToString - Basic SSR (line 28-31)
+ 2. renderToStaticMarkup - No hydration attributes (line 34-38)
+ 3. renderToStream - Streaming SSR with React Server Components
+
+ React Server Components (RSC)
+
+ DreamRSC.re handles the magic:
+
+ Content negotiation:
+ switch (Dream.header(request, "Accept")) {
+ | Some(accept) when is_react_component_header(accept) =>
+ stream_model(~location=Dream.target(request), app) (* RSC payload *)
+ | _ =>
+ stream_html(~bootstrapScripts, app) (* Full HTML *)
+
+ Server Actions (lines 50-87):
+ - Reads ACTION_ID header
+ - Decodes form data or request body
+ - Calls registered server function via FunctionReferences.get
+ - Streams response back as application/react.action
+
+ Request Flow
+
+ 1. Client request → Dream router
+ 2. Accept header check → RSC payload vs HTML
+ 3. Server function lookup → FunctionReferences registry
+ 4. Component rendering → ReactServerDOM.render_model/render_html
+ 5. Streaming response → Chunks sent via Dream.write
+
+ File Structure in OCaml syntax:
+
+ (* Main server setup *)
+ let server =
+ Dream.logger (
+ Dream.router [
+ get_and_post "/" Pages.Home.handler;
+ Dream.get "/static/**" (Dream.static "./build/client");
+ (* ... more routes *)
+ ]
+ )
+
+ (* Page handler example *)
+ let handler _request =
+ let app = Document.make [
+ Html.h1 [React.string "Hello"]
+ ] in
+ Dream.html (ReactDOM.renderToStaticMarkup app)
+
+ The beauty is it's a standard Dream web server that happens to render React components natively, with RSC streaming as an enhancement
+ layer on top!