others 0.1.0 → 0.1.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/Gemfile +3 -3
- data/Gemfile.lock +3 -3
- data/lib/others.rb +105 -100
- data/others.gemspec +1 -2
- data/test/test__helper.rb +2 -4
- data/test/test_others.rb +5 -2
- metadata +1 -1
checksums.yaml
CHANGED
@@ -1,7 +1,7 @@
|
|
1
1
|
---
|
2
2
|
SHA256:
|
3
|
-
metadata.gz:
|
4
|
-
data.tar.gz:
|
3
|
+
metadata.gz: e67d2f621c8f472bcdbc214377192996243a5604c6d70f498df9660a286357e7
|
4
|
+
data.tar.gz: 5260b4dfc3fd57b03bd950f23e201d889a0bb390a050fc0c3e18158b320cc887
|
5
5
|
SHA512:
|
6
|
-
metadata.gz:
|
7
|
-
data.tar.gz:
|
6
|
+
metadata.gz: 41a997bf264d6dae12f16f394536582593eacfa7a603577713259c53525d7898df938864881a90b7d9b3c392aeb536c77e41c14d38609b032956e939a1bc43a0
|
7
|
+
data.tar.gz: cca31ab3075ab250ca6c364b8b40490f2021ab75a9074b1a5db114aa3a8fed4167b44774761613ed8fb85a7b94923445575ef2dbe6d549ce6110c082aeb93df3
|
data/Gemfile
CHANGED
@@ -10,9 +10,9 @@ gem 'minitest', '~>5.24', require: false
|
|
10
10
|
gem 'minitest-reporters', '~>1.7', require: false
|
11
11
|
gem 'rake', '~>13.2', require: false
|
12
12
|
gem 'rubocop', '~>1.65', require: false
|
13
|
-
gem 'rubocop-minitest', '
|
14
|
-
gem 'rubocop-performance', '
|
15
|
-
gem 'rubocop-rake', '
|
13
|
+
gem 'rubocop-minitest', '~>0.38', require: false
|
14
|
+
gem 'rubocop-performance', '~>1.0', require: false
|
15
|
+
gem 'rubocop-rake', '~>0.7', require: false
|
16
16
|
gem 'simplecov', '~>0.22', require: false
|
17
17
|
gem 'simplecov-cobertura', '~>2.1', require: false
|
18
18
|
gem 'yard', '~>0.9', require: false
|
data/Gemfile.lock
CHANGED
@@ -83,9 +83,9 @@ DEPENDENCIES
|
|
83
83
|
others!
|
84
84
|
rake (~> 13.2)
|
85
85
|
rubocop (~> 1.65)
|
86
|
-
rubocop-minitest (
|
87
|
-
rubocop-performance (
|
88
|
-
rubocop-rake (
|
86
|
+
rubocop-minitest (~> 0.38)
|
87
|
+
rubocop-performance (~> 1.0)
|
88
|
+
rubocop-rake (~> 0.7)
|
89
89
|
simplecov (~> 0.22)
|
90
90
|
simplecov-cobertura (~> 2.1)
|
91
91
|
yard (~> 0.9)
|
data/lib/others.rb
CHANGED
@@ -3,115 +3,120 @@
|
|
3
3
|
# SPDX-FileCopyrightText: Copyright (c) 2024-2025 Yegor Bugayenko
|
4
4
|
# SPDX-License-Identifier: MIT
|
5
5
|
|
6
|
-
#
|
7
|
-
|
8
|
-
#
|
9
|
-
#
|
10
|
-
#
|
11
|
-
#
|
12
|
-
#
|
13
|
-
#
|
14
|
-
#
|
15
|
-
# @
|
16
|
-
#
|
17
|
-
#
|
18
|
-
#
|
19
|
-
|
20
|
-
#
|
21
|
-
#
|
22
|
-
#
|
23
|
-
#
|
24
|
-
#
|
25
|
-
#
|
26
|
-
#
|
27
|
-
#
|
28
|
-
#
|
29
|
-
#
|
30
|
-
#
|
31
|
-
#
|
32
|
-
#
|
33
|
-
# calc
|
34
|
-
#
|
35
|
-
#
|
36
|
-
#
|
37
|
-
#
|
38
|
-
#
|
39
|
-
#
|
40
|
-
|
41
|
-
|
42
|
-
|
43
|
-
|
44
|
-
|
45
|
-
|
6
|
+
# System module.
|
7
|
+
module Kernel
|
8
|
+
# Creates an object that responds to any method call by executing a provided block.
|
9
|
+
#
|
10
|
+
# This method can be used in two ways:
|
11
|
+
# 1. As a standalone function to create an object with dynamic method handling
|
12
|
+
# 2. Inside a class definition to add catch-all method handling to instances
|
13
|
+
#
|
14
|
+
# @param attrs [Hash] Instance variables to set on the created object (only for standalone usage)
|
15
|
+
# @param block [Proc] The block to execute when any method is called on the object
|
16
|
+
#
|
17
|
+
# @example Standalone usage with instance variables
|
18
|
+
# obj = others(counter: 0) do |method_name, *args|
|
19
|
+
# @counter += args.first
|
20
|
+
# end
|
21
|
+
# obj.add(5) # => 5
|
22
|
+
# obj.increment(3) # => 8
|
23
|
+
#
|
24
|
+
# @example Class usage for catch-all methods
|
25
|
+
# class Calculator
|
26
|
+
# def add(a, b)
|
27
|
+
# a + b
|
28
|
+
# end
|
29
|
+
# others do |method_name, *args|
|
30
|
+
# args.reduce(:*)
|
31
|
+
# end
|
32
|
+
# end
|
33
|
+
# calc = Calculator.new
|
34
|
+
# calc.add(2, 3) # => 5 (defined method)
|
35
|
+
# calc.multiply(2, 3, 4) # => 24 (caught by others)
|
36
|
+
#
|
37
|
+
# @return [Object] An instance that responds to any method call
|
38
|
+
#
|
39
|
+
# Author:: Yegor Bugayenko (yegor256@gmail.com)
|
40
|
+
# Copyright:: Copyright (c) 2024-2025 Yegor Bugayenko
|
41
|
+
# License:: MIT
|
42
|
+
def others(attrs = {}, &block)
|
43
|
+
if is_a?(Class)
|
44
|
+
class_exec(block) do |b|
|
45
|
+
# rubocop:disable Style/ClassVars
|
46
|
+
class_variable_set(:@@__others_block__, b)
|
47
|
+
# rubocop:enable Style/ClassVars
|
46
48
|
|
47
|
-
|
48
|
-
|
49
|
-
|
50
|
-
|
51
|
-
|
52
|
-
|
53
|
-
|
54
|
-
|
55
|
-
|
49
|
+
# Handles all undefined method calls by executing the stored block.
|
50
|
+
#
|
51
|
+
# @param args [Array] Method name and arguments passed to the undefined method
|
52
|
+
# @raise [RuntimeError] If a block is provided to the method call
|
53
|
+
# @return [Object] The result of executing the stored block
|
54
|
+
def method_missing(*args, &block)
|
55
|
+
b = self.class.class_variable_get(:@@__others_block__)
|
56
|
+
args += [block] if block_given?
|
57
|
+
instance_exec(*args, &b)
|
58
|
+
end
|
56
59
|
|
57
|
-
|
58
|
-
|
59
|
-
|
60
|
-
|
61
|
-
|
62
|
-
|
63
|
-
|
64
|
-
|
60
|
+
# Always returns true to indicate this object responds to any method.
|
61
|
+
#
|
62
|
+
# @param _mtd [Symbol, String] The method name being queried
|
63
|
+
# @param _inc [Boolean] Whether to include private methods
|
64
|
+
# @return [true] Always returns true
|
65
|
+
def respond_to?(_mtd, _inc = false)
|
66
|
+
true
|
67
|
+
end
|
65
68
|
|
66
|
-
|
67
|
-
|
68
|
-
|
69
|
-
|
70
|
-
|
71
|
-
|
72
|
-
|
73
|
-
end
|
74
|
-
end
|
75
|
-
else
|
76
|
-
c = Class.new do
|
77
|
-
def initialize(attrs, &block)
|
78
|
-
# rubocop:disable Style/HashEachMethods
|
79
|
-
# rubocop:disable Lint/UnusedBlockArgument
|
80
|
-
attrs.each do |k, v|
|
81
|
-
instance_eval("@#{k} = v", __FILE__, __LINE__) # @foo = v
|
69
|
+
# Indicates that any missing method should be considered as responding.
|
70
|
+
#
|
71
|
+
# @param _mtd [Symbol, String] The method name being queried
|
72
|
+
# @param _inc [Boolean] Whether to include private methods
|
73
|
+
# @return [true] Always returns true
|
74
|
+
def respond_to_missing?(_mtd, _inc = false)
|
75
|
+
true
|
82
76
|
end
|
83
|
-
# rubocop:enable Style/HashEachMethods
|
84
|
-
# rubocop:enable Lint/UnusedBlockArgument
|
85
|
-
@block = block
|
86
77
|
end
|
78
|
+
else
|
79
|
+
c = Class.new do
|
80
|
+
def initialize(attrs, &block)
|
81
|
+
# rubocop:disable Style/HashEachMethods
|
82
|
+
# rubocop:disable Lint/UnusedBlockArgument
|
83
|
+
attrs.each do |k, v|
|
84
|
+
instance_eval("@#{k} = v", __FILE__, __LINE__) # @foo = v
|
85
|
+
end
|
86
|
+
# rubocop:enable Style/HashEachMethods
|
87
|
+
# rubocop:enable Lint/UnusedBlockArgument
|
88
|
+
@block = block
|
89
|
+
end
|
87
90
|
|
88
|
-
|
89
|
-
|
90
|
-
|
91
|
-
|
92
|
-
|
93
|
-
|
94
|
-
|
95
|
-
|
91
|
+
# Handles all undefined method calls by executing the stored block.
|
92
|
+
#
|
93
|
+
# @param args [Array] Method name and arguments passed to the undefined method
|
94
|
+
# @raise [RuntimeError] If a block is provided to the method call
|
95
|
+
# @return [Object] The result of executing the stored block
|
96
|
+
def method_missing(*args, &block)
|
97
|
+
args += [block] if block_given?
|
98
|
+
instance_exec(*args, &@block)
|
99
|
+
end
|
96
100
|
|
97
|
-
|
98
|
-
|
99
|
-
|
100
|
-
|
101
|
-
|
102
|
-
|
103
|
-
|
104
|
-
|
101
|
+
# Always returns true to indicate this object responds to any method.
|
102
|
+
#
|
103
|
+
# @param _mtd [Symbol, String] The method name being queried
|
104
|
+
# @param _inc [Boolean] Whether to include private methods
|
105
|
+
# @return [true] Always returns true
|
106
|
+
def respond_to?(_mtd, _inc = false)
|
107
|
+
true
|
108
|
+
end
|
105
109
|
|
106
|
-
|
107
|
-
|
108
|
-
|
109
|
-
|
110
|
-
|
111
|
-
|
112
|
-
|
110
|
+
# Indicates that any missing method should be considered as responding.
|
111
|
+
#
|
112
|
+
# @param _mtd [Symbol, String] The method name being queried
|
113
|
+
# @param _inc [Boolean] Whether to include private methods
|
114
|
+
# @return [true] Always returns true
|
115
|
+
def respond_to_missing?(_mtd, _inc = false)
|
116
|
+
true
|
117
|
+
end
|
113
118
|
end
|
119
|
+
c.new(attrs, &block)
|
114
120
|
end
|
115
|
-
c.new(attrs, &block)
|
116
121
|
end
|
117
122
|
end
|
data/others.gemspec
CHANGED
@@ -4,13 +4,12 @@
|
|
4
4
|
# SPDX-License-Identifier: MIT
|
5
5
|
|
6
6
|
require 'English'
|
7
|
-
require_relative 'lib/others'
|
8
7
|
|
9
8
|
Gem::Specification.new do |s|
|
10
9
|
s.required_rubygems_version = Gem::Requirement.new('>= 0') if s.respond_to? :required_rubygems_version=
|
11
10
|
s.required_ruby_version = '>=3.0'
|
12
11
|
s.name = 'others'
|
13
|
-
s.version = '0.1.
|
12
|
+
s.version = '0.1.1'
|
14
13
|
s.license = 'MIT'
|
15
14
|
s.summary = 'others'
|
16
15
|
s.description =
|
data/test/test__helper.rb
CHANGED
@@ -8,21 +8,19 @@ $stdout.sync = true
|
|
8
8
|
require 'simplecov'
|
9
9
|
require 'simplecov-cobertura'
|
10
10
|
unless SimpleCov.running
|
11
|
-
SimpleCov.command_name('test')
|
12
11
|
SimpleCov.formatter = SimpleCov::Formatter::MultiFormatter.new(
|
13
12
|
[
|
14
13
|
SimpleCov::Formatter::HTMLFormatter,
|
15
14
|
SimpleCov::Formatter::CoberturaFormatter
|
16
15
|
]
|
17
16
|
)
|
18
|
-
SimpleCov.minimum_coverage
|
19
|
-
SimpleCov.minimum_coverage_by_file
|
17
|
+
SimpleCov.minimum_coverage 85
|
18
|
+
SimpleCov.minimum_coverage_by_file 85
|
20
19
|
SimpleCov.start do
|
21
20
|
add_filter 'test/'
|
22
21
|
add_filter 'vendor/'
|
23
22
|
add_filter 'target/'
|
24
23
|
track_files 'lib/**/*.rb'
|
25
|
-
track_files '*.rb'
|
26
24
|
end
|
27
25
|
end
|
28
26
|
|
data/test/test_others.rb
CHANGED
@@ -3,9 +3,8 @@
|
|
3
3
|
# SPDX-FileCopyrightText: Copyright (c) 2024-2025 Yegor Bugayenko
|
4
4
|
# SPDX-License-Identifier: MIT
|
5
5
|
|
6
|
-
require 'minitest/autorun'
|
7
|
-
require_relative '../lib/others'
|
8
6
|
require_relative 'test__helper'
|
7
|
+
require_relative '../lib/others'
|
9
8
|
|
10
9
|
# Others main module test.
|
11
10
|
# Author:: Yegor Bugayenko (yegor256@gmail.com)
|
@@ -29,11 +28,13 @@ class TestOthers < Minitest::Test
|
|
29
28
|
end
|
30
29
|
end
|
31
30
|
x.foo = 42
|
31
|
+
assert_respond_to(x, :foo)
|
32
32
|
assert_equal(42, x.foo)
|
33
33
|
end
|
34
34
|
|
35
35
|
def test_as_function_with_args
|
36
36
|
x = others(foo: 42) do |*args|
|
37
|
+
raise "Must be just two arg here, given: #{args}" unless args.size == 2
|
37
38
|
@foo + args[1]
|
38
39
|
end
|
39
40
|
assert_equal(97, x.bar(55))
|
@@ -61,10 +62,12 @@ class TestOthers < Minitest::Test
|
|
61
62
|
abc + 1
|
62
63
|
end
|
63
64
|
others do |*args|
|
65
|
+
raise "Must be just two arg here, given: #{args}" unless args.size == 2
|
64
66
|
args[1] + 2
|
65
67
|
end
|
66
68
|
end
|
67
69
|
x = cx.new
|
70
|
+
assert_respond_to(x, :foo)
|
68
71
|
assert_equal(43, x.foo(42))
|
69
72
|
assert_equal(44, x.bar(42))
|
70
73
|
end
|