diff --git a/.DS_Store b/.DS_Store deleted file mode 100644 index d9865a7..0000000 Binary files a/.DS_Store and /dev/null differ diff --git a/.gitignore b/.gitignore deleted file mode 100644 index 944c283..0000000 --- a/.gitignore +++ /dev/null @@ -1,2 +0,0 @@ -node_modules -.idea/ diff --git a/LICENSE b/LICENSE deleted file mode 100644 index c6ccaeb..0000000 --- a/LICENSE +++ /dev/null @@ -1,15 +0,0 @@ -The MIT License (MIT) - -Copyright (c) 2015-2016 LBRY Inc - -Permission is hereby granted, free of charge, to any person obtaining a copy of this software and associated documentation files (the -"Software"), to deal in the Software without restriction, including without limitation the rights to use, copy, modify, merge, publish, -distribute, sublicense, and/or sell copies of the Software, and to permit persons to whom the Software is furnished to do so, subject to the -following conditions: - -The above copyright notice and this permission notice shall be included in all copies or substantial portions of the Software. - -THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF -MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY -CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE -SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE. diff --git a/README.md b/README.md deleted file mode 100644 index 37717ba..0000000 --- a/README.md +++ /dev/null @@ -1,24 +0,0 @@ -# Bot for [LBRY's Slack](https://slack.lbry.io) - -Features: - -- Tipbot for LBC. Responds to `!tip`. -- Posts mining info to #mining every few hours and anytime someone says `!hash`. - - -## Requirements - -- node -- npm > 0.12.x - - -## Installation - -Create a bot and get the bot's API Token: https://YOURSLACK.slack.com/apps/manage/custom-integrations - -Then run: - -``` -npm install -SLACK_TOKEN= CHANNEL= node bot.js -``` diff --git a/app.js b/app.js deleted file mode 100644 index 72991dd..0000000 --- a/app.js +++ /dev/null @@ -1,85 +0,0 @@ -var SlackBot = require('slackbots'); -var request = require('request'); -var fs = require('fs'); -var path = require('path'); - -['SLACK_TOKEN', 'RPCUSER', 'RPCPASSWORD', 'MONGODB_URL'].forEach(function (envVar) { - if (!process.env[envVar]) { - throw new Error(envVar + ' env var required'); - } -}); - -var slackbot = new SlackBot({ - token: process.env.SLACK_TOKEN, - name: 'wunderbot' -}); - - -function sendWelcomeMessage(user) { - fs.readFile(path.join(path.dirname(require.main.filename), 'slack-greeting.md'), {encoding: 'utf-8'}, function (error, data) { - if (!error) { - slackbot.postMessage(user, data); - } - }); -}; - -var hashbot = require('./bots/hashbot'); -hashbot.init(slackbot, process.env.MINING_CHANNEL); - -var statbot = require('./bots/statbot'); -statbot.init(process.env.MARKET_TRADING_CHANNEL); - -var claimbot = require('./bots/claimbot'); -claimbot.init(slackbot, process.env.CLAIMS_CHANNEL, process.env.RPCUSER, process.env.RPCPASSWORD, process.env.MONGODB_URL); - -var pricebot = require('./bots/pricebot'); -pricebot.init(); //price bot only in PM - -var modbot = require('./bots/modbot'); -modbot.init(process.env.MONGODB_URL, process.env.SLACK_TOKEN, slackbot); - -slackbot.on('start', function() { - slackbot.on('message', function(data) { - modbot.check(slackbot,data); - if (data.type == 'team_join') { - setTimeout(function() { sendWelcomeMessage(data.user.id); }, 2000); //Delay because of slow slack api updates which sometimes does not send msg. - } - if (data.text) { -// gifbot.handle_msg(data.text, data.channel); - - var command = data.text.trim().split(' ')[0]; - - if (command === '!help') { - var helpMsg = "I'm Wunderbot, LBRY's slackbot. Here's what I can do:\n" + - '`!help` shows this message\n' + - '`!tip` sends LBC tips to others, and withdraws and deposits credits into the your tipping wallet *(now handled by <@tipbot>)*\n' + - '`!stats` shows market stats in trading channel\n' + - '`!price` works only in PM now\n' + - '`!hash` reports on the LBRY blockchain\n' + - '_type any of the above commands for more info_\n' + - '\n' + - 'I also update <#C266N3RMM|content> anytime new content is published on LBRY\n' + - '\n' + - 'My code is at https://github.com/lbryio/lbry-wunderbot. I love learning new tricks.\n'; - - slackbot.postMessage(data.channel, helpMsg, {icon_emoji: ':bulb:'}); - } - - if (command === hashbot.command) { - hashbot.respond(slackbot, data); - } - - if (command === '!tip' && data.channel.startsWith("D")) { - var tipMsg = 'Sorry, tipping is now handled by <@tipbot>\n'; - slackbot.postMessage(data.channel, tipMsg, {icon_emoji: ':bulb:'}); - } - - if (command === pricebot.command) { - pricebot.respond(slackbot, data); - } - if (command === statbot.command) { - statbot.respond(slackbot, data); - } - } - }); -}); diff --git a/bots/claimbot.js b/bots/claimbot.js deleted file mode 100644 index 2bbc265..0000000 --- a/bots/claimbot.js +++ /dev/null @@ -1,318 +0,0 @@ -'use strict'; - -var lbry; -var mongo; -var slackbot; -var channel; -var moment = require('moment'); -var request = require('request'); -var sleep = require('sleep'); - -module.exports = { - init: init, -}; - - -function init(slackbot_, channel_, rpcuser, rpcpassword, mongodburl) { - if (lbry) { - throw new Error('init was already called once'); - } - - slackbot = slackbot_; - - channel = channel_; - if (!channel_) { - console.log('No claims channel, disabling claimbot'); - return; - } - - const MongoClient = require('mongodb').MongoClient; - MongoClient.connect(mongodburl, function (err, db) { - if (err) { - throw err; - } - mongo = db; - - const bitcoin = require('bitcoin'); - lbry = new bitcoin.Client({ - host: 'localhost', - 'port': 9245, - 'user': rpcuser, - 'pass': rpcpassword - }); - - console.log('Activating claimbot'); - - setInterval(function () { - announceNewClaims(); - }, 60 * 1000); - announceNewClaims(); - }); -} - -function announceNewClaims() { - - if (!mongo) { - slackPost('Failed to connect to mongo', { icon_emoji: ':exclamation:' }); - return; - } - - if (!lbry) { - slackPost('Failed to connect to lbrycrd', { icon_emoji: ':exclamation:' }); - return; - } - - Promise.all([getLastBlock(), lbryCall('getinfo')]) - .then(function ([lastProcessedBlock, currentBlockInfo]) { - const currentHeight = currentBlockInfo['blocks']; - - // console.log('Checking for new blocks'); - - if (lastProcessedBlock === null) { - console.log('First run. Setting last processed block to ' + currentHeight + ' and exiting.'); - return setLastBlock(currentHeight); - } - - const testBlock = false; - - if (testBlock || lastProcessedBlock < currentHeight) { - const firstBlockToProcess = testBlock || lastProcessedBlock + 1, - lastBlockToProcess = testBlock || currentHeight; - - // console.log('Doing blocks ' + firstBlockToProcess + ' to ' + lastBlockToProcess); - return announceClaimsLoop(firstBlockToProcess, lastBlockToProcess, currentHeight); - - } - }) - .catch(function (err) { - slackPost(err.stack, { icon_emoji: ':exclamation:' }); - }); -} - -function announceClaimsLoop(block, lastBlock, currentHeight) { - // console.log('Doing block ' + block) - let claimsFound = 0; - return lbryCall('getblockhash', block) - .then(function (blockHash) { - return lbryCall('getblock', blockHash); - }) - .then(function (blockData) { - return Promise.all(blockData['tx'].map(getClaimsForTxid)) - }) - .then(function (arrayOfClaimArrays) { - const claims = Array.prototype.concat(...arrayOfClaimArrays).filter(function (c) { - return !!c; - }); - console.log('Found ' + claims.length + ' claims in ' + block); - claimsFound = claims.length; - return Promise.all(claims.map(function (claim) { - //slack has a rate limit. to avoid hitting it we must have a small delay between each message - //if claims were found in this block, then we wait, otherwise we don't - if (claimsFound > 0) - sleep.msleep(300); - return announceClaim(claim, block, currentHeight); - })); - }) - .then(function () { - return setLastBlock(block); - }) - .then(function () { - const nextBlock = block + 1; - if (nextBlock <= lastBlock) { - return announceClaimsLoop(nextBlock, lastBlock, currentHeight); - } - }); -} - -function announceClaim(claim, claimBlockHeight, currentHeight) { - //console.log(claim); - console.log('' + claimBlockHeight + ': New claim for ' + claim['name']); - var options = { - method: 'GET', - url: 'https://explorer.lbry.io/api/getclaimbyid/' + claim['claimId'] - //url: 'http://127.0.0.1:5000/claim_decode/' + claim['name'] - }; - - request(options, function (error, response, body) { - if (error) throw new Error(error); - try { - console.log(body); - - let claimData = null; - let channelName = null; - try { - body = JSON.parse(body); - if (body.hasOwnProperty('value') && body.value.hasOwnProperty('stream') && body.value.stream.hasOwnProperty('metadata')) { - claimData = body.value.stream.metadata; - channelName = (body.hasOwnProperty('channel_name') ? body['channel_name'] : null); - } - } - catch (e) { - console.error(e); - } - - return Promise.all([ - lbryCall('getvalueforname', claim['name']), - lbryCall('getclaimsforname', claim['name']), - ]) - .then(function ([currentWinningClaim, claimsForName]) { - //console.log(JSON.stringify(claimData)); - let value = null; - if (claimData !== null) - value = claimData; - else { - try { - value = JSON.parse(claim['value']); - } catch (e) { } - } - - const text = []; - - if (value) { - /*if (channelName) { - text.push("Channel: lbry://" + channelName); - } - else*/ - if (value['author']) { - text.push("author: " + value['author']); - } - if (value['description']) { - text.push(value['description']); - } - // if (value['content_type']) - // { - // text.push("*Content Type:* " + value['content_type']); - // } - if (value['nsfw']) { - text.push("*Warning: Adult Content*"); - } - - //"fee":{"currency":"LBC","amount":186,"version":"_0_0_1","address":"bTGoFCakvQXvBrJg1b7FJzombFUu6iRJsk"} - if (value['fee']) { - const fees = []; - text.push("Price: " + value['fee'].amount + " *" + value['fee'].currency + '*'); - /*for (var key in value['fee']) { - fees.push(value['fee'][key]['amount'] + ' ' + key); - } - text.push(fees.join(', '));*/ - } - } - - if (!claim['is controlling']) { - // the following is based on https://lbry.io/faq/claimtrie-implementation - const lastTakeoverHeight = claimsForName['nLastTakeoverHeight'], - maxDelay = 4032, // 7 days of blocks at 2.5min per block - activationDelay = Math.min(maxDelay, Math.floor((claimBlockHeight - lastTakeoverHeight) / 32)), - takeoverHeight = claimBlockHeight + activationDelay, - secondsPerBlock = 161, // in theory this should be 150, but in practice its closer to 161 - takeoverTime = Date.now() + ((takeoverHeight - currentHeight) * secondsPerBlock * 1000); - - text.push('Takes effect on approx. *' + moment(takeoverTime, 'x').format('MMMM Do [at] HH:mm [UTC]') + '* (block ' + takeoverHeight + ')'); - } - - const attachment = { - "fallback": "New claim for lbry://" + claim['name'], - "color": "#155b4a", - // "pretext": "New claim in block " + claimBlockHeight, - // "author_name": 'lbry://' + claim['name'], - // "author_link": 'lbry://' + claim['name'], - // "author_icon": "http://flickr.com/icons/bobby.jpg", - "title": "lbry://" + (channelName ? channelName + '/' : '') + claim['name'], //escapeSlackHtml(value['title']), - "title_link": "lbry://" + (channelName ? channelName + '/' : '') + claim['name'], - "text": escapeSlackHtml(text.join("\n")), - // "fields": [], - // "image_url": value['nsfw'] ? null : value['thumbnail'], - // "thumb_url": (!value || value['nsfw']) ? null : value['thumbnail'], - "unfurl_links": false, - "unfurl_media": false, - "link_names": false, - "parse": "none", - "footer": "Block " + claimBlockHeight + " • Claim ID " + claim['claimId'], - "mrkdwn_in": ['text'], - }; - - if (value) { - attachment['fallback'] += (': "' + value['title'] + '" by ' + value['author']); - attachment['author_name'] = 'lbry://' + (channelName ? channelName + '/' : '') + claim['name']; - attachment['author_link'] = 'lbry://' + (channelName ? channelName + '/' : '') + claim['name']; - attachment['title'] = escapeSlackHtml(value['title']); - if (!value['nsfw']) { - attachment['thumb_url'] = value['thumbnail']; - } - } - - slackPost('', { icon_emoji: ':bellhop_bell:', attachments: [attachment] }); - }); - } - catch (e) { - console.error(e); - } - }); -} - -function escapeSlackHtml(txt) { - return txt.replace('&', '&').replace('<', '<').replace('>', '>'); -} - -function getClaimsForTxid(txid) { - return lbryCall('getclaimsfortx', txid) - .catch(function (err) { - // an error here most likely means the transaction is spent, - // which also means there are no claims worth looking at - return []; - }); -} - -function getLastBlock() { - return new Promise(function (resolve, reject) { - mongo.collection('claimbot').findOne({}, function (err, obj) { - if (err) { - reject(err); - } - else if (!obj) { - mongo.collection('claimbot').createIndex({ 'last_block': 1 }, { unique: true }); - resolve(null); - } - else { - resolve(obj.last_block); - } - }); - }); -} - -function setLastBlock(block) { - return new Promise(function (resolve, reject) { - mongo.collection('claimbot').findOneAndUpdate( - { 'last_block': { '$exists': true } }, - { 'last_block': block }, - { 'upsert': true, 'returnOriginal': false }, - function (err, obj) { - if (!err && obj && obj.value.last_block != block) { - reject('Last value should be ' + block + ', but it is ' + obj.value.last_block); - } - else { - resolve(); - } - } - ); - }); -} - -function slackPost(text, params) { - slackbot.postMessage(channel, text, params).fail(function (value) { - console.log('FAILED TO SLACK to ' + channel + '. Text: "' + text + '". Params: ' + JSON.stringify(params) + "\nResponse: " + JSON.stringify(value)); - }); -} - -function lbryCall(...args) { - return new Promise(function (resolve, reject) { - lbry.cmd(...args, function (err, ...response) { - if (err) { - reject(new Error('JSONRPC call failed. Args: [' + args.join(', ') + ']')); - } - else { - resolve(...response); - } - }); - }); -} \ No newline at end of file diff --git a/bots/gifbot.js b/bots/gifbot.js deleted file mode 100644 index ab88df5..0000000 --- a/bots/gifbot.js +++ /dev/null @@ -1,186 +0,0 @@ -var XMLHttpRequest = require('xmlhttprequest').XMLHttpRequest; -var path = require('path'); -var fs = require('fs'); - -var slackbot; -var imgur; - -var cache = {}; -var cache_timeout = 3600; // 1h -var output_dir = path.resolve(path.dirname(require.main.filename), 'files'); - -//function will check if a directory exists, and create it if it doesn't -function checkDirectory(directory, callback) { - fs.stat(directory, function(err, stats) { - //Check if error defined and the error code is "not exists" - if (err && err.errno === 34) { - //Create the directory, call the callback. - fs.mkdir(directory, callback); - } else { - //just in case there was a different error: - callback(err) - } - }); -} - -module.exports = { - init: init, - handle_msg: handle_msg -}; - -function init(_slackbot, imgur_client_id) -{ - if (!imgur_client_id) - { - console.log('No imgur client id, disabling gifbot'); - return; - } - - slackbot = _slackbot; - imgur = require('imgur'); - imgur.setClientId(imgur_client_id); -} - -function jsonrpc_call(method, params, callback) { - var xhr = new XMLHttpRequest; - xhr.addEventListener('load', function() { - var response = JSON.parse(xhr.responseText); - callback(response); - }); - - xhr.addEventListener('error', function (e) { - callback({error: e}) - }); - - xhr.open('POST', 'http://localhost:5279/lbryapi', true); - payload = { - 'jsonrpc': '2.0', - 'method': method, - 'params': [params], - 'id': 0 - }; - console.log('JSONRPC', payload); - xhr.send(JSON.stringify(payload)); -} - -function handle_msg(msg, channel) -{ - if (!imgur) - { - return; - } - - var words = msg.trim().split(' '); - - words.forEach(function(word) - { - if (word.lastIndexOf(' - handle_url(word, channel); - } - }); -} - -function check_url(url, callback) -{ - jsonrpc_call('resolve_name', {'name': url}, function(response) - { - if (response.error) - { - callback(response.error); - return; - } - - var resolved = response.result; - if (!resolved) - { - callback(false); - return; - } - - if (resolved.fee) - { - callback(false); - return; - } - - var meta_version = resolved.ver ? resolved.ver : '0.0.1'; - var field_name = (meta_version == '0.0.1' || meta_version == '0.0.2') ? 'content-type' : 'content_type'; - var content_type = resolved[field_name]; - callback(content_type == 'image/gif'); - }); -} - -function handle_url(url, channel) -{ - console.log('Detected URL', url, 'on channel', channel); - - if (!cache[channel]) - { - cache[channel] = {}; - } - - var now = new Date().getTime() / 1000; - if (cache[channel][url]) - { - var elapsed = now - cache[channel][url]; - if (elapsed < cache_timeout) - { - console.log(url, 'is cached for this channel, ignoring...') - return; - } - } - - - check_url(url, function(valid) - { - if (valid) - { - console.log('Fetching', url); - fetch_url(url, channel); - } - - else - { - console.log('Ignoring', url); - } - }); -} - -function fetch_url(url, channel) -{ - checkDirectory(output_dir, function(error) - { - if(error) { - console.error("Could not create output directory", error); - slackbot.postMessage(channel, 'Unable to fetch URL [' + url + ']. Output directory missing.'); - } else { - jsonrpc_call('get', {'name': url, 'download_directory': output_dir}, function(response) - { - var result = response.result; - if (!result) - { - console.warn('Failed to fetch', url); - console.warn(response); - slackbot.postMessage(channel, 'Unable to fetch URL [' + url + ']. Insufficient funds?'); - return; - } - - var filename = result.path; - console.log('Uploading', filename); - imgur.uploadFile(filename).then(function(uploaded) - { - var link = uploaded.data.link; - console.log(link); - var attachments = [{image_url: link, title: url}]; - slackbot.postMessage(channel, null, {attachments: attachments}) - cache[channel][url] = new Date().getTime() / 1000; - }).catch(function(err) - { - console.error(err.message); - }); - }); - } - }); -} diff --git a/bots/hashbot.js b/bots/hashbot.js deleted file mode 100644 index 2b4a01c..0000000 --- a/bots/hashbot.js +++ /dev/null @@ -1,65 +0,0 @@ -var needle = require('needle'); - -var command = '!hash'; - -module.exports={ - command: command, - init: init, - respond: respond -}; - - -function init(slackbot, channel) { - if (channel) { - setInterval(function() { - sendMiningInfo(slackbot, channel); - }, 6 * 60 * 60 * 1000); -// sendMiningInfo(slackbot, channel); - } -} - - -function respond(slackbot, data) { - var words = data.text.trim().split(' '); - - if (words[0] !== command) { - // wtf? - return; - } - - if (words.length > 1) { - // e.g. "!hash and some other words" - return; - } - - sendMiningInfo(slackbot, data.channel); -} - - -function sendMiningInfo(slackbot, channel) { - needle.get('https://explorer.lbry.io/api/v1/status', function(error, response) { - if (error || response.statusCode !== 200) { - slackbot.postMessage(channel, 'Explorer API is not available'); - } - else { - var data, hashrate = "", difficulty = "", height = ""; - data = response.body; - height += data.status.height; - hashrate += data.status.hashrate; - difficulty += data.status.difficulty; - - slackbot.postMessage(channel, - // 'Blockchain stats:\n' + - 'Hashrate: ' + hashrate + '\n' + - 'Difficulty: ' + difficulty + '\n' + - 'Current block: ' + height + '\n' + - '_Source: https://explorer.lbry.io_' - , {icon_emoji: ':miner:'}); - } - }); -} - - -function numberWithCommas(x) { - return x.toString().replace(/\B(?=(\d{3})+(?!\d))/g, ","); -} diff --git a/bots/modbot.js b/bots/modbot.js deleted file mode 100644 index 738915b..0000000 --- a/bots/modbot.js +++ /dev/null @@ -1,104 +0,0 @@ -var needle = require('needle'); -var slackbot; -var mongo; -var command = '!m'; -var apitoken; -module.exports={ - command: command, - init: init, - check: check -}; - -var globalSlackParams = { - icon_emoji: ':lbr:' -}; - -function init(mongodburl,apitoken_, slackbot) { - const MongoClient = require('mongodb').MongoClient; - MongoClient.connect(mongodburl, function (err, db) { - if (err) { - throw err; - } - mongo = db; - - }); - apitoken = apitoken_ - slackbot.getChannels() - .then( data => { - data.channels.forEach(function(ch) { - mongo.collection('m_topic').findOneAndUpdate( - { 'channel': ch.id }, - { 'channel': ch.id, 'topic': ch.topic.value }, - { 'upsert': true, 'returnOriginal': false }, - function (err, obj) { - if(err){ - console.log(err); - } - }); - }, this); - }, err => { - console.log(err); - }) - console.log('Loaded moderationbot!'); -} - - -function check(slackbot, data) { - if(data.text){ - if (data.text.trim().split(' ')[0] === command) { - //Add commands here later aswell! - } - } - if(data.topic){ // Gets called on topic change in a channel - slackbot.getUser(data.user_profile.name) - .then( usr => { - if(usr.is_admin){ - mongo.collection('m_topic').findOneAndUpdate( - { 'channel': data.channel }, - { 'channel': data.channel, 'topic': data.topic }, - { 'upsert': true, 'returnOriginal': false }, - function (err, obj) { - if(err){ - console.log(err); - } - }); - }else if(!usr.is_bot){ - mongo.collection('m_topic').findOne({'channel': data.channel}, function(err, document) { - slackbot.postMessage(data.user,`Hey <@${data.user_profile.name}>, you are not allowed to change the topic in <#${data.channel}>!`, globalSlackParams); - if(process.env.CHANNEL_LOG){ - slackbot.postMessage(process.env.CHANNEL_LOG,`User <@${data.user_profile.name}> tried to change the topic in <#${data.channel}> to: \`\`\`${data.topic}!\`\`\``, globalSlackParams); - } - needle.get(`https://slack.com/api/channels.setTopic?token=${apitoken}&channel=${data.channel}&topic=${document.topic}`); - }); - } - }, err => { - console.log(err); - }) - } - if(data.type == 'pin_added'){ // Gets called on a user pin - needle.get(`https://slack.com/api/users.info?token=${apitoken}&user=${data.user}`, function(err, resp) { - if(!resp.body.user.is_admin){ - needle.get(`https://slack.com/api/pins.remove?token=${apitoken}&channel=${data.item.channel}×tamp=${data.item.message.ts}`); - slackbot.postMessage(data.user,`Hey <@${resp.body.user.name}>, you are not allowed to add pins in <#${data.channel_id}>!`, globalSlackParams); - if(process.env.CHANNEL_LOG){ - slackbot.postMessage(process.env.CHANNEL_LOG,`User <@${resp.body.user.name}> tried to pin a message in <#${data.channel_id}>!`, globalSlackParams); - } - } - }); - } - if(data.channel == process.env.CHANNEL_OA && data.type == 'message'){ //If user is trying to post in a admin only channel.. - needle.get(`https://slack.com/api/users.info?token=${apitoken}&user=${data.user}`, function(err, resp) { - if(!resp.body.user.is_admin){ - console.log(`https://slack.com/api/chat.delete?token=${apitoken}&ts=${data.ts}&channel=${data.channel}`); - needle.get(`https://slack.com/api/chat.delete?token=${apitoken}&ts=${data.ts}&channel=${data.channel}`); - if(data.subtype !=='channel_join' && data.subtype !=='channel_leave') { - slackbot.postMessage(data.user,`Hey <@${resp.body.user.name}>, you are not allowed to post messages in <#${data.channel}>!`, globalSlackParams); - if(data.subtype !=='channel_join' && data.subtype !=='channel_leave' && process.env.CHANNEL_LOG){ - slackbot.postMessage(process.env.CHANNEL_LOG,`User <@${resp.body.user.name}> tried to post a message in <#${data.channel}>!`, globalSlackParams); - } - } - } - }); - } -} - diff --git a/bots/pricebot.js b/bots/pricebot.js deleted file mode 100644 index bfad9c7..0000000 --- a/bots/pricebot.js +++ /dev/null @@ -1,216 +0,0 @@ -var jp = require('jsonpath'); -var moment = require('moment'); -var numeral = require('numeral'); -var request = require('request'); -var options = { - defaultCurrency: 'USD', - - // supported currencies and api steps to arrive at the final value - currencies: { - USD: { steps: ['LBCBTC', 'BTCUSD'], format: '$0,0.00' }, - GBP: { steps: ['LBCBTC', 'BTCGBP'], format: '£0,0.00' }, - AUD: { steps: ['LBCBTC', 'BTCAUD'], format: '$0,0.00' }, - BRL: { steps: ['LBCBTC', 'BTCBRL'], format: 'R$0,0.00' }, - CAD: { steps: ['LBCBTC', 'BTCCAD'], format: '$0,0.00' }, - CHF: { steps: ['LBCBTC', 'BTCCHF'], format: 'CHF 0,0.00' }, - CLP: { steps: ['LBCBTC', 'BTCCLP'], format: '$0,0.00' }, - CNY: { steps: ['LBCBTC', 'BTCCNY'], format: '¥0,0.00' }, - DKK: { steps: ['LBCBTC', 'BTCDKK'], format: 'kr 0,0.00' }, - EUR: { steps: ['LBCBTC', 'BTCEUR'], format: '€0,0.00' }, - HKD: { steps: ['LBCBTC', 'BTCHKD'], format: '$0,0.00' }, - INR: { steps: ['LBCBTC', 'BTCINR'], format: '₹0,0.00' }, - ISK: { steps: ['LBCBTC', 'BTCISK'], format: 'kr 0,0.00' }, - JPY: { steps: ['LBCBTC', 'BTCJPY'], format: '¥0,0.00' }, - KRW: { steps: ['LBCBTC', 'BTCKRW'], format: '₩0,0.00' }, - NZD: { steps: ['LBCBTC', 'BTCNZD'], format: '$0,0.00' }, - PLN: { steps: ['LBCBTC', 'BTCPLN'], format: 'zł 0,0.00' }, - RUB: { steps: ['LBCBTC', 'BTCRUB'], format: 'RUB 0,0.00' }, - SEK: { steps: ['LBCBTC', 'BTCSEK'], format: 'kr 0,0.00' }, - SGD: { steps: ['LBCBTC', 'BTCSGD'], format: '$0,0.00' }, - THB: { steps: ['LBCBTC', 'BTCTHB'], format: '฿0,0.00' }, - TWD: { steps: ['LBCBTC', 'BTCTWD'], format: 'NT$0,0.00' }, - IDR: { steps: ['LBCBTC', 'BTCIDR'], format: 'Rp0,0.00' }, - BTC: { steps: ['LBCBTC'], format: '0,0[.][00000000] BTC' } - }, - - // api steps - api: { - LBCBTC: { url: 'https://bittrex.com/api/v1.1/public/getticker?market=BTC-LBC', path: '$.result.Bid' }, - BTCUSD: { url: 'https://blockchain.info/ticker', path: '$.USD.buy' }, - BTCGBP: { url: 'https://blockchain.info/ticker', path: '$.GBP.buy' }, - BTCAUD: { url: 'https://blockchain.info/ticker', path: '$.AUD.buy' }, - BTCBRL: { url: 'https://blockchain.info/ticker', path: '$.BRL.buy' }, - BTCCAD: { url: 'https://blockchain.info/ticker', path: '$.CAD.buy' }, - BTCCHF: { url: 'https://blockchain.info/ticker', path: '$.CHF.buy' }, - BTCCLP: { url: 'https://blockchain.info/ticker', path: '$.CLP.buy' }, - BTCCNY: { url: 'https://blockchain.info/ticker', path: '$.CNY.buy' }, - BTCDKK: { url: 'https://blockchain.info/ticker', path: '$.DKK.buy' }, - BTCEUR: { url: 'https://blockchain.info/ticker', path: '$.EUR.buy' }, - BTCHKD: { url: 'https://blockchain.info/ticker', path: '$.HKD.buy' }, - BTCINR: { url: 'https://blockchain.info/ticker', path: '$.INR.buy' }, - BTCISK: { url: 'https://blockchain.info/ticker', path: '$.ISK.buy' }, - BTCJPY: { url: 'https://blockchain.info/ticker', path: '$.JPY.buy' }, - BTCKRW: { url: 'https://blockchain.info/ticker', path: '$.KRW.buy' }, - BTCNZD: { url: 'https://blockchain.info/ticker', path: '$.NZD.buy' }, - BTCPLN: { url: 'https://blockchain.info/ticker', path: '$.PLN.buy' }, - BTCRUB: { url: 'https://blockchain.info/ticker', path: '$.RUB.buy' }, - BTCSEK: { url: 'https://blockchain.info/ticker', path: '$.SEK.buy' }, - BTCSGD: { url: 'https://blockchain.info/ticker', path: '$.SGD.buy' }, - BTCTHB: { url: 'https://blockchain.info/ticker', path: '$.THB.buy' }, - BTCTWD: { url: 'https://blockchain.info/ticker', path: '$.TWD.buy' }, - BTCIDR: { url: 'https://min-api.cryptocompare.com/data/price?fsym=LBC&tsyms=IDR', path: '$.IDR'} - }, - - // display date/time format - dtFormat: 'Do MMM YYYY h:mma [UTC]', - - // refresh rate in milliseconds to retrieve a new price (default to 10 minutes) - refreshTime: 600000 -}; - -// store the last retrieved rate -var cachedRates = {}; - -var mktChannel; - -// !price {currency} -// !price {currency} {amount} -var command = '!price'; - -module.exports={ - command: command, - init: init, - respond: respond -}; - -function init(channel_) { - mktChannel = channel_; - if (!channel_) { - console.log('No market and trading channel. Pricebot will only respond to #bot-sandbox and DMs.'); - } - - var currencies = Object.keys(options.currencies); - for (var i = 0; i < currencies.length; i++) { - cachedRates[currencies[i]] = { rate: 0, time: null }; - } -} - -var globalSlackParams = {}; - -function respond(bot, data) { - var channel = data.channel, - words = data.text.trim().split(' ').filter( function(n){return n !== "";} ); - - if (words[0] !== command || (channel != mktChannel && channel !== 'C1TEEBS2Z' && !channel.startsWith('D'))) { - // if the received message isn't starting with the trigger, - // or the channel is not the market-and-trading channel, nor sandbox, nor a DM -> ignore - return; - } - - var currency = (words.length > 1) ? words[1].toUpperCase() : options.defaultCurrency; - var amount = (words.length > 2) ? parseFloat(words[2], 10) : 1; - var showHelp = (isNaN(amount)) || (Object.keys(options.currencies).indexOf(currency) === -1); - - var moveToBotSandbox = showHelp && channel !== 'C1TEEBS2Z' && !channel.startsWith("D"); - if (moveToBotSandbox) { - bot.postMessage(channel, 'Please use <#C1TEEBS2Z|bot-sandbox> to talk to bots.', globalSlackParams); - return; - } - - if (showHelp) { - doHelp(bot, channel); - } else { - doSteps(bot, channel, currency, amount); - } -} - -function doHelp(bot, channel) { - var message = - '`' + command + '`: show the price of 1 LBC in ' + options.defaultCurrency + '\n' + - '`' + command + ' help`: this message\n' + - '`' + command + ' CURRENCY`: show the price of 1 LBC in CURRENCY. Supported values for CURRENCY are Listed Below\n' + - '`' + command + ' CURRENCY AMOUNT`: show the price of AMOUNT LBC in CURRENCY\n' + - '`Supported Currencies:` *usd*, *gbp*, *eur*, *aud*, *brl*, *cad*, *chf*, *clp*, *cny*, *dkk*, *hkd*, *inr*, *isk*, *jpy*, *krw*, *nzd*, *pln* ,*rub*, *sek*, *sgd*, *thb*, *twd*, *idr* and *btc* (case-insensitive)'; - - if (!channel.startsWith("D")) { - message = - '*USE <#C1TEEBS2Z|bot-sandbox> FOR HELP*\n' + - message + - '\n' + - '*Everyone will see what I say. Send me a Direct Message if you want to interact privately.*\n' + - 'If I\'m not responding in some channel, you can invite me by @mentioning me.\n'; - } - - bot.postMessage(channel, message, globalSlackParams); -} - -function formatMessage(amount, rate, option) { - var value = numeral(rate.rate * amount).format(option.format); - return '*' + numeral(amount).format('0,0[.][00000000]') + ' LBC = ' + value + '*\n_last updated ' + rate.time.utc().format(options.dtFormat) + '_'; -} - -function doSteps(bot, channel, currency, amount) { - var option = options.currencies[currency]; - var shouldReload = true; - if (cachedRates[currency]) { - var cache = cachedRates[currency]; - shouldReload = cache.time === null || moment().diff(cache.time) >= options.refreshTime; - if (!shouldReload) { - var message = formatMessage(amount, cache, option); - bot.postMessage(channel, message); - } - } - - if (shouldReload) { - // copy the steps array - var steps = []; - for (var i = 0; i < option.steps.length; i++) { - steps.push(option.steps[i]); - } - - processSteps(bot, channel, currency, 0, amount, steps, option); - } -} - -function processSteps(bot, channel, currency, rate, amount, steps, option) { - if (steps.length > 0) { - var pairName = steps[0]; - if (!options.api[pairName]) { - bot.postMessage(channel, 'There was a configuration error. ' + pairName + ' pair was not found.'); - return; - } - - var pair = options.api[pairName]; - request.get(pair.url, function(error, response, body) { - if (error) { - bot.postMessage(channel, err.message ? err.message : 'The request could not be completed at this time. Please try again later.'); - return; - } - var pairRate = 0; - try { - pairRate = jp.query(JSON.parse(body), pair.path); - if (Array.isArray(pairRate) && pairRate.length > 0) { - pairRate = pairRate[0]; - } - } catch (ignored) { - // invalid response or pair rate - } - - if (pairRate > 0) { - rate = (rate === 0) ? pairRate : rate * pairRate; - steps.shift(); - if (steps.length > 0) { - processSteps(bot, channel, currency, rate, amount, steps, option); - return; - } - - // final step, cache and then response - var result = { rate: rate, time: moment() }; - cachedRates[currency] = result; - bot.postMessage(channel, formatMessage(amount, result, option)); - } else { - bot.postMessage(channel, 'The rate returned for the ' + pairName + ' pair was invalid.'); - } - }); - } -} diff --git a/bots/statbot.js b/bots/statbot.js deleted file mode 100644 index 262a47e..0000000 --- a/bots/statbot.js +++ /dev/null @@ -1,252 +0,0 @@ -var jp = require('jsonpath'); -var moment = require('moment'); -var numeral = require('numeral'); -var request = require('request'); - -var options = { - defaultCurrency: 'USD', - - // supported currencies and api steps to arrive at the final value - currencies: { - USD: { steps: ['LBCBTC', 'BTCUSD'], format: '$0,0.00', sign:'$' }, - BTC: { steps: ['LBCBTC'], format: 'BTC 0,0.00000000', sign:'BTC' }, - ETH: { steps: ['LBCETH'], format: 'ETH 0,0.00000000', sign: 'ETH' }, - GBP: { steps: ['LBCBTC', 'BTCGBP'], format: '£0,0.00', sign: '£' }, - EUR: { steps: ['LBCEUR'], format: '€0,0.00', sign: '€' } - }, - - // api steps - api: { - LBCBTC: { url: 'https://bittrex.com/api/v1.1/public/getticker?market=BTC-LBC', path: '$.result.Bid' }, - BTCUSD: { url: 'https://blockchain.info/ticker', path: '$.USD.buy' }, - BTCGBP: { url: 'https://blockchain.info/ticker', path: '$.GBP.buy' }, - LBCETH: { url: 'https://api.coinmarketcap.com/v1/ticker/library-credit/?convert=eth', path: '$[0].price_eth' }, - LBCEUR: { url: 'https://api.coinmarketcap.com/v1/ticker/library-credit/?convert=eur', path: '$[0].price_eur' } - }, - - // display date/time format - dtFormat: 'Do MMM YYYY h:mma [UTC]', - - // refresh rate in milliseconds to retrieve a new price (default to 10 minutes) - refreshTime: 300000 -}; - -// store the last retrieved rate -var cachedRates = {}; - -var mktChannel; - -// !price {currency} -// !price {currency} {amount} -var command = '!stats'; - -module.exports={ - command: command, - init: init, - respond: respond -}; - -function init(channel_) { - mktChannel = channel_; - if (!channel_) { - console.log('No market and trading channel. Statbot will only respond to DMs.'); - } - - var currencies = Object.keys(options.currencies); - for (var i = 0; i < currencies.length; i++) { - cachedRates[currencies[i]] = { rate: 0, time: null }; - } -} - -var globalSlackParams = {}; - -function respond(bot, data) { - var channel = data.channel, - words = data.text.trim().split(' ').filter( function(n){return n !== "";} ); - - if (words[0] !== command || (channel != mktChannel && !channel.startsWith('D'))) { - // if the received message isn't starting with the trigger, - // or the channel is not the market-and-trading channel, nor sandbox, nor a DM -> ignore - return; - } - - var currency = /*(words.length > 1) ? words[2].toUpperCase() :*/ options.defaultCurrency; - var amount = /*(words.length > 2) ? parseFloat(words[2], 10) :*/ 1; - var showHelp = (isNaN(amount)) || (Object.keys(options.currencies).indexOf(currency) === -1); - - var moveToBotSandbox = showHelp && channel !== mktChannel && !channel.startsWith("D"); - if (moveToBotSandbox) { - bot.postMessage(channel, 'Please use PM to talk to bot.', globalSlackParams); - return; - } - - if (showHelp) { - doHelp(bot, channel); - } else { - - doSteps(bot, channel, 'USD', amount); - doSteps(bot, channel, 'EUR', amount); - doSteps(bot, channel, 'GBP', amount); - doSteps(bot, channel, 'ETH', amount); - doSteps(bot, channel, 'BTC', amount); - setTimeout(function() { marketstats(bot,channel); }, 250); - //marketstats(bot,channel); - //volume24(bot,channel); can't get this part to work, someone help me fix - i think it's because 24h_volume_usd starts with number - } -} - -function doHelp(bot, channel) { - var message = - '`' + command + '`: show the price of 1 LBC in ' + options.defaultCurrency + '\n' + - '`' + command + ' help`: this message\n' + - '`' + command + ' CURRENCY`: show the price of 1 LBC in CURRENCY. Supported values for CURRENCY are *btc* and *usd* (case-insensitive)\n' + - '`' + command + ' CURRENCY AMOUNT`: show the price of AMOUNT LBC in CURRENCY\n'; - - if (!channel.startsWith("D")) { - message = - '*USE PM FOR HELP*\n' + - message + - '\n' + - '*Everyone will see what I say. Send me a Direct Message if you want to interact privately.*\n' + - 'If I\'m not responding in some channel, you can invite me by @mentioning me.\n'; - } - - bot.postMessage(channel, message, globalSlackParams); -} - -function formatMessage(amount, rate, option) { - var cur = option.sign; - var value = rate.rate * amount; - if (option.sign == '$' || option.sign == '£' || option.sign == '€'){ - return '*' + numeral(amount).format('0,0[.][00000000]') + ' LBC = ' + cur +' '+ value.toFixed(2) + '*'; - } - else { - return '*' + numeral(amount).format('0,0[.][00000000]') + ' LBC = ' + numeral(value).format('0,0[.][00000000]') + ' ' + cur + '*'; - } -} - -function formaty(n, decimals, currency) { - n = parseFloat(n); - return currency + " " + n.toFixed(2).replace(/(\d)(?=(\d{3})+\.)/g, "$1,"); -} - -function doSteps(bot, channel, currency, amount) { - - var option = options.currencies[currency]; - var shouldReload = true; - if (cachedRates[currency]) { - var cache = cachedRates[currency]; - shouldReload = cache.time === null || moment().diff(cache.time) >= options.refreshTime; - if (!shouldReload) { - var message = formatMessage(amount, cache, option); - bot.postMessage(channel, message, {icon_emoji: ':lbr:'}); - } - } - - if (shouldReload) { - // copy the steps array - var steps = []; - for (var i = 0; i < option.steps.length; i++) { - steps.push(option.steps[i]); - } - - processSteps(bot, channel, currency, 0, amount, steps, option); - } -} - -function marketstats(bot,channel) { - var statsurl='https://api.coinmarketcap.com/v1/ticker/library-credit/'; - - request.get(statsurl, function(error, response, body) { - if (error) { - bot.postMessage(channel, err.message ? err.message : 'The request could not be completed at this time. Please try again later.'); - return; - } - var marketcap = 0; - try { - marketcap = jp.query(JSON.parse(body), '$[0].market_cap_usd'); - if (Array.isArray(marketcap) && marketcap.length > 0) { - marketcap = marketcap[0]; - marketcap = formaty(marketcap,2,'$') - } - - } catch (ignored) { - // invalid response or pair rate - } - - var statmsg = '*'+'Marketcap: '+marketcap+'*\n'; - - bot.postMessage(channel, statmsg, {icon_emoji: ':lbr:'}); - - }); -} - -function volume24(bot,channel) { - var statsurl='https://api.coinmarketcap.com/v1/ticker/library-credit/'; - - request.get(statsurl, function(error, response, body) { - if (error) { - bot.postMessage(channel, err.message ? err.message : 'The request could not be completed at this time. Please try again later.'); - return; - } - var volume24 = 0; - try { - volume24 = jp.query(JSON.parse(body),'$[0].24h_volume_usd'); - if (Array.isArray(volume24) && volume24.length > 0) { - volume24 = volume24[0]; - } - - } catch (ignored) { - // invalid response or pair rate - } - - var statmsg = '*'+'Volume: $'+volume24+'*\n'; - - bot.postMessage(channel, statmsg, {icon_emoji: ':lbr:'}); - - }); -} - -function processSteps(bot, channel, currency, rate, amount, steps, option) { - if (steps.length > 0) { - var pairName = steps[0]; - if (!options.api[pairName]) { - bot.postMessage(channel, 'There was a configuration error. ' + pairName + ' pair was not found.'); - return; - } - - var pair = options.api[pairName]; - request.get(pair.url, function(error, response, body) { - if (error) { - bot.postMessage(channel, err.message ? err.message : 'The request could not be completed at this time. Please try again later.'); - return; - } - var pairRate = 0; - try { - pairRate = jp.query(JSON.parse(body), pair.path); - if (Array.isArray(pairRate) && pairRate.length > 0) { - pairRate = pairRate[0]; - } - } catch (ignored) { - // invalid response or pair rate - } - - if (pairRate > 0) { - rate = (rate === 0) ? pairRate : rate * pairRate; - steps.shift(); - if (steps.length > 0) { - processSteps(bot, channel, currency, rate, amount, steps, option); - return; - } - - // final step, cache and then response - var result = { rate: rate, time: moment() }; - cachedRates[currency] = result; - - bot.postMessage(channel, formatMessage(amount, result, option), {icon_emoji: ':bulb:'}); - } else { - bot.postMessage(channel, 'The rate returned for the ' + pairName + ' pair was invalid.'); - } - }); - } -} diff --git a/miner.png b/miner.png deleted file mode 100644 index 6bf095a..0000000 Binary files a/miner.png and /dev/null differ diff --git a/package-lock.json b/package-lock.json deleted file mode 100644 index a2b935b..0000000 --- a/package-lock.json +++ /dev/null @@ -1,622 +0,0 @@ -{ - "name": "hashbot", - "version": "1.0.2", - "lockfileVersion": 1, - "dependencies": { - "ajv": { - "version": "4.11.8", - "resolved": "https://registry.npmjs.org/ajv/-/ajv-4.11.8.tgz", - "integrity": "sha1-gv+wKynmYq5TvcIK8VlHcGc5xTY=" - }, - "asn1": { - "version": "0.2.3", - "resolved": "https://registry.npmjs.org/asn1/-/asn1-0.2.3.tgz", - "integrity": "sha1-2sh4dxPJlmhJ/IGAd36+nB3fO4Y=" - }, - "assert-plus": { - "version": "0.2.0", - "resolved": "https://registry.npmjs.org/assert-plus/-/assert-plus-0.2.0.tgz", - "integrity": "sha1-104bh+ev/A24qttwIfP+SBAasjQ=" - }, - "asynckit": { - "version": "0.4.0", - "resolved": "https://registry.npmjs.org/asynckit/-/asynckit-0.4.0.tgz", - "integrity": "sha1-x57Zf380y48robyXkLzDZkdLS3k=" - }, - "aws-sign2": { - "version": "0.6.0", - "resolved": "https://registry.npmjs.org/aws-sign2/-/aws-sign2-0.6.0.tgz", - "integrity": "sha1-FDQt0428yU0OW4fXY81jYSwOeU8=" - }, - "aws4": { - "version": "1.6.0", - "resolved": "https://registry.npmjs.org/aws4/-/aws4-1.6.0.tgz", - "integrity": "sha1-g+9cqGCysy5KDe7e6MdxudtXRx4=" - }, - "balanced-match": { - "version": "1.0.0", - "resolved": "https://registry.npmjs.org/balanced-match/-/balanced-match-1.0.0.tgz", - "integrity": "sha1-ibTRmasr7kneFk6gK4nORi1xt2c=" - }, - "bcrypt-pbkdf": { - "version": "1.0.1", - "resolved": "https://registry.npmjs.org/bcrypt-pbkdf/-/bcrypt-pbkdf-1.0.1.tgz", - "integrity": "sha1-Y7xdy2EzG5K8Bf1SiVPDNGKgb40=", - "optional": true - }, - "bitcoin": { - "version": "3.0.1", - "resolved": "https://registry.npmjs.org/bitcoin/-/bitcoin-3.0.1.tgz", - "integrity": "sha1-/54LYqcbu4rd2zTuLkJ9rCHBCW8=" - }, - "boom": { - "version": "2.10.1", - "resolved": "https://registry.npmjs.org/boom/-/boom-2.10.1.tgz", - "integrity": "sha1-OciRjO/1eZ+D+UkqhI9iWt0Mdm8=" - }, - "brace-expansion": { - "version": "1.1.8", - "resolved": "https://registry.npmjs.org/brace-expansion/-/brace-expansion-1.1.8.tgz", - "integrity": "sha1-wHshHHyVLsH479Uad+8NHTmQopI=" - }, - "bson": { - "version": "1.0.4", - "resolved": "https://registry.npmjs.org/bson/-/bson-1.0.4.tgz", - "integrity": "sha1-k8ENOeqltYQVy8QFLz5T5WKwtyw=" - }, - "buffer-shims": { - "version": "1.0.0", - "resolved": "https://registry.npmjs.org/buffer-shims/-/buffer-shims-1.0.0.tgz", - "integrity": "sha1-mXjOMXOIxkmth5MCjDR37wRKi1E=" - }, - "caseless": { - "version": "0.12.0", - "resolved": "https://registry.npmjs.org/caseless/-/caseless-0.12.0.tgz", - "integrity": "sha1-G2gcIf+EAzyCZUMJBolCDRhxUdw=" - }, - "cjson": { - "version": "0.2.1", - "resolved": "https://registry.npmjs.org/cjson/-/cjson-0.2.1.tgz", - "integrity": "sha1-c82KrWXZ4VBfmvF0TTt5wVJ2gqU=" - }, - "co": { - "version": "4.6.0", - "resolved": "https://registry.npmjs.org/co/-/co-4.6.0.tgz", - "integrity": "sha1-bqa989hTrlTMuOR7+gvz+QMfsYQ=" - }, - "colors": { - "version": "0.5.1", - "resolved": "https://registry.npmjs.org/colors/-/colors-0.5.1.tgz", - "integrity": "sha1-fQAj6usVTo7p/Oddy5I9DtFmd3Q=" - }, - "combined-stream": { - "version": "1.0.5", - "resolved": "https://registry.npmjs.org/combined-stream/-/combined-stream-1.0.5.tgz", - "integrity": "sha1-k4NwpXtKUd6ix3wV1cX9+JUWQAk=" - }, - "commander": { - "version": "2.9.0", - "resolved": "https://registry.npmjs.org/commander/-/commander-2.9.0.tgz", - "integrity": "sha1-nJkJQXbhIkDLItbFFGCYQA/g99Q=" - }, - "concat-map": { - "version": "0.0.1", - "resolved": "https://registry.npmjs.org/concat-map/-/concat-map-0.0.1.tgz", - "integrity": "sha1-2Klr13/Wjfd5OnMDajug1UBdR3s=" - }, - "core-util-is": { - "version": "1.0.2", - "resolved": "https://registry.npmjs.org/core-util-is/-/core-util-is-1.0.2.tgz", - "integrity": "sha1-tf1UIgqivFq1eqtxQMlAdUUDwac=" - }, - "cryptiles": { - "version": "2.0.5", - "resolved": "https://registry.npmjs.org/cryptiles/-/cryptiles-2.0.5.tgz", - "integrity": "sha1-O9/s3GCBR8HGcgL6KR59ylnqo7g=" - }, - "dashdash": { - "version": "1.14.1", - "resolved": "https://registry.npmjs.org/dashdash/-/dashdash-1.14.1.tgz", - "integrity": "sha1-hTz6D3y+L+1d4gMmuN1YEDX24vA=", - "dependencies": { - "assert-plus": { - "version": "1.0.0", - "resolved": "https://registry.npmjs.org/assert-plus/-/assert-plus-1.0.0.tgz", - "integrity": "sha1-8S4PPF13sLHN2RRpQuTpbB5N1SU=" - } - } - }, - "debug": { - "version": "2.6.8", - "resolved": "https://registry.npmjs.org/debug/-/debug-2.6.8.tgz", - "integrity": "sha1-5zFTHKLt4n0YgiJCfaF4IdaP9Pw=" - }, - "delayed-stream": { - "version": "1.0.0", - "resolved": "https://registry.npmjs.org/delayed-stream/-/delayed-stream-1.0.0.tgz", - "integrity": "sha1-3zrhmayt+31ECqrgsp4icrJOxhk=" - }, - "ebnf-parser": { - "version": "0.1.10", - "resolved": "https://registry.npmjs.org/ebnf-parser/-/ebnf-parser-0.1.10.tgz", - "integrity": "sha1-zR9rpHfFY4xAyX7ZtXLbW6tdgzE=" - }, - "ecc-jsbn": { - "version": "0.1.1", - "resolved": "https://registry.npmjs.org/ecc-jsbn/-/ecc-jsbn-0.1.1.tgz", - "integrity": "sha1-D8c6ntXw1Tw4GTOYUj735UN3dQU=", - "optional": true - }, - "es6-promise": { - "version": "3.2.1", - "resolved": "https://registry.npmjs.org/es6-promise/-/es6-promise-3.2.1.tgz", - "integrity": "sha1-7FYjOGgDKQkgcXDDlEjiREndH8Q=" - }, - "escodegen": { - "version": "0.0.21", - "resolved": "https://registry.npmjs.org/escodegen/-/escodegen-0.0.21.tgz", - "integrity": "sha1-U9ZSz6EDA4gnlFilJmxf/HCcY8M=", - "dependencies": { - "esprima": { - "version": "1.0.4", - "resolved": "https://registry.npmjs.org/esprima/-/esprima-1.0.4.tgz", - "integrity": "sha1-n1V+CPw7TSbs6d00+Pv0drYlha0=" - } - } - }, - "esprima": { - "version": "1.2.2", - "resolved": "https://registry.npmjs.org/esprima/-/esprima-1.2.2.tgz", - "integrity": "sha1-dqD9Zvz+FU/SkmZ9wmQBl1CxZXs=" - }, - "estraverse": { - "version": "0.0.4", - "resolved": "https://registry.npmjs.org/estraverse/-/estraverse-0.0.4.tgz", - "integrity": "sha1-AaCTLf7ldGhKWYr1pnw7+bZCjbI=" - }, - "extend": { - "version": "3.0.1", - "resolved": "https://registry.npmjs.org/extend/-/extend-3.0.1.tgz", - "integrity": "sha1-p1Xqe8Gt/MWjHOfnYtuq3F5jZEQ=" - }, - "extsprintf": { - "version": "1.0.2", - "resolved": "https://registry.npmjs.org/extsprintf/-/extsprintf-1.0.2.tgz", - "integrity": "sha1-4QgOBljjALBilJkMxw4VAiNf1VA=" - }, - "forever-agent": { - "version": "0.6.1", - "resolved": "https://registry.npmjs.org/forever-agent/-/forever-agent-0.6.1.tgz", - "integrity": "sha1-+8cfDEGt6zf5bFd60e1C2P2sypE=" - }, - "form-data": { - "version": "2.1.4", - "resolved": "https://registry.npmjs.org/form-data/-/form-data-2.1.4.tgz", - "integrity": "sha1-M8GDrPGTJ27KqYFDpp6Uv+4XUNE=" - }, - "getpass": { - "version": "0.1.7", - "resolved": "https://registry.npmjs.org/getpass/-/getpass-0.1.7.tgz", - "integrity": "sha1-Xv+OPmhNVprkyysSgmBOi6YhSfo=", - "dependencies": { - "assert-plus": { - "version": "1.0.0", - "resolved": "https://registry.npmjs.org/assert-plus/-/assert-plus-1.0.0.tgz", - "integrity": "sha1-8S4PPF13sLHN2RRpQuTpbB5N1SU=" - } - } - }, - "glob": { - "version": "4.5.3", - "resolved": "https://registry.npmjs.org/glob/-/glob-4.5.3.tgz", - "integrity": "sha1-xstz0yJsHv7wTePFbQEvAzd+4V8=" - }, - "graceful-readlink": { - "version": "1.0.1", - "resolved": "https://registry.npmjs.org/graceful-readlink/-/graceful-readlink-1.0.1.tgz", - "integrity": "sha1-TK+tdrxi8C+gObL5Tpo906ORpyU=" - }, - "har-schema": { - "version": "1.0.5", - "resolved": "https://registry.npmjs.org/har-schema/-/har-schema-1.0.5.tgz", - "integrity": "sha1-0mMTX0MwfALGAq/I/pWXDAFRNp4=" - }, - "har-validator": { - "version": "4.2.1", - "resolved": "https://registry.npmjs.org/har-validator/-/har-validator-4.2.1.tgz", - "integrity": "sha1-M0gdDxu/9gDdID11gSpqX7oALio=" - }, - "hawk": { - "version": "3.1.3", - "resolved": "https://registry.npmjs.org/hawk/-/hawk-3.1.3.tgz", - "integrity": "sha1-B4REvXwWQLD+VA0sm3PVlnjo4cQ=" - }, - "hoek": { - "version": "2.16.3", - "resolved": "https://registry.npmjs.org/hoek/-/hoek-2.16.3.tgz", - "integrity": "sha1-ILt0A9POo5jpHcRxCo/xuCdKJe0=" - }, - "http-signature": { - "version": "1.1.1", - "resolved": "https://registry.npmjs.org/http-signature/-/http-signature-1.1.1.tgz", - "integrity": "sha1-33LiZwZs0Kxn+3at+OE0qPvPkb8=" - }, - "iconv-lite": { - "version": "0.4.18", - "resolved": "https://registry.npmjs.org/iconv-lite/-/iconv-lite-0.4.18.tgz", - "integrity": "sha512-sr1ZQph3UwHTR0XftSbK85OvBbxe/abLGzEnPENCQwmHf7sck8Oyu4ob3LgBxWWxRoM+QszeUyl7jbqapu2TqA==" - }, - "imgur": { - "version": "0.1.7", - "resolved": "https://registry.npmjs.org/imgur/-/imgur-0.1.7.tgz", - "integrity": "sha1-xN1lInC1FDx2WEGFEmqBfKorLoU=" - }, - "inflight": { - "version": "1.0.6", - "resolved": "https://registry.npmjs.org/inflight/-/inflight-1.0.6.tgz", - "integrity": "sha1-Sb1jMdfQLQwJvJEKEHW6gWW1bfk=" - }, - "inherits": { - "version": "2.0.3", - "resolved": "https://registry.npmjs.org/inherits/-/inherits-2.0.3.tgz", - "integrity": "sha1-Yzwsg+PaQqUC9SRmAiSA9CCCYd4=" - }, - "is-typedarray": { - "version": "1.0.0", - "resolved": "https://registry.npmjs.org/is-typedarray/-/is-typedarray-1.0.0.tgz", - "integrity": "sha1-5HnICFjfDBsR3dppQPlgEfzaSpo=" - }, - "isarray": { - "version": "1.0.0", - "resolved": "https://registry.npmjs.org/isarray/-/isarray-1.0.0.tgz", - "integrity": "sha1-u5NdSFgsuhaMBoNJV6VKPgcSTxE=" - }, - "isstream": { - "version": "0.1.2", - "resolved": "https://registry.npmjs.org/isstream/-/isstream-0.1.2.tgz", - "integrity": "sha1-R+Y/evVa+m+S4VAOaQ64uFKcCZo=" - }, - "jison": { - "version": "0.4.13", - "resolved": "https://registry.npmjs.org/jison/-/jison-0.4.13.tgz", - "integrity": "sha1-kEFwfWIkE2f1iDRTK58ZwsNvrHg=", - "dependencies": { - "esprima": { - "version": "1.0.4", - "resolved": "https://registry.npmjs.org/esprima/-/esprima-1.0.4.tgz", - "integrity": "sha1-n1V+CPw7TSbs6d00+Pv0drYlha0=" - } - } - }, - "jison-lex": { - "version": "0.2.1", - "resolved": "https://registry.npmjs.org/jison-lex/-/jison-lex-0.2.1.tgz", - "integrity": "sha1-rEuBXozOUTLrErXfz+jXB7iETf4=" - }, - "jsbn": { - "version": "0.1.1", - "resolved": "https://registry.npmjs.org/jsbn/-/jsbn-0.1.1.tgz", - "integrity": "sha1-peZUwuWi3rXyAdls77yoDA7y9RM=", - "optional": true - }, - "json-schema": { - "version": "0.2.3", - "resolved": "https://registry.npmjs.org/json-schema/-/json-schema-0.2.3.tgz", - "integrity": "sha1-tIDIkuWaLwWVTOcnvT8qTogvnhM=" - }, - "json-stable-stringify": { - "version": "1.0.1", - "resolved": "https://registry.npmjs.org/json-stable-stringify/-/json-stable-stringify-1.0.1.tgz", - "integrity": "sha1-mnWdOcXy/1A/1TAGRu1EX4jE+a8=" - }, - "json-stringify-safe": { - "version": "5.0.1", - "resolved": "https://registry.npmjs.org/json-stringify-safe/-/json-stringify-safe-5.0.1.tgz", - "integrity": "sha1-Epai1Y/UXxmg9s4B1lcB4sc1tus=" - }, - "jsonify": { - "version": "0.0.0", - "resolved": "https://registry.npmjs.org/jsonify/-/jsonify-0.0.0.tgz", - "integrity": "sha1-LHS27kHZPKUbe1qu6PUDYx0lKnM=" - }, - "jsonpath": { - "version": "0.2.11", - "resolved": "https://registry.npmjs.org/jsonpath/-/jsonpath-0.2.11.tgz", - "integrity": "sha1-v+IuBmW5cS+Oe99+Lh+MCLWUxg4=" - }, - "JSONSelect": { - "version": "0.4.0", - "resolved": "https://registry.npmjs.org/JSONSelect/-/JSONSelect-0.4.0.tgz", - "integrity": "sha1-oI7cxn6z/L6Z7WMIVTRKDPKCu40=" - }, - "jsprim": { - "version": "1.4.0", - "resolved": "https://registry.npmjs.org/jsprim/-/jsprim-1.4.0.tgz", - "integrity": "sha1-o7h+QCmNjDgFUtjMdiigu5WiKRg=", - "dependencies": { - "assert-plus": { - "version": "1.0.0", - "resolved": "https://registry.npmjs.org/assert-plus/-/assert-plus-1.0.0.tgz", - "integrity": "sha1-8S4PPF13sLHN2RRpQuTpbB5N1SU=" - } - } - }, - "lex-parser": { - "version": "0.1.4", - "resolved": "https://registry.npmjs.org/lex-parser/-/lex-parser-0.1.4.tgz", - "integrity": "sha1-ZMTwJfF/1Tv7RXY/rrFvAVp0dVA=" - }, - "mime-db": { - "version": "1.27.0", - "resolved": "https://registry.npmjs.org/mime-db/-/mime-db-1.27.0.tgz", - "integrity": "sha1-gg9XIpa70g7CXtVeW13oaeVDbrE=" - }, - "mime-types": { - "version": "2.1.15", - "resolved": "https://registry.npmjs.org/mime-types/-/mime-types-2.1.15.tgz", - "integrity": "sha1-pOv1BkCUVpI3uM9wBGd20J/JKu0=" - }, - "minimatch": { - "version": "2.0.10", - "resolved": "https://registry.npmjs.org/minimatch/-/minimatch-2.0.10.tgz", - "integrity": "sha1-jQh8OcazjAAbl/ynzm0OHoCvusc=" - }, - "moment": { - "version": "2.18.1", - "resolved": "https://registry.npmjs.org/moment/-/moment-2.18.1.tgz", - "integrity": "sha1-w2GT3Tzhwu7SrbfIAtu8d6gbHA8=" - }, - "mongodb": { - "version": "2.2.29", - "resolved": "https://registry.npmjs.org/mongodb/-/mongodb-2.2.29.tgz", - "integrity": "sha512-MrQvIsN6zN80I4hdFo8w46w51cIqD2FJBGsUfApX9GmjXA1aCclEAJbOHaQWjCtabeWq57S3ECzqEKg/9bdBhA==" - }, - "mongodb-core": { - "version": "2.1.13", - "resolved": "https://registry.npmjs.org/mongodb-core/-/mongodb-core-2.1.13.tgz", - "integrity": "sha512-mbcvqLLZwVcpTrsfBDY3hRNk2SDNJWOvKKxFJSc0pnUBhYojymBc/L0THfQsWwKJrkb2nIXSjfFll1mG/I5OqQ==" - }, - "ms": { - "version": "2.0.0", - "resolved": "https://registry.npmjs.org/ms/-/ms-2.0.0.tgz", - "integrity": "sha1-VgiurfwAvmwpAd9fmGF4jeDVl8g=" - }, - "nan": { - "version": "2.6.2", - "resolved": "https://registry.npmjs.org/nan/-/nan-2.6.2.tgz", - "integrity": "sha1-5P805slf37WuzAjeZZb0NgWn20U=" - }, - "needle": { - "version": "1.6.0", - "resolved": "https://registry.npmjs.org/needle/-/needle-1.6.0.tgz", - "integrity": "sha1-9SpYWJchIWGOAC+OY4TK2sItYk8=" - }, - "nomnom": { - "version": "1.5.2", - "resolved": "https://registry.npmjs.org/nomnom/-/nomnom-1.5.2.tgz", - "integrity": "sha1-9DRUSKhTz71cDSYyDyR3qwUm/i8=", - "dependencies": { - "underscore": { - "version": "1.1.7", - "resolved": "https://registry.npmjs.org/underscore/-/underscore-1.1.7.tgz", - "integrity": "sha1-QLq4S60Z0jAJbo1u9ii/8FXYPbA=" - } - } - }, - "numeral": { - "version": "2.0.6", - "resolved": "https://registry.npmjs.org/numeral/-/numeral-2.0.6.tgz", - "integrity": "sha1-StCAk21EPCVhrtnyGX7//iX05QY=" - }, - "oauth-sign": { - "version": "0.8.2", - "resolved": "https://registry.npmjs.org/oauth-sign/-/oauth-sign-0.8.2.tgz", - "integrity": "sha1-Rqarfwrq2N6unsBWV4C31O/rnUM=" - }, - "once": { - "version": "1.4.0", - "resolved": "https://registry.npmjs.org/once/-/once-1.4.0.tgz", - "integrity": "sha1-WDsap3WWHUsROsF9nFC6753Xa9E=" - }, - "options": { - "version": "0.0.6", - "resolved": "https://registry.npmjs.org/options/-/options-0.0.6.tgz", - "integrity": "sha1-7CLTEoBrtT5zF3Pnza788cZDEo8=" - }, - "performance-now": { - "version": "0.2.0", - "resolved": "https://registry.npmjs.org/performance-now/-/performance-now-0.2.0.tgz", - "integrity": "sha1-M+8wxcd9TqIcWlOGnZG1bY8lVeU=" - }, - "process-nextick-args": { - "version": "1.0.7", - "resolved": "https://registry.npmjs.org/process-nextick-args/-/process-nextick-args-1.0.7.tgz", - "integrity": "sha1-FQ4gt1ZZCtP5EJPyWk8q2L/zC6M=" - }, - "punycode": { - "version": "1.4.1", - "resolved": "https://registry.npmjs.org/punycode/-/punycode-1.4.1.tgz", - "integrity": "sha1-wNWmOycYgArY4esPpSachN1BhF4=" - }, - "q": { - "version": "1.5.0", - "resolved": "https://registry.npmjs.org/q/-/q-1.5.0.tgz", - "integrity": "sha1-3QG6ydBtMObyGa7LglPunr3DCPE=" - }, - "qs": { - "version": "6.4.0", - "resolved": "https://registry.npmjs.org/qs/-/qs-6.4.0.tgz", - "integrity": "sha1-E+JtKK1rD/qpExLNO/cI7TUecjM=" - }, - "readable-stream": { - "version": "2.2.7", - "resolved": "https://registry.npmjs.org/readable-stream/-/readable-stream-2.2.7.tgz", - "integrity": "sha1-BwV6y+JGeyIELTb5jFrVBwVOlbE=" - }, - "request": { - "version": "2.81.0", - "resolved": "https://registry.npmjs.org/request/-/request-2.81.0.tgz", - "integrity": "sha1-xpKJRqDgbF+Nb4qTM0af/aRimKA=" - }, - "require_optional": { - "version": "1.0.1", - "resolved": "https://registry.npmjs.org/require_optional/-/require_optional-1.0.1.tgz", - "integrity": "sha512-qhM/y57enGWHAe3v/NcwML6a3/vfESLe/sGM2dII+gEO0BpKRUkWZow/tyloNqJyN6kXSl3RyyM8Ll5D/sJP8g==" - }, - "resolve-from": { - "version": "2.0.0", - "resolved": "https://registry.npmjs.org/resolve-from/-/resolve-from-2.0.0.tgz", - "integrity": "sha1-lICrIOlP+h2egKgEx+oUdhGWa1c=" - }, - "safe-buffer": { - "version": "5.1.0", - "resolved": "https://registry.npmjs.org/safe-buffer/-/safe-buffer-5.1.0.tgz", - "integrity": "sha512-aSLEDudu6OoRr/2rU609gRmnYboRLxgDG1z9o2Q0os7236FwvcqIOO8r8U5JUEwivZOhDaKlFO4SbPTJYyBEyQ==" - }, - "semver": { - "version": "5.3.0", - "resolved": "https://registry.npmjs.org/semver/-/semver-5.3.0.tgz", - "integrity": "sha1-myzl094C0XxgEq0yaqa00M9U+U8=" - }, - "slackbots": { - "version": "0.5.3", - "resolved": "https://registry.npmjs.org/slackbots/-/slackbots-0.5.3.tgz", - "integrity": "sha1-fpj5oCp6seYnwAt/WjfQzHR4QQ8=", - "dependencies": { - "extend": { - "version": "2.0.1", - "resolved": "https://registry.npmjs.org/extend/-/extend-2.0.1.tgz", - "integrity": "sha1-HugBBonnOV/5RIJByYZSvHWagmA=" - } - } - }, - "sleep": { - "version": "5.1.1", - "resolved": "https://registry.npmjs.org/sleep/-/sleep-5.1.1.tgz", - "integrity": "sha1-h4+h1E0I7rDyb7IBjvhinrGjq5Q=" - }, - "sntp": { - "version": "1.0.9", - "resolved": "https://registry.npmjs.org/sntp/-/sntp-1.0.9.tgz", - "integrity": "sha1-ZUEYTMkK7qbG57NeJlkIJEPGYZg=" - }, - "source-map": { - "version": "0.5.6", - "resolved": "https://registry.npmjs.org/source-map/-/source-map-0.5.6.tgz", - "integrity": "sha1-dc449SvwczxafwwRjYEzSiu19BI=", - "optional": true - }, - "sshpk": { - "version": "1.13.1", - "resolved": "https://registry.npmjs.org/sshpk/-/sshpk-1.13.1.tgz", - "integrity": "sha1-US322mKHFEMW3EwY/hzx2UBzm+M=", - "dependencies": { - "assert-plus": { - "version": "1.0.0", - "resolved": "https://registry.npmjs.org/assert-plus/-/assert-plus-1.0.0.tgz", - "integrity": "sha1-8S4PPF13sLHN2RRpQuTpbB5N1SU=" - } - } - }, - "static-eval": { - "version": "0.2.3", - "resolved": "https://registry.npmjs.org/static-eval/-/static-eval-0.2.3.tgz", - "integrity": "sha1-Aj8XrJ/uQm6niMEuo5IG3Bdfiyo=", - "dependencies": { - "escodegen": { - "version": "0.0.28", - "resolved": "https://registry.npmjs.org/escodegen/-/escodegen-0.0.28.tgz", - "integrity": "sha1-Dk/xcV8yh3XWyrUaxEpAbNer/9M=" - }, - "esprima": { - "version": "1.0.4", - "resolved": "https://registry.npmjs.org/esprima/-/esprima-1.0.4.tgz", - "integrity": "sha1-n1V+CPw7TSbs6d00+Pv0drYlha0=" - }, - "estraverse": { - "version": "1.3.2", - "resolved": "https://registry.npmjs.org/estraverse/-/estraverse-1.3.2.tgz", - "integrity": "sha1-N8K4k+8T1yPydth41g2FNRUqbEI=" - } - } - }, - "string_decoder": { - "version": "1.0.2", - "resolved": "https://registry.npmjs.org/string_decoder/-/string_decoder-1.0.2.tgz", - "integrity": "sha1-sp4fThEl+pehA4K4pTNze3SR4Xk=", - "dependencies": { - "safe-buffer": { - "version": "5.0.1", - "resolved": "https://registry.npmjs.org/safe-buffer/-/safe-buffer-5.0.1.tgz", - "integrity": "sha1-0mPKVGls2KMGtcplUekt5XkY++c=" - } - } - }, - "stringstream": { - "version": "0.0.5", - "resolved": "https://registry.npmjs.org/stringstream/-/stringstream-0.0.5.tgz", - "integrity": "sha1-TkhM1N5aC7vuGORjB3EKioFiGHg=" - }, - "tough-cookie": { - "version": "2.3.2", - "resolved": "https://registry.npmjs.org/tough-cookie/-/tough-cookie-2.3.2.tgz", - "integrity": "sha1-8IH3bkyFcg5sN6X6ztc3FQ2EByo=" - }, - "tunnel-agent": { - "version": "0.6.0", - "resolved": "https://registry.npmjs.org/tunnel-agent/-/tunnel-agent-0.6.0.tgz", - "integrity": "sha1-J6XeoGs2sEoKmWZ3SykIaPD8QP0=" - }, - "tweetnacl": { - "version": "0.14.5", - "resolved": "https://registry.npmjs.org/tweetnacl/-/tweetnacl-0.14.5.tgz", - "integrity": "sha1-WuaBd/GS1EViadEIr6k/+HQ/T2Q=", - "optional": true - }, - "ultron": { - "version": "1.0.2", - "resolved": "https://registry.npmjs.org/ultron/-/ultron-1.0.2.tgz", - "integrity": "sha1-rOEWq1V80Zc4ak6I9GhTeMiy5Po=" - }, - "underscore": { - "version": "1.7.0", - "resolved": "https://registry.npmjs.org/underscore/-/underscore-1.7.0.tgz", - "integrity": "sha1-a7rwh3UA02vjTsqlhODbn+8DUgk=" - }, - "util-deprecate": { - "version": "1.0.2", - "resolved": "https://registry.npmjs.org/util-deprecate/-/util-deprecate-1.0.2.tgz", - "integrity": "sha1-RQ1Nyfpw3nMnYvvS1KKJgUGaDM8=" - }, - "uuid": { - "version": "3.1.0", - "resolved": "https://registry.npmjs.org/uuid/-/uuid-3.1.0.tgz", - "integrity": "sha512-DIWtzUkw04M4k3bf1IcpS2tngXEL26YUD2M0tMDUpnUrz2hgzUBlD55a4FjdLGPvfHxS6uluGWvaVEqgBcVa+g==" - }, - "verror": { - "version": "1.3.6", - "resolved": "https://registry.npmjs.org/verror/-/verror-1.3.6.tgz", - "integrity": "sha1-z/XfEpRtKX0rqu+qJoniW+AcAFw=" - }, - "vow": { - "version": "0.4.16", - "resolved": "https://registry.npmjs.org/vow/-/vow-0.4.16.tgz", - "integrity": "sha1-u51U2TjV+AUg1linQOeoleMP7us=" - }, - "wrappy": { - "version": "1.0.2", - "resolved": "https://registry.npmjs.org/wrappy/-/wrappy-1.0.2.tgz", - "integrity": "sha1-tSQ9jz7BqjXxNkYFvA0QNuMKtp8=" - }, - "ws": { - "version": "1.1.4", - "resolved": "https://registry.npmjs.org/ws/-/ws-1.1.4.tgz", - "integrity": "sha1-V/QNA2gy5fUFVmKjl8Tedu1mv2E=" - }, - "xmlhttprequest": { - "version": "1.8.0", - "resolved": "https://registry.npmjs.org/xmlhttprequest/-/xmlhttprequest-1.8.0.tgz", - "integrity": "sha1-Z/4HXFwk/vOfnWX197f+dRcZaPw=" - } - } -} diff --git a/package.json b/package.json deleted file mode 100644 index eacc88e..0000000 --- a/package.json +++ /dev/null @@ -1,33 +0,0 @@ -{ - "name": "hashbot", - "version": "1.0.3", - "description": "A bot for slack wich displays lbrys current hashrate via the open api.", - "main": "app.js", - "dependencies": { - "bitcoin": "^3.0.1", - "imgur": "0.1.7", - "jsonpath": "0.2.11", - "moment": "^2.17.1", - "mongodb": "^2.2.22", - "needle": "^1.0.0", - "numeral": "2.0.6", - "request": "^2.81.0", - "slackbots": "^0.5.1", - "sleep": "^5.1.1", - "xmlhttprequest": "1.8.0" - }, - "devDependencies": {}, - "scripts": { - "test": "echo \"Error: no test specified\" && exit 1" - }, - "repository": { - "type": "git", - "url": "git+https://github.com/lbryio/hashbot.git" - }, - "author": "Fillerino", - "license": "MIT", - "bugs": { - "url": "https://github.com/lbryio/hashbot/issues" - }, - "homepage": "https://github.com/lbryio/hashbot#readme" -} diff --git a/picklerick.png b/picklerick.png deleted file mode 100644 index c092a56..0000000 Binary files a/picklerick.png and /dev/null differ diff --git a/rickshutup.png b/rickshutup.png deleted file mode 100644 index f53615b..0000000 Binary files a/rickshutup.png and /dev/null differ diff --git a/slack-greeting.md b/slack-greeting.md deleted file mode 100644 index 8134a24..0000000 --- a/slack-greeting.md +++ /dev/null @@ -1,11 +0,0 @@ -Welcome to LBRY Slack! - -- LBRY is currently in open beta. To download go here: https://lbry.io/get -- Ask questions only after reading the pinned items in each respective Slack channel. If there is still an issue or a question you have please reach out in the #help channel. -- If you're a developer we encourage you to join #dev. -- No spamming or referral links are permitted, you will be banned. -- Keep it on topic in the #general channel. -- Please put NSFW material only in the #random_nsfw channel. -- To upload images and gifs please use https://spee.ch/ -- Read the FAQ: http://lbry.io/faq -- Be courteous, kind, and generous and welcome to one of the best cryptocurrency communities around!