discordrb 1.3.12 → 1.4.0
Sign up to get free protection for your applications and to get access to all the features.
Potentially problematic release.
This version of discordrb might be problematic. Click here for more details.
- checksums.yaml +4 -4
- data/Rakefile +4 -0
- data/bin/console +3 -3
- data/discordrb.gemspec +14 -14
- data/examples/commands.rb +8 -8
- data/examples/ping.rb +3 -3
- data/examples/pm_send.rb +2 -2
- data/lib/discordrb.rb +1 -0
- data/lib/discordrb/api.rb +34 -8
- data/lib/discordrb/bot.rb +126 -18
- data/lib/discordrb/commands/command_bot.rb +19 -5
- data/lib/discordrb/data.rb +272 -39
- data/lib/discordrb/events/generic.rb +5 -1
- data/lib/discordrb/events/guilds.rb +56 -0
- data/lib/discordrb/games.rb +6 -4
- data/lib/discordrb/games_list.rb +1 -306
- data/lib/discordrb/permissions.rb +29 -3
- data/lib/discordrb/version.rb +1 -1
- data/util/update_lists.rb +20 -2
- metadata +3 -2
checksums.yaml
CHANGED
@@ -1,7 +1,7 @@
|
|
1
1
|
---
|
2
2
|
SHA1:
|
3
|
-
metadata.gz:
|
4
|
-
data.tar.gz:
|
3
|
+
metadata.gz: 1318b8f7407048d6ba422c2d3732ed9536fdb56d
|
4
|
+
data.tar.gz: d7f68a7d482a60a961c61c96c23c3a34592014e6
|
5
5
|
SHA512:
|
6
|
-
metadata.gz:
|
7
|
-
data.tar.gz:
|
6
|
+
metadata.gz: 8063043dce37200550f85b17d8a521e5da6f9f16c31d2663d5d7d0a2b64ac918644d7124e00a19e5acc50fc6a6fe00b537adae056a0e3b2b72b40395a26c6eb5
|
7
|
+
data.tar.gz: 5b2719cfb5f73cffe7b34957d9ca957766d7c277f57d951ffe2ad9af8ec1fc95af54c193032a4f7a4c0c832475f2227a1410e6351b37ddf22ac4d53f63e993dc
|
data/Rakefile
CHANGED
data/bin/console
CHANGED
@@ -1,7 +1,7 @@
|
|
1
1
|
#!/usr/bin/env ruby
|
2
2
|
|
3
|
-
require
|
4
|
-
require
|
3
|
+
require 'bundler/setup'
|
4
|
+
require 'discordrb'
|
5
5
|
|
6
6
|
# You can add fixtures and/or initialization code here to make experimenting
|
7
7
|
# with your gem easier. You can also use a different console, if you like.
|
@@ -10,5 +10,5 @@ require "discordrb"
|
|
10
10
|
# require "pry"
|
11
11
|
# Pry.start
|
12
12
|
|
13
|
-
require
|
13
|
+
require 'irb'
|
14
14
|
IRB.start
|
data/discordrb.gemspec
CHANGED
@@ -4,25 +4,25 @@ $LOAD_PATH.unshift(lib) unless $LOAD_PATH.include?(lib)
|
|
4
4
|
require 'discordrb/version'
|
5
5
|
|
6
6
|
Gem::Specification.new do |spec|
|
7
|
-
spec.name =
|
7
|
+
spec.name = 'discordrb'
|
8
8
|
spec.version = Discordrb::VERSION
|
9
|
-
spec.authors = [
|
10
|
-
spec.email = [
|
9
|
+
spec.authors = ['meew0']
|
10
|
+
spec.email = ['']
|
11
11
|
|
12
|
-
spec.summary =
|
13
|
-
spec.description =
|
14
|
-
spec.homepage =
|
15
|
-
spec.license =
|
12
|
+
spec.summary = 'Discord API for Ruby'
|
13
|
+
spec.description = 'A Ruby implementation of the Discord (https://discordapp.com) API.'
|
14
|
+
spec.homepage = 'https://github.com/meew0/discordrb'
|
15
|
+
spec.license = 'MIT'
|
16
16
|
|
17
17
|
spec.files = `git ls-files -z`.split("\x0").reject { |f| f.match(%r{^(test|spec|features)/}) }
|
18
|
-
spec.bindir =
|
18
|
+
spec.bindir = 'exe'
|
19
19
|
spec.executables = spec.files.grep(%r{^exe/}) { |f| File.basename(f) }
|
20
|
-
spec.require_paths = [
|
20
|
+
spec.require_paths = ['lib']
|
21
21
|
|
22
|
-
spec.add_dependency
|
23
|
-
spec.add_dependency
|
24
|
-
spec.add_dependency
|
22
|
+
spec.add_dependency 'faye-websocket'
|
23
|
+
spec.add_dependency 'rest-client'
|
24
|
+
spec.add_dependency 'activesupport'
|
25
25
|
|
26
|
-
spec.add_development_dependency
|
27
|
-
spec.add_development_dependency
|
26
|
+
spec.add_development_dependency 'bundler', '~> 1.10'
|
27
|
+
spec.add_development_dependency 'rake', '~> 10.0'
|
28
28
|
end
|
data/examples/commands.rb
CHANGED
@@ -2,17 +2,17 @@
|
|
2
2
|
|
3
3
|
require 'discordrb'
|
4
4
|
|
5
|
-
bot = Discordrb::Commands::CommandBot.new
|
5
|
+
bot = Discordrb::Commands::CommandBot.new 'email@example.com', 'hunter2', '!'
|
6
6
|
|
7
7
|
bot.command :user do |event|
|
8
8
|
event.user.name
|
9
9
|
end
|
10
10
|
|
11
|
-
bot.command :bold do |
|
11
|
+
bot.command :bold do |_event, *args|
|
12
12
|
"**#{args.join(' ')}**"
|
13
13
|
end
|
14
14
|
|
15
|
-
bot.command :italic do |
|
15
|
+
bot.command :italic do |_event, *args|
|
16
16
|
"**#{args.join(' ')}**"
|
17
17
|
end
|
18
18
|
|
@@ -20,7 +20,7 @@ bot.command(:join, permission_level: 1, chain_usable: false) do |event, invite|
|
|
20
20
|
event.bot.join invite
|
21
21
|
end
|
22
22
|
|
23
|
-
bot.command(:random, min_args: 0, max_args: 2, description:
|
23
|
+
bot.command(:random, min_args: 0, max_args: 2, description: 'Generates a random number between 0 and 1, 0 and max or min and max.', usage: 'random [min/max] [max]') do |_event, min, max|
|
24
24
|
if max
|
25
25
|
rand(min..max)
|
26
26
|
elsif min
|
@@ -31,10 +31,10 @@ bot.command(:random, min_args: 0, max_args: 2, description: "Generates a random
|
|
31
31
|
end
|
32
32
|
|
33
33
|
bot.command :long do |event|
|
34
|
-
event <<
|
35
|
-
event <<
|
36
|
-
event <<
|
37
|
-
event <<
|
34
|
+
event << 'This is a long message.'
|
35
|
+
event << 'It has multiple lines that are each sent by doing `event << line`.'
|
36
|
+
event << 'This is an easy way to do such long messages, or to create lines that should only be sent conditionally.'
|
37
|
+
event << 'Anyway, have a nice day.'
|
38
38
|
end
|
39
39
|
|
40
40
|
bot.run
|
data/examples/ping.rb
CHANGED
@@ -2,10 +2,10 @@
|
|
2
2
|
|
3
3
|
require 'discordrb'
|
4
4
|
|
5
|
-
bot = Discordrb::Bot.new
|
5
|
+
bot = Discordrb::Bot.new 'email@example.com', 'hunter2'
|
6
6
|
|
7
|
-
bot.message(with_text:
|
8
|
-
event.respond
|
7
|
+
bot.message(with_text: 'Ping!') do |event|
|
8
|
+
event.respond 'Pong!'
|
9
9
|
end
|
10
10
|
|
11
11
|
bot.run
|
data/examples/pm_send.rb
CHANGED
@@ -2,10 +2,10 @@
|
|
2
2
|
|
3
3
|
require 'discordrb'
|
4
4
|
|
5
|
-
bot = Discordrb::Bot.new
|
5
|
+
bot = Discordrb::Bot.new 'email@example.com', 'hunter2'
|
6
6
|
|
7
7
|
bot.mention do |event|
|
8
|
-
event.user.pm(
|
8
|
+
event.user.pm('You have mentioned me!')
|
9
9
|
end
|
10
10
|
|
11
11
|
bot.run
|
data/lib/discordrb.rb
CHANGED
data/lib/discordrb/api.rb
CHANGED
@@ -58,15 +58,33 @@ module Discordrb::API
|
|
58
58
|
end
|
59
59
|
|
60
60
|
# Create a server
|
61
|
-
def create_server(token, name, region)
|
61
|
+
def create_server(token, name, region = :london)
|
62
62
|
RestClient.post(
|
63
63
|
"#{APIBASE}/guilds",
|
64
|
-
{ 'name' => name, 'region' => region }.to_json,
|
64
|
+
{ 'name' => name, 'region' => region.to_s }.to_json,
|
65
65
|
Authorization: token,
|
66
66
|
content_type: :json
|
67
67
|
)
|
68
68
|
end
|
69
69
|
|
70
|
+
# Update a server
|
71
|
+
def update_server(token, server_id, name, region, icon, afk_channel_id, afk_timeout)
|
72
|
+
RestClient.patch(
|
73
|
+
"#{APIBASE}/guilds/#{server_id}",
|
74
|
+
{ 'name' => name, 'region' => region, 'icon' => icon, 'afk_channel_id' => afk_channel_id, 'afk_timeout' => afk_timeout }.to_json,
|
75
|
+
Authorization: token,
|
76
|
+
content_type: :json
|
77
|
+
)
|
78
|
+
end
|
79
|
+
|
80
|
+
# Delete a server
|
81
|
+
def delete_server(token, server_id)
|
82
|
+
RestClient.delete(
|
83
|
+
"#{APIBASE}/guilds/#{server_id}",
|
84
|
+
Authorization: token
|
85
|
+
)
|
86
|
+
end
|
87
|
+
|
70
88
|
# Leave a server
|
71
89
|
def leave_server(server_id)
|
72
90
|
RestClient.delete(
|
@@ -112,18 +130,18 @@ module Discordrb::API
|
|
112
130
|
end
|
113
131
|
|
114
132
|
# Join a server using an invite
|
115
|
-
def join_server(token,
|
133
|
+
def join_server(token, invite_code)
|
116
134
|
RestClient.post(
|
117
|
-
"#{APIBASE}/invite/#{
|
135
|
+
"#{APIBASE}/invite/#{invite_code}",
|
118
136
|
nil,
|
119
137
|
Authorization: token
|
120
138
|
)
|
121
139
|
end
|
122
140
|
|
123
141
|
# Resolve an invite
|
124
|
-
def resolve_invite(token,
|
142
|
+
def resolve_invite(token, invite_code)
|
125
143
|
RestClient.get(
|
126
|
-
"#{APIBASE}/invite/#{
|
144
|
+
"#{APIBASE}/invite/#{invite_code}",
|
127
145
|
Authorization: token
|
128
146
|
)
|
129
147
|
end
|
@@ -139,15 +157,23 @@ module Discordrb::API
|
|
139
157
|
end
|
140
158
|
|
141
159
|
# Create an instant invite from a server or a channel id
|
142
|
-
def create_invite(token,
|
160
|
+
def create_invite(token, channel_id, max_age = 0, max_uses = 0, temporary = false, xkcd = false)
|
143
161
|
RestClient.post(
|
144
|
-
"#{APIBASE}/channels/#{
|
162
|
+
"#{APIBASE}/channels/#{channel_id}/invites",
|
145
163
|
{ 'max_age' => max_age, 'max_uses' => max_uses, 'temporary' => temporary, 'xkcdpass' => xkcd }.to_json,
|
146
164
|
Authorization: token,
|
147
165
|
content_type: :json
|
148
166
|
)
|
149
167
|
end
|
150
168
|
|
169
|
+
# Delete an invite by code
|
170
|
+
def delete_invite(token, code)
|
171
|
+
RestClient.delete(
|
172
|
+
"#{APIBASE}/invites/#{code}",
|
173
|
+
Authorization: token
|
174
|
+
)
|
175
|
+
end
|
176
|
+
|
151
177
|
# Send a message to a channel
|
152
178
|
def send_message(token, channel_id, message, mentions = [], tts = false)
|
153
179
|
RestClient.post(
|
data/lib/discordrb/bot.rb
CHANGED
@@ -14,6 +14,7 @@ require 'discordrb/events/members'
|
|
14
14
|
require 'discordrb/events/guild_role_create'
|
15
15
|
require 'discordrb/events/guild_role_delete'
|
16
16
|
require 'discordrb/events/guild_role_update'
|
17
|
+
require 'discordrb/events/guilds'
|
17
18
|
require 'discordrb/events/await'
|
18
19
|
|
19
20
|
require 'discordrb/api'
|
@@ -27,7 +28,7 @@ module Discordrb
|
|
27
28
|
class Bot
|
28
29
|
include Discordrb::Events
|
29
30
|
|
30
|
-
attr_reader :bot_user, :token, :users, :servers
|
31
|
+
attr_reader :bot_user, :token, :users, :servers, :event_threads, :profile
|
31
32
|
attr_accessor :should_parse_self
|
32
33
|
|
33
34
|
def initialize(email, password, debug = false)
|
@@ -51,6 +52,9 @@ module Discordrb
|
|
51
52
|
@users = {}
|
52
53
|
|
53
54
|
@awaits = {}
|
55
|
+
|
56
|
+
@event_threads = []
|
57
|
+
@current_thread = 0
|
54
58
|
end
|
55
59
|
|
56
60
|
def run(async = false)
|
@@ -66,6 +70,7 @@ module Discordrb
|
|
66
70
|
@heartbeat_interval = 1
|
67
71
|
@heartbeat_active = false
|
68
72
|
@heartbeat_thread = Thread.new do
|
73
|
+
Thread.current[:discordrb_name] = 'heartbeat'
|
69
74
|
loop do
|
70
75
|
sleep @heartbeat_interval
|
71
76
|
send_heartbeat if @heartbeat_active
|
@@ -73,6 +78,7 @@ module Discordrb
|
|
73
78
|
end
|
74
79
|
|
75
80
|
@ws_thread = Thread.new do
|
81
|
+
Thread.current[:discordrb_name] = 'websocket'
|
76
82
|
loop do
|
77
83
|
websocket_connect
|
78
84
|
debug('Disconnected! Attempting to reconnect in 5 seconds.')
|
@@ -113,12 +119,23 @@ module Discordrb
|
|
113
119
|
@private_channels[id] = channel
|
114
120
|
end
|
115
121
|
|
116
|
-
def
|
122
|
+
def resolve_invite_code(invite)
|
123
|
+
invite = invite.code if invite.is_a? Discordrb::Invite
|
117
124
|
invite = invite[invite.rindex('/') + 1..-1] if invite.start_with?('http') || invite.start_with?('discord.gg')
|
125
|
+
invite
|
126
|
+
end
|
127
|
+
|
128
|
+
def join(invite)
|
129
|
+
invite = resolve_invite_code(invite)
|
118
130
|
resolved = JSON.parse(API.resolve_invite(@token, invite))['code']
|
119
131
|
API.join_server(@token, resolved)
|
120
132
|
end
|
121
133
|
|
134
|
+
def delete_invite(code)
|
135
|
+
invite = resolve_invite_code(code)
|
136
|
+
API.delete_invite(@token, invite)
|
137
|
+
end
|
138
|
+
|
122
139
|
def user(id)
|
123
140
|
@users[id]
|
124
141
|
end
|
@@ -164,6 +181,16 @@ module Discordrb
|
|
164
181
|
@awaits[key] = await
|
165
182
|
end
|
166
183
|
|
184
|
+
# Regions: :london, :amsterdam, :frankfurt, :us-east, :us-west, :singapore, :sydney
|
185
|
+
def create_server(name, region = :london)
|
186
|
+
response = API.create_server(@token, name, region)
|
187
|
+
id = JSON.parse(response)['id'].to_i
|
188
|
+
sleep 0.1 until @servers[id]
|
189
|
+
server = @servers[id]
|
190
|
+
debug "Successfully created server #{server.id} with name #{server.name}"
|
191
|
+
server
|
192
|
+
end
|
193
|
+
|
167
194
|
def parse_mention(mention)
|
168
195
|
# Mention format: <@id>
|
169
196
|
return nil unless /\<@(?<id>\d+)\>?/ =~ mention
|
@@ -269,6 +296,18 @@ module Discordrb
|
|
269
296
|
register_event(GuildMemberDeleteEvent, attributes, block)
|
270
297
|
end
|
271
298
|
|
299
|
+
def server_create(attributes = {}, &block)
|
300
|
+
register_event(GuildCreateEvent, attributes, block)
|
301
|
+
end
|
302
|
+
|
303
|
+
def server_update(attributes = {}, &block)
|
304
|
+
register_event(GuildUpdateEvent, attributes, block)
|
305
|
+
end
|
306
|
+
|
307
|
+
def server_delete(attributes = {}, &block)
|
308
|
+
register_event(GuildDeleteEvent, attributes, block)
|
309
|
+
end
|
310
|
+
|
272
311
|
def await(attributes = {}, &block)
|
273
312
|
register_event(AwaitEvent, attributes, block)
|
274
313
|
end
|
@@ -290,7 +329,12 @@ module Discordrb
|
|
290
329
|
end
|
291
330
|
|
292
331
|
def debug(message, important = false)
|
293
|
-
puts "[DEBUG @ #{Time.now}] #{message}" if @debug || important
|
332
|
+
puts "[DEBUG : #{Thread.current[:discordrb_name]} @ #{Time.now}] #{message}" if @debug || important
|
333
|
+
end
|
334
|
+
|
335
|
+
def log_exception(e)
|
336
|
+
debug("Exception: #{e.inspect}", true)
|
337
|
+
e.backtrace.each { |line| debug(line, true) }
|
294
338
|
end
|
295
339
|
|
296
340
|
def handler_class(event_class)
|
@@ -301,6 +345,31 @@ module Discordrb
|
|
301
345
|
|
302
346
|
private
|
303
347
|
|
348
|
+
####### ### ###### ## ## ########
|
349
|
+
## ## ## ## ## ## ## ## ##
|
350
|
+
## ## ## ## ## ## ##
|
351
|
+
## ## ## ## ######### ######
|
352
|
+
## ######### ## ## ## ##
|
353
|
+
## ## ## ## ## ## ## ## ##
|
354
|
+
####### ## ## ###### ## ## ########
|
355
|
+
|
356
|
+
def add_server(data)
|
357
|
+
server = Server.new(data, self)
|
358
|
+
@servers[server.id] = server
|
359
|
+
|
360
|
+
# Initialize users
|
361
|
+
server.members.each do |member|
|
362
|
+
if @users[member.id]
|
363
|
+
# If the user is already cached, just add the new roles
|
364
|
+
@users[member.id].merge_roles(server, member.roles[server.id])
|
365
|
+
else
|
366
|
+
@users[member.id] = member
|
367
|
+
end
|
368
|
+
end
|
369
|
+
|
370
|
+
server
|
371
|
+
end
|
372
|
+
|
304
373
|
### ## ## ######## ######## ######## ## ## ### ## ######
|
305
374
|
## ### ## ## ## ## ## ### ## ## ## ## ## ##
|
306
375
|
## #### ## ## ## ## ## #### ## ## ## ## ##
|
@@ -427,6 +496,27 @@ module Discordrb
|
|
427
496
|
server.delete_user(user_id)
|
428
497
|
end
|
429
498
|
|
499
|
+
# Internal handler for GUILD_CREATE
|
500
|
+
def create_guild(data)
|
501
|
+
add_server(data)
|
502
|
+
end
|
503
|
+
|
504
|
+
# Internal handler for GUILD_UPDATE
|
505
|
+
def update_guild(data)
|
506
|
+
@servers[data['id'].to_i].update_data(data)
|
507
|
+
end
|
508
|
+
|
509
|
+
# Internal handler for GUILD_DELETE
|
510
|
+
def delete_guild(data)
|
511
|
+
id = data['id']
|
512
|
+
|
513
|
+
@users.each do |_, user|
|
514
|
+
user.delete_roles(id)
|
515
|
+
end
|
516
|
+
|
517
|
+
@servers.delete(id)
|
518
|
+
end
|
519
|
+
|
430
520
|
# Internal handler for GUILD_ROLE_UPDATE
|
431
521
|
def update_guild_role(data)
|
432
522
|
role_data = data['role']
|
@@ -551,22 +641,12 @@ module Discordrb
|
|
551
641
|
debug("Desired heartbeat_interval: #{@heartbeat_interval}")
|
552
642
|
|
553
643
|
bot_user_id = data['user']['id'].to_i
|
644
|
+
@profile = Profile.new(data['user'], self, @email, @password)
|
554
645
|
|
555
646
|
# Initialize servers
|
556
647
|
@servers = {}
|
557
648
|
data['guilds'].each do |element|
|
558
|
-
|
559
|
-
@servers[server.id] = server
|
560
|
-
|
561
|
-
# Initialize users
|
562
|
-
server.members.each do |member|
|
563
|
-
if @users[member.id]
|
564
|
-
# If the user is already cached, just add the new roles
|
565
|
-
@users[member.id].merge_roles(server, member.roles[server.id])
|
566
|
-
else
|
567
|
-
@users[member.id] = member
|
568
|
-
end
|
569
|
-
end
|
649
|
+
add_server(element)
|
570
650
|
|
571
651
|
# Save the bot user
|
572
652
|
@bot_user = @users[bot_user_id]
|
@@ -664,10 +744,24 @@ module Discordrb
|
|
664
744
|
|
665
745
|
event = GuildRoleDeleteEvent.new(data, self)
|
666
746
|
raise_event(event)
|
747
|
+
when 'GUILD_CREATE'
|
748
|
+
create_guild(data)
|
749
|
+
|
750
|
+
event = GuildCreateEvent.new(data, self)
|
751
|
+
raise_event(event)
|
752
|
+
when 'GUILD_UPDATE'
|
753
|
+
update_guild(data)
|
754
|
+
|
755
|
+
event = GuildUpdateEvent.new(data, self)
|
756
|
+
raise_event(event)
|
757
|
+
when 'GUILD_DELETE'
|
758
|
+
delete_guild(data)
|
759
|
+
|
760
|
+
event = GuildDeleteEvent.new(data, self)
|
761
|
+
raise_event(event)
|
667
762
|
end
|
668
763
|
rescue Exception => e
|
669
|
-
|
670
|
-
e.backtrace.each { |line| debug(line) }
|
764
|
+
log_exception(e)
|
671
765
|
end
|
672
766
|
|
673
767
|
def websocket_close(event)
|
@@ -704,7 +798,21 @@ module Discordrb
|
|
704
798
|
|
705
799
|
handlers = @event_handlers[event.class]
|
706
800
|
(handlers || []).each do |handler|
|
707
|
-
handler.
|
801
|
+
call_event(handler, event) if handler.matches?(event)
|
802
|
+
end
|
803
|
+
end
|
804
|
+
|
805
|
+
def call_event(handler, event)
|
806
|
+
t = Thread.new do
|
807
|
+
@event_threads << t
|
808
|
+
Thread.current[:discordrb_name] = "et-#{@current_thread += 1}"
|
809
|
+
begin
|
810
|
+
handler.call(event)
|
811
|
+
rescue => e
|
812
|
+
log_exception(e)
|
813
|
+
ensure
|
814
|
+
@event_threads.delete(t)
|
815
|
+
end
|
708
816
|
end
|
709
817
|
end
|
710
818
|
|