Merge branch 'master' of https://github.com/fosscord/fosscord-server
This commit is contained in:
commit
dc01de5f6d
12591
api/assets/openapi.json
12591
api/assets/openapi.json
File diff suppressed because it is too large
Load Diff
@ -1,4 +1,33 @@
|
|||||||
{
|
{
|
||||||
|
"LoginSchema": {
|
||||||
|
"type": "object",
|
||||||
|
"properties": {
|
||||||
|
"login": {
|
||||||
|
"type": "string"
|
||||||
|
},
|
||||||
|
"password": {
|
||||||
|
"type": "string"
|
||||||
|
},
|
||||||
|
"undelete": {
|
||||||
|
"type": "boolean"
|
||||||
|
},
|
||||||
|
"captcha_key": {
|
||||||
|
"type": "string"
|
||||||
|
},
|
||||||
|
"login_source": {
|
||||||
|
"type": "string"
|
||||||
|
},
|
||||||
|
"gift_code_sku_id": {
|
||||||
|
"type": "string"
|
||||||
|
}
|
||||||
|
},
|
||||||
|
"additionalProperties": false,
|
||||||
|
"required": [
|
||||||
|
"login",
|
||||||
|
"password"
|
||||||
|
],
|
||||||
|
"$schema": "http://json-schema.org/draft-07/schema#"
|
||||||
|
},
|
||||||
"RegisterSchema": {
|
"RegisterSchema": {
|
||||||
"type": "object",
|
"type": "object",
|
||||||
"properties": {
|
"properties": {
|
||||||
@ -42,35 +71,6 @@
|
|||||||
],
|
],
|
||||||
"$schema": "http://json-schema.org/draft-07/schema#"
|
"$schema": "http://json-schema.org/draft-07/schema#"
|
||||||
},
|
},
|
||||||
"LoginSchema": {
|
|
||||||
"type": "object",
|
|
||||||
"properties": {
|
|
||||||
"login": {
|
|
||||||
"type": "string"
|
|
||||||
},
|
|
||||||
"password": {
|
|
||||||
"type": "string"
|
|
||||||
},
|
|
||||||
"undelete": {
|
|
||||||
"type": "boolean"
|
|
||||||
},
|
|
||||||
"captcha_key": {
|
|
||||||
"type": "string"
|
|
||||||
},
|
|
||||||
"login_source": {
|
|
||||||
"type": "string"
|
|
||||||
},
|
|
||||||
"gift_code_sku_id": {
|
|
||||||
"type": "string"
|
|
||||||
}
|
|
||||||
},
|
|
||||||
"additionalProperties": false,
|
|
||||||
"required": [
|
|
||||||
"login",
|
|
||||||
"password"
|
|
||||||
],
|
|
||||||
"$schema": "http://json-schema.org/draft-07/schema#"
|
|
||||||
},
|
|
||||||
"ChannelModifySchema": {
|
"ChannelModifySchema": {
|
||||||
"type": "object",
|
"type": "object",
|
||||||
"properties": {
|
"properties": {
|
||||||
@ -127,10 +127,10 @@
|
|||||||
"$ref": "#/definitions/ChannelPermissionOverwriteType"
|
"$ref": "#/definitions/ChannelPermissionOverwriteType"
|
||||||
},
|
},
|
||||||
"allow": {
|
"allow": {
|
||||||
"type": "bigint"
|
"type": "string"
|
||||||
},
|
},
|
||||||
"deny": {
|
"deny": {
|
||||||
"type": "bigint"
|
"type": "string"
|
||||||
}
|
}
|
||||||
},
|
},
|
||||||
"additionalProperties": false,
|
"additionalProperties": false,
|
||||||
@ -353,10 +353,10 @@
|
|||||||
"$ref": "#/definitions/ChannelPermissionOverwriteType"
|
"$ref": "#/definitions/ChannelPermissionOverwriteType"
|
||||||
},
|
},
|
||||||
"allow": {
|
"allow": {
|
||||||
"type": "bigint"
|
"type": "string"
|
||||||
},
|
},
|
||||||
"deny": {
|
"deny": {
|
||||||
"type": "bigint"
|
"type": "string"
|
||||||
}
|
}
|
||||||
},
|
},
|
||||||
"additionalProperties": false,
|
"additionalProperties": false,
|
||||||
@ -727,10 +727,10 @@
|
|||||||
"$ref": "#/definitions/ChannelPermissionOverwriteType"
|
"$ref": "#/definitions/ChannelPermissionOverwriteType"
|
||||||
},
|
},
|
||||||
"allow": {
|
"allow": {
|
||||||
"type": "bigint"
|
"type": "string"
|
||||||
},
|
},
|
||||||
"deny": {
|
"deny": {
|
||||||
"type": "bigint"
|
"type": "string"
|
||||||
}
|
}
|
||||||
},
|
},
|
||||||
"additionalProperties": false,
|
"additionalProperties": false,
|
||||||
@ -1050,10 +1050,10 @@
|
|||||||
"$ref": "#/definitions/ChannelPermissionOverwriteType"
|
"$ref": "#/definitions/ChannelPermissionOverwriteType"
|
||||||
},
|
},
|
||||||
"allow": {
|
"allow": {
|
||||||
"type": "bigint"
|
"type": "string"
|
||||||
},
|
},
|
||||||
"deny": {
|
"deny": {
|
||||||
"type": "bigint"
|
"type": "string"
|
||||||
}
|
}
|
||||||
},
|
},
|
||||||
"additionalProperties": false,
|
"additionalProperties": false,
|
||||||
@ -1352,10 +1352,10 @@
|
|||||||
"$ref": "#/definitions/ChannelPermissionOverwriteType"
|
"$ref": "#/definitions/ChannelPermissionOverwriteType"
|
||||||
},
|
},
|
||||||
"allow": {
|
"allow": {
|
||||||
"type": "bigint"
|
"type": "string"
|
||||||
},
|
},
|
||||||
"deny": {
|
"deny": {
|
||||||
"type": "bigint"
|
"type": "string"
|
||||||
}
|
}
|
||||||
},
|
},
|
||||||
"additionalProperties": false,
|
"additionalProperties": false,
|
||||||
@ -1657,10 +1657,10 @@
|
|||||||
"$ref": "#/definitions/ChannelPermissionOverwriteType"
|
"$ref": "#/definitions/ChannelPermissionOverwriteType"
|
||||||
},
|
},
|
||||||
"allow": {
|
"allow": {
|
||||||
"type": "bigint"
|
"type": "string"
|
||||||
},
|
},
|
||||||
"deny": {
|
"deny": {
|
||||||
"type": "bigint"
|
"type": "string"
|
||||||
}
|
}
|
||||||
},
|
},
|
||||||
"additionalProperties": false,
|
"additionalProperties": false,
|
||||||
@ -1758,10 +1758,10 @@
|
|||||||
"type": "object",
|
"type": "object",
|
||||||
"properties": {
|
"properties": {
|
||||||
"allow": {
|
"allow": {
|
||||||
"type": "bigint"
|
"type": "string"
|
||||||
},
|
},
|
||||||
"deny": {
|
"deny": {
|
||||||
"type": "bigint"
|
"type": "string"
|
||||||
},
|
},
|
||||||
"id": {
|
"id": {
|
||||||
"type": "string"
|
"type": "string"
|
||||||
@ -1971,10 +1971,10 @@
|
|||||||
"$ref": "#/definitions/ChannelPermissionOverwriteType"
|
"$ref": "#/definitions/ChannelPermissionOverwriteType"
|
||||||
},
|
},
|
||||||
"allow": {
|
"allow": {
|
||||||
"type": "bigint"
|
"type": "string"
|
||||||
},
|
},
|
||||||
"deny": {
|
"deny": {
|
||||||
"type": "bigint"
|
"type": "string"
|
||||||
}
|
}
|
||||||
},
|
},
|
||||||
"additionalProperties": false,
|
"additionalProperties": false,
|
||||||
@ -2278,10 +2278,10 @@
|
|||||||
"$ref": "#/definitions/ChannelPermissionOverwriteType"
|
"$ref": "#/definitions/ChannelPermissionOverwriteType"
|
||||||
},
|
},
|
||||||
"allow": {
|
"allow": {
|
||||||
"type": "bigint"
|
"type": "string"
|
||||||
},
|
},
|
||||||
"deny": {
|
"deny": {
|
||||||
"type": "bigint"
|
"type": "string"
|
||||||
}
|
}
|
||||||
},
|
},
|
||||||
"additionalProperties": false,
|
"additionalProperties": false,
|
||||||
@ -2580,10 +2580,10 @@
|
|||||||
"$ref": "#/definitions/ChannelPermissionOverwriteType"
|
"$ref": "#/definitions/ChannelPermissionOverwriteType"
|
||||||
},
|
},
|
||||||
"allow": {
|
"allow": {
|
||||||
"type": "bigint"
|
"type": "string"
|
||||||
},
|
},
|
||||||
"deny": {
|
"deny": {
|
||||||
"type": "bigint"
|
"type": "string"
|
||||||
}
|
}
|
||||||
},
|
},
|
||||||
"additionalProperties": false,
|
"additionalProperties": false,
|
||||||
@ -2894,10 +2894,10 @@
|
|||||||
"$ref": "#/definitions/ChannelPermissionOverwriteType"
|
"$ref": "#/definitions/ChannelPermissionOverwriteType"
|
||||||
},
|
},
|
||||||
"allow": {
|
"allow": {
|
||||||
"type": "bigint"
|
"type": "string"
|
||||||
},
|
},
|
||||||
"deny": {
|
"deny": {
|
||||||
"type": "bigint"
|
"type": "string"
|
||||||
}
|
}
|
||||||
},
|
},
|
||||||
"additionalProperties": false,
|
"additionalProperties": false,
|
||||||
@ -3221,10 +3221,10 @@
|
|||||||
"$ref": "#/definitions/ChannelPermissionOverwriteType"
|
"$ref": "#/definitions/ChannelPermissionOverwriteType"
|
||||||
},
|
},
|
||||||
"allow": {
|
"allow": {
|
||||||
"type": "bigint"
|
"type": "string"
|
||||||
},
|
},
|
||||||
"deny": {
|
"deny": {
|
||||||
"type": "bigint"
|
"type": "string"
|
||||||
}
|
}
|
||||||
},
|
},
|
||||||
"additionalProperties": false,
|
"additionalProperties": false,
|
||||||
@ -3587,10 +3587,10 @@
|
|||||||
"$ref": "#/definitions/ChannelPermissionOverwriteType"
|
"$ref": "#/definitions/ChannelPermissionOverwriteType"
|
||||||
},
|
},
|
||||||
"allow": {
|
"allow": {
|
||||||
"type": "bigint"
|
"type": "string"
|
||||||
},
|
},
|
||||||
"deny": {
|
"deny": {
|
||||||
"type": "bigint"
|
"type": "string"
|
||||||
}
|
}
|
||||||
},
|
},
|
||||||
"additionalProperties": false,
|
"additionalProperties": false,
|
||||||
@ -3889,10 +3889,10 @@
|
|||||||
"$ref": "#/definitions/ChannelPermissionOverwriteType"
|
"$ref": "#/definitions/ChannelPermissionOverwriteType"
|
||||||
},
|
},
|
||||||
"allow": {
|
"allow": {
|
||||||
"type": "bigint"
|
"type": "string"
|
||||||
},
|
},
|
||||||
"deny": {
|
"deny": {
|
||||||
"type": "bigint"
|
"type": "string"
|
||||||
}
|
}
|
||||||
},
|
},
|
||||||
"additionalProperties": false,
|
"additionalProperties": false,
|
||||||
@ -4191,10 +4191,10 @@
|
|||||||
"$ref": "#/definitions/ChannelPermissionOverwriteType"
|
"$ref": "#/definitions/ChannelPermissionOverwriteType"
|
||||||
},
|
},
|
||||||
"allow": {
|
"allow": {
|
||||||
"type": "bigint"
|
"type": "string"
|
||||||
},
|
},
|
||||||
"deny": {
|
"deny": {
|
||||||
"type": "bigint"
|
"type": "string"
|
||||||
}
|
}
|
||||||
},
|
},
|
||||||
"additionalProperties": false,
|
"additionalProperties": false,
|
||||||
@ -4505,10 +4505,10 @@
|
|||||||
"$ref": "#/definitions/ChannelPermissionOverwriteType"
|
"$ref": "#/definitions/ChannelPermissionOverwriteType"
|
||||||
},
|
},
|
||||||
"allow": {
|
"allow": {
|
||||||
"type": "bigint"
|
"type": "string"
|
||||||
},
|
},
|
||||||
"deny": {
|
"deny": {
|
||||||
"type": "bigint"
|
"type": "string"
|
||||||
}
|
}
|
||||||
},
|
},
|
||||||
"additionalProperties": false,
|
"additionalProperties": false,
|
||||||
@ -4814,10 +4814,10 @@
|
|||||||
"$ref": "#/definitions/ChannelPermissionOverwriteType"
|
"$ref": "#/definitions/ChannelPermissionOverwriteType"
|
||||||
},
|
},
|
||||||
"allow": {
|
"allow": {
|
||||||
"type": "bigint"
|
"type": "string"
|
||||||
},
|
},
|
||||||
"deny": {
|
"deny": {
|
||||||
"type": "bigint"
|
"type": "string"
|
||||||
}
|
}
|
||||||
},
|
},
|
||||||
"additionalProperties": false,
|
"additionalProperties": false,
|
||||||
@ -5119,10 +5119,10 @@
|
|||||||
"$ref": "#/definitions/ChannelPermissionOverwriteType"
|
"$ref": "#/definitions/ChannelPermissionOverwriteType"
|
||||||
},
|
},
|
||||||
"allow": {
|
"allow": {
|
||||||
"type": "bigint"
|
"type": "string"
|
||||||
},
|
},
|
||||||
"deny": {
|
"deny": {
|
||||||
"type": "bigint"
|
"type": "string"
|
||||||
}
|
}
|
||||||
},
|
},
|
||||||
"additionalProperties": false,
|
"additionalProperties": false,
|
||||||
@ -5424,10 +5424,10 @@
|
|||||||
"$ref": "#/definitions/ChannelPermissionOverwriteType"
|
"$ref": "#/definitions/ChannelPermissionOverwriteType"
|
||||||
},
|
},
|
||||||
"allow": {
|
"allow": {
|
||||||
"type": "bigint"
|
"type": "string"
|
||||||
},
|
},
|
||||||
"deny": {
|
"deny": {
|
||||||
"type": "bigint"
|
"type": "string"
|
||||||
}
|
}
|
||||||
},
|
},
|
||||||
"additionalProperties": false,
|
"additionalProperties": false,
|
||||||
@ -5725,10 +5725,10 @@
|
|||||||
"$ref": "#/definitions/ChannelPermissionOverwriteType"
|
"$ref": "#/definitions/ChannelPermissionOverwriteType"
|
||||||
},
|
},
|
||||||
"allow": {
|
"allow": {
|
||||||
"type": "bigint"
|
"type": "string"
|
||||||
},
|
},
|
||||||
"deny": {
|
"deny": {
|
||||||
"type": "bigint"
|
"type": "string"
|
||||||
}
|
}
|
||||||
},
|
},
|
||||||
"additionalProperties": false,
|
"additionalProperties": false,
|
||||||
@ -6046,10 +6046,10 @@
|
|||||||
"$ref": "#/definitions/ChannelPermissionOverwriteType"
|
"$ref": "#/definitions/ChannelPermissionOverwriteType"
|
||||||
},
|
},
|
||||||
"allow": {
|
"allow": {
|
||||||
"type": "bigint"
|
"type": "string"
|
||||||
},
|
},
|
||||||
"deny": {
|
"deny": {
|
||||||
"type": "bigint"
|
"type": "string"
|
||||||
}
|
}
|
||||||
},
|
},
|
||||||
"additionalProperties": false,
|
"additionalProperties": false,
|
||||||
@ -6374,10 +6374,10 @@
|
|||||||
"$ref": "#/definitions/ChannelPermissionOverwriteType"
|
"$ref": "#/definitions/ChannelPermissionOverwriteType"
|
||||||
},
|
},
|
||||||
"allow": {
|
"allow": {
|
||||||
"type": "bigint"
|
"type": "string"
|
||||||
},
|
},
|
||||||
"deny": {
|
"deny": {
|
||||||
"type": "bigint"
|
"type": "string"
|
||||||
}
|
}
|
||||||
},
|
},
|
||||||
"additionalProperties": false,
|
"additionalProperties": false,
|
||||||
@ -6680,10 +6680,10 @@
|
|||||||
"$ref": "#/definitions/ChannelPermissionOverwriteType"
|
"$ref": "#/definitions/ChannelPermissionOverwriteType"
|
||||||
},
|
},
|
||||||
"allow": {
|
"allow": {
|
||||||
"type": "bigint"
|
"type": "string"
|
||||||
},
|
},
|
||||||
"deny": {
|
"deny": {
|
||||||
"type": "bigint"
|
"type": "string"
|
||||||
}
|
}
|
||||||
},
|
},
|
||||||
"additionalProperties": false,
|
"additionalProperties": false,
|
||||||
@ -6988,10 +6988,10 @@
|
|||||||
"$ref": "#/definitions/ChannelPermissionOverwriteType"
|
"$ref": "#/definitions/ChannelPermissionOverwriteType"
|
||||||
},
|
},
|
||||||
"allow": {
|
"allow": {
|
||||||
"type": "bigint"
|
"type": "string"
|
||||||
},
|
},
|
||||||
"deny": {
|
"deny": {
|
||||||
"type": "bigint"
|
"type": "string"
|
||||||
}
|
}
|
||||||
},
|
},
|
||||||
"additionalProperties": false,
|
"additionalProperties": false,
|
||||||
@ -7302,10 +7302,10 @@
|
|||||||
"$ref": "#/definitions/ChannelPermissionOverwriteType"
|
"$ref": "#/definitions/ChannelPermissionOverwriteType"
|
||||||
},
|
},
|
||||||
"allow": {
|
"allow": {
|
||||||
"type": "bigint"
|
"type": "string"
|
||||||
},
|
},
|
||||||
"deny": {
|
"deny": {
|
||||||
"type": "bigint"
|
"type": "string"
|
||||||
}
|
}
|
||||||
},
|
},
|
||||||
"additionalProperties": false,
|
"additionalProperties": false,
|
||||||
@ -7610,10 +7610,10 @@
|
|||||||
"$ref": "#/definitions/ChannelPermissionOverwriteType"
|
"$ref": "#/definitions/ChannelPermissionOverwriteType"
|
||||||
},
|
},
|
||||||
"allow": {
|
"allow": {
|
||||||
"type": "bigint"
|
"type": "string"
|
||||||
},
|
},
|
||||||
"deny": {
|
"deny": {
|
||||||
"type": "bigint"
|
"type": "string"
|
||||||
}
|
}
|
||||||
},
|
},
|
||||||
"additionalProperties": false,
|
"additionalProperties": false,
|
||||||
@ -7939,10 +7939,10 @@
|
|||||||
"$ref": "#/definitions/ChannelPermissionOverwriteType"
|
"$ref": "#/definitions/ChannelPermissionOverwriteType"
|
||||||
},
|
},
|
||||||
"allow": {
|
"allow": {
|
||||||
"type": "bigint"
|
"type": "string"
|
||||||
},
|
},
|
||||||
"deny": {
|
"deny": {
|
||||||
"type": "bigint"
|
"type": "string"
|
||||||
}
|
}
|
||||||
},
|
},
|
||||||
"additionalProperties": false,
|
"additionalProperties": false,
|
||||||
@ -8244,10 +8244,10 @@
|
|||||||
"$ref": "#/definitions/ChannelPermissionOverwriteType"
|
"$ref": "#/definitions/ChannelPermissionOverwriteType"
|
||||||
},
|
},
|
||||||
"allow": {
|
"allow": {
|
||||||
"type": "bigint"
|
"type": "string"
|
||||||
},
|
},
|
||||||
"deny": {
|
"deny": {
|
||||||
"type": "bigint"
|
"type": "string"
|
||||||
}
|
}
|
||||||
},
|
},
|
||||||
"additionalProperties": false,
|
"additionalProperties": false,
|
||||||
@ -8550,10 +8550,10 @@
|
|||||||
"$ref": "#/definitions/ChannelPermissionOverwriteType"
|
"$ref": "#/definitions/ChannelPermissionOverwriteType"
|
||||||
},
|
},
|
||||||
"allow": {
|
"allow": {
|
||||||
"type": "bigint"
|
"type": "string"
|
||||||
},
|
},
|
||||||
"deny": {
|
"deny": {
|
||||||
"type": "bigint"
|
"type": "string"
|
||||||
}
|
}
|
||||||
},
|
},
|
||||||
"additionalProperties": false,
|
"additionalProperties": false,
|
||||||
@ -9039,10 +9039,10 @@
|
|||||||
"$ref": "#/definitions/ChannelPermissionOverwriteType"
|
"$ref": "#/definitions/ChannelPermissionOverwriteType"
|
||||||
},
|
},
|
||||||
"allow": {
|
"allow": {
|
||||||
"type": "bigint"
|
"type": "string"
|
||||||
},
|
},
|
||||||
"deny": {
|
"deny": {
|
||||||
"type": "bigint"
|
"type": "string"
|
||||||
}
|
}
|
||||||
},
|
},
|
||||||
"additionalProperties": false,
|
"additionalProperties": false,
|
||||||
|
@ -14,8 +14,8 @@
|
|||||||
"dev": "tsnd --respawn src/start.ts",
|
"dev": "tsnd --respawn src/start.ts",
|
||||||
"patch": "ts-patch install -s && npx patch-package",
|
"patch": "ts-patch install -s && npx patch-package",
|
||||||
"postinstall": "npm run patch",
|
"postinstall": "npm run patch",
|
||||||
"generate:docs": "node scripts/generate_openapi.ts",
|
"generate:docs": "node scripts/generate_openapi",
|
||||||
"generate:schema": "node scripts/generate_schema.ts"
|
"generate:schema": "node scripts/generate_schema"
|
||||||
},
|
},
|
||||||
"repository": {
|
"repository": {
|
||||||
"type": "git",
|
"type": "git",
|
||||||
|
@ -1,9 +1,9 @@
|
|||||||
// https://mermade.github.io/openapi-gui/#
|
// https://mermade.github.io/openapi-gui/#
|
||||||
// https://editor.swagger.io/
|
// https://editor.swagger.io/
|
||||||
import path from "path";
|
const path = require("path");
|
||||||
import fs from "fs";
|
const fs = require("fs");
|
||||||
import * as TJS from "typescript-json-schema";
|
const TJS = require("typescript-json-schema");
|
||||||
import "missing-native-js-functions";
|
require("missing-native-js-functions");
|
||||||
const schemaPath = path.join(__dirname, "..", "assets", "schemas.json");
|
const schemaPath = path.join(__dirname, "..", "assets", "schemas.json");
|
||||||
|
|
||||||
const settings = {
|
const settings = {
|
||||||
|
@ -62,8 +62,8 @@ export interface ChannelModifySchema {
|
|||||||
permission_overwrites?: {
|
permission_overwrites?: {
|
||||||
id: string;
|
id: string;
|
||||||
type: ChannelPermissionOverwriteType;
|
type: ChannelPermissionOverwriteType;
|
||||||
allow: bigint;
|
allow: string;
|
||||||
deny: bigint;
|
deny: string;
|
||||||
}[];
|
}[];
|
||||||
parent_id?: string;
|
parent_id?: string;
|
||||||
id?: string; // is not used (only for guild create)
|
id?: string; // is not used (only for guild create)
|
||||||
|
@ -3,6 +3,7 @@ import {
|
|||||||
Attachment,
|
Attachment,
|
||||||
Channel,
|
Channel,
|
||||||
ChannelType,
|
ChannelType,
|
||||||
|
Config,
|
||||||
DmChannelDTO,
|
DmChannelDTO,
|
||||||
Embed,
|
Embed,
|
||||||
emitEvent,
|
emitEvent,
|
||||||
@ -15,6 +16,7 @@ import { HTTPError } from "lambert-server";
|
|||||||
import { handleMessage, postHandleMessage, route } from "@fosscord/api";
|
import { handleMessage, postHandleMessage, route } from "@fosscord/api";
|
||||||
import multer from "multer";
|
import multer from "multer";
|
||||||
import { FindManyOptions, LessThan, MoreThan } from "typeorm";
|
import { FindManyOptions, LessThan, MoreThan } from "typeorm";
|
||||||
|
import { URL } from "url";
|
||||||
|
|
||||||
const router: Router = Router();
|
const router: Router = Router();
|
||||||
|
|
||||||
@ -111,6 +113,9 @@ router.get("/", async (req: Request, res: Response) => {
|
|||||||
});
|
});
|
||||||
// @ts-ignore
|
// @ts-ignore
|
||||||
if (!x.author) x.author = { discriminator: "0000", username: "Deleted User", public_flags: "0", avatar: null };
|
if (!x.author) x.author = { discriminator: "0000", username: "Deleted User", public_flags: "0", avatar: null };
|
||||||
|
x.attachments?.forEach((x) => {
|
||||||
|
x.proxy_url = `${Config.get().cdn.endpointPublic || "http://localhost:3003"}${new URL(x.proxy_url).pathname}`;
|
||||||
|
});
|
||||||
|
|
||||||
return x;
|
return x;
|
||||||
})
|
})
|
||||||
|
@ -1,4 +1,13 @@
|
|||||||
import { Channel, ChannelPermissionOverwrite, ChannelUpdateEvent, emitEvent, getPermission, Member, Role } from "@fosscord/util";
|
import {
|
||||||
|
Channel,
|
||||||
|
ChannelPermissionOverwrite,
|
||||||
|
ChannelPermissionOverwriteType,
|
||||||
|
ChannelUpdateEvent,
|
||||||
|
emitEvent,
|
||||||
|
getPermission,
|
||||||
|
Member,
|
||||||
|
Role
|
||||||
|
} from "@fosscord/util";
|
||||||
import { Router, Response, Request } from "express";
|
import { Router, Response, Request } from "express";
|
||||||
import { HTTPError } from "lambert-server";
|
import { HTTPError } from "lambert-server";
|
||||||
|
|
||||||
@ -14,7 +23,7 @@ router.put(
|
|||||||
route({ body: "ChannelPermissionOverwriteSchema", permission: "MANAGE_ROLES" }),
|
route({ body: "ChannelPermissionOverwriteSchema", permission: "MANAGE_ROLES" }),
|
||||||
async (req: Request, res: Response) => {
|
async (req: Request, res: Response) => {
|
||||||
const { channel_id, overwrite_id } = req.params;
|
const { channel_id, overwrite_id } = req.params;
|
||||||
const body = req.body as { allow: bigint; deny: bigint; type: number; id: string };
|
const body = req.body as ChannelPermissionOverwriteSchema;
|
||||||
|
|
||||||
var channel = await Channel.findOneOrFail({ id: channel_id });
|
var channel = await Channel.findOneOrFail({ id: channel_id });
|
||||||
if (!channel.guild_id) throw new HTTPError("Channel not found", 404);
|
if (!channel.guild_id) throw new HTTPError("Channel not found", 404);
|
||||||
@ -31,14 +40,12 @@ router.put(
|
|||||||
// @ts-ignore
|
// @ts-ignore
|
||||||
overwrite = {
|
overwrite = {
|
||||||
id: overwrite_id,
|
id: overwrite_id,
|
||||||
type: body.type,
|
type: body.type
|
||||||
allow: body.allow,
|
|
||||||
deny: body.deny
|
|
||||||
};
|
};
|
||||||
channel.permission_overwrites!.push(overwrite);
|
channel.permission_overwrites!.push(overwrite);
|
||||||
}
|
}
|
||||||
overwrite.allow = body.allow;
|
overwrite.allow = String(req.permission!.bitfield & (BigInt(body.allow) || 0n));
|
||||||
overwrite.deny = body.deny;
|
overwrite.deny = String(req.permission!.bitfield & (BigInt(body.deny) || 0n));
|
||||||
|
|
||||||
await Promise.all([
|
await Promise.all([
|
||||||
channel.save(),
|
channel.save(),
|
||||||
|
@ -5,14 +5,14 @@ import { route } from "@fosscord/api";
|
|||||||
const router = Router();
|
const router = Router();
|
||||||
|
|
||||||
router.get("/", route({}), (req: Request, res: Response) => {
|
router.get("/", route({}), (req: Request, res: Response) => {
|
||||||
const { endpoint } = Config.get().gateway;
|
const { endpointPublic } = Config.get().gateway;
|
||||||
res.json({ url: endpoint || process.env.GATEWAY || "ws://localhost:3002" });
|
res.json({ url: endpointPublic || process.env.GATEWAY || "ws://localhost:3002" });
|
||||||
});
|
});
|
||||||
|
|
||||||
router.get("/bot", route({}), (req: Request, res: Response) => {
|
router.get("/bot", route({}), (req: Request, res: Response) => {
|
||||||
const { endpoint } = Config.get().gateway;
|
const { endpointPublic } = Config.get().gateway;
|
||||||
res.json({
|
res.json({
|
||||||
url: endpoint || process.env.GATEWAY || "ws://localhost:3002",
|
url: endpointPublic || process.env.GATEWAY || "ws://localhost:3002",
|
||||||
shards: 1,
|
shards: 1,
|
||||||
session_start_limit: {
|
session_start_limit: {
|
||||||
total: 1000,
|
total: 1000,
|
||||||
|
@ -87,19 +87,21 @@ router.post("/", route({ body: "GuildCreateSchema" }), async (req: Request, res:
|
|||||||
});
|
});
|
||||||
|
|
||||||
await Promise.all(
|
await Promise.all(
|
||||||
body.channels?.map((x) => {
|
body.channels
|
||||||
var id = ids.get(x.id) || Snowflake.generate();
|
?.sort((a, b) => (a.parent_id ? -1 : 1))
|
||||||
|
.map((x) => {
|
||||||
|
var id = ids.get(x.id) || Snowflake.generate();
|
||||||
|
|
||||||
// TODO: should we abort if parent_id is a category? (to disallow sub category channels)
|
// TODO: should we abort if parent_id is a category? (to disallow sub category channels)
|
||||||
var parent_id = ids.get(x.parent_id);
|
var parent_id = ids.get(x.parent_id);
|
||||||
|
|
||||||
return Channel.createChannel({ ...x, guild_id, id, parent_id }, req.user_id, {
|
return Channel.createChannel({ ...x, guild_id, id, parent_id }, req.user_id, {
|
||||||
keepId: true,
|
keepId: true,
|
||||||
skipExistsCheck: true,
|
skipExistsCheck: true,
|
||||||
skipPermissionCheck: true,
|
skipPermissionCheck: true,
|
||||||
skipEventEmit: true
|
skipEventEmit: true
|
||||||
});
|
});
|
||||||
})
|
})
|
||||||
);
|
);
|
||||||
|
|
||||||
await Member.addToGuild(req.user_id, guild_id);
|
await Member.addToGuild(req.user_id, guild_id);
|
||||||
|
@ -1,53 +0,0 @@
|
|||||||
import { Config } from "@fosscord/util";
|
|
||||||
import FormData from "form-data";
|
|
||||||
import { HTTPError } from "lambert-server";
|
|
||||||
import fetch from "node-fetch";
|
|
||||||
|
|
||||||
export async function uploadFile(path: string, file: Express.Multer.File) {
|
|
||||||
const form = new FormData();
|
|
||||||
form.append("file", file.buffer, {
|
|
||||||
contentType: file.mimetype,
|
|
||||||
filename: file.originalname
|
|
||||||
});
|
|
||||||
|
|
||||||
const response = await fetch(`${Config.get().cdn.endpoint || "http://localhost:3003"}${path}`, {
|
|
||||||
headers: {
|
|
||||||
signature: Config.get().security.requestSignature,
|
|
||||||
...form.getHeaders()
|
|
||||||
},
|
|
||||||
method: "POST",
|
|
||||||
body: form
|
|
||||||
});
|
|
||||||
const result = await response.json();
|
|
||||||
|
|
||||||
if (response.status !== 200) throw result;
|
|
||||||
return result;
|
|
||||||
}
|
|
||||||
|
|
||||||
export async function handleFile(path: string, body?: string): Promise<string | undefined> {
|
|
||||||
if (!body || !body.startsWith("data:")) return body;
|
|
||||||
try {
|
|
||||||
const mimetype = body.split(":")[1].split(";")[0];
|
|
||||||
const buffer = Buffer.from(body.split(",")[1], "base64");
|
|
||||||
|
|
||||||
// @ts-ignore
|
|
||||||
const { id } = await uploadFile(path, { buffer, mimetype, originalname: "banner" });
|
|
||||||
return id;
|
|
||||||
} catch (error) {
|
|
||||||
console.error(error);
|
|
||||||
throw new HTTPError("Invalid " + path);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
export async function deleteFile(path: string) {
|
|
||||||
const response = await fetch(`${Config.get().cdn.endpoint || "http://localhost:3003"}${path}`, {
|
|
||||||
headers: {
|
|
||||||
signature: Config.get().security.requestSignature
|
|
||||||
},
|
|
||||||
method: "DELETE"
|
|
||||||
});
|
|
||||||
const result = await response.json();
|
|
||||||
|
|
||||||
if (response.status !== 200) throw result;
|
|
||||||
return result;
|
|
||||||
}
|
|
@ -81,10 +81,10 @@ export function route(opts: RouteOptions) {
|
|||||||
return async (req: Request, res: Response, next: NextFunction) => {
|
return async (req: Request, res: Response, next: NextFunction) => {
|
||||||
if (opts.permission) {
|
if (opts.permission) {
|
||||||
const required = new Permissions(opts.permission);
|
const required = new Permissions(opts.permission);
|
||||||
const permission = await getPermission(req.user_id, req.params.guild_id, req.params.channel_id);
|
req.permission = await getPermission(req.user_id, req.params.guild_id, req.params.channel_id);
|
||||||
|
|
||||||
// bitfield comparison: check if user lacks certain permission
|
// bitfield comparison: check if user lacks certain permission
|
||||||
if (!permission.has(required)) {
|
if (!req.permission.has(required)) {
|
||||||
throw DiscordApiErrors.MISSING_PERMISSIONS.withParams(opts.permission as string);
|
throw DiscordApiErrors.MISSING_PERMISSIONS.withParams(opts.permission as string);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
@ -24,16 +24,24 @@ const gateway = new GatewayServer({ server, port, production });
|
|||||||
async function main() {
|
async function main() {
|
||||||
await initDatabase();
|
await initDatabase();
|
||||||
await Config.init();
|
await Config.init();
|
||||||
|
// only set endpointPublic, if not already set
|
||||||
await Config.set({
|
await Config.set({
|
||||||
cdn: {
|
cdn: {
|
||||||
endpointClient: "${location.host}",
|
endpointClient: "${location.host}",
|
||||||
endpoint: `http://localhost:${port}`,
|
endpointPrivate: `http://localhost:${port}`,
|
||||||
|
...(!Config.get().cdn.endpointPublic && {
|
||||||
|
endpointPublic: `http://localhost:${port}`,
|
||||||
|
}),
|
||||||
},
|
},
|
||||||
gateway: {
|
gateway: {
|
||||||
endpointClient: '${location.protocol === "https:" ? "wss://" : "ws://"}${location.host}',
|
endpointClient:
|
||||||
endpoint: `ws://localhost:${port}`,
|
'${location.protocol === "https:" ? "wss://" : "ws://"}${location.host}',
|
||||||
|
endpointPrivate: `ws://localhost:${port}`,
|
||||||
|
...(!Config.get().gateway.endpointPublic && {
|
||||||
|
endpointPublic: `http://localhost:${port}`,
|
||||||
|
}),
|
||||||
},
|
},
|
||||||
});
|
} as any);
|
||||||
|
|
||||||
await Promise.all([api.start(), cdn.start(), gateway.start()]);
|
await Promise.all([api.start(), cdn.start(), gateway.start()]);
|
||||||
console.log(`[Server] listening on port ${port}`);
|
console.log(`[Server] listening on port ${port}`);
|
||||||
|
@ -9,16 +9,20 @@ export function initStats() {
|
|||||||
console.log(`[Process] running with pid: ${process.pid}`);
|
console.log(`[Process] running with pid: ${process.pid}`);
|
||||||
|
|
||||||
setInterval(async () => {
|
setInterval(async () => {
|
||||||
const [cpuUsed, memory, network] = await Promise.all([osu.cpu.usage(), osu.mem.info(), osu.netstat.inOut()]);
|
const [cpuUsed, memory, network] = await Promise.all([
|
||||||
|
osu.cpu.usage(),
|
||||||
|
osu.mem.info(),
|
||||||
|
osu.netstat.inOut(),
|
||||||
|
]);
|
||||||
var networkUsage = "";
|
var networkUsage = "";
|
||||||
if (typeof network === "object") {
|
if (typeof network === "object") {
|
||||||
networkUsage = `| [Network]: in ${network.total.inputMb}mb | out ${network.total.outputMb}mb`;
|
networkUsage = `| [Network]: in ${network.total.inputMb}mb | out ${network.total.outputMb}mb`;
|
||||||
}
|
}
|
||||||
|
|
||||||
console.log(
|
console.log(
|
||||||
`[CPU] ${cpuUsed.toFixed(2)}% | [Memory] ${Math.round(
|
`[CPU] ${cpuUsed.toPrecision(3)}% | [Memory] ${Math.round(
|
||||||
process.memoryUsage().rss / 1024 / 1024
|
process.memoryUsage().rss / 1024 / 1024
|
||||||
)}mb/${memory.totalMemMb.toFixed(0)}mb ${networkUsage}`
|
)}mb/${memory.totalMemMb.toFixed(0)}mb ${networkUsage}`
|
||||||
);
|
);
|
||||||
}, 1000 * 30);
|
}, 1000 * 5);
|
||||||
}
|
}
|
||||||
|
@ -8,6 +8,13 @@ import imageSize from "image-size";
|
|||||||
|
|
||||||
const router = Router();
|
const router = Router();
|
||||||
|
|
||||||
|
const SANITIZED_CONTENT_TYPE = [
|
||||||
|
"text/html",
|
||||||
|
"text/mhtml",
|
||||||
|
"multipart/related",
|
||||||
|
"application/xhtml+xml",
|
||||||
|
];
|
||||||
|
|
||||||
router.post(
|
router.post(
|
||||||
"/:channel_id",
|
"/:channel_id",
|
||||||
multer.single("file"),
|
multer.single("file"),
|
||||||
@ -24,7 +31,8 @@ router.post(
|
|||||||
const id = Snowflake.generate();
|
const id = Snowflake.generate();
|
||||||
const path = `attachments/${channel_id}/${id}/${filename}`;
|
const path = `attachments/${channel_id}/${id}/${filename}`;
|
||||||
|
|
||||||
const endpoint = Config.get()?.cdn.endpoint || "http://localhost:3003";
|
const endpoint =
|
||||||
|
Config.get()?.cdn.endpointPublic || "http://localhost:3003";
|
||||||
|
|
||||||
await storage.set(path, buffer);
|
await storage.set(path, buffer);
|
||||||
var width;
|
var width;
|
||||||
@ -61,8 +69,13 @@ router.get(
|
|||||||
);
|
);
|
||||||
if (!file) throw new HTTPError("File not found");
|
if (!file) throw new HTTPError("File not found");
|
||||||
const type = await FileType.fromBuffer(file);
|
const type = await FileType.fromBuffer(file);
|
||||||
|
let content_type = type?.mime || "application/octet-stream";
|
||||||
|
|
||||||
res.set("Content-Type", type?.mime);
|
if (SANITIZED_CONTENT_TYPE.includes(content_type)) {
|
||||||
|
content_type = "application/octet-stream";
|
||||||
|
}
|
||||||
|
|
||||||
|
res.set("Content-Type", content_type);
|
||||||
res.set("Cache-Control", "public, max-age=31536000");
|
res.set("Cache-Control", "public, max-age=31536000");
|
||||||
|
|
||||||
return res.send(file);
|
return res.send(file);
|
||||||
|
@ -44,7 +44,8 @@ router.post(
|
|||||||
if (ANIMATED_MIME_TYPES.includes(type.mime)) hash = `a_${hash}`; // animated icons have a_ infront of the hash
|
if (ANIMATED_MIME_TYPES.includes(type.mime)) hash = `a_${hash}`; // animated icons have a_ infront of the hash
|
||||||
|
|
||||||
const path = `avatars/${user_id}/${hash}`;
|
const path = `avatars/${user_id}/${hash}`;
|
||||||
const endpoint = Config.get().cdn.endpoint || "http://localhost:3003";
|
const endpoint =
|
||||||
|
Config.get().cdn.endpointPublic || "http://localhost:3003";
|
||||||
|
|
||||||
await storage.set(path, buffer);
|
await storage.set(path, buffer);
|
||||||
|
|
||||||
|
@ -320,8 +320,8 @@ export class Channel extends BaseClass {
|
|||||||
}
|
}
|
||||||
|
|
||||||
export interface ChannelPermissionOverwrite {
|
export interface ChannelPermissionOverwrite {
|
||||||
allow: bigint; // for bitfields we use bigints
|
allow: string;
|
||||||
deny: bigint; // for bitfields we use bigints
|
deny: string;
|
||||||
id: string;
|
id: string;
|
||||||
type: ChannelPermissionOverwriteType;
|
type: ChannelPermissionOverwriteType;
|
||||||
}
|
}
|
||||||
|
@ -1,12 +1,15 @@
|
|||||||
import { Column, Entity, JoinColumn, ManyToOne } from "typeorm";
|
import { Column, Entity, JoinColumn, ManyToOne, PrimaryColumn } from "typeorm";
|
||||||
import { BaseClass } from "./BaseClass";
|
import { BaseClass, BaseClassWithoutId } from "./BaseClass";
|
||||||
import crypto from "crypto";
|
import crypto from "crypto";
|
||||||
import { Snowflake } from "../util/Snowflake";
|
import { Snowflake } from "../util/Snowflake";
|
||||||
|
|
||||||
@Entity("config")
|
@Entity("config")
|
||||||
export class ConfigEntity extends BaseClass {
|
export class ConfigEntity extends BaseClassWithoutId {
|
||||||
@Column({ type: "simple-json" })
|
@PrimaryColumn()
|
||||||
value: ConfigValue;
|
key: string;
|
||||||
|
|
||||||
|
@Column({ type: "simple-json", nullable: true })
|
||||||
|
value: number | boolean | null | string | undefined;
|
||||||
}
|
}
|
||||||
|
|
||||||
export interface RateLimitOptions {
|
export interface RateLimitOptions {
|
||||||
@ -37,14 +40,16 @@ export interface KafkaBroker {
|
|||||||
export interface ConfigValue {
|
export interface ConfigValue {
|
||||||
gateway: {
|
gateway: {
|
||||||
endpointClient: string | null;
|
endpointClient: string | null;
|
||||||
endpoint: string | null;
|
endpointPrivate: string | null;
|
||||||
|
endpointPublic: string | null;
|
||||||
};
|
};
|
||||||
cdn: {
|
cdn: {
|
||||||
endpointClient: string | null;
|
endpointClient: string | null;
|
||||||
endpoint: string | null;
|
endpointPublic: string | null;
|
||||||
|
endpointPrivate: string | null;
|
||||||
};
|
};
|
||||||
general: {
|
general: {
|
||||||
instance_id: string;
|
instanceId: string;
|
||||||
};
|
};
|
||||||
permissions: {
|
permissions: {
|
||||||
user: {
|
user: {
|
||||||
@ -149,14 +154,16 @@ export interface ConfigValue {
|
|||||||
export const DefaultConfigOptions: ConfigValue = {
|
export const DefaultConfigOptions: ConfigValue = {
|
||||||
gateway: {
|
gateway: {
|
||||||
endpointClient: null,
|
endpointClient: null,
|
||||||
endpoint: null,
|
endpointPrivate: null,
|
||||||
|
endpointPublic: null,
|
||||||
},
|
},
|
||||||
cdn: {
|
cdn: {
|
||||||
endpointClient: null,
|
endpointClient: null,
|
||||||
endpoint: null,
|
endpointPrivate: null,
|
||||||
|
endpointPublic: null,
|
||||||
},
|
},
|
||||||
general: {
|
general: {
|
||||||
instance_id: Snowflake.generate(),
|
instanceId: Snowflake.generate(),
|
||||||
},
|
},
|
||||||
permissions: {
|
permissions: {
|
||||||
user: {
|
user: {
|
||||||
|
@ -1,22 +1,66 @@
|
|||||||
import "missing-native-js-functions";
|
import "missing-native-js-functions";
|
||||||
import { ConfigValue, ConfigEntity, DefaultConfigOptions } from "../entities/Config";
|
import { ConfigValue, ConfigEntity, DefaultConfigOptions } from "../entities/Config";
|
||||||
|
|
||||||
var config: ConfigEntity;
|
var config: ConfigValue;
|
||||||
|
var pairs: ConfigEntity[];
|
||||||
|
|
||||||
// TODO: use events to inform about config updates
|
// TODO: use events to inform about config updates
|
||||||
|
// Config keys are separated with _
|
||||||
|
|
||||||
export const Config = {
|
export const Config = {
|
||||||
init: async function init() {
|
init: async function init() {
|
||||||
if (config) return config;
|
if (config) return config;
|
||||||
config = (await ConfigEntity.findOne({ id: "0" })) || new ConfigEntity({ id: "0" });
|
pairs = await ConfigEntity.find();
|
||||||
|
config = pairsToConfig(pairs);
|
||||||
|
|
||||||
return this.set((config.value || {}).merge(DefaultConfigOptions));
|
return this.set((config || {}).merge(DefaultConfigOptions));
|
||||||
},
|
},
|
||||||
get: function get() {
|
get: function get() {
|
||||||
return config.value as ConfigValue;
|
return config;
|
||||||
},
|
},
|
||||||
set: function set(val: Partial<ConfigValue>) {
|
set: function set(val: Partial<ConfigValue>) {
|
||||||
if (!config) return;
|
if (!config || !val) return;
|
||||||
config.value = val.merge(config?.value || {});
|
config = val.merge(config);
|
||||||
return config.save();
|
console.log(config);
|
||||||
|
|
||||||
|
return applyConfig(config);
|
||||||
},
|
},
|
||||||
};
|
};
|
||||||
|
|
||||||
|
function applyConfig(val: ConfigValue) {
|
||||||
|
async function apply(obj: any, key = ""): Promise<any> {
|
||||||
|
if (typeof obj === "object" && obj !== null)
|
||||||
|
return Promise.all(Object.keys(obj).map((k) => apply(obj[k], key ? `${key}_${k}` : k)));
|
||||||
|
|
||||||
|
let pair = pairs.find((x) => x.key === key);
|
||||||
|
if (!pair) pair = new ConfigEntity();
|
||||||
|
|
||||||
|
pair.key = key;
|
||||||
|
pair.value = obj;
|
||||||
|
return pair.save();
|
||||||
|
}
|
||||||
|
|
||||||
|
return apply(val);
|
||||||
|
}
|
||||||
|
|
||||||
|
function pairsToConfig(pairs: ConfigEntity[]) {
|
||||||
|
var value: any = {};
|
||||||
|
|
||||||
|
pairs.forEach((p) => {
|
||||||
|
const keys = p.key.split("_");
|
||||||
|
let prev = "";
|
||||||
|
let obj = value;
|
||||||
|
let i = 0;
|
||||||
|
|
||||||
|
for (const key of keys) {
|
||||||
|
if (Number(key) && !obj[prev]) obj = obj[prev] = [];
|
||||||
|
if (i++ === keys.length - 1) obj[key] = p.value;
|
||||||
|
else if (!obj[key]) obj[key] = {};
|
||||||
|
|
||||||
|
prev = key;
|
||||||
|
obj = obj[key];
|
||||||
|
}
|
||||||
|
});
|
||||||
|
|
||||||
|
return value as ConfigValue;
|
||||||
|
}
|
||||||
|
@ -22,7 +22,7 @@ export function initDatabase() {
|
|||||||
//
|
//
|
||||||
entities: Object.values(Models).filter((x) => x.constructor.name !== "Object"),
|
entities: Object.values(Models).filter((x) => x.constructor.name !== "Object"),
|
||||||
synchronize: true,
|
synchronize: true,
|
||||||
logging: true,
|
logging: false,
|
||||||
cache: {
|
cache: {
|
||||||
duration: 1000 * 3, // cache all find queries for 3 seconds
|
duration: 1000 * 3, // cache all find queries for 3 seconds
|
||||||
},
|
},
|
||||||
|
@ -3,6 +3,7 @@
|
|||||||
import { Channel, ChannelPermissionOverwrite, Guild, Member, Role } from "../entities";
|
import { Channel, ChannelPermissionOverwrite, Guild, Member, Role } from "../entities";
|
||||||
import { BitField } from "./BitField";
|
import { BitField } from "./BitField";
|
||||||
import "missing-native-js-functions";
|
import "missing-native-js-functions";
|
||||||
|
import { BitFieldResolvable } from ".";
|
||||||
// TODO: check role hierarchy permission
|
// TODO: check role hierarchy permission
|
||||||
|
|
||||||
var HTTPError: any;
|
var HTTPError: any;
|
||||||
@ -17,11 +18,19 @@ export type PermissionResolvable = bigint | number | Permissions | PermissionRes
|
|||||||
|
|
||||||
type PermissionString = keyof typeof Permissions.FLAGS;
|
type PermissionString = keyof typeof Permissions.FLAGS;
|
||||||
|
|
||||||
const CUSTOM_PERMISSION_OFFSET = BigInt(1) << BigInt(48); // 16 free custom permission bits, and 11 for discord to add new ones
|
// BigInt doesn't have a bit limit (https://stackoverflow.com/questions/53335545/whats-the-biggest-bigint-value-in-js-as-per-spec)
|
||||||
|
const CUSTOM_PERMISSION_OFFSET = BigInt(1) << BigInt(64); // 27 permission bits left for discord to add new ones
|
||||||
|
|
||||||
export class Permissions extends BitField {
|
export class Permissions extends BitField {
|
||||||
cache: PermissionCache = {};
|
cache: PermissionCache = {};
|
||||||
|
|
||||||
|
constructor(bits: BitFieldResolvable = 0) {
|
||||||
|
super(bits);
|
||||||
|
if (this.bitfield & Permissions.FLAGS.ADMINISTRATOR) {
|
||||||
|
this.bitfield = ALL_PERMISSIONS;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
static FLAGS = {
|
static FLAGS = {
|
||||||
CREATE_INSTANT_INVITE: BigInt(1) << BigInt(0),
|
CREATE_INSTANT_INVITE: BigInt(1) << BigInt(0),
|
||||||
KICK_MEMBERS: BigInt(1) << BigInt(1),
|
KICK_MEMBERS: BigInt(1) << BigInt(1),
|
||||||
@ -92,7 +101,7 @@ export class Permissions extends BitField {
|
|||||||
}
|
}
|
||||||
|
|
||||||
overwriteChannel(overwrites: ChannelPermissionOverwrite[]) {
|
overwriteChannel(overwrites: ChannelPermissionOverwrite[]) {
|
||||||
if (!overwrites) return this
|
if (!overwrites) return this;
|
||||||
if (!this.cache) throw new Error("permission chache not available");
|
if (!this.cache) throw new Error("permission chache not available");
|
||||||
overwrites = overwrites.filter((x) => {
|
overwrites = overwrites.filter((x) => {
|
||||||
if (x.type === 0 && this.cache.roles?.some((r) => r.id === x.id)) return true;
|
if (x.type === 0 && this.cache.roles?.some((r) => r.id === x.id)) return true;
|
||||||
@ -175,6 +184,8 @@ export class Permissions extends BitField {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
const ALL_PERMISSIONS = Object.values(Permissions.FLAGS).reduce((total, val) => total | val, BigInt(0));
|
||||||
|
|
||||||
export type PermissionCache = {
|
export type PermissionCache = {
|
||||||
channel?: Channel | undefined;
|
channel?: Channel | undefined;
|
||||||
member?: Member | undefined;
|
member?: Member | undefined;
|
||||||
|
@ -11,7 +11,7 @@ export async function uploadFile(path: string, file: Express.Multer.File) {
|
|||||||
filename: file.originalname,
|
filename: file.originalname,
|
||||||
});
|
});
|
||||||
|
|
||||||
const response = await fetch(`${Config.get().cdn.endpoint || "http://localhost:3003"}${path}`, {
|
const response = await fetch(`${Config.get().cdn.endpointPrivate || "http://localhost:3003"}${path}`, {
|
||||||
headers: {
|
headers: {
|
||||||
signature: Config.get().security.requestSignature,
|
signature: Config.get().security.requestSignature,
|
||||||
...form.getHeaders(),
|
...form.getHeaders(),
|
||||||
@ -41,7 +41,7 @@ export async function handleFile(path: string, body?: string): Promise<string |
|
|||||||
}
|
}
|
||||||
|
|
||||||
export async function deleteFile(path: string) {
|
export async function deleteFile(path: string) {
|
||||||
const response = await fetch(`${Config.get().cdn.endpoint || "http://localhost:3003"}${path}`, {
|
const response = await fetch(`${Config.get().cdn.endpointPrivate || "http://localhost:3003"}${path}`, {
|
||||||
headers: {
|
headers: {
|
||||||
signature: Config.get().security.requestSignature,
|
signature: Config.get().security.requestSignature,
|
||||||
},
|
},
|
||||||
|
Loading…
x
Reference in New Issue
Block a user