The core engine
@vperms/core is the pure TypeScript engine: pattern matching, inheritance
traversal, precedence and resolution. It has no dependencies, no validation and
no I/O beyond the adapter abstraction. Most applications use the higher-level
vperms service instead, but the core is public and useful
when you need the building blocks directly.
The adapter contract
Section titled “The adapter contract”Everything the engine needs from storage goes through one abstract class:
import type { PermissionGrant, Subject } from "@vperms/core";
abstract class VeguiPermsAdapter { abstract findSubject(workspaceId: string, subjectId: string): Promise<Subject | null>; abstract saveSubject(workspaceId: string, subject: Subject): Promise<Subject>; abstract deleteSubject(workspaceId: string, subjectId: string): Promise<boolean>; abstract findSubjectGrants(workspaceId: string, subjectId: string): Promise<PermissionGrant[]>; abstract grantPermission( workspaceId: string, subjectId: string, permission: string, value: boolean, ): Promise<PermissionGrant>; abstract ungrantPermission( workspaceId: string, subjectId: string, permission: string, ): Promise<boolean>;}An adapter only stores and retrieves data. It performs no validation, resolution, inheritance or evaluation — the engine and service handle all of that. See Writing a custom adapter.
Matching
Section titled “Matching”import { matchesPattern, matchPermission } from "@vperms/core";
matchesPattern("workspaces.1.*", "workspaces.1.read"); // true
matchPermission( [ { permission: "workspaces.*", value: true, subjectId: "u", workspaceId: "w" }, { permission: "workspaces.1.*", value: false, subjectId: "u", workspaceId: "w" }, ], "workspaces.1.read",); // falsematchesPattern is the raw segment matcher. matchPermission sorts with
compareGrants and returns the best match, or null.
Precedence
Section titled “Precedence”import { compareGrants, permissionSpecificity } from "@vperms/core";
permissionSpecificity("workspaces.*.read"); // 5permissionSpecificity("workspaces.1.*"); // 4compareGrants(a, b) orders grants highest-priority-first. See
Resolution for the full rule list.
Inheritance and resolution
Section titled “Inheritance and resolution”import { resolveInheritedPermissions, resolveSubjectPermissions, canResolved,} from "@vperms/core";
const inherited = await resolveInheritedPermissions(adapter, workspaceId, subject, { defaultParents,});const effective = await resolveSubjectPermissions(adapter, workspaceId, subject, { defaultParents,});canResolved(effective, "workspaces.1.read");These are the exact functions the service calls. The vperms package
re-exports the most common of them (canResolved,
resolveSubjectPermissions, subjectPermissionsPermission,
SELF_PERMISSIONS_PERMISSION, the layer constants, and the shared types).
Layers
Section titled “Layers”import { EXPLICIT_PARENT_LAYER, // 0 TYPE_DEFAULT_PARENT_LAYER, // 1 GLOBAL_DEFAULT_PARENT_LAYER, // 2 BUILTIN_PERMISSION_LAYER, // 3} from "@vperms/core";Layer numbers are ordered by priority: lower is stronger. See the full API reference.