advanced_ruby_command_handler 0.1.5 → 2.0.1

Sign up to get free protection for your applications and to get access to all the features.
Files changed (37) hide show
  1. checksums.yaml +4 -4
  2. data/.github/workflows/ruby.yml +5 -30
  3. data/.gitignore +3 -1
  4. data/Gemfile +8 -0
  5. data/Gemfile.lock +21 -12
  6. data/README.md +28 -18
  7. data/lib/advanced_ruby_command_handler/base.rb +51 -0
  8. data/lib/advanced_ruby_command_handler/client.rb +20 -0
  9. data/lib/advanced_ruby_command_handler/command.rb +65 -0
  10. data/lib/advanced_ruby_command_handler/command_handler.rb +76 -0
  11. data/lib/advanced_ruby_command_handler/database.rb +16 -0
  12. data/lib/advanced_ruby_command_handler/defaults/events/message.rb +17 -0
  13. data/lib/advanced_ruby_command_handler/errors.rb +48 -0
  14. data/lib/advanced_ruby_command_handler/event.rb +9 -0
  15. data/lib/advanced_ruby_command_handler/logger.rb +38 -0
  16. data/lib/advanced_ruby_command_handler/utils.rb +9 -0
  17. data/lib/advanced_ruby_command_handler/version.rb +5 -5
  18. data/lib/advanced_ruby_command_handler.rb +12 -15
  19. data/sig/lib/advanced_ruby_command_handler/base.rbs +21 -0
  20. data/sig/lib/advanced_ruby_command_handler/database.rbs +7 -0
  21. data/sig/lib/advanced_ruby_command_handler/errors.rbs +19 -0
  22. data/tests/index.rb +17 -2
  23. data/tests/src/commands/tests/test.rb +13 -0
  24. data/tests/src/events/ready.rb +9 -0
  25. metadata +17 -14
  26. data/lib/advanced_ruby_command_handler/app/app.rb +0 -7
  27. data/lib/advanced_ruby_command_handler/app/client.rb +0 -63
  28. data/lib/advanced_ruby_command_handler/app/command.rb +0 -55
  29. data/lib/advanced_ruby_command_handler/app/command_handler.rb +0 -25
  30. data/lib/advanced_ruby_command_handler/app/defaults/events/message.rb +0 -24
  31. data/lib/advanced_ruby_command_handler/app/defaults/events/ready.rb +0 -9
  32. data/lib/advanced_ruby_command_handler/app/event_handler.rb +0 -27
  33. data/lib/advanced_ruby_command_handler/app/logger.rb +0 -62
  34. data/lib/advanced_ruby_command_handler/app/utils.rb +0 -19
  35. data/tests/commands/test/test.rb +0 -19
  36. data/tests/config.yml +0 -4
  37. data/tests/events/ready.rb +0 -9
checksums.yaml CHANGED
@@ -1,7 +1,7 @@
1
1
  ---
2
2
  SHA256:
3
- metadata.gz: b97941216c2de5b7a5c5eac1d8613b3fb6e0670e2c52e9efb01337ab7d9be3ff
4
- data.tar.gz: 1d11b79ca18ebb54e0fd7463e359955e005b022c326866a412cbe491d757e759
3
+ metadata.gz: a11ba24daab81b761181e660e6dbec31f61e66f60e9921ae88ed025ff428dc6f
4
+ data.tar.gz: 63c1cf7eaf789454969ef8e7340573c11bc81c42a10de4381bf06524aaaccd61
5
5
  SHA512:
6
- metadata.gz: 5ba9dca758046935b6fe4e888401eda55575461325d76fe5afbac37037de4c2b84f52f0d9ce9aa8004b121a7e2b8b3ae7e00a8c9aa7c601fa05d99a5c0176de7
7
- data.tar.gz: e21cd5ddac2ad88a7604eac57fa1b0919f723ef995d44758322053339a03820013ba05b7e72103fec3f5979c89942a1569c96950445bb29e924fcdfc5d4053b7
6
+ metadata.gz: ff38ee1aa4a2d6a1bb6a11ae8b791f626746ca87bf68787e2d3da82ca549c1401de947c8ee952ca45030b098cdba81295e83bd5daae97ff4447a53ab1b95f87f
7
+ data.tar.gz: c450efad33bc9ee1070d3658dca1aa2297f0d69da7da99021ba83c3a865766819a6f52a018251cf1ff4ddd1c95aa0c44ef2d805e29f41d8363d653454600940b
@@ -1,37 +1,12 @@
1
- # This workflow uses actions that are not certified by GitHub.
2
- # They are provided by a third-party and are governed by
3
- # separate terms of service, privacy policy, and support
4
- # documentation.
5
- # This workflow will download a prebuilt Ruby version, install dependencies and run tests with Rake
6
- # For more information see: https://github.com/marketplace/actions/setup-ruby-jruby-and-truffleruby
7
-
8
- name: Ruby
9
-
10
- on:
11
- push:
12
- branches: [ main ]
13
- pull_request:
14
- branches: [ main ]
15
-
1
+ name: My workflow
2
+ on: [push, pull_request]
16
3
  jobs:
17
4
  test:
18
-
19
5
  runs-on: ubuntu-latest
20
- strategy:
21
- matrix:
22
- ruby-version: ['2.6', '2.7', '3.0']
23
-
24
6
  steps:
25
7
  - uses: actions/checkout@v2
26
- - name: Set up Ruby
27
- # To automatically get bug fixes and new Ruby versions for ruby/setup-ruby,
28
- # change this to (see https://github.com/ruby/setup-ruby#versioning):
29
- # uses: ruby/setup-ruby@v1
30
- uses: ruby/setup-ruby@473e4d8fe5dd94ee328fdfca9f8c9c7afc9dae5e
8
+ - uses: ruby/setup-ruby@v1
31
9
  with:
32
- ruby-version: ${{ matrix.ruby-version }}
10
+ ruby-version: 2.6 # Not needed with a .ruby-version file
33
11
  bundler-cache: true # runs 'bundle install' and caches installed gems automatically
34
- - name: Install dependencies
35
- run: bundle install
36
- - name: Run tests
37
- run: bundle exec rake
12
+ - run: bundle exec rake
data/.gitignore CHANGED
@@ -8,4 +8,6 @@
8
8
  /tmp/
9
9
  /.idea/
10
10
  *.gem
11
- *.yml
11
+ *.yml
12
+ /sig/
13
+ *.env
data/Gemfile CHANGED
@@ -5,8 +5,16 @@ source "https://rubygems.org"
5
5
  # Specify your gem's dependencies in advanced_ruby_command_handler.gemspec
6
6
  gemspec
7
7
 
8
+ gem "rbs"
9
+
8
10
  gem "rake", "~> 13.0"
9
11
 
10
12
  gem "rubocop", "~> 1.7"
11
13
 
12
14
  gem "discordrb"
15
+
16
+ gem "mongo"
17
+
18
+ gem "dotenv", "~> 2.7", ">= 2.7.6"
19
+
20
+ gem "event_emitter"
data/Gemfile.lock CHANGED
@@ -1,13 +1,14 @@
1
1
  PATH
2
2
  remote: .
3
3
  specs:
4
- advanced_ruby_command_handler (0.1.5)
4
+ advanced_ruby_command_handler (2.0.1)
5
5
  discordrb
6
6
 
7
7
  GEM
8
8
  remote: https://rubygems.org/
9
9
  specs:
10
10
  ast (2.4.2)
11
+ bson (4.12.1)
11
12
  discordrb (3.4.0)
12
13
  discordrb-webhooks (~> 3.3.0)
13
14
  ffi (>= 1.9.24)
@@ -18,22 +19,26 @@ GEM
18
19
  rest-client (>= 2.1.0.rc1)
19
20
  domain_name (0.5.20190701)
20
21
  unf (>= 0.0.5, < 1.0.0)
22
+ dotenv (2.7.6)
21
23
  event_emitter (0.2.6)
22
- ffi (1.15.0-x64-mingw32)
24
+ ffi (1.15.4-x64-mingw32)
23
25
  http-accept (1.7.0)
24
- http-cookie (1.0.3)
26
+ http-cookie (1.0.4)
25
27
  domain_name (~> 0.5)
26
28
  mime-types (3.3.1)
27
29
  mime-types-data (~> 3.2015)
28
- mime-types-data (3.2020.1104)
30
+ mime-types-data (3.2021.0901)
31
+ mongo (2.15.1)
32
+ bson (>= 4.8.2, < 5.0.0)
29
33
  netrc (0.11.0)
30
34
  opus-ruby (1.0.1)
31
35
  ffi
32
- parallel (1.20.1)
33
- parser (3.0.1.1)
36
+ parallel (1.21.0)
37
+ parser (3.0.2.0)
34
38
  ast (~> 2.4.1)
35
39
  rainbow (3.0.0)
36
- rake (13.0.3)
40
+ rake (13.0.6)
41
+ rbs (1.6.2)
37
42
  regexp_parser (2.1.1)
38
43
  rest-client (2.1.0-x64-mingw32)
39
44
  ffi (~> 1.9)
@@ -42,22 +47,22 @@ GEM
42
47
  mime-types (>= 1.16, < 4.0)
43
48
  netrc (~> 0.8)
44
49
  rexml (3.2.5)
45
- rubocop (1.18.1)
50
+ rubocop (1.22.1)
46
51
  parallel (~> 1.10)
47
52
  parser (>= 3.0.0.0)
48
53
  rainbow (>= 2.2.2, < 4.0)
49
54
  regexp_parser (>= 1.8, < 3.0)
50
55
  rexml
51
- rubocop-ast (>= 1.7.0, < 2.0)
56
+ rubocop-ast (>= 1.12.0, < 2.0)
52
57
  ruby-progressbar (~> 1.7)
53
58
  unicode-display_width (>= 1.4.0, < 3.0)
54
- rubocop-ast (1.7.0)
59
+ rubocop-ast (1.12.0)
55
60
  parser (>= 3.0.1.1)
56
61
  ruby-progressbar (1.11.0)
57
62
  unf (0.1.4)
58
63
  unf_ext
59
- unf_ext (0.0.7.7)
60
- unicode-display_width (2.0.0)
64
+ unf_ext (0.0.8-x64-mingw32)
65
+ unicode-display_width (2.1.0)
61
66
  websocket (1.2.9)
62
67
  websocket-client-simple (0.3.0)
63
68
  event_emitter
@@ -69,7 +74,11 @@ PLATFORMS
69
74
  DEPENDENCIES
70
75
  advanced_ruby_command_handler!
71
76
  discordrb
77
+ dotenv (~> 2.7, >= 2.7.6)
78
+ event_emitter
79
+ mongo
72
80
  rake (~> 13.0)
81
+ rbs
73
82
  rubocop (~> 1.7)
74
83
 
75
84
  BUNDLED WITH
data/README.md CHANGED
@@ -1,7 +1,7 @@
1
1
 
2
2
  [![forthebadge](https://forthebadge.com/images/badges/made-with-ruby.svg)](https://forthebadge.com)
3
3
 
4
- [![Les Laboratoires Ruby](https://invidget.switchblade.xyz/4P7XcmbDnt)](https://discord.gg/4P7XcmbDnt)
4
+ [Les Laboratoires Ruby](https://discord.gg/4P7XcmbDnt)
5
5
 
6
6
  # AdvancedRubyCommandHandler
7
7
  ## Installation
@@ -29,55 +29,65 @@ Firstly, you have to create a ruby file, where you put the followwing line:
29
29
  require "advanced_ruby_command_handler"
30
30
  ```
31
31
 
32
- Then, initialize the command handler. Specifying the directories and the config file path
32
+ Then, initialize the command handler. Specifying the directories and the modules.
33
33
 
34
34
  ```rb
35
- client = CommandHandler.new(commands_dir: "src/commands", events_dir: "src/events", config_file: "src/private/config.yml")
35
+ command_handler = CommandHandler.new(Hash[
36
+ :commands_dir => "src/commands/",
37
+ :events_dir => "src/events/",
38
+ :commands_module_name => "Commands",
39
+ :events_module_name => "Events"
40
+ ])
41
+ .load_commands
42
+ .load_events
36
43
  ```
37
- Note: if these files dose not exist, the command handler will create them
44
+ Note: if these directories dosen't exist, the command handler will create them
38
45
 
39
46
  And run the bot:
40
47
  ```ruby
41
- client.run
48
+ command_handler.client.run
42
49
  ```
43
50
 
44
51
  ### Events&Commands
45
52
 
46
53
  The command handler have base events as message or ready, but you can create your owns events (in events directory).
47
54
 
48
- Create a file with the name of your event (see https://www.rubydoc.info/github/meew0/discordrb/Discordrb/Events)
55
+ Create a file with the name of your event (see [https://www.rubydoc.info/github/meew0/discordrb/Discordrb/Events](the doc))
49
56
 
50
57
  And use the following template:
51
58
  ```ruby
59
+ # src/events/message.rb
52
60
  # frozen_string_literal: true
53
61
 
54
62
  module Events
55
- def self.<event>(client)
56
- client.<event> do
57
- client.console_logger.info("Event!")
63
+ # self.<event_name>
64
+ def self.message(command_handler)
65
+ Event.new(:message, command_handler.client) do |message|
66
+ Logger.check("Message! : #{message.content}")
58
67
  end
59
- end
68
+ end
60
69
  end
61
70
  ```
62
- Now, when the event will be emitted, the program will puts "Event!"
71
+ Now, when a message is sent, the program will puts "Message! : 'message content'"
63
72
 
64
73
  If you want to add some commands in your bot, you can create sub directories in your command directory.
65
74
  In these directories, you can create ruby files for commands, here's an example:
66
75
 
67
76
  ```ruby
77
+ # src/commands/utils/ping.rb
68
78
  # frozen_string_literal: true
69
79
 
70
- require_relative "advanced_ruby_command_handler"
71
-
72
80
  module Commands
73
- def self.hello
74
- CommandHandler::Command.new({
75
- :name => "hello"
76
- }) do |message, client|
77
- message.respond "Hello Discord!"
81
+ # self.<command_name>
82
+ def self.ping
83
+ Command.new(Hash[
84
+ :name => "ping"
85
+ ]) do |client, message|
86
+ message.respond "Pong!"
78
87
  end
79
88
  end
80
89
  end
90
+
81
91
  ```
82
92
 
83
93
  Now you can create events and commands ! ;)
@@ -0,0 +1,51 @@
1
+ # frozen_string_literal: true
2
+
3
+ require "dotenv/load"
4
+ require "fileutils"
5
+
6
+ class BaseDatabase
7
+ attr_reader :client
8
+
9
+ def initialize(client)
10
+ @client = client
11
+ end
12
+
13
+ def to_s
14
+ @client.database.name
15
+ end
16
+
17
+ def options
18
+ @client.hash
19
+ end
20
+ end
21
+
22
+ class BaseClient < Discordrb::Bot
23
+ def initialize
24
+ %w[BOT_TOKEN BOT_BASE_PREFIX BOT_OWNER].each do |environment_variable|
25
+ raise Errors::MissingEnvironmentVariable.new(environment_variable, "Environment variable '#{environment_variable}' missing in your .env file") unless ENV[environment_variable]
26
+ end
27
+ super(:token => ENV["BOT_TOKEN"], :ignore_bots => true)
28
+ end
29
+ end
30
+
31
+ class BaseCommandHandler
32
+ attr_accessor :commands_dir, :events_dir
33
+ attr_reader :commands_module_name, :events_module_name
34
+
35
+ def initialize(options)
36
+ %i[commands_dir events_dir commands_module_name events_module_name].each do |dir|
37
+ raise Errors::MissingParameter.new(dir, "Parameter '#{dir}' unspecified") unless options[dir]
38
+ end
39
+ @commands_dir = options[:commands_dir]
40
+ @events_dir = options[:events_dir]
41
+ @commands_module_name = options[:commands_module_name]
42
+ @events_module_name = options[:events_module_name]
43
+ FileUtils.mkdir_p [@commands_dir, @events_dir]
44
+ end
45
+
46
+ def get_module_by_string(module_name)
47
+ raise Errors::NonExistingModule.new(module_name, "Module '#{module_name}' doesn't exist. Please specify an existing module") unless Object.const_defined?(module_name)
48
+
49
+ Object.const_get(module_name)
50
+ end
51
+ end
@@ -0,0 +1,20 @@
1
+ # frozen_string_literal: true
2
+
3
+ require "fileutils"
4
+ require "yaml"
5
+ require File.expand_path("base", File.dirname(__FILE__))
6
+
7
+ module AdvancedRubyCommandHandler
8
+ class Client < BaseClient
9
+ def run
10
+ Logger.check("Client run")
11
+ Thread.new do
12
+ Logger.info("Type '.exit' to turn off the bot")
13
+ loop do
14
+ Process.exit!(true) if $stdin.gets.chomp == ".exit"
15
+ end
16
+ end
17
+ super.run
18
+ end
19
+ end
20
+ end
@@ -0,0 +1,65 @@
1
+ # frozen_string_literal: true
2
+
3
+ class Command
4
+ attr_reader :run
5
+
6
+ def initialize(props, &block)
7
+ @run = block
8
+ load_proprieties(props)
9
+ end
10
+
11
+ def load_proprieties(props)
12
+ command_props = %i[
13
+ name
14
+ aliases
15
+ description
16
+ category
17
+ usage
18
+ args
19
+ strict_args
20
+ cooldown
21
+ owner_only
22
+ server_only
23
+ member_permissions
24
+ bot_permissions
25
+ ]
26
+ command_props.each do |prop|
27
+ Command.attr_accessor prop
28
+ end
29
+ @name = props[:name]
30
+ @aliases = props[:aliases] if props[:aliases]
31
+ @description = props[:description] if props[:description]
32
+ @category = props[:category] if props[:category]
33
+ @usage = props[:usage] if props[:usage]
34
+ @args = props[:args] if props[:args]
35
+ @strict_args = props[:strict_args] if props[:strict_args]
36
+ @cooldown = props[:cooldown] if props[:cooldown]
37
+ @owner_only = true if props[:owner_only]
38
+ @server_only = true if props[:server_only]
39
+
40
+ client_base_permissions = %i[
41
+ add_reactions
42
+ send_messages
43
+ embed_links
44
+ attach_files
45
+ use_external_emoji
46
+ ]
47
+ case props[:bot_permissions]
48
+ when String
49
+ permissions = props[:bot_permissions].split(/\s+/).map(&:to_sym)
50
+ client_base_permissions.each { |p| permissions << p unless permissions.include?(p) }
51
+ @bot_permissions = permissions
52
+ when Array
53
+ permissions = props[:bot_permissions].map(&:to_sym)
54
+ client_base_permissions.each { |p| permissions << p unless permissions.include?(p) }
55
+ @bot_permissions = permissions
56
+ else @bot_permissions = client_base_permissions end
57
+
58
+ @member_permissions = case props[:member_permissions]
59
+ when String
60
+ props[:member_permissions].split(/\s+/).map(&:to_sym)
61
+ else [] end
62
+ command_props.each { |p| instance_variable_set(:"@#{p}", false) unless instance_variable_get(:"@#{p}") }
63
+ end
64
+ private :load_proprieties
65
+ end
@@ -0,0 +1,76 @@
1
+ # frozen_string_literal: true
2
+
3
+ require "event_emitter"
4
+ require File.expand_path("base", File.dirname(__FILE__))
5
+ require File.expand_path("utils", File.dirname(__FILE__))
6
+
7
+ class CommandHandler < BaseCommandHandler
8
+ include EventEmitter
9
+ include Utils
10
+ attr_reader :client, :commands, :events, :commands_module, :events_module, :loaded_events
11
+
12
+ def initialize(options)
13
+ super(options)
14
+ @client = AdvancedRubyCommandHandler::Client.new
15
+ @loaded_events = []
16
+
17
+ Thread.new do
18
+ Logger.info("Type '.reload' to load/reload all the commands & events files")
19
+ loop do
20
+ next unless $stdin.gets.chomp == ".reload"
21
+
22
+ load_commands
23
+ load_events
24
+ Logger.check("All commands & events loaded")
25
+ end
26
+ end
27
+ end
28
+
29
+ def load_commands
30
+ @commands = []
31
+ Dir.entries(@commands_dir).each do |dir|
32
+ next if %w[. ..].include?(dir)
33
+
34
+ Dir.entries("#{@commands_dir}#{dir}").each do |file|
35
+ next if %w[. ..].include?(file)
36
+
37
+ load File.join(@commands_dir, dir, file)
38
+ @commands << File.basename(file, ".rb")
39
+ end
40
+ end
41
+ @commands_module = get_module_by_string(@commands_module_name)
42
+
43
+ emit :commands_loaded, @commands
44
+ self
45
+ end
46
+
47
+ def load_events
48
+ @events = []
49
+ Dir.entries(@events_dir).each do |file|
50
+ next if %w[. ..].include?(file)
51
+
52
+ load File.join(@events_dir, file)
53
+ @events << File.basename(file, ".rb")
54
+ end
55
+
56
+ Dir["#{File.dirname(__FILE__)}/defaults/events/*.rb"].sort.each do |default_event|
57
+ next if @loaded_events.include?(File.basename(default_event, ".rb")) || @events.include?(File.basename(default_event, ".rb"))
58
+
59
+ require default_event
60
+
61
+ @events << File.basename(default_event, ".rb")
62
+ end
63
+ @event_module = get_module_by_string(@events_module_name)
64
+
65
+ emit :events_loaded, @events
66
+
67
+ @events.each do |event|
68
+ next if @loaded_events.include?(event)
69
+
70
+ @event_module.method(event).call(self)
71
+ @loaded_events << event
72
+ end
73
+
74
+ self
75
+ end
76
+ end
@@ -0,0 +1,16 @@
1
+ # frozen_string_literal: true
2
+
3
+ require "mongo"
4
+ require File.expand_path("base", File.dirname(__FILE__))
5
+
6
+ module AdvancedRubyCommandHandler
7
+ class Database < BaseDatabase
8
+ attr_accessor :client, :path
9
+
10
+ def initialize(path)
11
+ @path = path
12
+ @client = Mongo::Client.new(path)
13
+ super(@client)
14
+ end
15
+ end
16
+ end
@@ -0,0 +1,17 @@
1
+ # frozen_string_literal: true
2
+
3
+ module Events
4
+ def self.message(command_handler)
5
+ Event.new(:message, command_handler.client) do |message|
6
+ next unless message.content.start_with?(ENV["BOT_BASE_PREFIX"])
7
+
8
+ args = message.content.slice(ENV["BOT_BASE_PREFIX"].size, message.content.size).strip.split(/\s+/)
9
+ command = command_handler.find_command(args.shift)
10
+
11
+ next unless command
12
+
13
+ command.run.call(command_handler.client, message.message)
14
+ Logger.check("Command #{command.name} used!")
15
+ end
16
+ end
17
+ end
@@ -0,0 +1,48 @@
1
+ # frozen_string_literal: true
2
+
3
+ module Errors
4
+ class LoadCommandError < RuntimeError
5
+ attr_reader :command
6
+
7
+ def initialize(command, message = nil)
8
+ super(message)
9
+ @command = command
10
+ end
11
+ end
12
+
13
+ class LoadEventError < RuntimeError
14
+ attr_reader :event
15
+
16
+ def initialize(event, message = nil)
17
+ super(message)
18
+ @event = event
19
+ end
20
+ end
21
+
22
+ class MissingEnvironmentVariable < RuntimeError
23
+ attr_reader :environment_variable
24
+
25
+ def initialize(environment_variable, message = nil)
26
+ super(message)
27
+ @environment_variable = environment_variable
28
+ end
29
+ end
30
+
31
+ class MissingParameter < RuntimeError
32
+ attr_reader :parameter
33
+
34
+ def initialize(parameter, message = nil)
35
+ super(message)
36
+ @parameter = parameter
37
+ end
38
+ end
39
+
40
+ class NonExistingModule < RuntimeError
41
+ attr_reader :module_name
42
+
43
+ def initialize(module_name, message = nil)
44
+ super(message)
45
+ @module_name = module_name
46
+ end
47
+ end
48
+ end
@@ -0,0 +1,9 @@
1
+ # frozen_string_literal: true
2
+
3
+ class Event
4
+ def initialize(event, client, &block)
5
+ return unless client.methods.include?(event)
6
+
7
+ client.method(event).call { |e| block.call(e) }
8
+ end
9
+ end
@@ -0,0 +1,38 @@
1
+ # frozen_string_literal: true
2
+
3
+ class Logger
4
+ COLORS = {
5
+ :default => "\e[38m",
6
+ :white => "\e[39m",
7
+ :black => "\e[30m",
8
+ :red => "\e[31m",
9
+ :green => "\e[32m",
10
+ :brown => "\e[33m",
11
+ :blue => "\e[34m",
12
+ :magenta => "\e[35m",
13
+ :cyan => "\e[36m",
14
+ :gray => "\e[37m",
15
+ :yellow => "\e[33m"
16
+ }.freeze
17
+ MODES = {
18
+ :info => :cyan,
19
+ :error => :red,
20
+ :warn => :yellow,
21
+ :check => :green
22
+ }.freeze
23
+
24
+ class << self
25
+ def console_color(color, message)
26
+ "#{COLORS[color]}#{message}\e[0m"
27
+ end
28
+
29
+ private :console_color
30
+ end
31
+
32
+ MODES.each do |mode, color|
33
+ define_singleton_method(mode) do |message|
34
+ time = Time.now.strftime("%Y-%m-%d-%H:%M:%S")
35
+ puts "[#{console_color(:magenta, time)}] - [#{console_color(color, mode.to_s.upcase)}] : #{message.to_s}"
36
+ end
37
+ end
38
+ end
@@ -0,0 +1,9 @@
1
+ # frozen_string_literal: true
2
+
3
+ module Utils
4
+ def find_command(name)
5
+ return unless commands_module.methods.include?(name.to_sym)
6
+
7
+ commands_module.method(name.to_sym).call
8
+ end
9
+ end
@@ -1,5 +1,5 @@
1
- # frozen_string_literal: true
2
-
3
- module AdvancedRubyCommandHandler
4
- VERSION = "0.1.5"
5
- end
1
+ # frozen_string_literal: true
2
+
3
+ module AdvancedRubyCommandHandler
4
+ VERSION = "2.0.1"
5
+ end
@@ -1,19 +1,16 @@
1
1
  # frozen_string_literal: true
2
2
 
3
- require_relative "advanced_ruby_command_handler/app/app"
4
- require_relative "advanced_ruby_command_handler/app/command"
5
- require_relative "advanced_ruby_command_handler/app/utils"
3
+ require "discordrb"
4
+ require File.expand_path("advanced_ruby_command_handler/database", File.dirname(__FILE__))
5
+ require File.expand_path("advanced_ruby_command_handler/errors", File.dirname(__FILE__))
6
+ require File.expand_path("advanced_ruby_command_handler/client", File.dirname(__FILE__))
7
+ require File.expand_path("advanced_ruby_command_handler/utils", File.dirname(__FILE__))
8
+ require File.expand_path("advanced_ruby_command_handler/command_handler", File.dirname(__FILE__))
9
+ require File.expand_path("advanced_ruby_command_handler/event", File.dirname(__FILE__))
10
+ require File.expand_path("advanced_ruby_command_handler/logger", File.dirname(__FILE__))
6
11
 
7
- ##
8
- # Represent the CommandHandler as a simply class
9
- module CommandHandler
10
- ##
11
- # @!method new
12
- # @param [String] commands_dir The command's directory path
13
- # @param [String] events_dir The event's directory path
14
- # @param [String] config_file The config's file path
15
- # @return [AdvancedRubyCommandHandler::Client] the created client
16
- def self.new(commands_dir: "commands", events_dir: "events", config_file: "config.yml")
17
- AdvancedRubyCommandHandler::Client.new(:commands_dir => commands_dir, :events_dir => events_dir, :config_file => config_file)
18
- end
12
+ module AdvancedRubyCommandHandler
13
+ include Discordrb
14
+ include Errors
15
+ include Utils
19
16
  end
@@ -0,0 +1,21 @@
1
+ class BaseDatabase
2
+ attr_reader client: Mongo::Client
3
+
4
+ def initialize: (Mongo::CLient client) -> void
5
+
6
+ def to_s: () -> String
7
+
8
+ def options: () -> Hash|String
9
+ end
10
+
11
+ class BaseClient < Discordrb::Bot
12
+ def initialize: () -> void
13
+ end
14
+
15
+ class BaseCommandHandler
16
+ attr_accessor commands_dir: String
17
+
18
+ attr_accessor events_dir: String
19
+
20
+ def initialize: (Hash options) -> void
21
+ end
@@ -0,0 +1,7 @@
1
+ class Database < BaseDatabase
2
+ attr_accessor database: Mongo::Client
3
+
4
+ attr_accessor path: String
5
+
6
+ def initialize: (String path) -> void
7
+ end
@@ -0,0 +1,19 @@
1
+ module Errors
2
+ class LoadCommandError < RuntimeError
3
+ attr_reader command: String
4
+
5
+ def initialize: (String command, ?String? message) -> void
6
+ end
7
+
8
+ class LoadEventError < RuntimeError
9
+ attr_reader event: String
10
+
11
+ def initialize: (String event, ?String? message) -> void
12
+ end
13
+
14
+ class MissingEnvironmentVariable < RuntimeError
15
+ attr_reader environment_variable: String
16
+
17
+ def initialize: (String environment_variable, ?String? message) -> void
18
+ end
19
+ end
data/tests/index.rb CHANGED
@@ -2,5 +2,20 @@
2
2
 
3
3
  require_relative "../lib/advanced_ruby_command_handler"
4
4
 
5
- CommandHandler.new(:commands_dir => "tests/commands", :events_dir => "tests/events", :config_file => "tests/config.yml")
6
- .run
5
+ command_handler = CommandHandler.new(Hash[
6
+ :commands_dir => "tests/src/commands/",
7
+ :events_dir => "tests/src/events/",
8
+ :commands_module_name => "Commands",
9
+ :events_module_name => "Events"
10
+ ])
11
+ command_handler.on :commands_loaded do |commands|
12
+ Logger.check("#{commands.size} commands loaded!")
13
+ end
14
+
15
+ command_handler.on :events_loaded do |events|
16
+ Logger.check("#{events.size} events loaded!")
17
+ end
18
+
19
+ command_handler.load_commands
20
+ .load_events
21
+ command_handler.client.run
@@ -0,0 +1,13 @@
1
+ # frozen_string_literal: true
2
+
3
+ require_relative "././../../../src/../../lib/advanced_ruby_command_handler/command"
4
+
5
+ module Commands
6
+ def self.test
7
+ Command.new(Hash[
8
+ :name => "test"
9
+ ]) do |client, message|
10
+ message.respond "#{client.profile.username} prêt!"
11
+ end
12
+ end
13
+ end
@@ -0,0 +1,9 @@
1
+ # frozen_string_literal: true
2
+
3
+ module Events
4
+ def self.ready(command_handler)
5
+ Event.new(:ready, command_handler.client) do
6
+ puts "Ready!"
7
+ end
8
+ end
9
+ end
metadata CHANGED
@@ -1,14 +1,14 @@
1
1
  --- !ruby/object:Gem::Specification
2
2
  name: advanced_ruby_command_handler
3
3
  version: !ruby/object:Gem::Version
4
- version: 0.1.5
4
+ version: 2.0.1
5
5
  platform: ruby
6
6
  authors:
7
7
  - senchuu
8
8
  autorequire:
9
9
  bindir: exe
10
10
  cert_chain: []
11
- date: 2021-09-02 00:00:00.000000000 Z
11
+ date: 2021-10-25 00:00:00.000000000 Z
12
12
  dependencies:
13
13
  - !ruby/object:Gem::Dependency
14
14
  name: discordrb
@@ -45,20 +45,23 @@ files:
45
45
  - bin/console
46
46
  - bin/setup
47
47
  - lib/advanced_ruby_command_handler.rb
48
- - lib/advanced_ruby_command_handler/app/app.rb
49
- - lib/advanced_ruby_command_handler/app/client.rb
50
- - lib/advanced_ruby_command_handler/app/command.rb
51
- - lib/advanced_ruby_command_handler/app/command_handler.rb
52
- - lib/advanced_ruby_command_handler/app/defaults/events/message.rb
53
- - lib/advanced_ruby_command_handler/app/defaults/events/ready.rb
54
- - lib/advanced_ruby_command_handler/app/event_handler.rb
55
- - lib/advanced_ruby_command_handler/app/logger.rb
56
- - lib/advanced_ruby_command_handler/app/utils.rb
48
+ - lib/advanced_ruby_command_handler/base.rb
49
+ - lib/advanced_ruby_command_handler/client.rb
50
+ - lib/advanced_ruby_command_handler/command.rb
51
+ - lib/advanced_ruby_command_handler/command_handler.rb
52
+ - lib/advanced_ruby_command_handler/database.rb
53
+ - lib/advanced_ruby_command_handler/defaults/events/message.rb
54
+ - lib/advanced_ruby_command_handler/errors.rb
55
+ - lib/advanced_ruby_command_handler/event.rb
56
+ - lib/advanced_ruby_command_handler/logger.rb
57
+ - lib/advanced_ruby_command_handler/utils.rb
57
58
  - lib/advanced_ruby_command_handler/version.rb
58
- - tests/commands/test/test.rb
59
- - tests/config.yml
60
- - tests/events/ready.rb
59
+ - sig/lib/advanced_ruby_command_handler/base.rbs
60
+ - sig/lib/advanced_ruby_command_handler/database.rbs
61
+ - sig/lib/advanced_ruby_command_handler/errors.rbs
61
62
  - tests/index.rb
63
+ - tests/src/commands/tests/test.rb
64
+ - tests/src/events/ready.rb
62
65
  homepage: https://github.com/Senchuu/Advanced-Bot.rb
63
66
  licenses:
64
67
  - MIT
@@ -1,7 +0,0 @@
1
- # frozen_string_literal: true
2
-
3
- require_relative "../version"
4
- require_relative "logger"
5
- require_relative "client"
6
-
7
- module AdvancedRubyCommandHandler; end
@@ -1,63 +0,0 @@
1
- # frozen_string_literal: true
2
-
3
- require "discordrb"
4
- require "fileutils"
5
- require "yaml"
6
- require_relative "command_handler"
7
- require_relative "event_handler"
8
- require_relative "utils"
9
-
10
- module AdvancedRubyCommandHandler
11
- class Client < Discordrb::Bot
12
- attr_reader :commands_dir, :events_dir, :commands, :config, :console_logger, :file_logger
13
-
14
- def initialize(commands_dir: "commands", events_dir: "events", config_file: "config.yml")
15
- FileUtils.mkdir_p [commands_dir, events_dir]
16
- @commands_dir = commands_dir
17
- @events_dir = events_dir
18
- @file_logger = AdvancedRubyCommandHandler::Logger.new(:file)
19
- @console_logger = AdvancedRubyCommandHandler::Logger.new(:console)
20
-
21
- base_data = YAML.dump({
22
- :token => "",
23
- :prefix => "",
24
- :owners => []
25
- })
26
-
27
- File.open(config_file, "w+") { |file| file.write(base_data) } unless File.exist? config_file
28
-
29
- @config = YAML.load_file(config_file)
30
-
31
- %i[token prefix owners].each do |prop|
32
- next if @config[prop] && !@config[prop].empty?
33
-
34
- @console_logger.error("You have to add '#{prop.to_s}' value in your config file")
35
- raise "'#{prop}' missing or empty"
36
- end
37
-
38
- super(:token => @config[:token])
39
-
40
- @commands = AdvancedRubyCommandHandler::CommandHandler.load_commands(self)
41
- AdvancedRubyCommandHandler::EventHandler.load_events(self)
42
- .each do |event|
43
- Events.method(event).call(self)
44
- end
45
-
46
- at_exit { @console_logger.info("Application exited") }
47
- end
48
-
49
- def run
50
- @console_logger.info("Client login!")
51
-
52
- Thread.new do
53
- @console_logger.info("Type '.exit' to turn off the bot")
54
- # @console_logger.info("Type '.reload' to reload the bot")
55
- loop do
56
- Process.exit!(true) if $stdin.gets.chomp == ".exit"
57
- end
58
- end
59
-
60
- super.run
61
- end
62
- end
63
- end
@@ -1,55 +0,0 @@
1
- # frozen_string_literal: true
2
-
3
- module CommandHandler
4
- class Command
5
- attr_reader :props, :run
6
-
7
- def initialize(props, &run)
8
- @props = load_proprieties(props)
9
- @run = run
10
- end
11
-
12
- def load_proprieties(props)
13
- return props unless props.instance_of?(Hash)
14
-
15
- props[:aliases] ||= nil
16
- props[:description] ||= nil
17
- props[:args] ||= nil
18
- props[:strict_args] ||= false
19
- props[:use_example] ||= nil
20
- props[:category] ||= nil
21
- props[:user_permissions] ||= []
22
- props[:client_permissions] ||= []
23
- if props[:client_permissions].instance_of?(Array) && props[:client_permissions].empty?
24
- props[:client_permissions].push(
25
- :add_reactions,
26
- :send_messages,
27
- :embed_links,
28
- :attach_files,
29
- :use_external_emoji
30
- )
31
- elsif props[:client_permissions] == :default
32
- props[:client_permissions] = %i[
33
- add_reactions
34
- send_messages
35
- embed_links
36
- attach_files
37
- use_external_emoji
38
- ]
39
- end
40
-
41
- Hash[
42
- :name => props[:name],
43
- :aliases => props[:aliases],
44
- :description => props[:description],
45
- :args => props[:args],
46
- :strict_args => props[:strict_args],
47
- :use_example => props[:use_example],
48
- :category => props[:category],
49
- :user_permissions => props[:user_permissions],
50
- :client_permissions => props[:client_permissions]
51
- ]
52
- end
53
- private :load_proprieties
54
- end
55
- end
@@ -1,25 +0,0 @@
1
- # frozen_string_literal: true
2
-
3
- require_relative "app"
4
-
5
- module AdvancedRubyCommandHandler
6
- module CommandHandler
7
- def self.load_commands(client)
8
- commands = []
9
- Dir.entries(client.commands_dir).each do |dir|
10
- next if %w[. ..].include?(dir)
11
-
12
- Dir.entries("#{client.commands_dir}/#{dir}").each do |file|
13
- next if %w[. ..].include?(file)
14
-
15
- p "#{client.commands_dir}/#{dir}/#{file}"
16
-
17
- load "#{client.commands_dir}/#{dir}/#{file}"
18
-
19
- commands << File.basename(file, ".rb")
20
- end
21
- end
22
- commands
23
- end
24
- end
25
- end
@@ -1,24 +0,0 @@
1
- # frozen_string_literal: true
2
-
3
- require_relative "../../utils"
4
-
5
- module Events
6
- def self.message(client)
7
- client.message(:start_with => client.config[:prefix]) do |message|
8
- args = message.content.slice(client.config[:prefix].size, message.content.size).split(" ")
9
- name = args.shift
10
- command = CommandHandler::Utils.get_command(name)
11
-
12
- next unless command
13
-
14
- begin
15
- command.run.call(message, client)
16
- rescue StandardError => e
17
- client.console_logger.error(e)
18
- client.file_logger.write(e, :errors)
19
- ensure
20
- client.console_logger.info("Command '#{command.props[:name]}' used by #{message.author.username}")
21
- end
22
- end
23
- end
24
- end
@@ -1,9 +0,0 @@
1
- # frozen_string_literal: true
2
-
3
- module Events
4
- def self.ready(client)
5
- client.ready do
6
- client.console_logger.info("Client ready!")
7
- end
8
- end
9
- end
@@ -1,27 +0,0 @@
1
- # frozen_string_literal: true
2
-
3
- require_relative "app"
4
-
5
- module AdvancedRubyCommandHandler
6
- module EventHandler
7
- def self.load_events(client)
8
- events = []
9
- Dir.entries(client.events_dir).each do |file|
10
- next if %w[. ..].include?(file)
11
-
12
- load "#{client.events_dir}/#{file}"
13
- events << File.basename(file, ".rb")
14
- end
15
-
16
- Dir["#{File.dirname(__FILE__)}/defaults/events/*.rb"].sort.each do |file|
17
- next if events.include?(File.basename(file, ".rb"))
18
-
19
- require file
20
-
21
- events << File.basename(file, ".rb")
22
- end
23
-
24
- events
25
- end
26
- end
27
- end
@@ -1,62 +0,0 @@
1
- # frozen_string_literal: true
2
-
3
- require "fileutils"
4
-
5
- module AdvancedRubyCommandHandler
6
- class Logger
7
- attr_reader :mode
8
- attr_accessor :write_targets
9
-
10
- COLORS = {
11
- :default => "\e[38m",
12
- :white => "\e[39m",
13
- :black => "\e[30m",
14
- :red => "\e[31m",
15
- :green => "\e[32m",
16
- :brown => "\e[33m",
17
- :blue => "\e[34m",
18
- :magenta => "\e[35m",
19
- :cyan => "\e[36m",
20
- :gray => "\e[37m",
21
- :yellow => "\e[33m"
22
- }.freeze
23
- MODES = {
24
- :info => :cyan,
25
- :error => :red,
26
- :warn => :yellow,
27
- :check => :green
28
- }.freeze
29
- def initialize(mode = :console, write_targets = { :errors => "logs/errors.txt", :informations => "logs/infos.txt" })
30
- @mode = mode.to_sym
31
- @write_targets = write_targets if @mode == :file
32
- end
33
-
34
- def console_color(color, message)
35
- "#{COLORS[color]}#{message}\e[0m"
36
- end
37
-
38
- def write(message, write_target = :informations)
39
- return Logger.new(:console).warn("The file logs aren't available on #{@mode} mode") unless @mode == :file
40
-
41
- time = Time.now.strftime("%Y-%m-%d-%H:%M:%S")
42
-
43
- FileUtils.mkdir_p File.dirname @write_targets[write_target]
44
-
45
- File.open(@write_targets[write_target], "w") unless File.exist? @write_targets[write_target]
46
-
47
- File.open(@write_targets[write_target], "a+") do |file|
48
- file.write("#{time} - #{write_target.to_s.upcase} : #{message}\n")
49
- end
50
- end
51
-
52
- MODES.each do |mode, color|
53
- define_method(mode) do |message|
54
- return Logger.new(:console).warn("The console logs aren't available on #{@mode} mode") unless @mode == :console
55
-
56
- time = Time.now.strftime("%Y-%m-%d-%H:%M:%S")
57
- puts "[#{console_color(:magenta, time)}] - [#{console_color(color, mode.to_s.upcase)}] : #{message.to_s}"
58
- end
59
- end
60
- private :console_color
61
- end
62
- end
@@ -1,19 +0,0 @@
1
- # frozen_string_literal: true
2
-
3
- module CommandHandler
4
- module Utils
5
- def self.get_command(command_name)
6
- return Commands.method(command_name).call if defined?(Commands) && Commands.respond_to?(command_name)
7
-
8
- false
9
- end
10
-
11
- # Do NOT use that
12
- # FIXME
13
- def reload_files(dirs)
14
- dirs.each do |dir|
15
- Dir.glob("#{dir}/**/*.rb").each { |file| load file }
16
- end
17
- end
18
- end
19
- end
@@ -1,19 +0,0 @@
1
- # frozen_string_literal: true
2
-
3
- require_relative "../../../lib/advanced_ruby_command_handler/app/command"
4
- require_relative "../../../lib/advanced_ruby_command_handler/app/utils"
5
-
6
- module Commands
7
- def self.test
8
- CommandHandler::Command.new({
9
- :name => "test",
10
- :aliases => ["t"],
11
- :description => "Une commande pour faire des tests!",
12
- :args => false,
13
- :use_example => :default,
14
- :category => :default
15
- }) do |message, _client|
16
- message.respond "Test"
17
- end
18
- end
19
- end
data/tests/config.yml DELETED
@@ -1,4 +0,0 @@
1
- ---
2
- :token: 'NzEwMTIxODk2OTM0NjM3NjY5.Xrv2jQ._ypS5jOkYr4onqigdoxGzF2dRj0'
3
- :prefix: '!'
4
- :owners: [123456789]
@@ -1,9 +0,0 @@
1
- # frozen_string_literal: true
2
-
3
- module Events
4
- def self.ready(client)
5
- client.ready do
6
- client.console_logger.info("Client ready!")
7
- end
8
- end
9
- end