mirror of
https://github.com/thelounge/thelounge
synced 2024-11-26 05:50:22 +00:00
Merge pull request #3281 from thelounge/mcinkay/input-refactor
Refactor command API for plugins
This commit is contained in:
commit
807856dbef
5 changed files with 68 additions and 21 deletions
|
@ -12,6 +12,7 @@ const UAParser = require("ua-parser-js");
|
||||||
const uuidv4 = require("uuid/v4");
|
const uuidv4 = require("uuid/v4");
|
||||||
const escapeRegExp = require("lodash/escapeRegExp");
|
const escapeRegExp = require("lodash/escapeRegExp");
|
||||||
const inputs = require("./plugins/inputs");
|
const inputs = require("./plugins/inputs");
|
||||||
|
const PublicClient = require("./plugins/packages/publicClient");
|
||||||
|
|
||||||
const MessageStorage = require("./plugins/messageStorage/sqlite");
|
const MessageStorage = require("./plugins/messageStorage/sqlite");
|
||||||
const TextFileMessageStorage = require("./plugins/messageStorage/text");
|
const TextFileMessageStorage = require("./plugins/messageStorage/text");
|
||||||
|
@ -336,20 +337,19 @@ Client.prototype.inputLine = function(data) {
|
||||||
const irc = target.network.irc;
|
const irc = target.network.irc;
|
||||||
let connected = irc && irc.connection && irc.connection.connected;
|
let connected = irc && irc.connection && irc.connection.connected;
|
||||||
|
|
||||||
if (Object.prototype.hasOwnProperty.call(inputs.userInputs, cmd) && typeof inputs.userInputs[cmd].input === "function") {
|
if (inputs.userInputs.has(cmd)) {
|
||||||
const plugin = inputs.userInputs[cmd];
|
const plugin = inputs.userInputs.get(cmd);
|
||||||
|
|
||||||
if (connected || plugin.allowDisconnected) {
|
if (typeof plugin.input === "function" && (connected || plugin.allowDisconnected)) {
|
||||||
connected = true;
|
connected = true;
|
||||||
plugin.input.apply(client,
|
plugin.input.apply(client, [target.network, target.chan, cmd, args]);
|
||||||
[
|
}
|
||||||
target.network,
|
} else if (inputs.pluginCommands.has(cmd)) {
|
||||||
target.chan,
|
const plugin = inputs.pluginCommands.get(cmd);
|
||||||
cmd,
|
|
||||||
args,
|
if (typeof plugin.input === "function" && (connected || plugin.allowDisconnected)) {
|
||||||
(command) => this.inputLine({target: data.target, text: command}),
|
connected = true;
|
||||||
]
|
plugin.input(new PublicClient(client), {network: target.network, chan: target.chan}, cmd, args);
|
||||||
);
|
|
||||||
}
|
}
|
||||||
} else if (connected) {
|
} else if (connected) {
|
||||||
irc.raw(text);
|
irc.raw(text);
|
||||||
|
|
|
@ -37,18 +37,25 @@ const userInputs = [
|
||||||
"whois",
|
"whois",
|
||||||
].reduce(function(plugins, name) {
|
].reduce(function(plugins, name) {
|
||||||
const plugin = require(`./${name}`);
|
const plugin = require(`./${name}`);
|
||||||
plugin.commands.forEach((command) => (plugins[command] = plugin));
|
plugin.commands.forEach((command) => plugins.set(command, plugin));
|
||||||
return plugins;
|
return plugins;
|
||||||
}, {});
|
}, new Map());
|
||||||
|
|
||||||
|
const pluginCommands = new Map();
|
||||||
|
|
||||||
const getCommands = () =>
|
const getCommands = () =>
|
||||||
Object.keys(userInputs)
|
Array.from(userInputs.keys())
|
||||||
|
.concat(Array.from(pluginCommands.keys()))
|
||||||
.map((command) => `/${command}`)
|
.map((command) => `/${command}`)
|
||||||
.concat(clientSideCommands)
|
.concat(clientSideCommands)
|
||||||
.concat(passThroughCommands)
|
.concat(passThroughCommands)
|
||||||
.sort();
|
.sort();
|
||||||
|
|
||||||
|
const addPluginCommand = (command, func) => pluginCommands.set(command, func);
|
||||||
|
|
||||||
module.exports = {
|
module.exports = {
|
||||||
|
addPluginCommand,
|
||||||
getCommands,
|
getCommands,
|
||||||
|
pluginCommands,
|
||||||
userInputs,
|
userInputs,
|
||||||
};
|
};
|
||||||
|
|
|
@ -16,14 +16,14 @@ module.exports = {
|
||||||
loadPackages,
|
loadPackages,
|
||||||
};
|
};
|
||||||
|
|
||||||
const packageApis = function(clientManager, packageName) {
|
const packageApis = function(packageName) {
|
||||||
return {
|
return {
|
||||||
Stylesheets: {
|
Stylesheets: {
|
||||||
addFile: addStylesheet.bind(this, packageName),
|
addFile: addStylesheet.bind(this, packageName),
|
||||||
},
|
},
|
||||||
Commands: {
|
Commands: {
|
||||||
add: (command, func) => inputs.userInputs[command] = func,
|
add: inputs.addPluginCommand,
|
||||||
runAsUser: (line, userName, target) => clientManager.findClient(userName).inputLine({target, text: line}),
|
runAsUser: (command, targetId, client) => client.inputLine({target: targetId, text: command}),
|
||||||
},
|
},
|
||||||
Config: {
|
Config: {
|
||||||
getConfig: () => Helper.config,
|
getConfig: () => Helper.config,
|
||||||
|
@ -43,7 +43,7 @@ function getPackage(name) {
|
||||||
return packageMap.get(name);
|
return packageMap.get(name);
|
||||||
}
|
}
|
||||||
|
|
||||||
function loadPackages(clientManager) {
|
function loadPackages() {
|
||||||
const packageJson = path.join(Helper.getPackagesPath(), "package.json");
|
const packageJson = path.join(Helper.getPackagesPath(), "package.json");
|
||||||
let packages;
|
let packages;
|
||||||
let anyPlugins = false;
|
let anyPlugins = false;
|
||||||
|
@ -83,7 +83,7 @@ function loadPackages(clientManager) {
|
||||||
}
|
}
|
||||||
|
|
||||||
if (packageFile.onServerStart) {
|
if (packageFile.onServerStart) {
|
||||||
packageFile.onServerStart(packageApis(clientManager, packageName));
|
packageFile.onServerStart(packageApis(packageName));
|
||||||
}
|
}
|
||||||
|
|
||||||
log.info(`Package ${colors.bold(packageName)} loaded`);
|
log.info(`Package ${colors.bold(packageName)} loaded`);
|
||||||
|
|
40
src/plugins/packages/publicClient.js
Normal file
40
src/plugins/packages/publicClient.js
Normal file
|
@ -0,0 +1,40 @@
|
||||||
|
module.exports = class PublicClient {
|
||||||
|
constructor(client) {
|
||||||
|
this.client = client;
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
*
|
||||||
|
* @param {String} command - IRC command to run, this is in the same format that a client would send to the server (eg: JOIN #test)
|
||||||
|
* @param {String} targetId - The id of the channel to simulate the command coming from. Replies will go to this channel if appropriate
|
||||||
|
*/
|
||||||
|
runAsUser(command, targetId) {
|
||||||
|
this.client.inputLine({target: targetId, text: command});
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
*
|
||||||
|
* @param {Object} attributes
|
||||||
|
*/
|
||||||
|
createChannel(attributes) {
|
||||||
|
return this.client.createChannel(attributes);
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Emits an `event` to the browser client, with `data` in the body of the event.
|
||||||
|
*
|
||||||
|
* @param {String} event - Name of the event, must be something the browser will recognise
|
||||||
|
* @param {Object} data - Body of the event, can be anything, but will need to be properly interpreted by the client
|
||||||
|
*/
|
||||||
|
sendToBrowser(event, data) {
|
||||||
|
this.client.emit(event, data);
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
*
|
||||||
|
* @param {Number} chanId
|
||||||
|
*/
|
||||||
|
getChannel(chanId) {
|
||||||
|
return this.client.find(chanId);
|
||||||
|
}
|
||||||
|
};
|
|
@ -173,7 +173,7 @@ module.exports = function() {
|
||||||
});
|
});
|
||||||
|
|
||||||
manager = new ClientManager();
|
manager = new ClientManager();
|
||||||
packages.loadPackages(manager);
|
packages.loadPackages();
|
||||||
|
|
||||||
new Identification((identHandler) => {
|
new Identification((identHandler) => {
|
||||||
manager.init(identHandler, sockets);
|
manager.init(identHandler, sockets);
|
||||||
|
|
Loading…
Reference in a new issue