UNPKG

permix

Version:

Permix is a lightweight, framework-agnostic, type-safe permissions management library for JavaScript applications on the client and server sides.

90 lines (89 loc) 2.44 kB
import { PermixNotFoundError, createCheckContext, createHooks, createPermix as createPermix$1, createTemplate } from "../core/index.mjs"; //#region src/elysia/permix.ts function buildPermix(resolveKey, options = {}) { const onForbidden = options.onForbidden ?? (({ context }) => { context.set.status = "Forbidden"; return { error: "Forbidden" }; }); const hooks = createHooks(); function get(context) { return context.store[resolveKey()] ?? null; } function getOrThrow(context) { const instance = get(context); if (!instance) throw new PermixNotFoundError(resolveKey()); return instance; } function setupMiddleware(callbackOrRules) { return async (context) => { const instance = createPermix$1(typeof callbackOrRules === "function" ? await callbackOrRules({ context }) : callbackOrRules); instance.hook("check", (ctx) => hooks.callHook("check", ctx)); context.store[resolveKey()] = instance; }; } const checkMiddleware = (...args) => { return async (context) => { if (!getOrThrow(context).check(...args)) return await onForbidden({ context, ...createCheckContext(...args) }); }; }; function getRules(context) { return get(context)?.getRules() ?? null; } function template(rules) { return createTemplate(rules); } return { setupMiddleware, checkMiddleware, template, get, getOrThrow, getRules, hook: hooks.hook, hookOnce: hooks.hookOnce, get key() { return resolveKey(); }, $inferDefinition: void 0, $inferPath: void 0 }; } /** * Create a middleware factory that wires Permix into Elysia routes. * * Use `.contextKey('name')` to set a custom context key (defaults to a unique * `Symbol('permix')`). * * @example * ```ts * import { Elysia } from 'elysia' * import { createPermix } from 'permix/elysia' * * const permix = createPermix<{ * post: ['create', 'read'] * }>() * * new Elysia() * .onBeforeHandle(permix.setupMiddleware(({ context }) => ({ * post: { create: true, read: true }, * }))) * .onBeforeHandle('/posts', permix.checkMiddleware('post.read')) * .get('/posts', () => ({ ok: true })) * .listen(3000) * ``` * * @link https://permix.letstri.dev/docs/integrations/elysia */ function createPermix(options = {}) { let key = Symbol("permix"); const permix = buildPermix(() => key, options); return Object.assign(permix, { contextKey(newKey) { key = newKey; return permix; } }); } //#endregion export { createPermix };