Problem
Currently, every route that needs authentication info does this:
const payload = c.get("jwtPayload") as { sub: string; role: UserRole };
// then uses payload.sub, payload.role
This has several issues:
- JWT-coupled — switching auth mechanisms breaks every single route
- Repetitive boilerplate — every handler casts and destructures manually
- Unsafe typing — the
as cast bypasses compile-time safety
- Already propagating — PR 2 (
reservations.ts) has 4 occurrences of the same pattern
Proposed Solution
1. Extend AppEnv.Variables in apps/backend/src/config/env.ts
export interface AppEnv {
Variables: {
db: Db;
userId: string;
userRole: UserRole;
};
// ... Bindings unchanged
}
2. Update authMiddleware in apps/backend/src/middleware/auth.ts
After JWT verification, set typed variables instead of only c.set("jwtPayload", payload):
c.set("userId", payload.sub as string);
c.set("userRole", payload.role as UserRole);
3. Update roleGuard
Read c.var.userRole instead of c.get("jwtPayload").
4. Update all routes
Replace in every route that uses jwtPayload:
// BEFORE
const payload = c.get("jwtPayload") as { sub: string; role: UserRole };
const userId = payload.sub;
const role = payload.role;
// AFTER
const userId = c.var.userId;
const role = c.var.userRole;
Files affected
apps/backend/src/config/env.ts — add userId and userRole to AppEnv.Variables
apps/backend/src/middleware/auth.ts — set vars in authMiddleware, update roleGuard
apps/backend/src/routes/reservations.ts — 4 jwtPayload occurrences
Note: Other routes (ventures, projects, products, services, auth, health) currently use c.var.db only and do NOT reference jwtPayload — no changes needed there.
Acceptance Criteria
Priority
Low — non-blocking refactor. Cleanup before adding more routes that would repeat the pattern.
Problem
Currently, every route that needs authentication info does this:
This has several issues:
ascast bypasses compile-time safetyreservations.ts) has 4 occurrences of the same patternProposed Solution
1. Extend
AppEnv.Variablesinapps/backend/src/config/env.ts2. Update
authMiddlewareinapps/backend/src/middleware/auth.tsAfter JWT verification, set typed variables instead of only
c.set("jwtPayload", payload):3. Update
roleGuardRead
c.var.userRoleinstead ofc.get("jwtPayload").4. Update all routes
Replace in every route that uses jwtPayload:
Files affected
apps/backend/src/config/env.ts— adduserIdanduserRoletoAppEnv.Variablesapps/backend/src/middleware/auth.ts— set vars in authMiddleware, update roleGuardapps/backend/src/routes/reservations.ts— 4 jwtPayload occurrencesNote: Other routes (ventures, projects, products, services, auth, health) currently use
c.var.dbonly and do NOT reference jwtPayload — no changes needed there.Acceptance Criteria
c.var.userIdreturnsstring(typed, no cast needed)c.var.userRolereturnsUserRole(typed, no cast needed)roleGuardusesc.var.userRoleinstead ofc.get("jwtPayload")c.var.userIdandc.var.userRolemake checkpassesc.get("jwtPayload")calls in route filesPriority
Low — non-blocking refactor. Cleanup before adding more routes that would repeat the pattern.