dev_suite 0.2.5 → 0.2.7

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.
Files changed (95) hide show
  1. checksums.yaml +4 -4
  2. data/.rubocop.yml +4 -5
  3. data/.vscode/extensions.json +8 -0
  4. data/.vscode/launch.json +39 -0
  5. data/.vscode/settings.json +28 -0
  6. data/Gemfile +4 -1
  7. data/Gemfile.lock +28 -2
  8. data/README.md +39 -31
  9. data/bin/rspec +27 -0
  10. data/lib/dev_suite/directory_tree/builder/base.rb +1 -1
  11. data/lib/dev_suite/directory_tree/builder/builder.rb +13 -0
  12. data/lib/dev_suite/directory_tree/builder.rb +1 -12
  13. data/lib/dev_suite/directory_tree/config/config.rb +1 -1
  14. data/lib/dev_suite/directory_tree/config/configuration.rb +18 -5
  15. data/lib/dev_suite/directory_tree/directory_tree.rb +0 -2
  16. data/lib/dev_suite/directory_tree/node/node.rb +12 -0
  17. data/lib/dev_suite/directory_tree/node.rb +1 -4
  18. data/lib/dev_suite/directory_tree/renderer/base.rb +1 -1
  19. data/lib/dev_suite/directory_tree/renderer/renderer.rb +14 -0
  20. data/lib/dev_suite/directory_tree/renderer.rb +1 -13
  21. data/lib/dev_suite/directory_tree/visualizer/base.rb +1 -1
  22. data/lib/dev_suite/directory_tree/visualizer/visualizer.rb +16 -0
  23. data/lib/dev_suite/directory_tree/visualizer.rb +1 -15
  24. data/lib/dev_suite/performance/config/config.rb +1 -1
  25. data/lib/dev_suite/performance/config/configuration.rb +3 -3
  26. data/lib/dev_suite/performance/data/data.rb +9 -0
  27. data/lib/dev_suite/performance/data.rb +1 -1
  28. data/lib/dev_suite/performance/profiler/base.rb +1 -1
  29. data/lib/dev_suite/performance/profiler/profiler.rb +16 -0
  30. data/lib/dev_suite/performance/profiler.rb +1 -20
  31. data/lib/dev_suite/performance/profiler_manager.rb +1 -0
  32. data/lib/dev_suite/performance/reporter/base.rb +1 -1
  33. data/lib/dev_suite/performance/reporter/reporter.rb +15 -0
  34. data/lib/dev_suite/performance/reporter.rb +1 -14
  35. data/lib/dev_suite/request_logger/adapter/adapter.rb +16 -12
  36. data/lib/dev_suite/request_logger/adapter/base.rb +1 -1
  37. data/lib/dev_suite/request_logger/adapter/faraday.rb +37 -0
  38. data/lib/dev_suite/request_logger/adapter/middleware/faraday.rb +22 -0
  39. data/lib/dev_suite/request_logger/adapter/net_http.rb +1 -0
  40. data/lib/dev_suite/request_logger/adapter.rb +1 -1
  41. data/lib/dev_suite/request_logger/config/config.rb +1 -1
  42. data/lib/dev_suite/request_logger/config/configuration.rb +2 -2
  43. data/lib/dev_suite/request_logger/extractor/base.rb +17 -0
  44. data/lib/dev_suite/request_logger/extractor/extractor.rb +22 -0
  45. data/lib/dev_suite/request_logger/extractor/faraday.rb +37 -0
  46. data/lib/dev_suite/request_logger/extractor/net_http.rb +36 -0
  47. data/lib/dev_suite/request_logger/extractor.rb +9 -0
  48. data/lib/dev_suite/request_logger/logger.rb +22 -28
  49. data/lib/dev_suite/request_logger/request.rb +19 -0
  50. data/lib/dev_suite/request_logger/request_logger.rb +3 -0
  51. data/lib/dev_suite/request_logger/response.rb +28 -0
  52. data/lib/dev_suite/utils/color/config/config.rb +1 -1
  53. data/lib/dev_suite/utils/color/config/configuration.rb +3 -3
  54. data/lib/dev_suite/utils/color/palette/base.rb +1 -14
  55. data/lib/dev_suite/utils/color/palette/palette.rb +16 -0
  56. data/lib/dev_suite/utils/color/palette.rb +1 -13
  57. data/lib/dev_suite/utils/color/strategy/base.rb +1 -1
  58. data/lib/dev_suite/utils/color/strategy/strategy.rb +20 -0
  59. data/lib/dev_suite/utils/color/strategy.rb +1 -19
  60. data/lib/dev_suite/utils/construct/component/base.rb +30 -0
  61. data/lib/dev_suite/utils/construct/component/component.rb +12 -0
  62. data/lib/dev_suite/utils/construct/component/initializer.rb +28 -0
  63. data/lib/dev_suite/utils/construct/component/manager.rb +57 -0
  64. data/lib/dev_suite/utils/construct/{config/configuration.rb → component.rb} +2 -4
  65. data/lib/dev_suite/utils/construct/config/attribute/attr_definition.rb +76 -0
  66. data/lib/dev_suite/utils/construct/config/attribute/attr_initialization.rb +22 -0
  67. data/lib/dev_suite/utils/construct/config/attribute/attr_resolving.rb +80 -0
  68. data/lib/dev_suite/utils/construct/config/attribute/attribute.rb +12 -3
  69. data/lib/dev_suite/utils/construct/config/base.rb +7 -2
  70. data/lib/dev_suite/utils/construct/config/config.rb +2 -10
  71. data/lib/dev_suite/utils/construct/config/dependency_handler.rb +56 -0
  72. data/lib/dev_suite/utils/construct/config/hook/hook.rb +10 -1
  73. data/lib/dev_suite/utils/construct/config/hook/hook_registry.rb +24 -0
  74. data/lib/dev_suite/utils/construct/config/hook/hook_runner.rb +20 -0
  75. data/lib/dev_suite/utils/construct/config/manager.rb +25 -17
  76. data/lib/dev_suite/utils/construct/construct.rb +1 -0
  77. data/lib/dev_suite/utils/dependency_loader.rb +71 -0
  78. data/lib/dev_suite/utils/file_loader/config/config.rb +1 -1
  79. data/lib/dev_suite/utils/file_loader/config/configuration.rb +1 -1
  80. data/lib/dev_suite/utils/file_loader/loader/base.rb +1 -1
  81. data/lib/dev_suite/utils/file_loader/loader/loader.rb +41 -0
  82. data/lib/dev_suite/utils/file_loader/loader.rb +2 -30
  83. data/lib/dev_suite/utils/table/config/config.rb +1 -1
  84. data/lib/dev_suite/utils/table/config/configuration.rb +2 -2
  85. data/lib/dev_suite/utils/table/formatter/formatter.rb +12 -0
  86. data/lib/dev_suite/utils/table/formatter.rb +1 -2
  87. data/lib/dev_suite/utils/table/renderer/base.rb +1 -1
  88. data/lib/dev_suite/utils/table/renderer/renderer.rb +16 -0
  89. data/lib/dev_suite/utils/table/renderer.rb +1 -13
  90. data/lib/dev_suite/utils/utils.rb +1 -0
  91. data/lib/dev_suite/version.rb +3 -1
  92. metadata +39 -6
  93. data/lib/dev_suite/utils/construct/config/attribute/manager.rb +0 -63
  94. data/lib/dev_suite/utils/construct/config/attribute/resolver.rb +0 -31
  95. data/lib/dev_suite/utils/construct/config/initializer.rb +0 -21
@@ -4,25 +4,7 @@ module DevSuite
4
4
  module Utils
5
5
  module Color
6
6
  module Strategy
7
- require_relative "strategy/base"
8
- require_relative "strategy/basic"
9
- require_relative "strategy/rgb"
10
- require_relative "strategy/theme"
11
-
12
- class << self
13
- def create(type)
14
- case type
15
- when :basic
16
- Basic.new
17
- when :rgb
18
- Rgb.new
19
- when :theme
20
- Theme.new
21
- else
22
- raise ArgumentError, "Unknown strategy type: #{type}"
23
- end
24
- end
25
- end
7
+ require_relative "strategy/strategy"
26
8
  end
27
9
  end
28
10
  end
@@ -0,0 +1,30 @@
1
+ # frozen_string_literal: true
2
+
3
+ module DevSuite
4
+ module Utils
5
+ module Construct
6
+ module Component
7
+ class Base
8
+ class << self
9
+ # Returns the key for the class. If the COMPONENT_KEY constant is defined, it returns its value.
10
+ # Otherwise, it generates a key based on the class name.
11
+ def component_key
12
+ return const_get(:COMPONENT_KEY) if const_defined?(:COMPONENT_KEY)
13
+
14
+ generate_key_from_class_name
15
+ end
16
+
17
+ private
18
+
19
+ # Generates a key from the class name by converting it to snake_case and symbolizing it.
20
+ def generate_key_from_class_name
21
+ class_name = name.split("::").last
22
+ snake_case_class_name = class_name.gsub(/([a-z\d])([A-Z])/, '\1_\2').downcase
23
+ snake_case_class_name.to_sym
24
+ end
25
+ end
26
+ end
27
+ end
28
+ end
29
+ end
30
+ end
@@ -0,0 +1,12 @@
1
+ # frozen_string_literal: true
2
+
3
+ module DevSuite
4
+ module Utils
5
+ module Construct
6
+ module Component
7
+ require_relative "base"
8
+ require_relative "manager"
9
+ end
10
+ end
11
+ end
12
+ end
@@ -0,0 +1,28 @@
1
+ # frozen_string_literal: true
2
+
3
+ module DevSuite
4
+ module Utils
5
+ module Construct
6
+ module Component
7
+ module Initializer
8
+ extend self
9
+
10
+ def define_constants(base)
11
+ structure_module = ensure_structure_module(base)
12
+ define_structure_component(structure_module)
13
+ end
14
+
15
+ private
16
+
17
+ def ensure_structure_module(base)
18
+ base.const_defined?(:Structure) ? base.const_get(:Structure) : base.const_set(:Structure, Module.new)
19
+ end
20
+
21
+ def define_structure_component(structure_module)
22
+ structure_module.const_set(:Component, Base) unless structure_module.const_defined?(:Component)
23
+ end
24
+ end
25
+ end
26
+ end
27
+ end
28
+ end
@@ -0,0 +1,57 @@
1
+ # frozen_string_literal: true
2
+
3
+ module DevSuite
4
+ module Utils
5
+ module Construct
6
+ module Component
7
+ module Manager
8
+ class << self
9
+ def included(base)
10
+ base.extend(ClassMethods)
11
+ end
12
+ end
13
+
14
+ module ClassMethods
15
+ # Stores a mapping of component symbols to their respective classes
16
+ def registered_components
17
+ @registered_components ||= {}
18
+ end
19
+
20
+ # Register a new component
21
+ def register_component(component_class)
22
+ raise ArgumentError,
23
+ "#{component_class} must define a component_key" unless component_class.respond_to?(:component_key)
24
+
25
+ registered_components[component_class.component_key] = component_class
26
+ end
27
+
28
+ # Build a single component
29
+ def build_component(component_key)
30
+ component_class = registered_components[component_key]
31
+
32
+ raise ArgumentError, "Component not found for key: #{component_key}" unless component_class
33
+
34
+ component_class.new
35
+ end
36
+
37
+ # Build multiple components
38
+ def build_components(component_keys)
39
+ component_keys.map { |key| build_component(key) }
40
+ end
41
+
42
+ def build_component_from_instance(instance)
43
+ component_class = registered_components.find do |klass, _|
44
+ instance.is_a?(klass)
45
+ end
46
+
47
+ raise ArgumentError,
48
+ "Component not found for instance: #{instance.class}" unless component_class
49
+
50
+ component_class.last.new
51
+ end
52
+ end
53
+ end
54
+ end
55
+ end
56
+ end
57
+ end
@@ -3,10 +3,8 @@
3
3
  module DevSuite
4
4
  module Utils
5
5
  module Construct
6
- module Config
7
- class Configuration < Base
8
- include Settings::Manager
9
- end
6
+ module Component
7
+ require_relative "component/component"
10
8
  end
11
9
  end
12
10
  end
@@ -0,0 +1,76 @@
1
+ # frozen_string_literal: true
2
+
3
+ module DevSuite
4
+ module Utils
5
+ module Construct
6
+ module Config
7
+ module Attribute
8
+ module AttrDefinition
9
+ def config_attr(attr, default_value: nil, type: nil, resolver: nil)
10
+ config_attrs[attr] = build_attr_details(
11
+ default_value: default_value,
12
+ type: type,
13
+ resolver: resolver,
14
+ )
15
+ define_config_attr_methods(attr)
16
+ end
17
+
18
+ def config_attrs
19
+ @config_attrs ||= {}
20
+ end
21
+
22
+ def config_attr_present?(attr)
23
+ config_attrs.key?(attr)
24
+ end
25
+
26
+ private
27
+
28
+ def build_attr_details(default_value:, type:, resolver:)
29
+ {
30
+ default_value: default_value,
31
+ type: type,
32
+ resolver: resolver,
33
+ }
34
+ end
35
+
36
+ def define_config_attr_methods(attr)
37
+ define_getter_methods(attr)
38
+ define_setter_methods(attr)
39
+ define_delete_method(attr)
40
+ end
41
+
42
+ def define_getter_methods(attr)
43
+ define_method(attr) do
44
+ instance_variable_get("@#{attr}")
45
+ end
46
+
47
+ define_method("original_#{attr}") do
48
+ instance_variable_get("@original_#{attr}")
49
+ end
50
+ end
51
+
52
+ def define_setter_methods(attr)
53
+ define_method("#{attr}=") do |value|
54
+ set_config_attr(attr: attr, value: value)
55
+ end
56
+ end
57
+
58
+ def define_delete_method(attr)
59
+ define_method("#{attr}.delete") do |*keys|
60
+ current_value = instance_variable_get("@#{attr}")
61
+ original_value = instance_variable_get("@original_#{attr}")
62
+
63
+ if original_value.is_a?(Array) && current_value.is_a?(Array)
64
+ keys.each do |key|
65
+ original_value.delete(key)
66
+ set_config_attr(attr: attr, value: original_value)
67
+ end
68
+ end
69
+ end
70
+ end
71
+ end
72
+ end
73
+ end
74
+ end
75
+ end
76
+ end
@@ -0,0 +1,22 @@
1
+ # frozen_string_literal: true
2
+
3
+ module DevSuite
4
+ module Utils
5
+ module Construct
6
+ module Config
7
+ module Attribute
8
+ module AttrInitialization
9
+ private
10
+
11
+ # Initializes all configuration attributes with their default values
12
+ def initialize_config_attrs
13
+ self.class.config_attrs.each do |attr, details|
14
+ send("#{attr}=", details[:default_value]) unless instance_variable_defined?("@#{attr}")
15
+ end
16
+ end
17
+ end
18
+ end
19
+ end
20
+ end
21
+ end
22
+ end
@@ -0,0 +1,80 @@
1
+ # frozen_string_literal: true
2
+
3
+ module DevSuite
4
+ module Utils
5
+ module Construct
6
+ module Config
7
+ module Attribute
8
+ require_relative "validator"
9
+
10
+ module AttrResolving
11
+ private
12
+
13
+ # Sets a configuration attribute value with validation and resolution
14
+ def set_config_attr(attr:, value:)
15
+ attr_details = fetch_attr_details(attr)
16
+
17
+ store_original_value(attr, value)
18
+ validated_value = validate_config_attr(attr, value, attr_details)
19
+ resolved_value = resolve_config_attr_value(validated_value, attr_details)
20
+
21
+ store_resolved_value(attr, resolved_value)
22
+ end
23
+
24
+ # Fetches the details of a configuration attribute
25
+ def fetch_attr_details(attr_name)
26
+ self.class.config_attrs[attr_name]
27
+ end
28
+
29
+ # Stores the original value of an attribute before processing
30
+ def store_original_value(attr_name, value)
31
+ instance_variable_set("@original_#{attr_name}", value)
32
+ end
33
+
34
+ # Stores the resolved value of an attribute after processing
35
+ def store_resolved_value(attr_name, value)
36
+ instance_variable_set("@#{attr_name}", value)
37
+ end
38
+
39
+ # Validates the value of a configuration attribute
40
+ def validate_config_attr(attr_name, value, attr_details)
41
+ if attr_details[:type]
42
+ Validator.validate_config_attr_type!(
43
+ attr: attr_name,
44
+ value: value,
45
+ type: attr_details[:type],
46
+ )
47
+ end
48
+ value
49
+ end
50
+
51
+ # Resolves the value of a configuration attribute
52
+ def resolve_config_attr_value(value, attr_details)
53
+ if attr_details[:resolver]
54
+ resolve_config_attr(
55
+ value: value,
56
+ resolver: attr_details[:resolver],
57
+ )
58
+ else
59
+ value
60
+ end
61
+ end
62
+
63
+ # Resolves the value of an attribute based on its resolver.
64
+ # If no resolver is provided, the value is returned as is.
65
+ def resolve_config_attr(value:, resolver:)
66
+ case resolver
67
+ when Proc
68
+ resolver.call(value)
69
+ when Symbol
70
+ send(resolver, value)
71
+ else
72
+ value
73
+ end
74
+ end
75
+ end
76
+ end
77
+ end
78
+ end
79
+ end
80
+ end
@@ -5,9 +5,18 @@ module DevSuite
5
5
  module Construct
6
6
  module Config
7
7
  module Attribute
8
- require_relative "validator"
9
- require_relative "resolver"
10
- require_relative "manager"
8
+ require_relative "attr_definition"
9
+ require_relative "attr_initialization"
10
+ require_relative "attr_resolving"
11
+
12
+ class << self
13
+ def included(base)
14
+ base.extend(AttrDefinition)
15
+ end
16
+ end
17
+
18
+ include AttrInitialization
19
+ include AttrResolving
11
20
  end
12
21
  end
13
22
  end
@@ -5,8 +5,13 @@ module DevSuite
5
5
  module Construct
6
6
  module Config
7
7
  class Base
8
- include Attribute::Manager
9
- include Hook::Manager
8
+ # Foundation for all configurations
9
+ include Attribute
10
+ include Hook
11
+
12
+ # Include the settings manager and dependency handler
13
+ include Settings::Manager
14
+ include DependencyHandler
10
15
 
11
16
  def initialize
12
17
  run_hooks(:before_initialize)
@@ -6,18 +6,10 @@ module DevSuite
6
6
  module Config
7
7
  require_relative "attribute"
8
8
  require_relative "hook"
9
- require_relative "base"
10
9
  require_relative "settings"
11
- require_relative "configuration"
10
+ require_relative "dependency_handler"
11
+ require_relative "base"
12
12
  require_relative "manager"
13
- require_relative "initializer"
14
-
15
- class << self
16
- def included(base)
17
- base.extend(Manager)
18
- Initializer.define_config_constants(base)
19
- end
20
- end
21
13
  end
22
14
  end
23
15
  end
@@ -0,0 +1,56 @@
1
+ # frozen_string_literal: true
2
+
3
+ module DevSuite
4
+ module Utils
5
+ module Construct
6
+ module Config
7
+ module DependencyHandler
8
+ class << self
9
+ def included(base)
10
+ base.class_eval do
11
+ attr_accessor(:missing_dependencies)
12
+ end
13
+ base.include(InstanceMethods)
14
+ end
15
+ end
16
+
17
+ module InstanceMethods
18
+ def initialize(*args)
19
+ super
20
+ @missing_dependencies ||= []
21
+ end
22
+
23
+ def delete_option_on_failure(attr_name, option_key, *missing_dependencies)
24
+ log_missing_dependency(attr_name, option_key, missing_dependencies)
25
+ send(attr_name).delete(option_key)
26
+ track_missing_dependency(missing_dependencies)
27
+ end
28
+
29
+ private
30
+
31
+ def track_missing_dependency(missing_dependencies)
32
+ @missing_dependencies = missing_dependencies
33
+ end
34
+
35
+ def log_missing_dependency(attr_name, option_key, missing_dependencies)
36
+ missing_dependencies.each do |dependency|
37
+ Utils::Logger.log(
38
+ "Missing dependency: #{dependency}. " \
39
+ "Please add `gem '#{dependency}'` to your Gemfile and run `bundle install`.",
40
+ level: :warn,
41
+ emoji: :warning,
42
+ )
43
+
44
+ Utils::Logger.log(
45
+ "Deleting option #{option_key} from `config.#{attr_name}`",
46
+ level: :warn,
47
+ emoji: :warning,
48
+ )
49
+ end
50
+ end
51
+ end
52
+ end
53
+ end
54
+ end
55
+ end
56
+ end
@@ -5,7 +5,16 @@ module DevSuite
5
5
  module Construct
6
6
  module Config
7
7
  module Hook
8
- require_relative "manager"
8
+ require_relative "hook_registry"
9
+ require_relative "hook_runner"
10
+
11
+ class << self
12
+ def included(base)
13
+ base.extend(HookRegistry)
14
+ end
15
+ end
16
+
17
+ include HookRunner
9
18
  end
10
19
  end
11
20
  end
@@ -0,0 +1,24 @@
1
+ # frozen_string_literal: true
2
+
3
+ module DevSuite
4
+ module Utils
5
+ module Construct
6
+ module Config
7
+ module Hook
8
+ module HookRegistry
9
+ # Registers a hook for a specific stage
10
+ def register_hook(stage, &block)
11
+ hooks[stage] ||= []
12
+ hooks[stage] << block
13
+ end
14
+
15
+ # Retrieves the hooks registered for this class
16
+ def hooks
17
+ @hooks ||= {}
18
+ end
19
+ end
20
+ end
21
+ end
22
+ end
23
+ end
24
+ end
@@ -0,0 +1,20 @@
1
+ # frozen_string_literal: true
2
+
3
+ module DevSuite
4
+ module Utils
5
+ module Construct
6
+ module Config
7
+ module Hook
8
+ module HookRunner
9
+ private
10
+
11
+ # Runs all hooks registered for a given stage
12
+ def run_hooks(stage)
13
+ self.class.hooks[stage]&.each { |hook| instance_eval(&hook) }
14
+ end
15
+ end
16
+ end
17
+ end
18
+ end
19
+ end
20
+ end
@@ -5,26 +5,34 @@ module DevSuite
5
5
  module Construct
6
6
  module Config
7
7
  module Manager
8
- # Provides access to a single instance of the configuration class
9
- # It dynamically uses the Configuration class in the including module's namespace
10
- def configuration
11
- @configuration ||= self::Configuration.new
8
+ class << self
9
+ def included(base)
10
+ base.extend(ClassMethods)
11
+ end
12
12
  end
13
13
 
14
- # Allows block-based configuration
15
- # Example usage:
16
- # ConfigClass.configure do |config|
17
- # config.attr_name = value
18
- # end
19
- def configure
20
- yield(configuration)
21
- rescue StandardError => e
22
- ErrorHandler.handle_error(e)
23
- end
14
+ module ClassMethods
15
+ # Provides access to a single instance of the configuration class
16
+ # It dynamically uses the Configuration class in the including module's namespace
17
+ def configuration
18
+ @configuration ||= self::Configuration.new
19
+ end
20
+
21
+ # Allows block-based configuration
22
+ # Example usage:
23
+ # ConfigClass.configure do |config|
24
+ # config.attr_name = value
25
+ # end
26
+ def configure
27
+ yield(configuration)
28
+ rescue StandardError => e
29
+ ErrorHandler.handle_error(e)
30
+ end
24
31
 
25
- # Resets the configuration by reinitializing it with default values
26
- def reset!
27
- @configuration = self::Configuration.new # Reinitialize the configuration instance
32
+ # Resets the configuration by reinitializing it with default values
33
+ def reset!
34
+ @configuration = self::Configuration.new # Reinitialize the configuration instance
35
+ end
28
36
  end
29
37
  end
30
38
  end
@@ -4,6 +4,7 @@ module DevSuite
4
4
  module Utils
5
5
  module Construct
6
6
  require_relative "config"
7
+ require_relative "component"
7
8
  end
8
9
  end
9
10
  end
@@ -0,0 +1,71 @@
1
+ # frozen_string_literal: true
2
+
3
+ module DevSuite
4
+ module Utils
5
+ module DependencyLoader
6
+ class << self
7
+ # Public method to safely load multiple dependencies.
8
+ # Executes the given block if all dependencies are successfully loaded.
9
+ # Calls the on_failure handler with the list of missing dependencies if any are not found.
10
+ #
11
+ # @param dependencies [Array<String>] List of gem names to load.
12
+ # @param on_failure [Proc] Handler to call with missing dependencies if any are not found.
13
+ # @yield Executes the block if all dependencies are loaded.
14
+ def safe_load_dependencies(*dependencies, on_failure: method(:default_failure_handler))
15
+ missing_dependencies = find_missing_dependencies(dependencies)
16
+
17
+ if missing_dependencies.empty?
18
+ yield if block_given?
19
+ else
20
+ on_failure.call(missing_dependencies)
21
+ end
22
+ end
23
+
24
+ # Check if a gem is installed by attempting to require it.
25
+ #
26
+ # @param gem_name [String] The name of the gem to check.
27
+ # @return [Boolean] true if the gem is installed, false otherwise.
28
+ def gem_installed?(gem_name)
29
+ require gem_name
30
+ true
31
+ rescue LoadError
32
+ false
33
+ end
34
+
35
+ private
36
+
37
+ # Finds and returns a list of missing dependencies from the provided list.
38
+ #
39
+ # @param dependencies [Array<String>] List of gem names to check.
40
+ # @return [Array<String>] List of missing dependencies.
41
+ def find_missing_dependencies(dependencies)
42
+ dependencies.reject { |gem_name| gem_installed?(gem_name) }
43
+ end
44
+
45
+ # Default failure handler that logs missing dependencies.
46
+ #
47
+ # @param missing_dependencies [Array<String>] List of missing dependencies.
48
+ def default_failure_handler(missing_dependencies)
49
+ missing_dependencies.each do |gem_name|
50
+ log_missing_dependency(gem_name)
51
+ end
52
+ end
53
+
54
+ # Logs a warning about a missing dependency.
55
+ #
56
+ # @param gem_name [String] The name of the missing gem.
57
+ def log_missing_dependency(gem_name)
58
+ gem_simple_name = gem_name.split("/").last.capitalize
59
+ message = "#{gem_simple_name} gem not installed. Please add `gem '#{gem_simple_name.downcase}'` " \
60
+ "to your Gemfile and run `bundle install`."
61
+
62
+ Utils::Logger.log(
63
+ message,
64
+ level: :warn,
65
+ emoji: :warning,
66
+ )
67
+ end
68
+ end
69
+ end
70
+ end
71
+ end
@@ -4,7 +4,7 @@ module DevSuite
4
4
  module Utils
5
5
  module FileLoader
6
6
  module Config
7
- include Construct::Config
7
+ include Construct::Config::Manager
8
8
 
9
9
  require_relative "configuration"
10
10
  end