simple-web-app

Unnamed repository; edit this file 'description' to name the repository.
Log | Files | Refs | README

commit d824539220c6ce5105a4937b7b4c3c0c04ce423c
parent b29468f52db172037b861e7c6a907d2d66dfaf11
Author: Silas Brack <silasbrack@gmail.com>
Date:   Thu, 11 Jun 2026 12:30:33 +0200

feat: add SSE helper module for Datastar-compliant responses

Adds src/sse.rs with helpers that format proper SSE
datastar-patch-elements events per the Datastar SSE spec,
replacing the non-standard custom header approach.

Co-Authored-By: Claude Opus 4.6 (1M context) <noreply@anthropic.com>

Diffstat:
Msrc/main.rs | 1+
Asrc/sse.rs | 35+++++++++++++++++++++++++++++++++++
2 files changed, 36 insertions(+), 0 deletions(-)

diff --git a/src/main.rs b/src/main.rs @@ -3,6 +3,7 @@ mod db; mod error; mod handlers; mod routes; +mod sse; mod state; mod templates; mod trailbase; diff --git a/src/sse.rs b/src/sse.rs @@ -0,0 +1,35 @@ +use axum::{body::Body, http::{StatusCode, header}, response::Response}; + +pub fn patch_elements(html: &str) -> Response { + patch_elements_with_options(html, None, None) +} + +pub fn patch_elements_with_selector(html: &str, selector: &str) -> Response { + patch_elements_with_options(html, Some(selector), None) +} + +fn patch_elements_with_options( + html: &str, + selector: Option<&str>, + mode: Option<&str>, +) -> Response { + let mut data_lines = Vec::new(); + if let Some(sel) = selector { + data_lines.push(format!("data: selector {sel}")); + } + if let Some(m) = mode { + data_lines.push(format!("data: mode {m}")); + } + for line in html.lines() { + data_lines.push(format!("data: elements {line}")); + } + + let body = format!("event: datastar-patch-elements\n{}\n\n", data_lines.join("\n")); + + Response::builder() + .status(StatusCode::OK) + .header(header::CONTENT_TYPE, "text/event-stream") + .header(header::CACHE_CONTROL, "no-cache") + .body(Body::from(body)) + .unwrap() +}