warning 0.10.1 → 1.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 +5 -5
- data/CHANGELOG +32 -0
- data/MIT-LICENSE +1 -1
- data/README.rdoc +56 -5
- data/lib/warning.rb +144 -26
- data/test/fixtures/mismatched_indentations.rb +4 -0
- data/test/test_freeze_warning.rb +7 -7
- data/test/test_warning.rb +286 -34
- metadata +29 -10
checksums.yaml
CHANGED
@@ -1,7 +1,7 @@
|
|
1
1
|
---
|
2
|
-
|
3
|
-
metadata.gz:
|
4
|
-
data.tar.gz:
|
2
|
+
SHA256:
|
3
|
+
metadata.gz: aed045b84ec748f7558ea24268aef892d0efcd7d0f0f51cca7b5cf5f95d1aae7
|
4
|
+
data.tar.gz: ad651f6e4f47d4b6064f7863d145d2747fab8477a27a5234e2e3336d85d1ae17
|
5
5
|
SHA512:
|
6
|
-
metadata.gz:
|
7
|
-
data.tar.gz:
|
6
|
+
metadata.gz: ead742a4b97033e1d1b6ec6460039d7f2138ba8586709a2819303ad0d6791daa26821ee7fd35a9701b2bf7d4ae01f47ef485781331ca77f116ef92d1ec06dada
|
7
|
+
data.tar.gz: 935a429f2a967a57e67bf44739e0583abf186fe3baeaee0ce61532e9083844971ba956ca55831f18092d80652f7090d30f0d1da06758186fccebb98b0f78b18a
|
data/CHANGELOG
CHANGED
@@ -1,3 +1,35 @@
|
|
1
|
+
=== 1.2.1 (2021-10-04)
|
2
|
+
|
3
|
+
* Recognize additional void context warnings (kachick) (#13)
|
4
|
+
|
5
|
+
=== 1.2.0 (2021-02-16)
|
6
|
+
|
7
|
+
* Add support for :void_context as regexp argument to Warning.ignore (jeremyevans)
|
8
|
+
|
9
|
+
* Support :category keyword to Warning.warn on Ruby 3.0 (jeremyevans)
|
10
|
+
|
11
|
+
* Fix :taint warning handling on Ruby 3.0 (jeremyevans)
|
12
|
+
|
13
|
+
* Fix :ambiguous_slash warning handling on Ruby 3.0 (jeremyevans)
|
14
|
+
|
15
|
+
=== 1.1.0 (2020-06-12)
|
16
|
+
|
17
|
+
* Allow Warning.process to be called with a hash of actions instead of a block (jeremyevans)
|
18
|
+
|
19
|
+
* Handle Warning.process blocks that return :default, :backtrace, or :raise specially (jeremyevans)
|
20
|
+
|
21
|
+
* Add support for :mismatched_indentations as regexp argument to Warning.ignore (qortex) (#7)
|
22
|
+
|
23
|
+
=== 1.0.0 (2020-01-21)
|
24
|
+
|
25
|
+
* Add support for :taint as regexp argument to Warning.ignore (jeremyevans)
|
26
|
+
|
27
|
+
* Add support for :safe as regexp argument to Warning.ignore (jeremyevans)
|
28
|
+
|
29
|
+
* Add Warning.dedup for deduplicating warnings (jeremyevans)
|
30
|
+
|
31
|
+
* Add support for :keyword_separation as regexp argument to Warning.ignore (jeremyevans)
|
32
|
+
|
1
33
|
=== 0.10.1 (2017-11-16)
|
2
34
|
|
3
35
|
* Correctly handle Warning.freeze (jeremyevans)
|
data/MIT-LICENSE
CHANGED
data/README.rdoc
CHANGED
@@ -2,8 +2,9 @@
|
|
2
2
|
|
3
3
|
ruby-warning adds custom processing for warnings, including the
|
4
4
|
ability to ignore specific warning messages, ignore warnings
|
5
|
-
in specific files/directories,
|
6
|
-
warnings
|
5
|
+
in specific files/directories, include backtraces with warnings,
|
6
|
+
treat warnings as errors, deduplicate warnings, and add
|
7
|
+
custom handling for all warnings in specific files/directories.
|
7
8
|
|
8
9
|
ruby-warning requires ruby 2.4+, as previous versions of ruby do
|
9
10
|
not support custom processing of warnings.
|
@@ -30,13 +31,18 @@ appropriate regexp. The supported symbols are:
|
|
30
31
|
* :ambiguous_slash
|
31
32
|
* :bignum
|
32
33
|
* :fixnum
|
34
|
+
* :keyword_separation
|
33
35
|
* :method_redefined
|
36
|
+
* :mismatched_indentations
|
34
37
|
* :missing_gvar
|
35
38
|
* :missing_ivar
|
36
39
|
* :not_reached
|
40
|
+
* :safe
|
37
41
|
* :shadow
|
42
|
+
* :taint
|
38
43
|
* :unused_var
|
39
44
|
* :useless_operator
|
45
|
+
* :void_context
|
40
46
|
|
41
47
|
<tt>Warning.process</tt> takes an optional path prefix and a block, and if the
|
42
48
|
warning string starts with the path prefix, it calls the block with the warning
|
@@ -44,15 +50,35 @@ string instead of performing the default behavior. You can call
|
|
44
50
|
<tt>Warning.process</tt> multiple times and it will operate intelligently,
|
45
51
|
choosing the longest path prefix that the string starts with.
|
46
52
|
|
47
|
-
<tt>Warning.
|
48
|
-
|
53
|
+
<tt>Warning.process</tt> blocks can return +:default+ to use the default
|
54
|
+
behavior, +:backtrace+ to use the default behavior and also print the backtrace
|
55
|
+
or +:raise+ to raise the warning string as a RuntimeError.
|
56
|
+
|
57
|
+
<tt>Warning.process</tt> can also accept a hash of actions instead of a block,
|
58
|
+
with keys being regexps (or symbols supported by <tt>Warning.ignore</tt>) and
|
59
|
+
values being callable objects (or +:default+, +:backtrace+, or +:raise+).
|
60
|
+
|
61
|
+
<tt>Warning.dedup</tt> deduplicates warnings, so that if a warning is received
|
62
|
+
that is the same as a warning that has already been processed, the warning is
|
63
|
+
ignored. Note that this should be used with care, since if the application
|
64
|
+
generates an arbitrary number of unique warnings, that can lead to unbounded
|
65
|
+
memory growth.
|
66
|
+
|
67
|
+
<tt>Warning.clear</tt> resets the library to its initial state, clearing the
|
68
|
+
current ignored warnings and warning processors, and turning off deduplication.
|
49
69
|
|
50
70
|
By using path prefixes, it's fairly easy for a gem to set that specific warnings
|
51
71
|
should be ignored inside the gem's directory.
|
52
72
|
|
53
73
|
Note that path prefixes will not correctly handle warnings raised by
|
54
74
|
<tt>Kernel#warn</tt>, unless the warning message given to <tt>Kernel#warn</tt>
|
55
|
-
starts with the filename where the warning is used.
|
75
|
+
starts with the filename where the warning is used. The <tt>Kernel#warn</tt>
|
76
|
+
+:uplevel+ option will make sure the warning starts with the filename.
|
77
|
+
|
78
|
+
Note that many of the warnings this library can ignore are warnings caused
|
79
|
+
during compilation (i.e. when files are loaded via require). You should
|
80
|
+
require this library and setup the appropriate warning handling before
|
81
|
+
loading any code that could cause warnings.
|
56
82
|
|
57
83
|
= Examples
|
58
84
|
|
@@ -78,6 +104,31 @@ starts with the filename where the warning is used.
|
|
78
104
|
LOGGER.error(warning)
|
79
105
|
end
|
80
106
|
|
107
|
+
# Write warnings in the current file to $stderr, but include backtrace
|
108
|
+
Warning.process(__FILE__) do |warning|
|
109
|
+
:backtrace
|
110
|
+
end
|
111
|
+
|
112
|
+
# Raise warnings in the current file as RuntimeErrors, with the warning
|
113
|
+
# string as the exception message
|
114
|
+
Warning.process(__FILE__) do |warning|
|
115
|
+
:raise
|
116
|
+
end
|
117
|
+
|
118
|
+
# Raise keyword argument separation warnings in the current file as
|
119
|
+
# RuntimeErrors, and write ambiguous slash warnings to $stderr, including
|
120
|
+
# the backtrace
|
121
|
+
Warning.process(__FILE__, keyword_separation: :raise,
|
122
|
+
ambiguous_slash: :backtrace)
|
123
|
+
|
124
|
+
# Deduplicate warnings
|
125
|
+
Warning.dedup
|
126
|
+
|
127
|
+
# Ignore all warnings in Gem dependencies
|
128
|
+
Gem.path.each do |path|
|
129
|
+
Warning.ignore(//, path)
|
130
|
+
end
|
131
|
+
|
81
132
|
= License
|
82
133
|
|
83
134
|
MIT
|
data/lib/warning.rb
CHANGED
@@ -4,7 +4,7 @@ module Warning
|
|
4
4
|
module Processor
|
5
5
|
# Map of symbols to regexps for warning messages to ignore.
|
6
6
|
IGNORE_MAP = {
|
7
|
-
ambiguous_slash: /: warning: ambiguous first argument; put parentheses or a space even after `\/' operator\n\z/,
|
7
|
+
ambiguous_slash: /: warning: ambiguous first argument; put parentheses or a space even after `\/' operator\n\z|: warning: ambiguity between regexp and two divisions: wrap regexp in parentheses or add a space after `\/' operator\n\z/,
|
8
8
|
arg_prefix: /: warning: `[&\*]' interpreted as argument prefix\n\z/,
|
9
9
|
bignum: /: warning: constant ::Bignum is deprecated\n\z/,
|
10
10
|
fixnum: /: warning: constant ::Fixnum is deprecated\n\z/,
|
@@ -15,16 +15,38 @@ module Warning
|
|
15
15
|
shadow: /: warning: shadowing outer local variable - \w+\n\z/,
|
16
16
|
unused_var: /: warning: assigned but unused variable - \w+\n\z/,
|
17
17
|
useless_operator: /: warning: possibly useless use of [><!=]+ in void context\n\z/,
|
18
|
+
keyword_separation: /: warning: (?:Using the last argument (?:for `.+' )?as keyword parameters is deprecated; maybe \*\* should be added to the call|Passing the keyword argument (?:for `.+' )?as the last hash parameter is deprecated|Splitting the last argument (?:for `.+' )?into positional and keyword parameters is deprecated|The called method (?:`.+' )?is defined here)\n\z/,
|
19
|
+
safe: /: warning: (?:rb_safe_level_2_warning|rb_safe_level|rb_set_safe_level_force|rb_set_safe_level|rb_secure|rb_insecure_operation|rb_check_safe_obj|\$SAFE) will (?:be removed|become a normal global variable) in Ruby 3\.0\n\z/,
|
20
|
+
taint: /: warning: (?:rb_error_untrusted|rb_check_trusted|Pathname#taint|Pathname#untaint|rb_env_path_tainted|Object#tainted\?|Object#taint|Object#untaint|Object#untrusted\?|Object#untrust|Object#trust|rb_obj_infect|rb_tainted_str_new|rb_tainted_str_new_cstr) is deprecated and will be removed in Ruby 3\.2\.?\n\z/,
|
21
|
+
mismatched_indentations: /: warning: mismatched indentations at '.+' with '.+' at \d+\n\z/,
|
22
|
+
void_context: /possibly useless use of (?:a )?\S+ in void context/,
|
18
23
|
}
|
19
24
|
|
20
|
-
#
|
25
|
+
# Map of action symbols to procs that return the symbol
|
26
|
+
ACTION_PROC_MAP = {
|
27
|
+
default: proc{|_| :default},
|
28
|
+
backtrace: proc{|_| :backtrace},
|
29
|
+
raise: proc{|_| :raise},
|
30
|
+
}
|
31
|
+
private_constant :ACTION_PROC_MAP
|
32
|
+
|
33
|
+
# Clear all current ignored warnings, warning processors, and duplicate check cache.
|
34
|
+
# Also disables deduplicating warnings if that is currently enabled.
|
21
35
|
def clear
|
22
36
|
synchronize do
|
23
37
|
@ignore.clear
|
24
38
|
@process.clear
|
39
|
+
@dedup = false
|
25
40
|
end
|
26
41
|
end
|
27
42
|
|
43
|
+
# Deduplicate warnings, suppress warning messages if the same warning message
|
44
|
+
# has already occurred. Note that this can lead to unbounded memory use
|
45
|
+
# if unique warnings are generated.
|
46
|
+
def dedup
|
47
|
+
@dedup = {}
|
48
|
+
end
|
49
|
+
|
28
50
|
def freeze
|
29
51
|
@ignore.freeze
|
30
52
|
@process.freeze
|
@@ -40,6 +62,7 @@ module Warning
|
|
40
62
|
# :ambiguous_slash :: Ignore warnings for things like <tt>method /regexp/</tt>
|
41
63
|
# :bignum :: Ignore warnings when referencing the ::Bignum constant.
|
42
64
|
# :fixnum :: Ignore warnings when referencing the ::Fixnum constant.
|
65
|
+
# :keyword_separation :: Ignore warnings related to keyword argument separation.
|
43
66
|
# :method_redefined :: Ignore warnings when defining a method in a class/module where a
|
44
67
|
# method of the same name was already defined in that class/module.
|
45
68
|
# :missing_gvar :: Ignore warnings for accesses to global variables
|
@@ -47,10 +70,14 @@ module Warning
|
|
47
70
|
# :missing_ivar :: Ignore warnings for accesses to instance variables
|
48
71
|
# that have not yet been initialized
|
49
72
|
# :not_reached :: Ignore statement not reached warnings.
|
73
|
+
# :safe :: Ignore warnings related to $SAFE and related C-API functions.
|
50
74
|
# :shadow :: Ignore warnings related to shadowing outer local variables.
|
75
|
+
# :taint :: Ignore warnings related to taint and related methods and C-API functions.
|
51
76
|
# :unused_var :: Ignore warnings for unused variables.
|
52
77
|
# :useless_operator :: Ignore warnings when using operators such as == and > when the
|
53
78
|
# result is not used.
|
79
|
+
# :void_context :: Ignore warnings for :: to reference constants when the result is not
|
80
|
+
# used (often used to trigger autoload).
|
54
81
|
#
|
55
82
|
# Examples:
|
56
83
|
#
|
@@ -66,14 +93,7 @@ module Warning
|
|
66
93
|
# # Ignore all uninitialized instance variable and method redefined warnings in current file
|
67
94
|
# Warning.ignore([:missing_ivar, :method_redefined], __FILE__)
|
68
95
|
def ignore(regexp, path='')
|
69
|
-
|
70
|
-
when Regexp
|
71
|
-
# already regexp
|
72
|
-
when Symbol
|
73
|
-
regexp = IGNORE_MAP.fetch(regexp)
|
74
|
-
when Array
|
75
|
-
regexp = Regexp.union(regexp.map{|re| IGNORE_MAP.fetch(re)})
|
76
|
-
else
|
96
|
+
unless regexp = convert_regexp(regexp)
|
77
97
|
raise TypeError, "first argument to Warning.ignore should be Regexp, Symbol, or Array of Symbols, got #{regexp.inspect}"
|
78
98
|
end
|
79
99
|
|
@@ -95,7 +115,52 @@ module Warning
|
|
95
115
|
# Warning.process(__FILE__) do |warning|
|
96
116
|
# LOGGER.error(warning)
|
97
117
|
# end
|
98
|
-
|
118
|
+
#
|
119
|
+
# The block can return one of the following symbols:
|
120
|
+
#
|
121
|
+
# :default :: Take the default action (call super, printing to $stderr).
|
122
|
+
# :backtrace :: Take the default action (call super, printing to $stderr),
|
123
|
+
# and also print the backtrace.
|
124
|
+
# :raise :: Raise a RuntimeError with the warning as the message.
|
125
|
+
#
|
126
|
+
# If the block returns anything else, it is assumed the block completely handled
|
127
|
+
# the warning and takes no other action.
|
128
|
+
#
|
129
|
+
# Instead of passing a block, you can pass a hash of actions to take for specific
|
130
|
+
# warnings, using regexp as keys and a callable objects as values:
|
131
|
+
#
|
132
|
+
# Warning.process(__FILE__,
|
133
|
+
# /instance variable @\w+ not initialized/ => proc do |warning|
|
134
|
+
# LOGGER.warning(warning)
|
135
|
+
# end,
|
136
|
+
# /global variable `\$\w+' not initialized/ => proc do |warning|
|
137
|
+
# LOGGER.error(warning)
|
138
|
+
# end
|
139
|
+
# )
|
140
|
+
#
|
141
|
+
# Instead of passing a regexp as a key, you can pass a symbol that is recognized
|
142
|
+
# by Warning.ignore. Instead of passing a callable object as a value, you can
|
143
|
+
# pass a symbol, which will be treated as a callable object that returns that symbol:
|
144
|
+
#
|
145
|
+
# Warning.process(__FILE__, :missing_ivar=>:backtrace, :keyword_separation=>:raise)
|
146
|
+
def process(path='', actions=nil, &block)
|
147
|
+
if block
|
148
|
+
if actions
|
149
|
+
raise ArgumentError, "cannot pass both actions and block to Warning.process"
|
150
|
+
end
|
151
|
+
elsif actions
|
152
|
+
block = {}
|
153
|
+
actions.each do |regexp, value|
|
154
|
+
unless regexp = convert_regexp(regexp)
|
155
|
+
raise TypeError, "action provided to Warning.process should be Regexp, Symbol, or Array of Symbols, got #{regexp.inspect}"
|
156
|
+
end
|
157
|
+
|
158
|
+
block[regexp] = ACTION_PROC_MAP[value] || value
|
159
|
+
end
|
160
|
+
else
|
161
|
+
raise ArgumentError, "must pass either actions or block to Warning.process"
|
162
|
+
end
|
163
|
+
|
99
164
|
synchronize do
|
100
165
|
@process << [path, block]
|
101
166
|
@process.sort_by!(&:first)
|
@@ -104,28 +169,80 @@ module Warning
|
|
104
169
|
nil
|
105
170
|
end
|
106
171
|
|
107
|
-
|
108
|
-
|
109
|
-
|
110
|
-
|
111
|
-
|
112
|
-
|
113
|
-
|
172
|
+
|
173
|
+
if RUBY_VERSION >= '3.0'
|
174
|
+
method_args = ', category: nil'
|
175
|
+
super_ = "category ? super : super(str)"
|
176
|
+
else
|
177
|
+
super_ = "super"
|
178
|
+
end
|
179
|
+
|
180
|
+
class_eval(<<-END, __FILE__, __LINE__+1)
|
181
|
+
def warn(str#{method_args})
|
182
|
+
synchronize{@ignore.dup}.each do |path, regexp|
|
183
|
+
if str.start_with?(path) && str =~ regexp
|
184
|
+
return
|
185
|
+
end
|
114
186
|
end
|
115
|
-
end
|
116
187
|
|
117
|
-
|
118
|
-
|
119
|
-
|
120
|
-
|
188
|
+
if @dedup
|
189
|
+
if synchronize{@dedup[str]}
|
190
|
+
return
|
191
|
+
end
|
192
|
+
|
193
|
+
synchronize{@dedup[str] = true}
|
121
194
|
end
|
122
|
-
end
|
123
195
|
|
124
|
-
|
125
|
-
|
196
|
+
action = catch(:action) do
|
197
|
+
synchronize{@process.dup}.each do |path, block|
|
198
|
+
if str.start_with?(path)
|
199
|
+
if block.is_a?(Hash)
|
200
|
+
block.each do |regexp, blk|
|
201
|
+
if str =~ regexp
|
202
|
+
throw :action, blk.call(str)
|
203
|
+
end
|
204
|
+
end
|
205
|
+
else
|
206
|
+
throw :action, block.call(str)
|
207
|
+
end
|
208
|
+
end
|
209
|
+
end
|
210
|
+
|
211
|
+
:default
|
212
|
+
end
|
213
|
+
|
214
|
+
case action
|
215
|
+
when :default
|
216
|
+
#{super_}
|
217
|
+
when :backtrace
|
218
|
+
#{super_}
|
219
|
+
$stderr.puts caller
|
220
|
+
when :raise
|
221
|
+
raise str
|
222
|
+
else
|
223
|
+
# nothing
|
224
|
+
end
|
225
|
+
|
226
|
+
nil
|
227
|
+
end
|
228
|
+
END
|
126
229
|
|
127
230
|
private
|
128
231
|
|
232
|
+
# Convert the given Regexp, Symbol, or Array of Symbols into a Regexp.
|
233
|
+
def convert_regexp(regexp)
|
234
|
+
case regexp
|
235
|
+
when Regexp
|
236
|
+
regexp
|
237
|
+
when Symbol
|
238
|
+
IGNORE_MAP.fetch(regexp)
|
239
|
+
when Array
|
240
|
+
Regexp.union(regexp.map{|re| IGNORE_MAP.fetch(re)})
|
241
|
+
else
|
242
|
+
# nothing
|
243
|
+
end
|
244
|
+
end
|
245
|
+
|
129
246
|
def synchronize(&block)
|
130
247
|
@monitor.synchronize(&block)
|
131
248
|
end
|
@@ -133,6 +250,7 @@ module Warning
|
|
133
250
|
|
134
251
|
@ignore = []
|
135
252
|
@process = []
|
253
|
+
@dedup = false
|
136
254
|
@monitor = Monitor.new
|
137
255
|
|
138
256
|
extend Processor
|
data/test/test_freeze_warning.rb
CHANGED
@@ -1,4 +1,5 @@
|
|
1
|
-
|
1
|
+
ENV['MT_NO_PLUGINS'] = '1' # Work around stupid autoloading of plugins
|
2
|
+
require 'minitest/global_expectations/autorun'
|
2
3
|
require 'warning'
|
3
4
|
|
4
5
|
class WarningFreezeTest < Minitest::Test
|
@@ -39,31 +40,30 @@ class WarningFreezeTest < Minitest::Test
|
|
39
40
|
end
|
40
41
|
|
41
42
|
def test_warning_ignore
|
42
|
-
obj = Object.new
|
43
43
|
w = nil
|
44
44
|
|
45
|
-
Warning.ignore(/
|
45
|
+
Warning.ignore(/global variable `\$test_warning_ignore' not initialized/)
|
46
46
|
Warning.process do |warning|
|
47
47
|
w = [4, warning]
|
48
48
|
end
|
49
49
|
Warning.freeze
|
50
50
|
|
51
51
|
assert_raises RuntimeError do
|
52
|
-
Warning.ignore(/
|
52
|
+
Warning.ignore(/global variable `\$test_warning_ignore' not initialized/)
|
53
53
|
end
|
54
54
|
assert_raises RuntimeError do
|
55
55
|
Warning.process{|warning| w = [4, warning]}
|
56
56
|
end
|
57
57
|
|
58
58
|
assert_warning '' do
|
59
|
-
|
59
|
+
$test_warning_ignore
|
60
60
|
end
|
61
61
|
assert_nil w
|
62
62
|
|
63
63
|
assert_warning '' do
|
64
|
-
|
64
|
+
$test_warning_ignore2
|
65
65
|
end
|
66
66
|
assert_equal(4, w.first)
|
67
|
-
assert_match(/
|
67
|
+
assert_match(/global variable `\$test_warning_ignore2' not initialized/, w.last)
|
68
68
|
end
|
69
69
|
end
|
data/test/test_warning.rb
CHANGED
@@ -1,11 +1,17 @@
|
|
1
|
-
|
1
|
+
ENV['MT_NO_PLUGINS'] = '1' # Work around stupid autoloading of plugins
|
2
|
+
require 'minitest/global_expectations/autorun'
|
2
3
|
require 'warning'
|
4
|
+
require 'pathname'
|
3
5
|
|
4
6
|
class WarningTest < Minitest::Test
|
5
7
|
module EnvUtil
|
6
8
|
def verbose_warning
|
9
|
+
stderr = ""
|
7
10
|
class << (stderr = "")
|
8
11
|
alias write <<
|
12
|
+
def puts(*a)
|
13
|
+
self << a.join("\n")
|
14
|
+
end
|
9
15
|
end
|
10
16
|
stderr, $stderr, verbose, $VERBOSE = $stderr, stderr, $VERBOSE, true
|
11
17
|
yield stderr
|
@@ -42,49 +48,65 @@ class WarningTest < Minitest::Test
|
|
42
48
|
Warning.clear
|
43
49
|
end
|
44
50
|
|
45
|
-
def
|
46
|
-
|
51
|
+
def test_warning_dedup
|
52
|
+
gvar = ->{$test_warning_dedup}
|
53
|
+
|
54
|
+
assert_warning(/global variable `\$test_warning_dedup' not initialized/) do
|
55
|
+
gvar.call
|
56
|
+
end
|
57
|
+
assert_warning(/global variable `\$test_warning_dedup' not initialized/) do
|
58
|
+
gvar.call
|
59
|
+
end
|
47
60
|
|
48
|
-
|
49
|
-
|
61
|
+
Warning.dedup
|
62
|
+
|
63
|
+
assert_warning(/global variable `\$test_warning_dedup' not initialized/) do
|
64
|
+
gvar.call
|
65
|
+
end
|
66
|
+
assert_warning('') do
|
67
|
+
gvar.call
|
50
68
|
end
|
69
|
+
end
|
51
70
|
|
52
|
-
|
53
|
-
|
71
|
+
def test_warning_ignore
|
72
|
+
assert_warning(/global variable `\$test_warning_ignore' not initialized/) do
|
73
|
+
assert_nil($test_warning_ignore)
|
54
74
|
end
|
55
75
|
|
56
|
-
Warning.ignore(/
|
76
|
+
Warning.ignore(/global variable `\$test_warning_ignore' not initialized/)
|
57
77
|
|
58
78
|
assert_warning '' do
|
59
|
-
assert_nil(
|
79
|
+
assert_nil($test_warning_ignore)
|
60
80
|
end
|
61
81
|
|
62
|
-
assert_warning(/
|
63
|
-
assert_nil(
|
82
|
+
assert_warning(/global variable `\$test_warning_ignore2' not initialized/) do
|
83
|
+
assert_nil($test_warning_ignore2)
|
64
84
|
end
|
65
85
|
|
66
|
-
Warning.ignore(/
|
86
|
+
Warning.ignore(/global variable `\$test_warning_ignore2' not initialized/, __FILE__)
|
67
87
|
|
68
88
|
assert_warning '' do
|
69
|
-
assert_nil(
|
89
|
+
assert_nil($test_warning_ignore2)
|
70
90
|
end
|
71
91
|
|
72
|
-
assert_warning(/
|
73
|
-
assert_nil(
|
92
|
+
assert_warning(/global variable `\$test_warning_ignore3' not initialized/) do
|
93
|
+
assert_nil($test_warning_ignore3)
|
74
94
|
end
|
75
95
|
|
76
|
-
Warning.ignore(/
|
96
|
+
Warning.ignore(/global variable `\$test_warning_ignore3' not initialized/, __FILE__ + 'a')
|
77
97
|
|
78
|
-
assert_warning(/
|
79
|
-
assert_nil(
|
98
|
+
assert_warning(/global variable `\$test_warning_ignore3' not initialized/) do
|
99
|
+
assert_nil($test_warning_ignore3)
|
80
100
|
end
|
81
101
|
end
|
82
102
|
|
83
103
|
def test_warning_ignore_missing_ivar
|
84
104
|
Warning.clear
|
85
105
|
|
86
|
-
|
87
|
-
|
106
|
+
unless RUBY_VERSION >= '3.0'
|
107
|
+
assert_warning(/instance variable @ivar not initialized/) do
|
108
|
+
assert_nil(instance_variable_get(:@ivar))
|
109
|
+
end
|
88
110
|
end
|
89
111
|
|
90
112
|
Warning.ignore(:missing_ivar, __FILE__)
|
@@ -156,9 +178,43 @@ class WarningTest < Minitest::Test
|
|
156
178
|
end
|
157
179
|
end
|
158
180
|
|
181
|
+
def test_warning_ignore_void_context
|
182
|
+
assert_warning(/warning: possibly useless use of :: in void context/) do
|
183
|
+
instance_eval('::Object; nil', __FILE__, __LINE__)
|
184
|
+
end
|
185
|
+
|
186
|
+
Warning.ignore(:void_context, __FILE__)
|
187
|
+
|
188
|
+
assert_warning '' do
|
189
|
+
instance_eval('::Object; nil', __FILE__, __LINE__)
|
190
|
+
end
|
191
|
+
|
192
|
+
assert_warning '' do
|
193
|
+
instance_eval('Object; nil', __FILE__, __LINE__)
|
194
|
+
end
|
195
|
+
|
196
|
+
assert_warning '' do
|
197
|
+
instance_eval('v = 0; v; nil', __FILE__, __LINE__)
|
198
|
+
end
|
199
|
+
|
200
|
+
assert_warning '' do
|
201
|
+
instance_eval('1 > 1; nil', __FILE__, __LINE__)
|
202
|
+
end
|
203
|
+
|
204
|
+
assert_warning '' do
|
205
|
+
instance_eval('defined? C; nil', __FILE__, __LINE__)
|
206
|
+
end
|
207
|
+
|
208
|
+
if RUBY_VERSION >= '2.6'
|
209
|
+
assert_warning '' do
|
210
|
+
instance_eval('1..; nil', __FILE__, __LINE__)
|
211
|
+
end
|
212
|
+
end
|
213
|
+
end
|
214
|
+
|
159
215
|
def test_warning_ignore_ambiguous_slash
|
160
216
|
def self.d(re); end
|
161
|
-
assert_warning(/warning:
|
217
|
+
assert_warning(/warning: ambi/) do
|
162
218
|
instance_eval('d /a/', __FILE__)
|
163
219
|
end
|
164
220
|
|
@@ -219,6 +275,98 @@ class WarningTest < Minitest::Test
|
|
219
275
|
assert_warning '' do
|
220
276
|
instance_eval('lambda{|a| lambda{|a|}}', __FILE__)
|
221
277
|
end
|
278
|
+
end if RUBY_VERSION < '2.6'
|
279
|
+
|
280
|
+
if RUBY_VERSION > '2.7' && RUBY_VERSION < '2.8'
|
281
|
+
def h2kw(**kw)
|
282
|
+
end
|
283
|
+
def kw2h(h, **kw)
|
284
|
+
end
|
285
|
+
def skw(h=1, a: 1)
|
286
|
+
end
|
287
|
+
|
288
|
+
def test_warning_ignore_keyword
|
289
|
+
assert_warning(/warning: Using the last argument as keyword parameters is deprecated; maybe \*\* should be added to the call.*The called method `h2kw' is defined here/m) do
|
290
|
+
h2kw({})
|
291
|
+
end
|
292
|
+
assert_warning(/warning: Passing the keyword argument as the last hash parameter is deprecated.*The called method `kw2h' is defined here/m) do
|
293
|
+
kw2h(a: 1)
|
294
|
+
end
|
295
|
+
assert_warning(/warning: Splitting the last argument into positional and keyword parameters is deprecated.*The called method `skw' is defined here/m) do
|
296
|
+
skw("b" => 1, a: 2)
|
297
|
+
end
|
298
|
+
assert_warning(/warning: Splitting the last argument into positional and keyword parameters is deprecated.*The called method `skw' is defined here/m) do
|
299
|
+
skw({"b" => 1, a: 2})
|
300
|
+
end
|
301
|
+
|
302
|
+
Warning.ignore(:keyword_separation, __FILE__)
|
303
|
+
|
304
|
+
assert_warning '' do
|
305
|
+
h2kw({})
|
306
|
+
kw2h(a: 1)
|
307
|
+
skw("b" => 1, a: 2)
|
308
|
+
skw({"b" => 1, a: 2})
|
309
|
+
end
|
310
|
+
end
|
311
|
+
|
312
|
+
def test_warning_ignore_safe
|
313
|
+
assert_warning(/\$SAFE will become a normal global variable in Ruby 3\.0/) do
|
314
|
+
$SAFE = 0
|
315
|
+
end
|
316
|
+
|
317
|
+
Warning.ignore(:safe, __FILE__)
|
318
|
+
|
319
|
+
assert_warning("") do
|
320
|
+
$SAFE = 0
|
321
|
+
end
|
322
|
+
end
|
323
|
+
end
|
324
|
+
|
325
|
+
if RUBY_VERSION > '2.7' && RUBY_VERSION < '3.2'
|
326
|
+
|
327
|
+
def test_warning_ignore_taint
|
328
|
+
o = Object.new
|
329
|
+
|
330
|
+
assert_warning(/Object#taint is deprecated and will be removed in Ruby 3\.2/) do
|
331
|
+
o.taint
|
332
|
+
end
|
333
|
+
assert_warning(/Object#untaint is deprecated and will be removed in Ruby 3\.2/) do
|
334
|
+
o.untaint
|
335
|
+
end
|
336
|
+
assert_warning(/Object#tainted\? is deprecated and will be removed in Ruby 3\.2/) do
|
337
|
+
o.tainted?
|
338
|
+
end
|
339
|
+
assert_warning(/Object#trust is deprecated and will be removed in Ruby 3\.2/) do
|
340
|
+
o.trust
|
341
|
+
end
|
342
|
+
assert_warning(/Object#untrust is deprecated and will be removed in Ruby 3\.2/) do
|
343
|
+
o.untrust
|
344
|
+
end
|
345
|
+
assert_warning(/Object#untrusted\? is deprecated and will be removed in Ruby 3\.2/) do
|
346
|
+
o.untrusted?
|
347
|
+
end
|
348
|
+
|
349
|
+
path = Pathname.new(__FILE__)
|
350
|
+
assert_warning(/Pathname#taint is deprecated and will be removed in Ruby 3\.2/) do
|
351
|
+
path.taint
|
352
|
+
end
|
353
|
+
assert_warning(/Pathname#untaint is deprecated and will be removed in Ruby 3\.2/) do
|
354
|
+
path.untaint
|
355
|
+
end
|
356
|
+
|
357
|
+
Warning.ignore(:taint, __FILE__)
|
358
|
+
|
359
|
+
assert_warning("") do
|
360
|
+
o.taint
|
361
|
+
o.untaint
|
362
|
+
o.tainted?
|
363
|
+
o.trust
|
364
|
+
o.untrust
|
365
|
+
o.untrusted?
|
366
|
+
p.taint
|
367
|
+
p.untaint
|
368
|
+
end
|
369
|
+
end
|
222
370
|
end
|
223
371
|
|
224
372
|
def test_warning_ignore_symbol_array
|
@@ -235,16 +383,27 @@ class WarningTest < Minitest::Test
|
|
235
383
|
end
|
236
384
|
end
|
237
385
|
|
386
|
+
def test_warning_ignore_mismatched_indentation
|
387
|
+
assert_warning(/warning: mismatched indentations/) do
|
388
|
+
load 'test/fixtures/mismatched_indentations.rb'
|
389
|
+
end
|
390
|
+
|
391
|
+
Warning.ignore(:mismatched_indentations, 'test/fixtures/mismatched_indentations.rb')
|
392
|
+
|
393
|
+
assert_warning '' do
|
394
|
+
load 'test/fixtures/mismatched_indentations.rb'
|
395
|
+
end
|
396
|
+
end
|
397
|
+
|
238
398
|
def test_warning_process
|
239
|
-
obj = Object.new
|
240
399
|
warn = nil
|
241
400
|
|
242
401
|
Warning.process(__FILE__+'a') do |warning|
|
243
402
|
warn = [0, warning]
|
244
403
|
end
|
245
404
|
|
246
|
-
assert_warning(/
|
247
|
-
|
405
|
+
assert_warning(/global variable `\$test_warning_process' not initialized/) do
|
406
|
+
$test_warning_process
|
248
407
|
end
|
249
408
|
assert_nil(warn)
|
250
409
|
|
@@ -253,10 +412,10 @@ class WarningTest < Minitest::Test
|
|
253
412
|
end
|
254
413
|
|
255
414
|
assert_warning '' do
|
256
|
-
|
415
|
+
$test_warning_process2
|
257
416
|
end
|
258
417
|
assert_equal(1, warn.first)
|
259
|
-
assert_match(/
|
418
|
+
assert_match(/global variable `\$test_warning_process2' not initialized/, warn.last)
|
260
419
|
warn = nil
|
261
420
|
|
262
421
|
Warning.process(File.dirname(__FILE__)) do |warning|
|
@@ -264,10 +423,10 @@ class WarningTest < Minitest::Test
|
|
264
423
|
end
|
265
424
|
|
266
425
|
assert_warning '' do
|
267
|
-
|
426
|
+
$test_warning_process3
|
268
427
|
end
|
269
428
|
assert_equal(1, warn.first)
|
270
|
-
assert_match(/
|
429
|
+
assert_match(/global variable `\$test_warning_process3' not initialized/, warn.last)
|
271
430
|
warn = nil
|
272
431
|
|
273
432
|
Warning.process(__FILE__+':') do |warning|
|
@@ -275,16 +434,16 @@ class WarningTest < Minitest::Test
|
|
275
434
|
end
|
276
435
|
|
277
436
|
assert_warning '' do
|
278
|
-
|
437
|
+
$test_warning_process4
|
279
438
|
end
|
280
439
|
assert_equal(3, warn.first)
|
281
|
-
assert_match(/
|
440
|
+
assert_match(/global variable `\$test_warning_process4' not initialized/, warn.last)
|
282
441
|
warn = nil
|
283
442
|
|
284
443
|
Warning.clear
|
285
444
|
|
286
|
-
assert_warning(/
|
287
|
-
|
445
|
+
assert_warning(/global variable `\$test_warning_process5' not initialized/) do
|
446
|
+
$test_warning_process5
|
288
447
|
end
|
289
448
|
assert_nil(warn)
|
290
449
|
|
@@ -293,9 +452,102 @@ class WarningTest < Minitest::Test
|
|
293
452
|
end
|
294
453
|
|
295
454
|
assert_warning '' do
|
296
|
-
|
455
|
+
$test_warning_process6
|
297
456
|
end
|
298
457
|
assert_equal(4, warn.first)
|
299
|
-
assert_match(/
|
458
|
+
assert_match(/global variable `\$test_warning_process6' not initialized/, warn.last)
|
459
|
+
end
|
460
|
+
|
461
|
+
def test_warning_process_block_return_default
|
462
|
+
w = nil
|
463
|
+
Warning.process(__FILE__) do |warning|
|
464
|
+
w = warning
|
465
|
+
:default
|
466
|
+
end
|
467
|
+
|
468
|
+
assert_warning(/global variable `\$test_warning_process_block_return_default' not initialized/) do
|
469
|
+
$test_warning_process_block_return_default
|
470
|
+
end
|
471
|
+
assert_match(/global variable `\$test_warning_process_block_return_default' not initialized/, w)
|
472
|
+
end
|
473
|
+
|
474
|
+
def test_warning_process_block_return_backtrace
|
475
|
+
w = nil
|
476
|
+
Warning.process(__FILE__) do |warning|
|
477
|
+
w = warning
|
478
|
+
:backtrace
|
479
|
+
end
|
480
|
+
|
481
|
+
assert_warning(/global variable `\$test_warning_process_block_return_backtrace' not initialized.*#{__FILE__}/m) do
|
482
|
+
$test_warning_process_block_return_backtrace
|
483
|
+
end
|
484
|
+
assert_match(/global variable `\$test_warning_process_block_return_backtrace' not initialized/, w)
|
485
|
+
end
|
486
|
+
|
487
|
+
def test_warning_process_block_return_raise
|
488
|
+
w = nil
|
489
|
+
Warning.process(__FILE__) do |warning|
|
490
|
+
w = warning
|
491
|
+
:raise
|
492
|
+
end
|
493
|
+
|
494
|
+
assert_raises(RuntimeError) do
|
495
|
+
$test_warning_process_block_return_raise
|
496
|
+
end
|
497
|
+
assert_match(/global variable `\$test_warning_process_block_return_raise' not initialized/, w)
|
498
|
+
end
|
499
|
+
|
500
|
+
def test_warning_process_action
|
501
|
+
w = nil
|
502
|
+
Warning.process(__FILE__, :method_redefined=>:default, :missing_gvar=>:backtrace, :ambiguous_slash=>:raise)
|
503
|
+
Warning.process(__FILE__, :not_reached=>proc do |warning|
|
504
|
+
w = warning
|
505
|
+
:raise
|
506
|
+
end)
|
507
|
+
|
508
|
+
assert_warning(/warning: method redefined/) do
|
509
|
+
Class.new do
|
510
|
+
def a; end
|
511
|
+
def a; end
|
512
|
+
end
|
513
|
+
end
|
514
|
+
|
515
|
+
assert_warning(/global variable `\$test_warning_process_action' not initialized.*#{__FILE__}/m) do
|
516
|
+
$test_warning_process_action
|
517
|
+
end
|
518
|
+
|
519
|
+
Warning.process(__FILE__) do |warning|
|
520
|
+
w = warning
|
521
|
+
:raise
|
522
|
+
end
|
523
|
+
|
524
|
+
assert_raises(RuntimeError, /warning: ambi/) do
|
525
|
+
EnvUtil.verbose_warning{instance_eval('d /a/', __FILE__)}
|
526
|
+
end
|
527
|
+
|
528
|
+
assert_raises(RuntimeError, /warning: statement not reached/) do
|
529
|
+
EnvUtil.verbose_warning{instance_eval('def self.b; return; 1 end', __FILE__)}
|
530
|
+
end
|
531
|
+
assert_match(/warning: statement not reached/, w)
|
532
|
+
end
|
533
|
+
|
534
|
+
def test_warning_process_action_and_block
|
535
|
+
assert_raises(ArgumentError) do
|
536
|
+
Warning.process(__FILE__)
|
537
|
+
end
|
538
|
+
end
|
539
|
+
|
540
|
+
def test_warning_process_no_action_and_no_block
|
541
|
+
assert_raises(ArgumentError) do
|
542
|
+
Warning.process(__FILE__, :missing_ivar=>:default){}
|
543
|
+
end
|
544
|
+
end
|
545
|
+
|
546
|
+
if RUBY_VERSION >= '3.0'
|
547
|
+
def test_warning_warn_category_keyword
|
548
|
+
assert_warning('foo') do
|
549
|
+
Warning.warn("foo", category: :deprecated)
|
550
|
+
end
|
551
|
+
end
|
300
552
|
end
|
301
553
|
end
|
metadata
CHANGED
@@ -1,20 +1,35 @@
|
|
1
1
|
--- !ruby/object:Gem::Specification
|
2
2
|
name: warning
|
3
3
|
version: !ruby/object:Gem::Version
|
4
|
-
version:
|
4
|
+
version: 1.2.1
|
5
5
|
platform: ruby
|
6
6
|
authors:
|
7
7
|
- Jeremy Evans
|
8
8
|
autorequire:
|
9
9
|
bindir: bin
|
10
10
|
cert_chain: []
|
11
|
-
date:
|
12
|
-
dependencies:
|
11
|
+
date: 2021-10-04 00:00:00.000000000 Z
|
12
|
+
dependencies:
|
13
|
+
- !ruby/object:Gem::Dependency
|
14
|
+
name: minitest-global_expectations
|
15
|
+
requirement: !ruby/object:Gem::Requirement
|
16
|
+
requirements:
|
17
|
+
- - ">="
|
18
|
+
- !ruby/object:Gem::Version
|
19
|
+
version: '0'
|
20
|
+
type: :development
|
21
|
+
prerelease: false
|
22
|
+
version_requirements: !ruby/object:Gem::Requirement
|
23
|
+
requirements:
|
24
|
+
- - ">="
|
25
|
+
- !ruby/object:Gem::Version
|
26
|
+
version: '0'
|
13
27
|
description: |
|
14
28
|
ruby-warning adds custom processing for warnings, including the
|
15
29
|
ability to ignore specific warning messages, ignore warnings
|
16
|
-
in specific files/directories,
|
17
|
-
warnings
|
30
|
+
in specific files/directories, include backtraces with warnings,
|
31
|
+
treat warnings as errors, deduplicate warnings, and add
|
32
|
+
custom handling for all warnings in specific files/directories.
|
18
33
|
email: code@jeremyevans.net
|
19
34
|
executables: []
|
20
35
|
extensions: []
|
@@ -28,12 +43,17 @@ files:
|
|
28
43
|
- README.rdoc
|
29
44
|
- Rakefile
|
30
45
|
- lib/warning.rb
|
46
|
+
- test/fixtures/mismatched_indentations.rb
|
31
47
|
- test/test_freeze_warning.rb
|
32
48
|
- test/test_warning.rb
|
33
49
|
homepage: https://github.com/jeremyevans/ruby-warning
|
34
50
|
licenses:
|
35
51
|
- MIT
|
36
|
-
metadata:
|
52
|
+
metadata:
|
53
|
+
bug_tracker_uri: https://github.com/jeremyevans/ruby-warning/issues
|
54
|
+
changelog_uri: https://github.com/jeremyevans/ruby-warning/blob/master/CHANGELOG
|
55
|
+
documentation_uri: https://github.com/jeremyevans/ruby-warning/blob/master/README.rdoc
|
56
|
+
source_code_uri: https://github.com/jeremyevans/ruby-warning
|
37
57
|
post_install_message:
|
38
58
|
rdoc_options:
|
39
59
|
- "--quiet"
|
@@ -47,17 +67,16 @@ require_paths:
|
|
47
67
|
- lib
|
48
68
|
required_ruby_version: !ruby/object:Gem::Requirement
|
49
69
|
requirements:
|
50
|
-
- - "
|
70
|
+
- - ">="
|
51
71
|
- !ruby/object:Gem::Version
|
52
|
-
version: 2.
|
72
|
+
version: 2.4.0
|
53
73
|
required_rubygems_version: !ruby/object:Gem::Requirement
|
54
74
|
requirements:
|
55
75
|
- - ">="
|
56
76
|
- !ruby/object:Gem::Version
|
57
77
|
version: '0'
|
58
78
|
requirements: []
|
59
|
-
|
60
|
-
rubygems_version: 2.6.13
|
79
|
+
rubygems_version: 3.2.22
|
61
80
|
signing_key:
|
62
81
|
specification_version: 4
|
63
82
|
summary: Add custom processing for warnings
|