Authentication
HTMX apps use the same StreetJS authentication you’d
use for an API — sessions, JWT, RBAC — but responses are HTML fragments and
client-side redirects via HX-Redirect.
Login flow
1
2
3
4
5
6
7
8
9
10
11
@Post('/login')
async login(ctx: StreetContext) {
const { email, password } = ctx.body as { email: string; password: string };
const user = await this.auth.verify(email, password);
if (!user) {
ctx.htmx.fragment('<p class="error">Invalid email or password.</p>', 401);
return;
}
await ctx.session.set('userId', user.id); // server-side session
ctx.htmx.hx({ redirect: '/dashboard' }).fragment(''); // HX-Redirect
}
HX-Redirect tells HTMX to navigate the browser — a clean post/redirect/get
without a JSON round-trip.
Protecting routes
Use the standard StreetJS auth middleware/guards. For HTMX, an unauthenticated
request to a protected page should redirect to /login:
1
2
3
4
5
6
@Get('/dashboard')
@Auth() // core guard
async dashboard(ctx: StreetContext) {
if (!ctx.user) { ctx.htmx.hx({ redirect: '/login' }).fragment(''); return; }
ctx.htmx.view('dashboard', { title: 'Dashboard', user: ctx.user });
}
Register
Same pattern — validate, create the user (hash via the core vault), start a
session, then HX-Redirect. Return field errors as fragments targeted at the
form’s error container.
CSRF
Always include } in auth forms — see Forms & CSRF.
Next: Realtime.