fix(authz): reject Surface: system from HTTP requests (B8)
System means "the plane itself, in-process" (router, coordinator, adapters, lease-expiry reclaim) and is unconditionally FullControl with no token gate. But it was reachable straight from the X-Orchestra-Surface HTTP header, both in authz.HTTP's token check and in main.go's own `surface` closure (which every handler actually calls to authorize an event — it re-parses the header independently of what the HTTP middleware resolved). Since no deployment configures ORCHESTRA_SYSTEM_TOKEN (no legitimate HTTP caller should ever need one), tokens[System] is always "", so the token check was skipped entirely: any LAN request with "X-Orchestra-Surface: system" got unauthenticated full control to emit any event on any task. Both the authz.HTTP middleware and main.go's `surface` closure now downgrade System to Web before doing anything else with it, so the header can never resolve to System over HTTP regardless of token config. AUDIT.md B8.
This commit is contained in:
@@ -75,6 +75,16 @@ func HTTP(tokens map[Surface]string, next http.Handler) http.Handler {
|
||||
if s == "" {
|
||||
s = Web
|
||||
}
|
||||
// System means "the plane itself, in-process" (router, coordinator,
|
||||
// adapters, lease-expiry reclaim) and is always FullControl with no
|
||||
// token gate — it must never be reachable by declaring it over HTTP.
|
||||
// Without this, tokens[System] being unset (as it is by default: no
|
||||
// caller ever needs a System token) makes the check at line ~78 a
|
||||
// no-op, and any LAN request with this header gets unauthenticated
|
||||
// full control over every task.
|
||||
if s == System {
|
||||
s = Web
|
||||
}
|
||||
if expected := tokens[s]; expected != "" && r.Header.Get("Authorization") != "Bearer "+expected {
|
||||
http.Error(w, "unauthorized surface", http.StatusUnauthorized)
|
||||
return
|
||||
|
||||
Reference in New Issue
Block a user