diff --git a/package-lock.json b/package-lock.json index fcb4d68..903fd91 100644 --- a/package-lock.json +++ b/package-lock.json @@ -9,6 +9,11 @@ "resolved": "https://registry.npmjs.org/@types/color-name/-/color-name-1.1.1.tgz", "integrity": "sha512-rr+OQyAjxze7GgWrSaJwydHStIhHq2lvY3BOC2Mj7KnzI7XK0Uw1TOOdI9lDoajEbSWLiYgoo4f1R51erQfhPQ==" }, + "agent-base": { + "version": "5.1.1", + "resolved": "https://registry.npmjs.org/agent-base/-/agent-base-5.1.1.tgz", + "integrity": "sha512-TMeqbNl2fMW0nMjTEPOwe3J/PRFP4vqeoNuQMG0HlMrtm5QxKqdvAkZ1pRBQ/ulIyDD5Yq0nJ7YbdD8ey0TO3g==" + }, "ajv": { "version": "6.12.2", "resolved": "https://registry.npmjs.org/ajv/-/ajv-6.12.2.tgz", @@ -72,6 +77,14 @@ } } }, + "argparse": { + "version": "1.0.10", + "resolved": "https://registry.npmjs.org/argparse/-/argparse-1.0.10.tgz", + "integrity": "sha512-o5Roy6tNG4SL/FOkCAN6RzjiakZS25RLYFrcMttJqbdd8BWrnA+fGz57iN5Pb06pvBGvl5gQ0B48dJlslXvoTg==", + "requires": { + "sprintf-js": "~1.0.2" + } + }, "array-back": { "version": "3.1.0", "resolved": "https://registry.npmjs.org/array-back/-/array-back-3.1.0.tgz", @@ -243,9 +256,9 @@ "integrity": "sha1-G2gcIf+EAzyCZUMJBolCDRhxUdw=" }, "chalk": { - "version": "4.0.0", - "resolved": "https://registry.npmjs.org/chalk/-/chalk-4.0.0.tgz", - "integrity": "sha512-N9oWFcegS0sFr9oh1oz2d7Npos6vNoWW9HvtCg5N1KRFpUhaAhvTv5Y58g880fZaEYSNm3qDz8SU1UrGvp+n7A==", + "version": "4.1.0", + "resolved": "https://registry.npmjs.org/chalk/-/chalk-4.1.0.tgz", + "integrity": "sha512-qwx12AxXe2Q5xQ43Ac//I6v5aXTipYrSESdOgzrN+9XjgEpyjpKuvSGaN4qE93f7TQTlerQQ8S+EQ0EyDoVL1A==", "requires": { "ansi-styles": "^4.1.0", "supports-color": "^7.1.0" @@ -708,6 +721,26 @@ "resolved": "https://registry.npmjs.org/fast-json-stable-stringify/-/fast-json-stable-stringify-2.1.0.tgz", "integrity": "sha512-lhd/wF+Lk98HZoTCtlVraHtfh5XYijIjalXck7saUtuanSDyLMxnHhSXEDJqHxD7msR8D0uCmqlkwjCV8xvwHw==" }, + "fca-unofficial": { + "version": "github:fca-unofficial/fca-unofficial#df96e1597a1d516b10c0cfea59dfebd694bd1c20", + "from": "github:fca-unofficial/fca-unofficial", + "requires": { + "bluebird": "^2.11.0", + "cheerio": "^0.22.0", + "https-proxy-agent": "^4.0.0", + "mqtt": "^3.0.0", + "npmlog": "^1.2.0", + "request": "^2.53.0", + "websocket-stream": "^5.5.0" + }, + "dependencies": { + "bluebird": { + "version": "2.11.0", + "resolved": "https://registry.npmjs.org/bluebird/-/bluebird-2.11.0.tgz", + "integrity": "sha1-U0uQM8AiyVecVro7Plpcqvu2UOE=" + } + } + }, "find-replace": { "version": "3.0.0", "resolved": "https://registry.npmjs.org/find-replace/-/find-replace-3.0.0.tgz", @@ -882,6 +915,15 @@ "sshpk": "^1.7.0" } }, + "https-proxy-agent": { + "version": "4.0.0", + "resolved": "https://registry.npmjs.org/https-proxy-agent/-/https-proxy-agent-4.0.0.tgz", + "integrity": "sha512-zoDhWrkR3of1l9QAL8/scJZyLu8j/gBkcwcaQOZh7Gyh/+uJQzGVETdgT30akuwkpL8HTRfssqI3BZuV18teDg==", + "requires": { + "agent-base": "5", + "debug": "4" + } + }, "inflight": { "version": "1.0.6", "resolved": "https://registry.npmjs.org/inflight/-/inflight-1.0.6.tgz", @@ -1080,6 +1122,36 @@ "resolved": "https://registry.npmjs.org/lodash.some/-/lodash.some-4.6.0.tgz", "integrity": "sha1-G7nzFO9ri63tE7VJFpsqlF62jk0=" }, + "memjs": { + "version": "1.2.2", + "resolved": "https://registry.npmjs.org/memjs/-/memjs-1.2.2.tgz", + "integrity": "sha512-j6I5cQsjT8izm0FcBZrwga4VmlhTMsBTPKdyKolQenLulHNvKuNcDgDmBhQvScqNLy4tjpCCFwiqFK+5l6J20g==" + }, + "messenger-botcore": { + "version": "2.2.0", + "resolved": "https://registry.npmjs.org/messenger-botcore/-/messenger-botcore-2.2.0.tgz", + "integrity": "sha512-k5t24tz3bXYVQJcVPqrSnDc1CE3163HLJMt/hTJQn9eZAD6vntYyycjPpyNdO64OBfrM14b4mEHz+mThE9E9RA==", + "requires": { + "argparse": "^1.0.10", + "facebook-chat-api": "github:Schmavery/facebook-chat-api", + "fca-unofficial": "github:fca-unofficial/fca-unofficial", + "memjs": "^1.2.2" + }, + "dependencies": { + "facebook-chat-api": { + "version": "github:Schmavery/facebook-chat-api#fdac7fb45141df25d6ebf36f9b59b7c483fb3938", + "from": "github:Schmavery/facebook-chat-api", + "requires": { + "bluebird": "^3.0.0", + "cheerio": "^0.22.0", + "mqtt": "^3.0.0", + "npmlog": "^1.2.0", + "request": "^2.53.0", + "websocket-stream": "^5.5.0" + } + } + } + }, "mime-db": { "version": "1.43.0", "resolved": "https://registry.npmjs.org/mime-db/-/mime-db-1.43.0.tgz", @@ -1387,6 +1459,11 @@ "readable-stream": "^3.0.0" } }, + "sprintf-js": { + "version": "1.0.3", + "resolved": "https://registry.npmjs.org/sprintf-js/-/sprintf-js-1.0.3.tgz", + "integrity": "sha1-BOaSb2YolTVPPdAVIDYzuFcpfiw=" + }, "sshpk": { "version": "1.16.1", "resolved": "https://registry.npmjs.org/sshpk/-/sshpk-1.16.1.tgz", diff --git a/package.json b/package.json index b7ba3aa..a3908fc 100644 --- a/package.json +++ b/package.json @@ -10,6 +10,7 @@ "test": "echo test | mnotify", "init": "mnotify --init", "help": "mnotify --help", + "botcore": "mnotify --using-botcore", "postinstall": "src/postinstall.js" }, "repository": { @@ -29,10 +30,11 @@ }, "homepage": "https://github.com/AstroCB/mnotify#readme", "dependencies": { - "chalk": "^4.0.0", + "chalk": "^4.1.0", "command-line-args": "^5.1.1", "command-line-usage": "^6.1.0", "facebook-chat-api": "^1.8.0", + "messenger-botcore": "^2.2.0", "readline-sync": "^1.4.10" } } diff --git a/src/mnotify.js b/src/mnotify.js index b0c390d..0d39303 100755 --- a/src/mnotify.js +++ b/src/mnotify.js @@ -19,7 +19,8 @@ const argDefs = [ { "name": "init", "type": Boolean, "description": "Initialize mnotify so that it can be used to send notifications." }, { "name": "help", "alias": "h", "type": Boolean, "description": "Display this help message." }, { "name": "check-login", "alias": "c", "type": Boolean, "description": "Check whether your currently-stored login information is valid." }, - { "name": "update-password", "alias": "p", "type": String, "description": "Update your sending account's password without re-running init." } + { "name": "update-password", "alias": "p", "type": String, "description": "Update your sending account's password without re-running init." }, + { "name": "using-botcore", "alias": "b", "type": Boolean, "description": `Process sender account logins using BotCore ({underline https://github.com/AstroCB/BotCore}) instead of a raw username/password. You must still run ${chalk.blue("mnotify --init")} before using this command in order to configure the receiver's account.`} ]; const helpSections = [ @@ -146,6 +147,14 @@ if (require.main === module) { }); } else if (options["update-password"]) { tools.updatePassword(options["update-password"]); + } else if (options["using-botcore"]) { + tools.botcoreLogin(err => { + if (err) { + console.log(chalk.red(err)); + } else { + start(); + } + }); } else { start(); } diff --git a/src/tools.js b/src/tools.js index 5e677ca..5e0998d 100644 --- a/src/tools.js +++ b/src/tools.js @@ -1,6 +1,7 @@ const fs = require("fs"); const chalk = require("chalk"); const login = require("facebook-chat-api"); +const botcore = require("messenger-botcore"); // Location of config directory (respects user settings) exports.getConfigDir = () => { @@ -25,8 +26,8 @@ exports.loadConfig = () => { } } -exports.saveConfig = config => { - fs.writeFile(exports.getConfigPath(), JSON.stringify(config), () => { }); +exports.saveConfig = (config, callback = () => { }) => { + fs.writeFile(exports.getConfigPath(), JSON.stringify(config), callback); } exports.printNoConfigError = () => { @@ -91,6 +92,43 @@ exports.checkLogin = (fail, succeed) => { } } +exports.botcoreLogin = callback => { + const requiredVars = ["MEMCACHIER_USERNAME", "MEMCACHIER_SERVERS", "MEMCACHIER_PASSWORD"]; + requiredVars.forEach(v => { + if (!process.env[v]) { + return callback(`Failed to access BotCore; make sure your required credentials [${requiredVars.join(", ")}]\ +are stored as environment variables: https://github.com/AstroCB/BotCore/blob/master/DOCS.md#credentialsobj`); + } + }); + + botcore.login.login(process.env, (err, api) => { + if (err) { + callback(`Error with login: ${err}`); + } else { + // Close out BotCore memcache connection to avoid hanging + const mem = botcore.login.getMemCache(); + if (mem) { + mem.close(); + } + + let config; + try { + config = this.loadConfig(); + } catch { + console.log(chalk.yellow(`Error loading config; even when logging in with BotCore,\ +you must still configure mnotify to set up the receiver's account.`)); + + // Call with no error anyway to passthrough to the default init that happens in start() + return callback(null); + } + + // Update the login in the config + config.appState = api.getAppState(); + this.saveConfig(config, callback); + } + }); +} + // Stored options for common invocations exports.silentOpt = {