feature: rooms and events implemented on the backend
This commit is contained in:
parent
df00324e24
commit
85024c6e62
29 changed files with 1659 additions and 115 deletions
56
models/event.ts
Normal file
56
models/event.ts
Normal file
|
@ -0,0 +1,56 @@
|
|||
import { by_character, by_lurid } from '@andyburke/fsdb/organizers';
|
||||
import { FSDB_COLLECTION } from 'jsr:@andyburke/fsdb';
|
||||
import { FSDB_INDEXER_SYMLINKS } from '@andyburke/fsdb/indexers';
|
||||
|
||||
/**
|
||||
* @typedef {object} TIMESTAMPS
|
||||
* @property {string} created when the event was created
|
||||
* @property {string} updated when the event was last updated
|
||||
*/
|
||||
|
||||
/**
|
||||
* Event
|
||||
*
|
||||
* @property {string} id - room_id(lurid):event_id(lurid)
|
||||
* @property {string} creator_id - id of the source user
|
||||
* @property {string} room_id - id of the target room
|
||||
* @property {string} type - event type
|
||||
* @property {string[]} [tags] - optional event tags
|
||||
* @property {Record<string,any>} [data] - optional data payload of the event
|
||||
* @property {TIMESTAMPS} timestamps - timestamps that will be set by the server
|
||||
*/
|
||||
export type EVENT = {
|
||||
id: string;
|
||||
creator_id: string;
|
||||
type: string;
|
||||
tags?: string[];
|
||||
data?: Record<string, any>;
|
||||
timestamps: {
|
||||
created: string;
|
||||
updated: string;
|
||||
};
|
||||
};
|
||||
|
||||
export const EVENTS = new FSDB_COLLECTION<EVENT>({
|
||||
name: 'events',
|
||||
id_field: 'id',
|
||||
organize: (combined_id) => {
|
||||
const [room_id, event_id] = combined_id.split(':', 2);
|
||||
return ['rooms', room_id, event_id.substring(0, 14), `${event_id}.json`];
|
||||
},
|
||||
indexers: {
|
||||
creator_id: new FSDB_INDEXER_SYMLINKS<EVENT>({
|
||||
name: 'creator_id',
|
||||
field: 'creator_id',
|
||||
organize: by_lurid
|
||||
}),
|
||||
|
||||
tags: new FSDB_INDEXER_SYMLINKS<EVENT>({
|
||||
name: 'tags',
|
||||
get_values_to_index: (event): string[] => {
|
||||
return (event.tags ?? []).map((tag) => tag.toLowerCase());
|
||||
},
|
||||
organize: by_character
|
||||
})
|
||||
}
|
||||
});
|
87
models/room.ts
Normal file
87
models/room.ts
Normal file
|
@ -0,0 +1,87 @@
|
|||
import { by_character, by_lurid } from '@andyburke/fsdb/organizers';
|
||||
import { FSDB_COLLECTION } from 'jsr:@andyburke/fsdb';
|
||||
import { FSDB_INDEXER_SYMLINKS } from '@andyburke/fsdb/indexers';
|
||||
|
||||
/**
|
||||
* @typedef {object} ROOM_PERMISSIONS
|
||||
* @property {string[]} read a list of user_ids with read permission for the room
|
||||
* @property {string[]} write a list of user_ids with write permission for the room
|
||||
* @property {string[]} read_events a list of user_ids with read_events permission for this room
|
||||
* @property {string[]} write_events a list of user_ids with write_events permission for this room
|
||||
*/
|
||||
|
||||
/**
|
||||
* ROOM
|
||||
*
|
||||
* @property {string} id - lurid (stable)
|
||||
* @property {string} name - channel name (max 64 characters, unique, unstable)
|
||||
* @property {string} creator_id - user id of the room creator
|
||||
* @property {ROOM_PERMISSIONS} permissions - permissions setup for the room
|
||||
* @property {string} [icon_url] - optional url for room icon
|
||||
* @property {string} [topic] - optional topic for the room
|
||||
* @property {string} [rules] - optional room rules (Markdown/text)
|
||||
* @property {string[]} [tags] - optional tags for the room
|
||||
* @property {Record<string,any>} [meta] - optional metadata about the room
|
||||
* @property {Record<string,string>} [emojis] - optional emojis table, eg: { 'rofl': 🤣, 'blap': 'https://somewhere.someplace/image.jpg' }
|
||||
*/
|
||||
|
||||
export type ROOM = {
|
||||
id: string;
|
||||
name: string;
|
||||
creator_id: string;
|
||||
permissions: {
|
||||
read: string[];
|
||||
write: string[];
|
||||
read_events: string[];
|
||||
write_events: string[];
|
||||
};
|
||||
icon_url?: string;
|
||||
topic?: string;
|
||||
rules?: string;
|
||||
tags?: string[];
|
||||
meta?: Record<string, any>;
|
||||
emojis?: Record<string, string>; // either: string: emoji eg: { 'rofl: 🤣, ... } or { 'rofl': 🤣, 'blap': 'https://somewhere.someplace/image.jpg' }
|
||||
timestamps: {
|
||||
created: string;
|
||||
updated: string;
|
||||
archived: string | undefined;
|
||||
};
|
||||
};
|
||||
|
||||
export const ROOMS = new FSDB_COLLECTION<ROOM>({
|
||||
name: 'rooms',
|
||||
id_field: 'id',
|
||||
organize: by_lurid,
|
||||
indexers: {
|
||||
creator_id: new FSDB_INDEXER_SYMLINKS<ROOM>({
|
||||
name: 'creator_id',
|
||||
field: 'creator_id',
|
||||
to_many: true,
|
||||
organize: by_lurid
|
||||
}),
|
||||
|
||||
name: new FSDB_INDEXER_SYMLINKS<ROOM>({
|
||||
name: 'name',
|
||||
get_values_to_index: (room) => [room.name.toLowerCase()],
|
||||
organize: by_character
|
||||
}),
|
||||
|
||||
tags: new FSDB_INDEXER_SYMLINKS<ROOM>({
|
||||
name: 'tags',
|
||||
get_values_to_index: (room): string[] => {
|
||||
return (room.tags ?? []).map((tag) => tag.toLowerCase());
|
||||
},
|
||||
to_many: true,
|
||||
organize: by_character
|
||||
}),
|
||||
|
||||
topic: new FSDB_INDEXER_SYMLINKS<ROOM>({
|
||||
name: 'topic',
|
||||
get_values_to_index: (room): string[] => {
|
||||
return (room.topic ?? '').split(/\W/);
|
||||
},
|
||||
to_many: true,
|
||||
organize: by_character
|
||||
})
|
||||
}
|
||||
});
|
|
@ -5,6 +5,7 @@ import { by_character } from 'jsr:@andyburke/fsdb/organizers';
|
|||
export type USER = {
|
||||
id: string;
|
||||
username: string;
|
||||
permissions: string[];
|
||||
timestamps: {
|
||||
created: string;
|
||||
updated: string;
|
||||
|
|
|
@ -1,15 +0,0 @@
|
|||
import { FSDB_COLLECTION } from 'jsr:@andyburke/fsdb';
|
||||
|
||||
export type USER_PERMISSIONS = {
|
||||
user_id: string;
|
||||
permissions: string[];
|
||||
timestamps: {
|
||||
created: string;
|
||||
updated: string;
|
||||
};
|
||||
};
|
||||
|
||||
export const PERMISSIONS_STORE = new FSDB_COLLECTION<USER_PERMISSIONS>({
|
||||
name: 'user_permissions',
|
||||
id_field: 'user_id'
|
||||
});
|
Loading…
Add table
Add a link
Reference in a new issue