mirror of
https://github.com/Studio-Saelix/sencho.git
synced 2026-08-12 19:57:37 +00:00
feat(rbac): make stack-scoped grants node-specific (#1727)
* feat(rbac): make stack-scoped grants node-specific Qualify stack role assignments as (nodeId, stackName), migrate legacy rows to the default node, and forward bound multi-action evidence on Proxy/Pilot hops so scoped users keep least-privilege remote access without shipping the full grant table. * fix: mirror scoped-stack-auth-evidence capability to frontend, sanitize node id in role assignment log Backend added the scoped-stack-auth-evidence capability without the matching frontend entry, failing the capability parity test. The role assignment log also interpolated the node id without sanitizeForLog, unlike the rest of the line. * fix(rbac): honor node-wide scopes and fix proxied DELETE cleanup Node-scoped grants now authorize that role's stack actions on the same node in the backend resolver, frontend can(), and remote evidence. Proxied DELETE cleanup uses the gate-stashed route because pathRewrite mutates req.path before proxyRes. Add proxy integration coverage and drop the stale scoped-permissions screenshot. * fix(rbac): preserve node-qualified grants during repair
This commit is contained in:
@@ -1,5 +1,6 @@
|
||||
import type { UserRole, ApiTokenScope, ApiToken } from '../services/DatabaseService';
|
||||
import type { LicenseTier } from '../services/license-types';
|
||||
import type { PermissionAction } from '../middleware/permissions';
|
||||
|
||||
// Extend Express Request type for user and node context.
|
||||
// This file is imported for its side effects only (ambient declaration).
|
||||
@@ -27,6 +28,22 @@ declare global {
|
||||
deployContext?: import('../services/network/missingExternalNetworksError').DeployInvocationContext;
|
||||
/** Verified JWT scope for machine credentials (`node_proxy` / `pilot_tunnel`). */
|
||||
machineAuthScope?: 'node_proxy' | 'pilot_tunnel';
|
||||
/**
|
||||
* Hub-bound stack-scoped action evidence, trusted only when set under
|
||||
* machine auth (`node_proxy` / `pilot_tunnel`). Never set from browser sessions.
|
||||
*/
|
||||
scopedStackEvidence?: { stackName: string; actions: ReadonlySet<PermissionAction> };
|
||||
/**
|
||||
* Hub-side pending evidence to attach on the outbound proxy hop when
|
||||
* the caller's global role alone would not grant the primary action.
|
||||
*/
|
||||
proxyScopedStackEvidence?: { stackName: string; actions: readonly PermissionAction[] };
|
||||
/**
|
||||
* Named-stack classification from the hub gate. Stashed because
|
||||
* http-proxy pathRewrite mutates req.url before proxyRes, so
|
||||
* re-classifying req.path there would miss DELETE cleanup.
|
||||
*/
|
||||
proxyNamedStackRoute?: { stackName: string; action: PermissionAction };
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
Reference in New Issue
Block a user