onyxcord 2.1.0 → 3.2.1
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- checksums.yaml +4 -4
- data/lib/onyxcord/application_commands/command.rb +4 -97
- data/lib/onyxcord/application_commands/context.rb +4 -94
- data/lib/onyxcord/application_commands/option.rb +4 -75
- data/lib/onyxcord/application_commands/registry.rb +4 -45
- data/lib/onyxcord/application_commands.rb +8 -5
- data/lib/onyxcord/bot.rb +24 -1759
- data/lib/onyxcord/{cache.rb → cache/manager.rb} +16 -14
- data/lib/onyxcord/cache/stores/gateway.rb +272 -0
- data/lib/onyxcord/commands/bot/channels.rb +48 -0
- data/lib/onyxcord/commands/bot/execution.rb +174 -0
- data/lib/onyxcord/commands/bot/message_dispatch.rb +58 -0
- data/lib/onyxcord/commands/bot/permissions.rb +72 -0
- data/lib/onyxcord/commands/bot.rb +209 -0
- data/lib/onyxcord/commands/container.rb +21 -2
- data/lib/onyxcord/commands/parser.rb +30 -1
- data/lib/onyxcord/container.rb +16 -960
- data/lib/onyxcord/core/bot/application_commands.rb +210 -0
- data/lib/onyxcord/core/bot/awaits.rb +112 -0
- data/lib/onyxcord/core/bot/invites.rb +42 -0
- data/lib/onyxcord/core/bot/messaging.rb +161 -0
- data/lib/onyxcord/core/bot/oauth.rb +27 -0
- data/lib/onyxcord/core/bot/presence.rb +103 -0
- data/lib/onyxcord/core/bot/runtime.rb +183 -0
- data/lib/onyxcord/core/bot/voice.rb +69 -0
- data/lib/onyxcord/{logger.rb → core/logger.rb} +5 -0
- data/lib/onyxcord/core/version.rb +5 -0
- data/lib/onyxcord/events/await/base.rb +48 -0
- data/lib/onyxcord/events/await.rb +1 -46
- data/lib/onyxcord/events/ban/base.rb +54 -0
- data/lib/onyxcord/events/ban/remove.rb +11 -0
- data/lib/onyxcord/events/bans.rb +2 -58
- data/lib/onyxcord/events/channels/base.rb +91 -0
- data/lib/onyxcord/events/channels/delete.rb +73 -0
- data/lib/onyxcord/events/channels/pins.rb +44 -0
- data/lib/onyxcord/events/channels/recipients.rb +77 -0
- data/lib/onyxcord/events/channels.rb +4 -239
- data/lib/onyxcord/events/guilds/audit_logs.rb +79 -0
- data/lib/onyxcord/events/guilds/base.rb +97 -0
- data/lib/onyxcord/events/guilds/emoji.rb +147 -0
- data/lib/onyxcord/events/guilds.rb +3 -267
- data/lib/onyxcord/events/handlers/channels.rb +133 -0
- data/lib/onyxcord/events/handlers/core.rb +146 -0
- data/lib/onyxcord/events/handlers/guilds.rb +375 -0
- data/lib/onyxcord/events/handlers/interactions.rb +238 -0
- data/lib/onyxcord/events/handlers/lifetime.rb +71 -0
- data/lib/onyxcord/events/handlers/messages.rb +218 -0
- data/lib/onyxcord/events/handlers/presence.rb +56 -0
- data/lib/onyxcord/events/handlers/raw.rb +39 -0
- data/lib/onyxcord/events/handlers/reactions.rb +98 -0
- data/lib/onyxcord/events/handlers/scheduled_events.rb +243 -0
- data/lib/onyxcord/events/handlers/voice.rb +46 -0
- data/lib/onyxcord/events/integration/base.rb +45 -0
- data/lib/onyxcord/events/integration/create.rb +11 -0
- data/lib/onyxcord/events/integration/delete.rb +48 -0
- data/lib/onyxcord/events/integration/update.rb +11 -0
- data/lib/onyxcord/events/integrations.rb +4 -98
- data/lib/onyxcord/events/interactions/application_commands.rb +185 -0
- data/lib/onyxcord/events/interactions/autocomplete.rb +62 -0
- data/lib/onyxcord/events/interactions/base.rb +175 -0
- data/lib/onyxcord/events/interactions/components.rb +221 -0
- data/lib/onyxcord/events/interactions/permissions.rb +53 -0
- data/lib/onyxcord/events/interactions.rb +5 -622
- data/lib/onyxcord/events/invite/create.rb +79 -0
- data/lib/onyxcord/events/invite/delete.rb +55 -0
- data/lib/onyxcord/events/invites.rb +2 -125
- data/lib/onyxcord/events/lifetime/base.rb +31 -0
- data/lib/onyxcord/events/lifetime.rb +1 -29
- data/lib/onyxcord/events/member/add.rb +12 -0
- data/lib/onyxcord/events/member/base.rb +67 -0
- data/lib/onyxcord/events/member/delete.rb +21 -0
- data/lib/onyxcord/events/member/update.rb +25 -0
- data/lib/onyxcord/events/members.rb +4 -108
- data/lib/onyxcord/events/message/base.rb +295 -0
- data/lib/onyxcord/events/message/ids.rb +71 -0
- data/lib/onyxcord/events/message/mentions.rb +55 -0
- data/lib/onyxcord/events/message/updates.rb +27 -0
- data/lib/onyxcord/events/message.rb +4 -397
- data/lib/onyxcord/events/poll/add.rb +11 -0
- data/lib/onyxcord/events/poll/base.rb +106 -0
- data/lib/onyxcord/events/poll/remove.rb +11 -0
- data/lib/onyxcord/events/polls.rb +3 -116
- data/lib/onyxcord/events/presence/playing.rb +77 -0
- data/lib/onyxcord/events/presence/status.rb +60 -0
- data/lib/onyxcord/events/presence.rb +2 -129
- data/lib/onyxcord/events/raw/base.rb +74 -0
- data/lib/onyxcord/events/raw.rb +1 -72
- data/lib/onyxcord/events/reactions/base.rb +143 -0
- data/lib/onyxcord/events/reactions/clear.rb +99 -0
- data/lib/onyxcord/events/reactions.rb +2 -216
- data/lib/onyxcord/events/role/create.rb +46 -0
- data/lib/onyxcord/events/role/delete.rb +40 -0
- data/lib/onyxcord/events/role/update.rb +11 -0
- data/lib/onyxcord/events/roles.rb +3 -85
- data/lib/onyxcord/events/scheduled_events/events.rb +112 -0
- data/lib/onyxcord/events/scheduled_events/users.rb +91 -0
- data/lib/onyxcord/events/scheduled_events.rb +2 -169
- data/lib/onyxcord/events/thread/base.rb +49 -0
- data/lib/onyxcord/events/thread/members.rb +44 -0
- data/lib/onyxcord/events/thread/update.rb +18 -0
- data/lib/onyxcord/events/threads.rb +3 -98
- data/lib/onyxcord/events/typing/base.rb +73 -0
- data/lib/onyxcord/events/typing.rb +1 -71
- data/lib/onyxcord/events/voice/server_update.rb +48 -0
- data/lib/onyxcord/events/voice/state_update.rb +137 -0
- data/lib/onyxcord/events/voice_server_update.rb +2 -46
- data/lib/onyxcord/events/voice_state_update.rb +2 -135
- data/lib/onyxcord/events/webhook/update.rb +65 -0
- data/lib/onyxcord/events/webhooks.rb +1 -63
- data/lib/onyxcord/gateway/client.rb +460 -0
- data/lib/onyxcord/interactions/command.rb +120 -0
- data/lib/onyxcord/interactions/context.rb +109 -0
- data/lib/onyxcord/interactions/internal/application_command.rb +203 -0
- data/lib/onyxcord/interactions/internal/message.rb +152 -0
- data/lib/onyxcord/interactions/internal/metadata.rb +109 -0
- data/lib/onyxcord/interactions/internal/option_builder.rb +230 -0
- data/lib/onyxcord/interactions/internal/permission_builder.rb +90 -0
- data/lib/onyxcord/interactions/option.rb +88 -0
- data/lib/onyxcord/interactions/registry.rb +50 -0
- data/lib/onyxcord/interactions.rb +16 -0
- data/lib/onyxcord/internal/async_runtime.rb +32 -0
- data/lib/onyxcord/internal/event_bus.rb +591 -0
- data/lib/onyxcord/internal/event_executor.rb +155 -0
- data/lib/onyxcord/internal/gateway/opcodes.rb +22 -0
- data/lib/onyxcord/internal/gateway/session.rb +45 -0
- data/lib/onyxcord/internal/http.rb +189 -0
- data/lib/onyxcord/internal/json.rb +51 -0
- data/lib/onyxcord/{message_payload.rb → internal/message_payload.rb} +3 -3
- data/lib/onyxcord/internal/rate_limiter/async_rest.rb +151 -0
- data/lib/onyxcord/internal/rate_limiter/gateway.rb +44 -0
- data/lib/onyxcord/internal/rate_limiter/rest.rb +144 -0
- data/lib/onyxcord/internal/websocket.rb +79 -0
- data/lib/onyxcord/light/data.rb +1 -1
- data/lib/onyxcord/light/integrations.rb +1 -1
- data/lib/onyxcord/light/light_bot.rb +7 -7
- data/lib/onyxcord/{data → models}/activity.rb +2 -2
- data/lib/onyxcord/{data → models}/application.rb +3 -3
- data/lib/onyxcord/{data → models}/avatar_decoration.rb +1 -1
- data/lib/onyxcord/{data → models}/channel.rb +23 -23
- data/lib/onyxcord/{data → models}/collectibles.rb +1 -1
- data/lib/onyxcord/{data → models}/emoji.rb +1 -1
- data/lib/onyxcord/models/interaction.rb +450 -0
- data/lib/onyxcord/{data → models}/invite.rb +1 -1
- data/lib/onyxcord/{data → models}/member.rb +11 -11
- data/lib/onyxcord/{data → models}/message.rb +18 -14
- data/lib/onyxcord/{data → models}/poll.rb +2 -2
- data/lib/onyxcord/{data → models}/primary_server.rb +1 -1
- data/lib/onyxcord/{data → models}/profile.rb +4 -4
- data/lib/onyxcord/{data → models}/role.rb +6 -12
- data/lib/onyxcord/{data → models}/scheduled_event.rb +5 -5
- data/lib/onyxcord/{data → models}/server.rb +41 -41
- data/lib/onyxcord/{data → models}/server_preview.rb +2 -2
- data/lib/onyxcord/{data → models}/team.rb +1 -1
- data/lib/onyxcord/{data → models}/user.rb +5 -5
- data/lib/onyxcord/{data → models}/webhook.rb +10 -10
- data/lib/onyxcord/models.rb +57 -0
- data/lib/onyxcord/{api.rb → rest/client.rb} +23 -22
- data/lib/onyxcord/{api → rest/routes}/application.rb +79 -57
- data/lib/onyxcord/rest/routes/channel/base.rb +73 -0
- data/lib/onyxcord/rest/routes/channel/groups.rb +78 -0
- data/lib/onyxcord/rest/routes/channel/messages.rb +130 -0
- data/lib/onyxcord/rest/routes/channel/permissions.rb +73 -0
- data/lib/onyxcord/rest/routes/channel/pins.rb +45 -0
- data/lib/onyxcord/rest/routes/channel/polls.rb +32 -0
- data/lib/onyxcord/rest/routes/channel/reactions.rb +86 -0
- data/lib/onyxcord/rest/routes/channel/threads.rb +176 -0
- data/lib/onyxcord/rest/routes/channel/webhooks.rb +47 -0
- data/lib/onyxcord/rest/routes/channel.rb +12 -0
- data/lib/onyxcord/{api/interaction.rb → rest/routes/interaction/base.rb} +7 -25
- data/lib/onyxcord/rest/routes/interaction/response.rb +24 -0
- data/lib/onyxcord/rest/routes/interaction.rb +4 -0
- data/lib/onyxcord/{api → rest/routes}/invite.rb +7 -7
- data/lib/onyxcord/rest/routes/server/admin.rb +174 -0
- data/lib/onyxcord/rest/routes/server/assets.rb +25 -0
- data/lib/onyxcord/rest/routes/server/bans.rb +67 -0
- data/lib/onyxcord/rest/routes/server/base.rb +77 -0
- data/lib/onyxcord/rest/routes/server/channels.rb +58 -0
- data/lib/onyxcord/rest/routes/server/emoji.rb +48 -0
- data/lib/onyxcord/rest/routes/server/members.rb +109 -0
- data/lib/onyxcord/rest/routes/server/messages.rb +19 -0
- data/lib/onyxcord/rest/routes/server/roles.rb +156 -0
- data/lib/onyxcord/rest/routes/server/scheduled_events.rb +86 -0
- data/lib/onyxcord/rest/routes/server.rb +12 -0
- data/lib/onyxcord/{api → rest/routes}/user.rb +23 -23
- data/lib/onyxcord/{api → rest/routes}/webhook.rb +22 -22
- data/lib/onyxcord/{allowed_mentions.rb → utils/allowed_mentions.rb} +1 -1
- data/lib/onyxcord/utils/timestamp.rb +69 -0
- data/lib/onyxcord/voice/{voice_bot.rb → client.rb} +4 -4
- data/lib/onyxcord/voice/encoder.rb +1 -1
- data/lib/onyxcord/voice/network/udp.rb +135 -0
- data/lib/onyxcord/voice/network/websocket.rb +225 -0
- data/lib/onyxcord/voice/network.rb +5 -357
- data/lib/onyxcord/webhooks/builder.rb +1 -1
- data/lib/onyxcord/webhooks/client.rb +13 -13
- data/lib/onyxcord/webhooks/modal/group_builder.rb +55 -0
- data/lib/onyxcord/webhooks/modal/label_builder.rb +183 -0
- data/lib/onyxcord/webhooks/modal.rb +2 -239
- data/lib/onyxcord/webhooks/version.rb +3 -3
- data/lib/onyxcord/webhooks/view/container_builder.rb +80 -0
- data/lib/onyxcord/webhooks/view/file_builder.rb +24 -0
- data/lib/onyxcord/webhooks/view/media_gallery_builder.rb +50 -0
- data/lib/onyxcord/webhooks/view/row_builder.rb +120 -0
- data/lib/onyxcord/webhooks/view/section_builder.rb +61 -0
- data/lib/onyxcord/webhooks/view/select_menu_builder.rb +77 -0
- data/lib/onyxcord/webhooks/view/separator_builder.rb +22 -0
- data/lib/onyxcord/webhooks/view/text_display_builder.rb +20 -0
- data/lib/onyxcord/webhooks/view.rb +9 -425
- data/lib/onyxcord.rb +106 -42
- metadata +207 -92
- data/.github/CONTRIBUTING.md +0 -13
- data/.github/ISSUE_TEMPLATE/bug_report.md +0 -38
- data/.github/ISSUE_TEMPLATE/feature_request.md +0 -24
- data/.github/pull_request_template.md +0 -37
- data/.github/workflows/ci.yml +0 -78
- data/.github/workflows/codeql.yml +0 -65
- data/.github/workflows/deploy.yml +0 -54
- data/.github/workflows/release.yml +0 -51
- data/.gitignore +0 -17
- data/.markdownlint.json +0 -4
- data/.overcommit.yml +0 -7
- data/.rspec +0 -2
- data/.rubocop.yml +0 -129
- data/.yardopts +0 -1
- data/CHANGELOG.md +0 -257
- data/Gemfile +0 -6
- data/LICENSE.txt +0 -21
- data/README.md +0 -448
- data/Rakefile +0 -13
- data/lib/onyxcord/api/channel.rb +0 -703
- data/lib/onyxcord/api/server.rb +0 -775
- data/lib/onyxcord/async/runtime.rb +0 -30
- data/lib/onyxcord/commands/command_bot.rb +0 -505
- data/lib/onyxcord/data/interaction.rb +0 -1151
- data/lib/onyxcord/data.rb +0 -57
- data/lib/onyxcord/event_executor.rb +0 -153
- data/lib/onyxcord/gateway.rb +0 -505
- data/lib/onyxcord/http.rb +0 -186
- data/lib/onyxcord/json.rb +0 -49
- data/lib/onyxcord/rate_limiter/async_rest.rb +0 -150
- data/lib/onyxcord/rate_limiter/gateway.rb +0 -42
- data/lib/onyxcord/rate_limiter/rest.rb +0 -142
- data/lib/onyxcord/version.rb +0 -7
- data/lib/onyxcord/websocket.rb +0 -77
- data/onyxcord.gemspec +0 -63
- /data/lib/onyxcord/{configuration.rb → core/configuration.rb} +0 -0
- /data/lib/onyxcord/{errors.rb → core/errors.rb} +0 -0
- /data/lib/onyxcord/{upload.rb → internal/upload.rb} +0 -0
- /data/lib/onyxcord/{data → models}/attachment.rb +0 -0
- /data/lib/onyxcord/{data → models}/audit_logs.rb +0 -0
- /data/lib/onyxcord/{data → models}/call.rb +0 -0
- /data/lib/onyxcord/{data → models}/channel_tag.rb +0 -0
- /data/lib/onyxcord/{data → models}/component.rb +0 -0
- /data/lib/onyxcord/{data → models}/embed.rb +0 -0
- /data/lib/onyxcord/{data → models}/install_params.rb +0 -0
- /data/lib/onyxcord/{data → models}/integration.rb +0 -0
- /data/lib/onyxcord/{data → models}/message_activity.rb +0 -0
- /data/lib/onyxcord/{data → models}/overwrite.rb +0 -0
- /data/lib/onyxcord/{data → models}/reaction.rb +0 -0
- /data/lib/onyxcord/{data → models}/recipient.rb +0 -0
- /data/lib/onyxcord/{data → models}/role_connection_data.rb +0 -0
- /data/lib/onyxcord/{data → models}/role_subscription.rb +0 -0
- /data/lib/onyxcord/{data → models}/snapshot.rb +0 -0
- /data/lib/onyxcord/{data → models}/timestamp.rb +0 -0
- /data/lib/onyxcord/{data → models}/voice_region.rb +0 -0
- /data/lib/onyxcord/{data → models}/voice_state.rb +0 -0
- /data/lib/onyxcord/{colour_rgb.rb → utils/colour_rgb.rb} +0 -0
- /data/lib/onyxcord/{id_object.rb → utils/id_object.rb} +0 -0
- /data/lib/onyxcord/{message_components.rb → utils/message_components.rb} +0 -0
- /data/lib/onyxcord/{paginator.rb → utils/paginator.rb} +0 -0
- /data/lib/onyxcord/{permissions.rb → utils/permissions.rb} +0 -0
|
@@ -0,0 +1,144 @@
|
|
|
1
|
+
# frozen_string_literal: true
|
|
2
|
+
|
|
3
|
+
require_relative '../json'
|
|
4
|
+
|
|
5
|
+
module OnyxCord
|
|
6
|
+
module Internal
|
|
7
|
+
module RateLimiter
|
|
8
|
+
# Discord REST rate limiter keyed by route/major parameter and remapped to
|
|
9
|
+
# X-RateLimit-Bucket whenever Discord returns a concrete bucket id.
|
|
10
|
+
class Rest
|
|
11
|
+
DEFAULT_ENTRY_TTL = 3600
|
|
12
|
+
DEFAULT_PRUNE_INTERVAL = 100
|
|
13
|
+
|
|
14
|
+
def initialize(clock: -> { Time.now }, entry_ttl: DEFAULT_ENTRY_TTL, prune_interval: DEFAULT_PRUNE_INTERVAL)
|
|
15
|
+
@route_buckets = {}
|
|
16
|
+
@bucket_mutexes = {}
|
|
17
|
+
@bucket_last_used = {}
|
|
18
|
+
@global_mutex = Mutex.new
|
|
19
|
+
@clock = clock
|
|
20
|
+
@entry_ttl = entry_ttl
|
|
21
|
+
@prune_interval = prune_interval
|
|
22
|
+
@requests_since_prune = 0
|
|
23
|
+
end
|
|
24
|
+
|
|
25
|
+
def before_request(route, major_parameter)
|
|
26
|
+
mutex_wait(mutex_for(route, major_parameter))
|
|
27
|
+
mutex_wait(@global_mutex) if @global_mutex.locked?
|
|
28
|
+
end
|
|
29
|
+
|
|
30
|
+
def record_response(route, major_parameter, headers)
|
|
31
|
+
headers = normalize_headers(headers)
|
|
32
|
+
bucket = headers[:x_ratelimit_bucket]
|
|
33
|
+
key = route_key(route, major_parameter)
|
|
34
|
+
touch(key)
|
|
35
|
+
|
|
36
|
+
if bucket
|
|
37
|
+
bucket = bucket_key(bucket, major_parameter)
|
|
38
|
+
@route_buckets[key] = bucket
|
|
39
|
+
touch(bucket)
|
|
40
|
+
end
|
|
41
|
+
|
|
42
|
+
return unless headers[:x_ratelimit_remaining] == '0'
|
|
43
|
+
|
|
44
|
+
wait_seconds = headers[:x_ratelimit_reset_after].to_f
|
|
45
|
+
return unless wait_seconds.positive?
|
|
46
|
+
|
|
47
|
+
sync_wait(wait_seconds, mutex_for(route, major_parameter))
|
|
48
|
+
end
|
|
49
|
+
|
|
50
|
+
def handle_rate_limit(route, major_parameter, response)
|
|
51
|
+
headers = normalize_headers(response.headers)
|
|
52
|
+
mutex = headers[:x_ratelimit_global] == 'true' || headers[:x_ratelimit_scope] == 'global' ? @global_mutex : mutex_for(route, major_parameter)
|
|
53
|
+
wait_seconds = retry_after(response, headers)
|
|
54
|
+
|
|
55
|
+
sync_wait(wait_seconds, mutex) if wait_seconds.positive?
|
|
56
|
+
end
|
|
57
|
+
|
|
58
|
+
def stats
|
|
59
|
+
{
|
|
60
|
+
route_buckets: @route_buckets.size,
|
|
61
|
+
bucket_mutexes: @bucket_mutexes.size,
|
|
62
|
+
tracked_keys: @bucket_last_used.size
|
|
63
|
+
}
|
|
64
|
+
end
|
|
65
|
+
|
|
66
|
+
def prune!
|
|
67
|
+
return 0 unless @entry_ttl
|
|
68
|
+
|
|
69
|
+
cutoff = @clock.call - @entry_ttl
|
|
70
|
+
stale_keys = @bucket_last_used.select { |_, last_used| last_used < cutoff }.keys
|
|
71
|
+
|
|
72
|
+
stale_keys.each do |key|
|
|
73
|
+
@bucket_mutexes.delete(key)
|
|
74
|
+
@bucket_last_used.delete(key)
|
|
75
|
+
@route_buckets.delete(key)
|
|
76
|
+
@route_buckets.delete_if { |_, bucket_key| bucket_key == key }
|
|
77
|
+
end
|
|
78
|
+
|
|
79
|
+
@requests_since_prune = 0
|
|
80
|
+
stale_keys.length
|
|
81
|
+
end
|
|
82
|
+
|
|
83
|
+
private
|
|
84
|
+
|
|
85
|
+
def mutex_for(route, major_parameter)
|
|
86
|
+
key = resolved_key(route, major_parameter)
|
|
87
|
+
touch(key)
|
|
88
|
+
@bucket_mutexes[key] ||= Mutex.new
|
|
89
|
+
end
|
|
90
|
+
|
|
91
|
+
def resolved_key(route, major_parameter)
|
|
92
|
+
@route_buckets[route_key(route, major_parameter)] || route_key(route, major_parameter)
|
|
93
|
+
end
|
|
94
|
+
|
|
95
|
+
def route_key(route, major_parameter)
|
|
96
|
+
[route, major_parameter].freeze
|
|
97
|
+
end
|
|
98
|
+
|
|
99
|
+
def bucket_key(bucket, major_parameter)
|
|
100
|
+
[:bucket, bucket, major_parameter].freeze
|
|
101
|
+
end
|
|
102
|
+
|
|
103
|
+
def retry_after(response, headers)
|
|
104
|
+
body = response.respond_to?(:body) ? response.body : response.to_s
|
|
105
|
+
if body && !body.empty?
|
|
106
|
+
data = JSON.parse(body)
|
|
107
|
+
return data['retry_after'].to_f if data['retry_after']
|
|
108
|
+
end
|
|
109
|
+
|
|
110
|
+
(headers[:retry_after] || 0).to_f
|
|
111
|
+
rescue JSON::ParserError
|
|
112
|
+
(headers[:retry_after] || 0).to_f
|
|
113
|
+
end
|
|
114
|
+
|
|
115
|
+
def normalize_headers(headers)
|
|
116
|
+
headers.each_with_object({}) do |(key, value), memo|
|
|
117
|
+
memo[key.to_s.tr('-', '_').downcase.to_sym] = value.to_s
|
|
118
|
+
end
|
|
119
|
+
end
|
|
120
|
+
|
|
121
|
+
def touch(key)
|
|
122
|
+
@bucket_last_used[key] = @clock.call
|
|
123
|
+
prune_if_needed
|
|
124
|
+
end
|
|
125
|
+
|
|
126
|
+
def prune_if_needed
|
|
127
|
+
return unless @prune_interval
|
|
128
|
+
|
|
129
|
+
@requests_since_prune += 1
|
|
130
|
+
prune! if @requests_since_prune >= @prune_interval
|
|
131
|
+
end
|
|
132
|
+
|
|
133
|
+
def sync_wait(time, mutex)
|
|
134
|
+
mutex.synchronize { sleep time }
|
|
135
|
+
end
|
|
136
|
+
|
|
137
|
+
def mutex_wait(mutex)
|
|
138
|
+
mutex.lock
|
|
139
|
+
mutex.unlock
|
|
140
|
+
end
|
|
141
|
+
end
|
|
142
|
+
end
|
|
143
|
+
end
|
|
144
|
+
end
|
|
@@ -0,0 +1,79 @@
|
|
|
1
|
+
# frozen_string_literal: true
|
|
2
|
+
|
|
3
|
+
require_relative 'async_runtime'
|
|
4
|
+
require 'async/http/endpoint'
|
|
5
|
+
require 'async/http/protocol/http11'
|
|
6
|
+
require 'async/websocket/client'
|
|
7
|
+
|
|
8
|
+
module OnyxCord
|
|
9
|
+
module Internal
|
|
10
|
+
class WebSocket
|
|
11
|
+
attr_reader :connected
|
|
12
|
+
|
|
13
|
+
alias_method :connected?, :connected
|
|
14
|
+
|
|
15
|
+
def initialize(host, open_handler, message_handler, error_handler, close_handler)
|
|
16
|
+
@host = host
|
|
17
|
+
@open_handler = open_handler
|
|
18
|
+
@message_handler = message_handler
|
|
19
|
+
@error_handler = error_handler
|
|
20
|
+
@close_handler = close_handler
|
|
21
|
+
|
|
22
|
+
@connection = nil
|
|
23
|
+
@connected = false
|
|
24
|
+
|
|
25
|
+
connect
|
|
26
|
+
end
|
|
27
|
+
|
|
28
|
+
def send(data)
|
|
29
|
+
return unless @connection
|
|
30
|
+
|
|
31
|
+
data = data.to_json if data.is_a?(Hash)
|
|
32
|
+
@connection.write(Protocol::WebSocket::TextMessage.generate(data))
|
|
33
|
+
@connection.flush
|
|
34
|
+
rescue StandardError => e
|
|
35
|
+
@error_handler&.call(e)
|
|
36
|
+
end
|
|
37
|
+
|
|
38
|
+
def close
|
|
39
|
+
@connected = false
|
|
40
|
+
@connection&.close
|
|
41
|
+
rescue StandardError
|
|
42
|
+
# Ignore errors on close
|
|
43
|
+
end
|
|
44
|
+
|
|
45
|
+
private
|
|
46
|
+
|
|
47
|
+
def connect
|
|
48
|
+
endpoint = websocket_endpoint(@host)
|
|
49
|
+
|
|
50
|
+
@task = AsyncRuntime.async do
|
|
51
|
+
Async::WebSocket::Client.connect(endpoint, extensions: nil) do |connection|
|
|
52
|
+
@connection = connection
|
|
53
|
+
@connected = true
|
|
54
|
+
@open_handler&.call
|
|
55
|
+
|
|
56
|
+
while (message = connection.read)
|
|
57
|
+
@message_handler&.call(message.to_str)
|
|
58
|
+
end
|
|
59
|
+
rescue StandardError => e
|
|
60
|
+
@error_handler&.call(e)
|
|
61
|
+
ensure
|
|
62
|
+
@connected = false
|
|
63
|
+
@close_handler&.call(nil)
|
|
64
|
+
end
|
|
65
|
+
end
|
|
66
|
+
rescue StandardError => e
|
|
67
|
+
@error_handler&.call(e)
|
|
68
|
+
end
|
|
69
|
+
|
|
70
|
+
def websocket_endpoint(url)
|
|
71
|
+
Async::HTTP::Endpoint.parse(
|
|
72
|
+
url,
|
|
73
|
+
protocol: Async::HTTP::Protocol::HTTP11,
|
|
74
|
+
alpn_protocols: ['http/1.1']
|
|
75
|
+
)
|
|
76
|
+
end
|
|
77
|
+
end
|
|
78
|
+
end
|
|
79
|
+
end
|
data/lib/onyxcord/light/data.rb
CHANGED
|
@@ -1,8 +1,8 @@
|
|
|
1
1
|
# frozen_string_literal: true
|
|
2
2
|
|
|
3
|
-
require 'onyxcord/
|
|
4
|
-
require 'onyxcord/
|
|
5
|
-
require 'onyxcord/
|
|
3
|
+
require 'onyxcord/rest/client'
|
|
4
|
+
require 'onyxcord/rest/routes/invite'
|
|
5
|
+
require 'onyxcord/rest/routes/user'
|
|
6
6
|
require 'onyxcord/light/data'
|
|
7
7
|
require 'onyxcord/light/integrations'
|
|
8
8
|
|
|
@@ -31,13 +31,13 @@ module OnyxCord::Light
|
|
|
31
31
|
|
|
32
32
|
# @return [LightProfile] the details of the user this bot is connected to.
|
|
33
33
|
def profile
|
|
34
|
-
response = OnyxCord::
|
|
34
|
+
response = OnyxCord::REST::User.profile(@token)
|
|
35
35
|
LightProfile.new(JSON.parse(response), self)
|
|
36
36
|
end
|
|
37
37
|
|
|
38
38
|
# @return [Array<LightServer>] the servers this bot is connected to.
|
|
39
39
|
def servers
|
|
40
|
-
response = OnyxCord::
|
|
40
|
+
response = OnyxCord::REST::User.servers(@token)
|
|
41
41
|
JSON.parse(response).map { |e| LightServer.new(e, self) }
|
|
42
42
|
end
|
|
43
43
|
|
|
@@ -45,13 +45,13 @@ module OnyxCord::Light
|
|
|
45
45
|
# @param code [String] The code part of the invite (for example 0cDvIgU2voWn4BaD if the invite URL is
|
|
46
46
|
# https://discord.gg/0cDvIgU2voWn4BaD)
|
|
47
47
|
def join(code)
|
|
48
|
-
OnyxCord::
|
|
48
|
+
OnyxCord::REST::Invite.accept(@token, code)
|
|
49
49
|
end
|
|
50
50
|
|
|
51
51
|
# Gets the connections associated with this account.
|
|
52
52
|
# @return [Array<Connection>] this account's connections.
|
|
53
53
|
def connections
|
|
54
|
-
response = OnyxCord::
|
|
54
|
+
response = OnyxCord::REST::User.connections(@token)
|
|
55
55
|
JSON.parse(response).map { |e| Connection.new(e, self) }
|
|
56
56
|
end
|
|
57
57
|
end
|
|
@@ -188,14 +188,14 @@ module OnyxCord
|
|
|
188
188
|
# @param format [String, nil] If `nil`, the URL will default to `webp`. You can otherwise specify one of `webp`, `jpg`, or `png`.
|
|
189
189
|
# @return [String] the URL to the large image asset.
|
|
190
190
|
def large_image_url(format = 'webp')
|
|
191
|
-
|
|
191
|
+
REST.asset_url(@application_id, @large_image_id, format)
|
|
192
192
|
end
|
|
193
193
|
|
|
194
194
|
# Utility function to get an Asset's large image URL.
|
|
195
195
|
# @param format [String, nil] If `nil`, the URL will default to `webp`. You can otherwise specify one of `webp`, `jpg`, or `png`.
|
|
196
196
|
# @return [String] the URL to the small image asset.
|
|
197
197
|
def small_image_url(format = 'webp')
|
|
198
|
-
|
|
198
|
+
REST.asset_url(@application_id, @small_image_id, format)
|
|
199
199
|
end
|
|
200
200
|
end
|
|
201
201
|
|
|
@@ -131,14 +131,14 @@ module OnyxCord
|
|
|
131
131
|
# @param format [String] The URL will default to `webp`. You can otherwise specify one of `webp`, `jpg` or `png` to override this.
|
|
132
132
|
# @return [String, nil] The URL of the icon image (`nil` if no image is set).
|
|
133
133
|
def icon_url(format: 'webp')
|
|
134
|
-
|
|
134
|
+
REST.app_icon_url(@id, @icon_id, format) if @icon_id
|
|
135
135
|
end
|
|
136
136
|
|
|
137
137
|
# Utility method to get a application's cover image URL.
|
|
138
138
|
# @param format [String] The URL will default to `webp`. You can otherwise specify one of `webp`, `jpg` or `png` to override this.
|
|
139
139
|
# @return [String, nil] The URL of the cover image (`nil` if no cover is set).
|
|
140
140
|
def cover_image_url(format: 'webp')
|
|
141
|
-
|
|
141
|
+
REST.app_cover_url(@id, @cover_image_id, format) if @cover_image_id
|
|
142
142
|
end
|
|
143
143
|
|
|
144
144
|
# Delete an integration types config for the application.
|
|
@@ -236,7 +236,7 @@ module OnyxCord
|
|
|
236
236
|
data[:flags] = ((@flags & ~to_flags.call(remove_flags)) | to_flags.call(add_flags))
|
|
237
237
|
end
|
|
238
238
|
|
|
239
|
-
update_data(JSON.parse(
|
|
239
|
+
update_data(JSON.parse(REST::Application.update_current_application(@bot.token, **data)))
|
|
240
240
|
nil
|
|
241
241
|
end
|
|
242
242
|
|
|
@@ -1,7 +1,7 @@
|
|
|
1
1
|
# frozen_string_literal: true
|
|
2
2
|
|
|
3
3
|
require 'onyxcord/webhooks/view'
|
|
4
|
-
require 'onyxcord/message_components'
|
|
4
|
+
require 'onyxcord/utils/message_components'
|
|
5
5
|
require 'time'
|
|
6
6
|
|
|
7
7
|
module OnyxCord
|
|
@@ -412,7 +412,7 @@ module OnyxCord
|
|
|
412
412
|
move_argument << hash
|
|
413
413
|
end
|
|
414
414
|
|
|
415
|
-
|
|
415
|
+
REST::Server.update_channel_positions(@bot.token, @server_id, move_argument)
|
|
416
416
|
end
|
|
417
417
|
|
|
418
418
|
# Check if this channel is marked as NSFW.
|
|
@@ -667,13 +667,13 @@ module OnyxCord
|
|
|
667
667
|
# Deletes a message on this channel. Mostly useful in case a message needs to be deleted when only the ID is known
|
|
668
668
|
# @param message [Message, String, Integer, String, Integer] The message, or its ID, that should be deleted.
|
|
669
669
|
def delete_message(message)
|
|
670
|
-
|
|
670
|
+
REST::Channel.delete_message(@bot.token, @id, message.resolve_id)
|
|
671
671
|
end
|
|
672
672
|
|
|
673
673
|
# Permanently deletes this channel
|
|
674
674
|
# @param reason [String] The reason the for the channel deletion.
|
|
675
675
|
def delete(reason = nil)
|
|
676
|
-
|
|
676
|
+
REST::Channel.delete(@bot.token, @id, reason)
|
|
677
677
|
end
|
|
678
678
|
|
|
679
679
|
# Sets this channel's name. The name must be alphanumeric with dashes, unless this is a voice channel (then there are no limitations)
|
|
@@ -743,7 +743,7 @@ module OnyxCord
|
|
|
743
743
|
thing = Overwrite.new(thing, allow: allow_bits, deny: deny_bits)
|
|
744
744
|
end
|
|
745
745
|
|
|
746
|
-
|
|
746
|
+
REST::Channel.update_permission(@bot.token, @id, thing.id, thing.allow.bits, thing.deny.bits, thing.type, reason)
|
|
747
747
|
end
|
|
748
748
|
|
|
749
749
|
# Deletes a permission overwrite for this channel
|
|
@@ -752,7 +752,7 @@ module OnyxCord
|
|
|
752
752
|
def delete_overwrite(target, reason = nil)
|
|
753
753
|
raise 'Tried deleting a overwrite for an invalid target' unless target.respond_to?(:resolve_id)
|
|
754
754
|
|
|
755
|
-
|
|
755
|
+
REST::Channel.delete_permission(@bot.token, @id, target.resolve_id, reason)
|
|
756
756
|
end
|
|
757
757
|
|
|
758
758
|
# The list of users currently in this channel. For a voice channel, it will return all the members currently
|
|
@@ -780,7 +780,7 @@ module OnyxCord
|
|
|
780
780
|
# last_ten_messages = channel.history(10, message.id)
|
|
781
781
|
# @return [Array<Message>] the retrieved messages.
|
|
782
782
|
def history(amount, before_id = nil, after_id = nil, around_id = nil)
|
|
783
|
-
logs =
|
|
783
|
+
logs = REST::Channel.messages(@bot.token, @id, amount, before_id, after_id, around_id)
|
|
784
784
|
JSON.parse(logs).map { |message| Message.new(message, @bot) }
|
|
785
785
|
end
|
|
786
786
|
|
|
@@ -788,7 +788,7 @@ module OnyxCord
|
|
|
788
788
|
# @note For internal use only
|
|
789
789
|
# @!visibility private
|
|
790
790
|
def history_ids(amount, before_id = nil, after_id = nil, around_id = nil)
|
|
791
|
-
logs =
|
|
791
|
+
logs = REST::Channel.messages(@bot.token, @id, amount, before_id, after_id, around_id)
|
|
792
792
|
JSON.parse(logs).map { |message| message['id'].to_i }
|
|
793
793
|
end
|
|
794
794
|
|
|
@@ -798,7 +798,7 @@ module OnyxCord
|
|
|
798
798
|
def load_message(message_id)
|
|
799
799
|
raise ArgumentError, 'message_id cannot be nil' if message_id.nil?
|
|
800
800
|
|
|
801
|
-
response =
|
|
801
|
+
response = REST::Channel.message(@bot.token, @id, message_id)
|
|
802
802
|
Message.new(JSON.parse(response), @bot)
|
|
803
803
|
rescue OnyxCord::Errors::UnknownMessage
|
|
804
804
|
nil
|
|
@@ -811,7 +811,7 @@ module OnyxCord
|
|
|
811
811
|
# @return [Array<Message>] the messages pinned in the channel.
|
|
812
812
|
def pins(limit: 50)
|
|
813
813
|
get_pins = proc do |fetch_limit, before = nil|
|
|
814
|
-
resp =
|
|
814
|
+
resp = REST::Channel.pinned_messages(@bot.token, @id, fetch_limit, before&.iso8601)
|
|
815
815
|
JSON.parse(resp)['items'].map { |pin| Message.new(pin['message'].merge({ 'pinned_at' => pin['pinned_at'] }), @bot) }
|
|
816
816
|
end
|
|
817
817
|
|
|
@@ -853,7 +853,7 @@ module OnyxCord
|
|
|
853
853
|
when 0
|
|
854
854
|
0
|
|
855
855
|
when 1
|
|
856
|
-
|
|
856
|
+
REST::Channel.delete_message(@bot.token, @id, messages.first, reason)
|
|
857
857
|
1
|
|
858
858
|
else
|
|
859
859
|
bulk_delete(messages, strict, reason)
|
|
@@ -904,7 +904,7 @@ module OnyxCord
|
|
|
904
904
|
# @param reason [String] The reason the for the creation of this invite.
|
|
905
905
|
# @return [Invite] the created invite.
|
|
906
906
|
def make_invite(max_age = 0, max_uses = 0, temporary = false, unique = false, reason = nil)
|
|
907
|
-
response =
|
|
907
|
+
response = REST::Channel.create_invite(@bot.token, @id, max_age, max_uses, temporary, unique, reason)
|
|
908
908
|
Invite.new(JSON.parse(response), @bot)
|
|
909
909
|
end
|
|
910
910
|
|
|
@@ -916,7 +916,7 @@ module OnyxCord
|
|
|
916
916
|
# @example Send a typing indicator for the bot in a given channel.
|
|
917
917
|
# channel.start_typing()
|
|
918
918
|
def start_typing
|
|
919
|
-
|
|
919
|
+
REST::Channel.start_typing(@bot.token, @id)
|
|
920
920
|
end
|
|
921
921
|
|
|
922
922
|
# Creates a webhook in this channel
|
|
@@ -928,7 +928,7 @@ module OnyxCord
|
|
|
928
928
|
def create_webhook(name, avatar = nil, reason = nil)
|
|
929
929
|
raise ArgumentError, 'Tried to create a webhook in a non-server channel' unless server
|
|
930
930
|
|
|
931
|
-
response =
|
|
931
|
+
response = REST::Channel.create_webhook(@bot.token, @id, name, avatar, reason)
|
|
932
932
|
Webhook.new(JSON.parse(response), @bot)
|
|
933
933
|
end
|
|
934
934
|
|
|
@@ -937,7 +937,7 @@ module OnyxCord
|
|
|
937
937
|
def webhooks
|
|
938
938
|
raise 'Tried to request webhooks from a non-server channel' unless server
|
|
939
939
|
|
|
940
|
-
webhooks = JSON.parse(
|
|
940
|
+
webhooks = JSON.parse(REST::Channel.webhooks(@bot.token, @id))
|
|
941
941
|
webhooks.map { |webhook_data| Webhook.new(webhook_data, @bot) }
|
|
942
942
|
end
|
|
943
943
|
|
|
@@ -946,7 +946,7 @@ module OnyxCord
|
|
|
946
946
|
def invites
|
|
947
947
|
raise 'Tried to request invites from a non-server channel' unless server
|
|
948
948
|
|
|
949
|
-
invites = JSON.parse(
|
|
949
|
+
invites = JSON.parse(REST::Channel.invites(@bot.token, @id))
|
|
950
950
|
invites.map { |invite_data| Invite.new(invite_data, @bot) }
|
|
951
951
|
end
|
|
952
952
|
|
|
@@ -957,7 +957,7 @@ module OnyxCord
|
|
|
957
957
|
def follow(target, reason: nil)
|
|
958
958
|
raise 'Cannot follow a non-announcement channel' unless news?
|
|
959
959
|
|
|
960
|
-
JSON.parse(
|
|
960
|
+
JSON.parse(REST::Channel.follow_channel(@bot.token, @id, target.resolve_id, reason))['webhook_id'].to_i
|
|
961
961
|
end
|
|
962
962
|
|
|
963
963
|
# Returns the last message or forum post created in this channel.
|
|
@@ -985,9 +985,9 @@ module OnyxCord
|
|
|
985
985
|
type = TYPES[type] || type
|
|
986
986
|
|
|
987
987
|
data = if message
|
|
988
|
-
|
|
988
|
+
REST::Channel.start_thread_with_message(@bot.token, @id, message_id, name, auto_archive_duration)
|
|
989
989
|
else
|
|
990
|
-
|
|
990
|
+
REST::Channel.start_thread_without_message(@bot.token, @id, name, auto_archive_duration, type)
|
|
991
991
|
end
|
|
992
992
|
|
|
993
993
|
@bot.ensure_channel(JSON.parse(data))
|
|
@@ -1026,7 +1026,7 @@ module OnyxCord
|
|
|
1026
1026
|
builder = builder.to_json_hash
|
|
1027
1027
|
|
|
1028
1028
|
message = { content: builder[:content], embeds: builder[:embeds], allowed_mentions: builder[:allowed_mentions], components: components, sticker_ids: stickers&.map(&:resolve_id), flags: flags }
|
|
1029
|
-
response = JSON.parse(
|
|
1029
|
+
response = JSON.parse(REST::Channel.start_thread_in_forum_or_media_channel(@bot.token, @id, name, message.compact, attachments, rate_limit_per_user, auto_archive_duration, tags&.map(&:resolve_id), reason))
|
|
1030
1030
|
|
|
1031
1031
|
Message.new(response['message'].merge!('channel_id' => response['id'], 'thread' => response), @bot)
|
|
1032
1032
|
end
|
|
@@ -1207,7 +1207,7 @@ module OnyxCord
|
|
|
1207
1207
|
data[:flags] = ((@flags & ~to_flags.call(remove_flags)) | to_flags.call(add_flags))
|
|
1208
1208
|
end
|
|
1209
1209
|
|
|
1210
|
-
update_data(JSON.parse(
|
|
1210
|
+
update_data(JSON.parse(REST::Channel.update!(@bot.token, @id, **data, reason: reason)))
|
|
1211
1211
|
nil
|
|
1212
1212
|
end
|
|
1213
1213
|
|
|
@@ -1249,7 +1249,7 @@ module OnyxCord
|
|
|
1249
1249
|
# @note For internal use only
|
|
1250
1250
|
# @!visibility private
|
|
1251
1251
|
def update_data(new_data = nil)
|
|
1252
|
-
new_data ||= JSON.parse(
|
|
1252
|
+
new_data ||= JSON.parse(REST::Channel.resolve(@bot.token, @id))
|
|
1253
1253
|
@type = new_data['type'] || 0
|
|
1254
1254
|
@topic = new_data['topic']
|
|
1255
1255
|
@bitrate = new_data['bitrate']
|
|
@@ -1316,7 +1316,7 @@ module OnyxCord
|
|
|
1316
1316
|
true
|
|
1317
1317
|
end
|
|
1318
1318
|
|
|
1319
|
-
|
|
1319
|
+
REST::Channel.bulk_delete_messages(@bot.token, @id, ids, reason)
|
|
1320
1320
|
ids.size
|
|
1321
1321
|
end
|
|
1322
1322
|
|
|
@@ -40,7 +40,7 @@ module OnyxCord
|
|
|
40
40
|
# nameplate instead of the animated URL.
|
|
41
41
|
# @return [String] The CDN url of this nameplate.
|
|
42
42
|
def url(static: false)
|
|
43
|
-
static ?
|
|
43
|
+
static ? REST.static_nameplate_url(@asset) : REST.nameplate_url(@asset)
|
|
44
44
|
end
|
|
45
45
|
end
|
|
46
46
|
end
|