mirror of
https://github.com/spacebarchat/server.git
synced 2026-05-24 16:45:16 +00:00
Update plugin loading, update example plugin, add ci task for testing if builds work
This commit is contained in:
@@ -0,0 +1,29 @@
|
||||
on:
|
||||
workflow_dispatch:
|
||||
push:
|
||||
paths:
|
||||
- "**"
|
||||
|
||||
name: Test Build
|
||||
|
||||
jobs:
|
||||
insiders-build:
|
||||
strategy:
|
||||
matrix:
|
||||
os: [windows, macos, ubuntu]
|
||||
include:
|
||||
- os: windows
|
||||
- os: macos
|
||||
- os: ubuntu
|
||||
runs-on: ${{ matrix.os }}-latest
|
||||
steps:
|
||||
- uses: actions/checkout@v2
|
||||
- uses: actions/setup-node@v2
|
||||
env:
|
||||
MONGOMS_VERSION: 4.4.3
|
||||
with:
|
||||
node-version: 18
|
||||
- run: |
|
||||
cd bundle
|
||||
npm run setup
|
||||
npm run build clean logerrors pretty-errors propagate-err
|
||||
@@ -0,0 +1,116 @@
|
||||
const { execSync } = require("child_process");
|
||||
const path = require("path");
|
||||
const fs = require("fs");
|
||||
const { argv, stdout, exit } = require("process");
|
||||
const { execIn, parts, getDirs, walk, sanitizeVarName } = require("./utils");
|
||||
|
||||
if (argv.includes("help")) {
|
||||
console.log(`Fosscord build script help:
|
||||
Arguments:
|
||||
clean Cleans up previous builds
|
||||
verbose Enable verbose logging
|
||||
logerrors Log build errors to console
|
||||
pretty-errors Pretty-print build errors
|
||||
silent No output to console or files.
|
||||
propagate-err Exit script with error code if build fails.`);
|
||||
exit(0);
|
||||
}
|
||||
|
||||
let steps = 5,
|
||||
i = 0;
|
||||
if (argv.includes("clean")) steps++;
|
||||
|
||||
const verbose = argv.includes("verbose") || argv.includes("v");
|
||||
const logerr = argv.includes("logerrors");
|
||||
const pretty = argv.includes("pretty-errors");
|
||||
const silent = argv.includes("silent");
|
||||
|
||||
if (silent) console.error = console.log = function () {};
|
||||
|
||||
if (argv.includes("clean")) {
|
||||
console.log(`[${++i}/${steps}] Cleaning...`);
|
||||
let d = "../" + "/dist";
|
||||
if (fs.existsSync(d)) {
|
||||
fs.rmSync(d, { recursive: true });
|
||||
if (verbose) console.log(`Deleted ${d}!`);
|
||||
}
|
||||
}
|
||||
|
||||
console.log(`[${++i}/${steps}] Compiling src files ...`);
|
||||
|
||||
let buildFlags = "";
|
||||
if (pretty) buildFlags += "--pretty ";
|
||||
|
||||
console.log(`[${++i}/${steps}] Building plugin index...`);
|
||||
let pluginDir = path.join(__dirname, "..", "src", "plugins");
|
||||
let output = 'import { Plugin } from "util/plugin";\n';
|
||||
|
||||
const dirs = fs.readdirSync(pluginDir).filter((x) => {
|
||||
try {
|
||||
fs.readdirSync(path.join(pluginDir, x));
|
||||
return true;
|
||||
} catch (e) {
|
||||
return false;
|
||||
}
|
||||
});
|
||||
dirs.forEach((x) => {
|
||||
let pluginManifest = require(path.join(pluginDir, x, "plugin.json"));
|
||||
output += `import * as ${sanitizeVarName(x)} from "./${x}/${pluginManifest.mainClass}";\n`;
|
||||
});
|
||||
output += `\nexport const PluginIndex: any = {\n`;
|
||||
dirs.forEach((x) => {
|
||||
output += ` "${x}": new ${sanitizeVarName(x)}.default(),\n`; //ctor test: '${path.resolve(path.join(pluginDir, x))}', require('./${x}/plugin.json')
|
||||
});
|
||||
output += `};`;
|
||||
|
||||
fs.writeFileSync(path.join(__dirname, "..", "src", "plugins", "PluginIndex.ts"), output);
|
||||
|
||||
if (!argv.includes("copyonly")) {
|
||||
console.log(`[${++i}/${steps}] Compiling source code...`);
|
||||
|
||||
let buildFlags = "";
|
||||
if (pretty) buildFlags += "--pretty ";
|
||||
|
||||
try {
|
||||
execSync(
|
||||
'node "' +
|
||||
path.join(__dirname, "..", "node_modules", "typescript", "lib", "tsc.js") +
|
||||
'" -p "' +
|
||||
path.join(__dirname, "..") +
|
||||
'" ' +
|
||||
buildFlags,
|
||||
{
|
||||
cwd: path.join(__dirname, ".."),
|
||||
shell: true,
|
||||
env: process.env,
|
||||
encoding: "utf8"
|
||||
}
|
||||
);
|
||||
} catch (error) {
|
||||
if (verbose || logerr) {
|
||||
error.stdout.split(/\r?\n/).forEach((line) => {
|
||||
let _line = line.replace("dist/", "", 1);
|
||||
if (!pretty && _line.includes(".ts(")) {
|
||||
//reformat file path for easy jumping
|
||||
_line = _line.replace("(", ":", 1).replace(",", ":", 1).replace(")", "", 1);
|
||||
}
|
||||
console.error(_line);
|
||||
});
|
||||
}
|
||||
console.error(`Build failed! Please check build.log for info!`);
|
||||
if (!silent) {
|
||||
if (pretty) fs.writeFileSync("build.log.ansi", error.stdout);
|
||||
fs.writeFileSync(
|
||||
"build.log",
|
||||
error.stdout.replaceAll(/[\u001b\u009b][[()#;?]*(?:[0-9]{1,4}(?:;[0-9]{0,4})*)?[0-9A-ORZcf-nqry=><]/g, "")
|
||||
);
|
||||
}
|
||||
throw error;
|
||||
}
|
||||
}
|
||||
|
||||
console.log(`[${++i}/${steps}] Copying plugin data...`);
|
||||
let pluginFiles = walk(pluginDir).filter((x) => !x.endsWith(".ts"));
|
||||
pluginFiles.forEach((x) => {
|
||||
fs.copyFileSync(x, x.replace("src", "dist"));
|
||||
});
|
||||
@@ -0,0 +1,7 @@
|
||||
import { Plugin } from "@fosscord/util";
|
||||
|
||||
export default class TestPlugin extends Plugin {
|
||||
onPluginLoaded(): void {
|
||||
console.log("Hello from test plugin! IT WORKS!!!!!!!");
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,10 @@
|
||||
{
|
||||
"id": "example-plugin",
|
||||
"name": "Fosscord example plugin",
|
||||
"authors": [
|
||||
"The Arcane Brony"
|
||||
],
|
||||
"repository": "https://github.com/fosscord/fosscord-server",
|
||||
"license": "",
|
||||
"index": "ExamplePlugin.js"
|
||||
}
|
||||
+5
-3
@@ -1,17 +1,17 @@
|
||||
/*
|
||||
Spacebar: A FOSS re-implementation and extension of the Discord.com backend.
|
||||
Copyright (C) 2023 Spacebar and Spacebar Contributors
|
||||
|
||||
|
||||
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/>.
|
||||
*/
|
||||
@@ -29,3 +29,5 @@ export * from "./imports";
|
||||
export * from "./config";
|
||||
export * from "./connections";
|
||||
export * from "./Signing";
|
||||
export * from "./schemas";
|
||||
export * from "./plugin";
|
||||
@@ -6,7 +6,14 @@ type PluginEvents = {
|
||||
loaded: () => void;
|
||||
};
|
||||
|
||||
export class Plugin extends (EventEmitter as new () => TypedEventEmitter<PluginEvents>) {
|
||||
//this doesnt work, check later:
|
||||
//(EventEmitter as new () => TypedEventEmitter<PluginEvents>) {
|
||||
export class Plugin extends EventEmitter {
|
||||
private _untypedOn = this.on
|
||||
private _untypedEmit = this.emit
|
||||
public on = <K extends keyof PluginEvents>(event: K, listener: PluginEvents[K]): this => this._untypedOn(event, listener)
|
||||
public emit = <K extends keyof PluginEvents>(event: K, ...args: Parameters<PluginEvents[K]>): boolean => this._untypedEmit(event, ...args)
|
||||
|
||||
async init() {
|
||||
// insert default config into database?
|
||||
}
|
||||
|
||||
@@ -2,7 +2,7 @@ import path from "path";
|
||||
import fs from "fs";
|
||||
import { Plugin, PluginManifest } from "./";
|
||||
|
||||
const root = process.env.PLUGIN_LOCATION || "../plugins";
|
||||
const root = process.env.PLUGIN_LOCATION || "dist/plugins";
|
||||
|
||||
let pluginsLoaded = false;
|
||||
export class PluginLoader {
|
||||
@@ -24,7 +24,7 @@ export class PluginLoader {
|
||||
console.log(
|
||||
`Plugin info: ${manifest.name} (${manifest.id}), written by ${manifest.authors}, available at ${manifest.repository}`
|
||||
);
|
||||
const module_ = require(path.join(modPath, "dist", "index.js")) as Plugin;
|
||||
const module_ = require(path.join(modPath, manifest.index)) as Plugin;
|
||||
try {
|
||||
await module_.init();
|
||||
module_.emit("loaded");
|
||||
|
||||
@@ -6,4 +6,5 @@ export class PluginManifest {
|
||||
license: string;
|
||||
version: string // semver
|
||||
versionCode: number // integer
|
||||
index: string;
|
||||
}
|
||||
Reference in New Issue
Block a user