-
Notifications
You must be signed in to change notification settings - Fork 0
/
slackbot2.js
170 lines (136 loc) · 5.44 KB
/
slackbot2.js
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
166
167
168
169
170
const responseFile = require('./responses.json');
const config = require('./botConfig.json');
const autoResponses = responseFile.autoresponses;
const greetings = responseFile.greetings;
const token = config.token;
const Discord = require('discord.js');
const bot = new Discord.Client();
const randomUserMacro = '\{randomUser\}';
const userMacro = '\{user\}'
const guildMacro = '\{server\}';
function pickRandomArrayElt(array) {
return array[Math.floor(Math.random() * array.length)];
}
function pickRandomUsername(channel) {
const botName = bot.user.username;
if(channel.members == undefined) {
return '';
}
let members = Array.from(channel.members.values());
members = members.filter(member => member.user.username !== botName);
const randMember = pickRandomArrayElt(members);
if(randMember != undefined) {
return randMember.user.username;
}
return '';
}
function expandResponseMacros(authorUsername, guildName, channel, reply) {
let botResponse = reply.replace(userMacro, authorUsername);
botResponse = botResponse.replace(guildMacro, guildName);
if(botResponse.includes(randomUserMacro)){
const randomUser = pickRandomUsername(channel);
if(randomUser !== '') {
botResponse = botResponse.replace(randomUserMacro, randomUser);
}
else {
botResponse = '';
}
}
return botResponse;
}
function isPunctuation(char) {
return /[\s\W\d]/.test(char);
}
function matchesTrigger(messageContent, trigger) {
const subStrIndex = messageContent.toLowerCase().indexOf(trigger.toLowerCase());
if(subStrIndex >= 0) {
const precededBySpace = (subStrIndex === 0
|| isPunctuation(messageContent.charAt(subStrIndex - 1)));
const followedBySpace = (subStrIndex + trigger.length === messageContent.length)
|| isPunctuation(messageContent.charAt(subStrIndex + trigger.length));
return precededBySpace && followedBySpace;
}
return false;
}
function findTriggerIndex(messageContent) {
return autoResponses.findIndex(autoresp =>
autoresp.triggers.find(trigger => matchesTrigger(messageContent, trigger)));
}
function filterValidResponses(responses, message) {
return responses.filter(response =>
// Responses requiring a guildMacro or a randomUserMacro can not be sent
// in direct messages so we need to remove them.
(!response.includes(randomUserMacro) || message.channel) &&
(!response.includes(guildMacro) || message.guild)
);
}
function respond(message, triggerIndex) {
const responses = autoResponses[triggerIndex].responses;
if(responses.length > 0) {
const validResponses = filterValidResponses(responses, message);
if(validResponses !== []) {
let botResponse = pickRandomArrayElt(validResponses);
let guildName = message.guild ? message.guild.name : '';
botResponse = expandResponseMacros(message.author.username,
guildName,
message.channel,
botResponse);
if(botResponse !== '') {
message.channel.send(botResponse).catch(console.error);
}
}
}
}
function react(message, triggerIndex) {
const reactions = autoResponses[triggerIndex].reactions;
if(reactions !== undefined && reactions.length > 0) {
reactions.forEach(botReaction => {
if(botReaction.spawnRate >= 1 || Math.random() < botReaction.spawnRate) {
const isCustomEmoji = /\w+/.test(botReaction.reaction);
if(isCustomEmoji) {
const emoji = bot.emojis.cache.find(emoji => emoji.name === botReaction.reaction);
if(emoji) {
message.react(emoji).catch(console.error);
}
}
else { // Unicode emoji.
message.react(botReaction.reaction).catch(console.error);
}
}
});
}
}
bot.on('message', async message => {
const author = message.author.username;
const botName = bot.user.username;
if (author !== botName && (!message.author.bot || config.respondToBots)) {
const triggerIndex = findTriggerIndex(message.content);
if(triggerIndex > -1) {
respond(message, triggerIndex);
react(message, triggerIndex);
}
}
});
bot.on('guildMemberAdd', guildMember => {
if(greetings !== []) {
let guild = guildMember.guild;
let systemChannel = guild.systemChannel;
const greeting = expandResponseMacros(guildMember.user.username,
guild.name,
systemChannel,
pickRandomArrayElt(greetings));
systemChannel.send(greeting);
}
});
bot.on('ready', () => {
// Loading all guild members requires the developer to enable the server members intent
// inside the bot tab of the developer portal page.
if(config.loadGuildMembersOnStart) {
for(const guild of Array.from(bot.guilds.cache.values())) {
bot.guilds.cache.get(guild.id)
.members.fetch()
.catch(console.error);
}
}
});
bot.login(token);