@casual-simulation/aux-common
Version:
Common library for AUX projects
422 lines • 15.6 kB
JavaScript
/* CasualOS is a set of web-based tools designed to facilitate the creation of real-time, multi-user, context-aware interactive experiences.
*
* Copyright (c) 2019-2025 Casual Simulation, Inc.
*
* This program is free software: you can redistribute it and/or modify
* it under the terms of the GNU Affero General Public License as
* published by the Free Software Foundation, either version 3 of the
* License, or (at your option) any later version.
*
* This program is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
* GNU Affero General Public License for more details.
*
* You should have received a copy of the GNU Affero General Public License
* along with this program. If not, see <https://www.gnu.org/licenses/>.
*/
import { memoize } from 'es-toolkit';
import { z } from 'zod';
export const DATA_RESOURCE_KIND = 'data';
export const FILE_RESOURCE_KIND = 'file';
export const EVENT_RESOURCE_KIND = 'event';
export const MARKER_RESOURCE_KIND = 'marker';
export const ROLE_RESOURCE_KIND = 'role';
export const INST_RESOURCE_KIND = 'inst';
export const LOOM_RESOURCE_KIND = 'loom';
export const SLOYD_RESOURCE_KIND = 'ai.sloyd';
export const HUME_RESOURCE_KIND = 'ai.hume';
export const OPENAI_REALTIME_RESOURCE_KIND = 'ai.openai.realtime';
export const AI_CHAT_RESOURCE_KIND = 'ai.chat';
export const AI_IMAGE_RESOURCE_KIND = 'ai.image';
export const AI_SKYBOX_RESOURCE_KIND = 'ai.skybox';
export const WEBHOOK_RESOURCE_KIND = 'webhook';
export const NOTIFICATION_RESOURCE_KIND = 'notification';
export const PACKAGE_RESOURCE_KIND = 'package';
export const PACKAGE_VERSION_RESOURCE_KIND = 'package.version';
export const SEARCH_RESOURCE_KIND = 'search';
export const DATABASE_RESOURCE_KIND = 'database';
export const PURCHASABLE_ITEM_RESOURCE_KIND = 'purchasableItem';
export const CONTRACT_RESOURCE_KIND = 'contract';
export const INVOICE_RESOURCE_KIND = 'invoice';
export const READ_ACTION = 'read';
export const CREATE_ACTION = 'create';
export const UPDATE_ACTION = 'update';
export const DELETE_ACTION = 'delete';
export const ASSIGN_ACTION = 'assign';
export const UNASSIGN_ACTION = 'unassign';
export const INCREMENT_ACTION = 'increment';
export const COUNT_ACTION = 'count';
export const LIST_ACTION = 'list';
export const GRANT_PERMISSION_ACTION = 'grantPermission';
export const REVOKE_PERMISSION_ACTION = 'revokePermission';
export const GRANT_ACTION = 'grant';
export const REVOKE_ACTION = 'revoke';
export const SEND_ACTION_ACTION = 'sendAction';
export const UPDATE_DATA_ACTION = 'updateData';
export const RUN_ACTION = 'run';
export const SEND_ACTION = 'send';
export const SUBSCRIBE_ACTION = 'subscribe';
export const UNSUBSCRIBE_ACTION = 'unsubscribe';
export const LIST_SUBSCRIPTIONS_ACTION = 'listSubscriptions';
export const PURCHASE_ACTION = 'purchase';
export const APPROVE_ACTION = 'approve';
export const CANCEL_ACTION = 'cancel';
export const SUBJECT_TYPE_VALIDATION = memoize(() => z.enum(['user', 'inst', 'role']));
export const DATA_ACTION_KINDS_VALIDATION = memoize(() => z.enum([
READ_ACTION,
CREATE_ACTION,
UPDATE_ACTION,
DELETE_ACTION,
LIST_ACTION,
]));
export const FILE_ACTION_KINDS_VALIDATION = memoize(() => z.enum([
READ_ACTION,
CREATE_ACTION,
UPDATE_ACTION,
DELETE_ACTION,
LIST_ACTION,
]));
export const EVENT_ACTION_KINDS_VALIDATION = memoize(() => z.enum([INCREMENT_ACTION, COUNT_ACTION, UPDATE_ACTION, LIST_ACTION]));
export const MARKER_ACTION_KINDS_VALIDATION = memoize(() => z.enum([
ASSIGN_ACTION,
UNASSIGN_ACTION,
GRANT_PERMISSION_ACTION,
REVOKE_PERMISSION_ACTION,
READ_ACTION,
]));
export const ROLE_ACTION_KINDS_VALIDATION = memoize(() => z.enum([
GRANT_ACTION,
REVOKE_ACTION,
READ_ACTION,
UPDATE_ACTION,
LIST_ACTION,
]));
export const INST_ACTION_KINDS_VALIDATION = memoize(() => z.enum([
CREATE_ACTION,
READ_ACTION,
UPDATE_ACTION,
UPDATE_DATA_ACTION,
DELETE_ACTION,
LIST_ACTION,
SEND_ACTION_ACTION,
]));
export const LOOM_ACTION_KINDS_VALIDATION = memoize(() => z.enum([CREATE_ACTION]));
export const SLOYD_ACTION_KINDS_VALIDATION = memoize(() => z.enum([CREATE_ACTION]));
export const HUME_ACTION_KINDS_VALIDATION = memoize(() => z.enum([CREATE_ACTION]));
export const OPENAI_REALTIME_ACTION_KINDS_VALIDATION = memoize(() => z.enum([CREATE_ACTION]));
export const AI_CHAT_ACTION_KINDS_VALIDATION = memoize(() => z.enum([CREATE_ACTION]));
export const AI_IMAGE_ACTION_KINDS_VALIDATION = memoize(() => z.enum([CREATE_ACTION]));
export const AI_SKYBOX_ACTION_KINDS_VALIDATION = memoize(() => z.enum([CREATE_ACTION]));
export const WEBHOOK_ACTION_KINDS_VALIDATION = memoize(() => z.enum([
CREATE_ACTION,
READ_ACTION,
UPDATE_ACTION,
DELETE_ACTION,
LIST_ACTION,
RUN_ACTION,
]));
export const NOTIFICATION_ACTION_KINDS_VALIDATION = memoize(() => z.enum([
CREATE_ACTION,
READ_ACTION,
UPDATE_ACTION,
DELETE_ACTION,
LIST_ACTION,
SEND_ACTION,
SUBSCRIBE_ACTION,
UNSUBSCRIBE_ACTION,
LIST_SUBSCRIPTIONS_ACTION,
]));
export const PACKAGE_ACTION_KINDS_VALIDATION = memoize(() => z.enum([
CREATE_ACTION,
READ_ACTION,
UPDATE_ACTION,
DELETE_ACTION,
LIST_ACTION,
RUN_ACTION,
]));
export const PACKAGE_VERSION_ACTION_KINDS_VALIDATION = memoize(() => z.enum([
CREATE_ACTION,
READ_ACTION,
UPDATE_ACTION,
DELETE_ACTION,
LIST_ACTION,
RUN_ACTION,
]));
export const SEARCH_ACTION_KINDS_VALIDATION = memoize(() => z.enum([
CREATE_ACTION,
READ_ACTION,
UPDATE_ACTION,
DELETE_ACTION,
LIST_ACTION,
]));
export const DATABASE_ACTION_KINDS_VALIDATION = memoize(() => z.enum([
CREATE_ACTION,
READ_ACTION,
UPDATE_ACTION,
DELETE_ACTION,
LIST_ACTION,
]));
export const PURCHASABLE_ITEM_ACTION_KINDS_VALIDATION = memoize(() => z.enum([
CREATE_ACTION,
READ_ACTION,
UPDATE_ACTION,
DELETE_ACTION,
LIST_ACTION,
PURCHASE_ACTION,
]));
export const CONTRACT_ACTION_KINDS_VALIDATION = memoize(() => z.enum([
CREATE_ACTION,
READ_ACTION,
UPDATE_ACTION,
DELETE_ACTION,
LIST_ACTION,
PURCHASE_ACTION,
CANCEL_ACTION,
]));
export const INVOICE_ACTION_KINDS_VALIDATION = memoize(() => z.enum([
CREATE_ACTION,
READ_ACTION,
UPDATE_ACTION,
DELETE_ACTION,
LIST_ACTION,
APPROVE_ACTION,
CANCEL_ACTION,
]));
export const RESOURCE_KIND_VALIDATION = memoize(() => z.enum([
DATA_RESOURCE_KIND,
FILE_RESOURCE_KIND,
EVENT_RESOURCE_KIND,
MARKER_RESOURCE_KIND,
ROLE_RESOURCE_KIND,
INST_RESOURCE_KIND,
LOOM_RESOURCE_KIND,
SLOYD_RESOURCE_KIND,
HUME_RESOURCE_KIND,
OPENAI_REALTIME_RESOURCE_KIND,
AI_CHAT_RESOURCE_KIND,
AI_IMAGE_RESOURCE_KIND,
AI_SKYBOX_RESOURCE_KIND,
WEBHOOK_RESOURCE_KIND,
NOTIFICATION_RESOURCE_KIND,
PACKAGE_RESOURCE_KIND,
PACKAGE_VERSION_RESOURCE_KIND,
SEARCH_RESOURCE_KIND,
DATABASE_RESOURCE_KIND,
PURCHASABLE_ITEM_RESOURCE_KIND,
CONTRACT_RESOURCE_KIND,
INVOICE_RESOURCE_KIND,
]));
export const ACTION_KINDS_VALIDATION = memoize(() => z.enum([
CREATE_ACTION,
READ_ACTION,
UPDATE_ACTION,
UPDATE_DATA_ACTION,
DELETE_ACTION,
LIST_ACTION,
SEND_ACTION_ACTION,
ASSIGN_ACTION,
UNASSIGN_ACTION,
GRANT_ACTION,
REVOKE_ACTION,
INCREMENT_ACTION,
COUNT_ACTION,
GRANT_PERMISSION_ACTION,
REVOKE_PERMISSION_ACTION,
RUN_ACTION,
SEND_ACTION,
SUBSCRIBE_ACTION,
UNSUBSCRIBE_ACTION,
LIST_SUBSCRIPTIONS_ACTION,
PURCHASE_ACTION,
APPROVE_ACTION,
CANCEL_ACTION,
]));
export const ENTITLEMENT_FEATURE_VALIDATION = memoize(() => z.enum([
'data',
'file',
'event',
'inst',
'notification',
'package',
'permissions',
'webhook',
'ai',
'search',
'database',
]));
export const ENTITLEMENT_VALIDATION = memoize(() => z.object({
feature: ENTITLEMENT_FEATURE_VALIDATION(),
scope: z.enum(['personal', 'owned', 'studio', 'shared', 'designated']),
designatedRecords: z.array(z.string()).optional(),
}));
export const PERMISSION_VALIDATION = memoize(() => z.object({
subjectType: SUBJECT_TYPE_VALIDATION(),
subjectId: z.string().min(1),
resourceId: z.string().min(1).nullable().optional(),
expireTimeMs: z.number().nullable(),
marker: z.string().min(1).max(100).optional(),
}));
export const DATA_PERMISSION_VALIDATION = memoize(() => PERMISSION_VALIDATION().extend({
resourceKind: z.literal(DATA_RESOURCE_KIND),
action: DATA_ACTION_KINDS_VALIDATION().nullable(),
}));
export const FILE_PERMISSION_OPTIONS_VALIDATION = memoize(() => z.object({
maxFileSizeInBytes: z.number().nonnegative().optional(),
allowedMimeTypes: z
.union([z.literal(true), z.array(z.string())])
.optional(),
}));
export const FILE_PERMISSION_VALIDATION = memoize(() => PERMISSION_VALIDATION().extend({
resourceKind: z.literal(FILE_RESOURCE_KIND),
action: FILE_ACTION_KINDS_VALIDATION().nullable(),
options: FILE_PERMISSION_OPTIONS_VALIDATION(),
}));
export const EVENT_PERMISSION_VALIDATION = memoize(() => PERMISSION_VALIDATION().extend({
resourceKind: z.literal(EVENT_RESOURCE_KIND),
resourceId: z.string().min(1).nullable(),
action: EVENT_ACTION_KINDS_VALIDATION().nullable(),
}));
export const MARKER_PERMISSION_VALIDATION = memoize(() => PERMISSION_VALIDATION().extend({
resourceKind: z.literal(MARKER_RESOURCE_KIND),
action: MARKER_ACTION_KINDS_VALIDATION().nullable(),
}));
export const ROLE_PERMISSION_OPTIONS_VALIDATION = memoize(() => z.object({
maxDurationMs: z.number().optional(),
}));
export const ROLE_PERMISSION_VALIDATION = memoize(() => PERMISSION_VALIDATION().extend({
resourceKind: z.literal(ROLE_RESOURCE_KIND),
action: ROLE_ACTION_KINDS_VALIDATION().nullable(),
options: ROLE_PERMISSION_OPTIONS_VALIDATION(),
}));
export const INST_PERMISSION_VALIDATION = memoize(() => PERMISSION_VALIDATION().extend({
resourceKind: z.literal(INST_RESOURCE_KIND),
action: INST_ACTION_KINDS_VALIDATION().nullable(),
}));
export const LOOM_PERMISSION_VALIDATION = memoize(() => PERMISSION_VALIDATION().extend({
resourceKind: z.literal(LOOM_RESOURCE_KIND),
action: LOOM_ACTION_KINDS_VALIDATION().nullable(),
}));
export const SLOYD_PERMISSION_VALIDATION = memoize(() => PERMISSION_VALIDATION().extend({
resourceKind: z.literal(SLOYD_RESOURCE_KIND),
action: SLOYD_ACTION_KINDS_VALIDATION().nullable(),
}));
export const HUME_PERMISSION_VALIDATION = memoize(() => PERMISSION_VALIDATION().extend({
resourceKind: z.literal(HUME_RESOURCE_KIND),
action: HUME_ACTION_KINDS_VALIDATION().nullable(),
}));
export const OPENAI_REALTIME_PERMISSION_VALIDATION = memoize(() => PERMISSION_VALIDATION().extend({
resourceKind: z.literal(OPENAI_REALTIME_RESOURCE_KIND),
action: OPENAI_REALTIME_ACTION_KINDS_VALIDATION().nullable(),
}));
export const AI_CHAT_PERMISSION_VALIDATION = memoize(() => PERMISSION_VALIDATION().extend({
resourceKind: z.literal(AI_CHAT_RESOURCE_KIND),
action: AI_CHAT_ACTION_KINDS_VALIDATION().nullable(),
}));
export const AI_IMAGE_PERMISSION_VALIDATION = memoize(() => PERMISSION_VALIDATION().extend({
resourceKind: z.literal(AI_IMAGE_RESOURCE_KIND),
action: AI_IMAGE_ACTION_KINDS_VALIDATION().nullable(),
}));
export const AI_SKYBOX_PERMISSION_VALIDATION = memoize(() => PERMISSION_VALIDATION().extend({
resourceKind: z.literal(AI_SKYBOX_RESOURCE_KIND),
action: AI_SKYBOX_ACTION_KINDS_VALIDATION().nullable(),
}));
export const WEBHOOK_PERMISSION_VALIDATION = memoize(() => PERMISSION_VALIDATION().extend({
resourceKind: z.literal(WEBHOOK_RESOURCE_KIND),
action: WEBHOOK_ACTION_KINDS_VALIDATION().nullable(),
}));
export const NOTIFICATION_PERMISSION_VALIDATION = memoize(() => PERMISSION_VALIDATION().extend({
resourceKind: z.literal(NOTIFICATION_RESOURCE_KIND),
action: NOTIFICATION_ACTION_KINDS_VALIDATION().nullable(),
}));
export const PACKAGE_PERMISSION_VALIDATION = memoize(() => PERMISSION_VALIDATION().extend({
resourceKind: z.literal(PACKAGE_RESOURCE_KIND),
action: PACKAGE_ACTION_KINDS_VALIDATION().nullable(),
}));
export const PACKAGE_VERSION_PERMISSION_VALIDATION = memoize(() => PERMISSION_VALIDATION().extend({
resourceKind: z.literal(PACKAGE_VERSION_RESOURCE_KIND),
action: PACKAGE_VERSION_ACTION_KINDS_VALIDATION().nullable(),
}));
export const SEARCH_PERMISSION_VALIDATION = memoize(() => PERMISSION_VALIDATION().extend({
resourceKind: z.literal(SEARCH_RESOURCE_KIND),
action: SEARCH_ACTION_KINDS_VALIDATION().nullable(),
}));
export const DATABASE_PERMISSION_VALIDATION = memoize(() => PERMISSION_VALIDATION().extend({
resourceKind: z.literal(DATABASE_RESOURCE_KIND),
action: DATABASE_ACTION_KINDS_VALIDATION().nullable(),
}));
export const PURCHASABLE_ITEM_PERMISSION_VALIDATION = memoize(() => PERMISSION_VALIDATION().extend({
resourceKind: z.literal(PURCHASABLE_ITEM_RESOURCE_KIND),
action: PURCHASABLE_ITEM_ACTION_KINDS_VALIDATION().nullable(),
}));
export const CONTRACT_PERMISSION_VALIDATION = memoize(() => PERMISSION_VALIDATION().extend({
resourceKind: z.literal(CONTRACT_RESOURCE_KIND),
action: CONTRACT_ACTION_KINDS_VALIDATION().nullable(),
}));
export const INVOICE_PERMISSION_VALIDATION = memoize(() => PERMISSION_VALIDATION().extend({
resourceKind: z.literal(INVOICE_RESOURCE_KIND),
action: INVOICE_ACTION_KINDS_VALIDATION().nullable(),
}));
export const AVAILABLE_PERMISSIONS_VALIDATION = z.discriminatedUnion('resourceKind', [
DATA_PERMISSION_VALIDATION(),
FILE_PERMISSION_VALIDATION(),
EVENT_PERMISSION_VALIDATION(),
MARKER_PERMISSION_VALIDATION(),
ROLE_PERMISSION_VALIDATION(),
INST_PERMISSION_VALIDATION(),
LOOM_PERMISSION_VALIDATION(),
SLOYD_PERMISSION_VALIDATION(),
HUME_PERMISSION_VALIDATION(),
OPENAI_REALTIME_PERMISSION_VALIDATION(),
AI_CHAT_PERMISSION_VALIDATION(),
AI_IMAGE_PERMISSION_VALIDATION(),
AI_SKYBOX_PERMISSION_VALIDATION(),
WEBHOOK_PERMISSION_VALIDATION(),
NOTIFICATION_PERMISSION_VALIDATION(),
PACKAGE_PERMISSION_VALIDATION(),
PACKAGE_VERSION_PERMISSION_VALIDATION(),
SEARCH_PERMISSION_VALIDATION(),
DATABASE_PERMISSION_VALIDATION(),
PURCHASABLE_ITEM_PERMISSION_VALIDATION(),
CONTRACT_PERMISSION_VALIDATION(),
INVOICE_PERMISSION_VALIDATION(),
]);
// /**
// * Defines an interface that represents a policy document.
// * That is, a list of permissions that are granted to specific roles.
// */
// export interface PolicyDocument {
// /**
// * The list of permissions that are allowed by this policy document.
// */
// permissions: AvailablePermissions[];
// }
/**
* The name of the admin role.
*/
export const ADMIN_ROLE_NAME = 'admin';
/**
* The name of the recordOwner role.
*/
export const RECORD_OWNER_ROLE_NAME = 'recordOwner';
/**
* The name of the "publicRead" resource marker.
* Used by default for data, file, and event records.
*/
export const PUBLIC_READ_MARKER = 'publicRead';
/**
* The name of the "publicWrite" resource marker.
* Used by default for public insts.
*/
export const PUBLIC_WRITE_MARKER = 'publicWrite';
/**
* The name of the "private" resource marker.
* Used by default for private insts.
*/
export const PRIVATE_MARKER = 'private';
/**
* The name of the "account" resource marker.
* Used by default for policy and role records.
*/
export const ACCOUNT_MARKER = 'account';
//# sourceMappingURL=PolicyPermissions.js.map