//#region src/gateway/security/operator-scopes.ts
/**
* Operator scope system for fine-grained gateway API authorization.
*
* Each gateway API method maps to one or more required scopes.
* Clients declare their scopes at connection time; the gateway enforces
* that the declared scopes cover the method being invoked.
*/
const ADMIN_SCOPE = "operator.admin";
const READ_SCOPE = "operator.read";
const WRITE_SCOPE = "operator.write";
const KNOWN_OPERATOR_SCOPES = new Set([
	ADMIN_SCOPE,
	READ_SCOPE,
	WRITE_SCOPE
]);
function isOperatorScope(value) {
	return typeof value === "string" && KNOWN_OPERATOR_SCOPES.has(value);
}
/** Default scopes granted to authenticated CLI / direct connections. */
const DEFAULT_OPERATOR_SCOPES = [
	ADMIN_SCOPE,
	READ_SCOPE,
	WRITE_SCOPE
];
/**
* Route-level scope requirements.
* Maps HTTP route path prefixes to required minimum scope.
*/
const ROUTE_SCOPE_REQUIREMENTS = [
	{
		prefix: "/api/config",
		scope: ADMIN_SCOPE
	},
	{
		prefix: "/api/update",
		scope: ADMIN_SCOPE
	},
	{
		prefix: "/api/extensions/registry",
		scope: ADMIN_SCOPE
	},
	{
		prefix: "/api/agent",
		scope: WRITE_SCOPE
	},
	{
		prefix: "/api/sessions",
		scope: WRITE_SCOPE
	},
	{
		prefix: "/api/cron",
		scope: WRITE_SCOPE
	},
	{
		prefix: "/api/channels",
		scope: WRITE_SCOPE
	},
	{
		prefix: "/api/agents",
		scope: WRITE_SCOPE
	},
	{
		prefix: "/api/workspace",
		scope: WRITE_SCOPE
	},
	{
		prefix: "/api/skills",
		scope: WRITE_SCOPE
	},
	{
		prefix: "/api/marketplace/install",
		scope: ADMIN_SCOPE
	},
	{
		prefix: "/api/marketplace/uninstall",
		scope: ADMIN_SCOPE
	},
	{
		prefix: "/api/commands",
		scope: WRITE_SCOPE
	},
	{
		prefix: "/api/host-fs",
		scope: WRITE_SCOPE
	},
	{
		prefix: "/api/status",
		scope: READ_SCOPE
	},
	{
		prefix: "/api/models",
		scope: READ_SCOPE
	},
	{
		prefix: "/api/logs",
		scope: READ_SCOPE
	},
	{
		prefix: "/api/doctor",
		scope: READ_SCOPE
	},
	{
		prefix: "/api/events",
		scope: READ_SCOPE
	}
];
/** Scope hierarchy: admin > write > read. */
const SCOPE_HIERARCHY = {
	[ADMIN_SCOPE]: 3,
	[WRITE_SCOPE]: 2,
	[READ_SCOPE]: 1
};
function scopeSatisfies(granted, required) {
	return SCOPE_HIERARCHY[granted] >= SCOPE_HIERARCHY[required];
}
/**
* Check whether a set of granted scopes satisfies the required scope for a route.
*/
function authorizeRouteScope(routePath, grantedScopes) {
	const routeRequirement = ROUTE_SCOPE_REQUIREMENTS.find((entry) => routePath.startsWith(entry.prefix));
	if (!routeRequirement) return authorizeScope(READ_SCOPE, grantedScopes);
	return authorizeScope(routeRequirement.scope, grantedScopes);
}
/**
* Check whether any of the granted scopes satisfies the required scope.
*/
function authorizeScope(requiredScope, grantedScopes) {
	if (grantedScopes.some((granted) => scopeSatisfies(granted, requiredScope))) return { allowed: true };
	return {
		allowed: false,
		requiredScope
	};
}
/**
* Parse scopes from a comma-separated header value.
*/
function parseScopesHeader(headerValue) {
	if (!headerValue?.trim()) return [...DEFAULT_OPERATOR_SCOPES];
	return headerValue.split(",").map((scope) => scope.trim()).filter(isOperatorScope);
}
//#endregion
export { ADMIN_SCOPE, DEFAULT_OPERATOR_SCOPES, KNOWN_OPERATOR_SCOPES, READ_SCOPE, WRITE_SCOPE, authorizeRouteScope, authorizeScope, isOperatorScope, parseScopesHeader };

//# sourceMappingURL=operator-scopes.js.map