ruby-lint 1.0.2 → 1.0.3
Sign up to get free protection for your applications and to get access to all the features.
- checksums.yaml +4 -4
- data/doc/changelog.md +17 -0
- data/lib/ruby-lint/analysis/argument_amount.rb +9 -1
- data/lib/ruby-lint/analysis/base.rb +4 -1
- data/lib/ruby-lint/definition/ruby_object.rb +23 -3
- data/lib/ruby-lint/definition_builder/ruby_method.rb +9 -4
- data/lib/ruby-lint/definition_builder/ruby_module.rb +1 -1
- data/lib/ruby-lint/definitions/core/array.rb +28 -2
- data/lib/ruby-lint/definitions/core/range.rb +5 -2
- data/lib/ruby-lint/file_scanner.rb +8 -3
- data/lib/ruby-lint/parser.rb +37 -3
- data/lib/ruby-lint/runner.rb +6 -1
- data/lib/ruby-lint/version.rb +1 -1
- data/lib/ruby-lint/virtual_machine.rb +6 -3
- data/spec/ruby-lint/analysis/argument_amount_spec.rb +14 -0
- data/spec/ruby-lint/analysis/base_spec.rb +8 -0
- data/spec/ruby-lint/definition/ruby_object_spec.rb +34 -0
- data/spec/ruby-lint/file_scanner_spec.rb +8 -0
- data/spec/ruby-lint/parser_spec.rb +7 -0
- data/spec/ruby-lint/virtual_machine/classes/sclass_spec.rb +5 -3
- metadata +2 -2
checksums.yaml
CHANGED
@@ -1,7 +1,7 @@
|
|
1
1
|
---
|
2
2
|
SHA1:
|
3
|
-
metadata.gz:
|
4
|
-
data.tar.gz:
|
3
|
+
metadata.gz: 0b345fdf9724a766a2684c0977f862cd7e408ce9
|
4
|
+
data.tar.gz: a6d56efba7d749595035211678c38c8a4323c94d
|
5
5
|
SHA512:
|
6
|
-
metadata.gz:
|
7
|
-
data.tar.gz:
|
6
|
+
metadata.gz: efe10626ab798f0d8069d5bceb3c39efb634c1afbf009490c0a01670ca2f049ddabbbf9f17f3f9a84058cb69fe14c9b42f3031da4d9211c1d8f075d3889596af
|
7
|
+
data.tar.gz: 14f98dd7fdf7875035021f5830da8574c0f4ab82bbbc7775a1476a26e56052dd4259ba0d67e9c8a1893e090bc5c4db3dc069e6f2ac2d0ddd4ceae06617872813
|
data/doc/changelog.md
CHANGED
@@ -5,6 +5,23 @@ This document contains a short summary of the various releases of ruby-lint.
|
|
5
5
|
For a full list of commits included in each release see the corresponding Git
|
6
6
|
tags (named after the versions).
|
7
7
|
|
8
|
+
## 1.0.3 - 2013-12-23
|
9
|
+
|
10
|
+
* `self` is now defined as a class and instance method to ensure that the right
|
11
|
+
data is used in these two scopes. See
|
12
|
+
`28f604ded884be2e43ef7ce93892a3cade4c93d7` for a more in depth explanation.
|
13
|
+
* Block arguments passed to methods are now ignored by the `ArgumentAmount`
|
14
|
+
analysis class.
|
15
|
+
* Configuration objects are now passed to analysis classes.
|
16
|
+
* ruby-lint can now parse empty Ruby files! Previously this would crash the
|
17
|
+
parser.
|
18
|
+
* Range now inherits from Enumerable.
|
19
|
+
* The definitions for Array have been re-generated.
|
20
|
+
* Fix for searching for Ruby files when no directories were given to the file
|
21
|
+
scanner class. Previously this would cause ruby-lint to start scanning from
|
22
|
+
`/`. See <https://github.com/YorickPeterse/ruby-lint/issues/83> for more
|
23
|
+
information.
|
24
|
+
|
8
25
|
## 1.0.2 - 2013-12-19
|
9
26
|
|
10
27
|
This release changes the default file scanner directories from `$PWD` to
|
@@ -27,7 +27,7 @@ module RubyLint
|
|
27
27
|
|
28
28
|
return unless method
|
29
29
|
|
30
|
-
given = args
|
30
|
+
given = argument_amount(args)
|
31
31
|
min, max = argument_range(method)
|
32
32
|
|
33
33
|
unless correct_argument_amount(min, max, given)
|
@@ -112,6 +112,14 @@ module RubyLint
|
|
112
112
|
|
113
113
|
return min, max
|
114
114
|
end
|
115
|
+
|
116
|
+
##
|
117
|
+
# @param [RubyLint::AST::Node] nodes
|
118
|
+
# @return [Fixnum]
|
119
|
+
#
|
120
|
+
def argument_amount(nodes)
|
121
|
+
return nodes.reject { |n| n.type == :block_pass }.length
|
122
|
+
end
|
115
123
|
end # ArgumentAmount
|
116
124
|
end # Analysis
|
117
125
|
end # RubyLint
|
@@ -10,8 +10,11 @@ module RubyLint
|
|
10
10
|
# @!attribute [r] vm
|
11
11
|
# @return [RubyLint::VirtualMachine]
|
12
12
|
#
|
13
|
+
# @!attribute [r] config
|
14
|
+
# @return [RubyLint::Configuration]
|
15
|
+
#
|
13
16
|
class Base < Iterator
|
14
|
-
attr_reader :report, :vm
|
17
|
+
attr_reader :report, :vm, :config
|
15
18
|
|
16
19
|
##
|
17
20
|
# Array containing the callback names for which a new scope should be
|
@@ -83,7 +83,6 @@ module RubyLint
|
|
83
83
|
:gvar,
|
84
84
|
:instance_method,
|
85
85
|
:ivar,
|
86
|
-
:keyword,
|
87
86
|
:method
|
88
87
|
].freeze
|
89
88
|
|
@@ -107,7 +106,6 @@ module RubyLint
|
|
107
106
|
:gvar,
|
108
107
|
:instance_method,
|
109
108
|
:ivar,
|
110
|
-
:keyword,
|
111
109
|
:kwoptarg,
|
112
110
|
:lvar,
|
113
111
|
:member,
|
@@ -543,7 +541,7 @@ module RubyLint
|
|
543
541
|
definition = add_child_definition(:const, name, &block)
|
544
542
|
end
|
545
543
|
|
546
|
-
definition.
|
544
|
+
definition.define_self
|
547
545
|
|
548
546
|
return definition
|
549
547
|
end
|
@@ -610,6 +608,28 @@ module RubyLint
|
|
610
608
|
self.parents.concat(definitions)
|
611
609
|
end
|
612
610
|
|
611
|
+
##
|
612
|
+
# Defines `self` on the current definition as both a class and instance
|
613
|
+
# method.
|
614
|
+
#
|
615
|
+
def define_self
|
616
|
+
if instance?
|
617
|
+
self_instance = self
|
618
|
+
self_class = instance(:instance_type => :class)
|
619
|
+
else
|
620
|
+
self_instance = self.instance
|
621
|
+
self_class = self
|
622
|
+
end
|
623
|
+
|
624
|
+
define_method('self') do |method|
|
625
|
+
method.returns(self_class)
|
626
|
+
end
|
627
|
+
|
628
|
+
define_instance_method('self') do |method|
|
629
|
+
method.returns(self_instance)
|
630
|
+
end
|
631
|
+
end
|
632
|
+
|
613
633
|
##
|
614
634
|
# Returns a pretty formatted String that shows some info about the
|
615
635
|
# current definition.
|
@@ -51,17 +51,22 @@ module RubyLint
|
|
51
51
|
# @return [RubyLint::Definition::RubyObject]
|
52
52
|
#
|
53
53
|
def new_definition(parents)
|
54
|
-
type
|
54
|
+
type = options[:type]
|
55
|
+
instance_type = :instance
|
55
56
|
|
56
|
-
|
57
|
-
|
57
|
+
# FIXME: setting the instance type of a method to a `class` is a bit of
|
58
|
+
# a hack to ensure that class methods cause lookups inside them to be
|
59
|
+
# performed on class level.
|
60
|
+
if has_receiver? and options[:receiver].class?
|
61
|
+
type = :method
|
62
|
+
instance_type = :class
|
58
63
|
end
|
59
64
|
|
60
65
|
return Definition::RubyMethod.new(
|
61
66
|
:name => method_name,
|
62
67
|
:parents => parents,
|
63
68
|
:type => type,
|
64
|
-
:instance_type =>
|
69
|
+
:instance_type => instance_type,
|
65
70
|
:visibility => options[:visibility],
|
66
71
|
:line => node.line,
|
67
72
|
:column => node.column,
|
@@ -1,8 +1,8 @@
|
|
1
1
|
# This file was automatically generated, any manual changes will be lost the
|
2
2
|
# next time this file is generated.
|
3
3
|
#
|
4
|
-
# Created: 2013-
|
5
|
-
# Platform: rbx 2.
|
4
|
+
# Created: 2013-12-23 09:38:51 +0100
|
5
|
+
# Platform: rbx 2.2.1
|
6
6
|
|
7
7
|
RubyLint::GlobalScope.definitions.define_constant('Array') do |klass|
|
8
8
|
klass.inherits(RubyLint::GlobalScope.constant_proxy('Object'))
|
@@ -17,6 +17,8 @@ RubyLint::GlobalScope.definitions.define_constant('Array') do |klass|
|
|
17
17
|
method.define_argument('obj')
|
18
18
|
end
|
19
19
|
|
20
|
+
klass.define_method('yaml_tag_subclasses?')
|
21
|
+
|
20
22
|
klass.define_instance_method('&') do |method|
|
21
23
|
method.define_argument('other')
|
22
24
|
end
|
@@ -217,6 +219,11 @@ RubyLint::GlobalScope.definitions.define_constant('Array') do |klass|
|
|
217
219
|
method.define_optional_argument('obj')
|
218
220
|
end
|
219
221
|
|
222
|
+
klass.define_instance_method('initialize') do |method|
|
223
|
+
method.define_optional_argument('size_or_array')
|
224
|
+
method.define_optional_argument('obj')
|
225
|
+
end
|
226
|
+
|
220
227
|
klass.define_instance_method('inject') do |method|
|
221
228
|
method.define_optional_argument('initial')
|
222
229
|
method.define_optional_argument('sym')
|
@@ -396,6 +403,10 @@ RubyLint::GlobalScope.definitions.define_constant('Array') do |klass|
|
|
396
403
|
|
397
404
|
klass.define_instance_method('start=')
|
398
405
|
|
406
|
+
klass.define_instance_method('taguri')
|
407
|
+
|
408
|
+
klass.define_instance_method('taguri=')
|
409
|
+
|
399
410
|
klass.define_instance_method('take') do |method|
|
400
411
|
method.define_argument('n')
|
401
412
|
end
|
@@ -416,6 +427,10 @@ RubyLint::GlobalScope.definitions.define_constant('Array') do |klass|
|
|
416
427
|
|
417
428
|
klass.define_instance_method('to_tuple')
|
418
429
|
|
430
|
+
klass.define_instance_method('to_yaml') do |method|
|
431
|
+
method.define_optional_argument('opts')
|
432
|
+
end
|
433
|
+
|
419
434
|
klass.define_instance_method('total')
|
420
435
|
|
421
436
|
klass.define_instance_method('total=')
|
@@ -442,6 +457,11 @@ RubyLint::GlobalScope.definitions.define_constant('Array') do |klass|
|
|
442
457
|
method.define_argument('memo')
|
443
458
|
end
|
444
459
|
|
460
|
+
klass.define_instance_method('yaml_initialize') do |method|
|
461
|
+
method.define_argument('tag')
|
462
|
+
method.define_argument('val')
|
463
|
+
end
|
464
|
+
|
445
465
|
klass.define_instance_method('zip') do |method|
|
446
466
|
method.define_rest_argument('others')
|
447
467
|
end
|
@@ -536,6 +556,12 @@ RubyLint::GlobalScope.definitions.define_constant('Array::Enumerator') do |klass
|
|
536
556
|
method.define_argument('obj')
|
537
557
|
end
|
538
558
|
|
559
|
+
klass.define_instance_method('initialize') do |method|
|
560
|
+
method.define_optional_argument('receiver_or_size')
|
561
|
+
method.define_optional_argument('method_name')
|
562
|
+
method.define_rest_argument('method_args')
|
563
|
+
end
|
564
|
+
|
539
565
|
klass.define_instance_method('inject') do |method|
|
540
566
|
method.define_optional_argument('initial')
|
541
567
|
method.define_optional_argument('sym')
|
@@ -4,7 +4,10 @@
|
|
4
4
|
# Platform: rbx 2.0.0.rc1
|
5
5
|
#
|
6
6
|
RubyLint::GlobalScope.definitions.define_constant('Range') do |klass|
|
7
|
-
klass.inherits(
|
7
|
+
klass.inherits(
|
8
|
+
RubyLint::GlobalScope.constant_proxy('Object'),
|
9
|
+
RubyLint::GlobalScope.constant_proxy('Enumerable')
|
10
|
+
)
|
8
11
|
|
9
12
|
klass.define_method('__class_init__')
|
10
13
|
|
@@ -103,4 +106,4 @@ RubyLint::GlobalScope.definitions.define_constant('Range::SortedElement') do |kl
|
|
103
106
|
klass.define_instance_method('value')
|
104
107
|
end
|
105
108
|
|
106
|
-
RubyLint::GlobalScope.definitions.lookup(:const, 'Range').deep_freeze
|
109
|
+
RubyLint::GlobalScope.definitions.lookup(:const, 'Range').deep_freeze
|
@@ -60,9 +60,7 @@ module RubyLint
|
|
60
60
|
# @return [Array]
|
61
61
|
#
|
62
62
|
def scan(constant)
|
63
|
-
|
64
|
-
# than running a Dir.glob for every call to #scan.
|
65
|
-
@glob_cache ||= Dir.glob("#{directories.join(',')}/**/*.rb")
|
63
|
+
@glob_cache ||= directories.empty? ? [] : glob_ruby_files
|
66
64
|
|
67
65
|
unless constant_paths_cached?(constant)
|
68
66
|
build_constant_paths_cache(constant)
|
@@ -73,6 +71,13 @@ module RubyLint
|
|
73
71
|
|
74
72
|
private
|
75
73
|
|
74
|
+
##
|
75
|
+
# @return [Array]
|
76
|
+
#
|
77
|
+
def glob_ruby_files
|
78
|
+
return Dir.glob("#{directories.join(',')}/**/*.rb")
|
79
|
+
end
|
80
|
+
|
76
81
|
##
|
77
82
|
# Searches all the files that could potentially define the given constant
|
78
83
|
# and caches them.
|
data/lib/ruby-lint/parser.rb
CHANGED
@@ -39,13 +39,47 @@ module RubyLint
|
|
39
39
|
buffer = ::Parser::Source::Buffer.new(file, line)
|
40
40
|
buffer.source = code
|
41
41
|
ast, comments = internal_parser.parse_with_comments(buffer)
|
42
|
-
associator = ::Parser::Source::Comment::Associator.new(ast, comments)
|
43
42
|
|
44
43
|
internal_parser.reset
|
45
44
|
|
46
|
-
|
45
|
+
associated = associate_comments(ast, comments)
|
47
46
|
|
48
|
-
return
|
47
|
+
return create_root_node(ast), associated
|
48
|
+
end
|
49
|
+
|
50
|
+
private
|
51
|
+
|
52
|
+
##
|
53
|
+
# @param [RubyLint::AST::Node|NilClass] ast
|
54
|
+
# @return [RubyLint::AST::Node]
|
55
|
+
#
|
56
|
+
def create_root_node(ast)
|
57
|
+
if ast
|
58
|
+
children = [ast]
|
59
|
+
location = ast.location
|
60
|
+
# empty input.
|
61
|
+
else
|
62
|
+
children = []
|
63
|
+
location = nil
|
64
|
+
end
|
65
|
+
|
66
|
+
return AST::Node.new(:root, children, :location => location)
|
67
|
+
end
|
68
|
+
|
69
|
+
##
|
70
|
+
# @param [RubyLint::AST::Node|NilClass] ast
|
71
|
+
# @param [Mixed] comments
|
72
|
+
# @return [Hash]
|
73
|
+
#
|
74
|
+
def associate_comments(ast, comments)
|
75
|
+
if ast
|
76
|
+
associator = ::Parser::Source::Comment::Associator.new(ast, comments)
|
77
|
+
associated = associator.associate
|
78
|
+
else
|
79
|
+
associated = {}
|
80
|
+
end
|
81
|
+
|
82
|
+
return associated
|
49
83
|
end
|
50
84
|
end # Parser
|
51
85
|
end # RubyLint
|
data/lib/ruby-lint/runner.rb
CHANGED
@@ -175,7 +175,12 @@ module RubyLint
|
|
175
175
|
end
|
176
176
|
|
177
177
|
classes.each do |const|
|
178
|
-
instance = const.new(
|
178
|
+
instance = const.new(
|
179
|
+
:vm => vm,
|
180
|
+
:report => report,
|
181
|
+
:config => configuration
|
182
|
+
)
|
183
|
+
|
179
184
|
instance.iterate(ast)
|
180
185
|
end
|
181
186
|
end
|
data/lib/ruby-lint/version.rb
CHANGED
@@ -443,7 +443,10 @@ module RubyLint
|
|
443
443
|
# Pushes the value of `self` onto the current stack.
|
444
444
|
#
|
445
445
|
def on_self
|
446
|
-
|
446
|
+
scope = current_scope
|
447
|
+
method = scope.lookup(scope.method_call_type, 'self')
|
448
|
+
|
449
|
+
push_value(method.return_value)
|
447
450
|
end
|
448
451
|
|
449
452
|
##
|
@@ -522,7 +525,7 @@ module RubyLint
|
|
522
525
|
def on_sclass(node)
|
523
526
|
parent = node.children[0]
|
524
527
|
definition = evaluate_node(parent)
|
525
|
-
@method_type =
|
528
|
+
@method_type = definition.method_call_type
|
526
529
|
|
527
530
|
associate_node(node, definition)
|
528
531
|
|
@@ -748,7 +751,7 @@ Received: #{arguments.length}
|
|
748
751
|
:instance_type => :instance
|
749
752
|
)
|
750
753
|
|
751
|
-
definitions.
|
754
|
+
definitions.define_self
|
752
755
|
|
753
756
|
return definitions
|
754
757
|
end
|
@@ -114,4 +114,18 @@ Person.new(10, 20)
|
|
114
114
|
second.column.should == 1
|
115
115
|
second.message.should == 'wrong number of arguments (expected 1 but got 2)'
|
116
116
|
end
|
117
|
+
|
118
|
+
example 'ignore block arguments' do
|
119
|
+
code = <<-CODE
|
120
|
+
def example; end
|
121
|
+
|
122
|
+
block = proc {}
|
123
|
+
|
124
|
+
example(&block)
|
125
|
+
CODE
|
126
|
+
|
127
|
+
report = build_report(code, RubyLint::Analysis::ArgumentAmount)
|
128
|
+
|
129
|
+
report.entries.empty?.should == true
|
130
|
+
end
|
117
131
|
end
|
@@ -10,6 +10,14 @@ describe RubyLint::Analysis::Base do
|
|
10
10
|
blk.should_not raise_error
|
11
11
|
end
|
12
12
|
|
13
|
+
example 'allow config objects to be passed in' do
|
14
|
+
vm = RubyLint::VirtualMachine.new
|
15
|
+
config = RubyLint::Configuration.new
|
16
|
+
base = RubyLint::Analysis::Base.new(:vm => vm, :config => config)
|
17
|
+
|
18
|
+
base.config.should == config
|
19
|
+
end
|
20
|
+
|
13
21
|
example 'enable analysis by default' do
|
14
22
|
RubyLint::Analysis::Base.analyze?(double(:ast), double(:vm)).should == true
|
15
23
|
end
|
@@ -227,4 +227,38 @@ describe ruby_object do
|
|
227
227
|
@method.callers.frozen?.should == true
|
228
228
|
end
|
229
229
|
end
|
230
|
+
|
231
|
+
context 'defining self' do
|
232
|
+
before do
|
233
|
+
@class = ruby_object.new(:instance_type => :class)
|
234
|
+
@instance = ruby_object.new(:instance_type => :instance)
|
235
|
+
|
236
|
+
@class.define_self
|
237
|
+
@instance.define_self
|
238
|
+
end
|
239
|
+
|
240
|
+
example 'define instance level self for an instance' do
|
241
|
+
@instance.lookup(:instance_method, 'self')
|
242
|
+
.return_value
|
243
|
+
.should == @instance
|
244
|
+
end
|
245
|
+
|
246
|
+
example 'define class level self for an instance' do
|
247
|
+
@instance.lookup(:method, 'self')
|
248
|
+
.return_value
|
249
|
+
.parents
|
250
|
+
.should == [@instance]
|
251
|
+
end
|
252
|
+
|
253
|
+
example 'define instance level self for a class' do
|
254
|
+
@class.lookup(:instance_method, 'self')
|
255
|
+
.return_value
|
256
|
+
.parents
|
257
|
+
.should == [@class]
|
258
|
+
end
|
259
|
+
|
260
|
+
example 'define class level self for a class' do
|
261
|
+
@class.lookup(:method, 'self').return_value.should == @class
|
262
|
+
end
|
263
|
+
end
|
230
264
|
end
|
@@ -61,4 +61,12 @@ describe RubyLint::FileScanner do
|
|
61
61
|
|
62
62
|
scanner.scan('Example::User').empty?.should == true
|
63
63
|
end
|
64
|
+
|
65
|
+
example 'do not scan when there are no directories' do
|
66
|
+
scanner = RubyLint::FileScanner.new([])
|
67
|
+
|
68
|
+
scanner.should_not receive(:glob_ruby_files)
|
69
|
+
|
70
|
+
scanner.scan('Foo')
|
71
|
+
end
|
64
72
|
end
|
@@ -20,7 +20,7 @@ end
|
|
20
20
|
.should == true
|
21
21
|
end
|
22
22
|
|
23
|
-
example 'define
|
23
|
+
example 'define an instance method using `class << self` in the global scope' do
|
24
24
|
code = <<-CODE
|
25
25
|
class << self
|
26
26
|
def example
|
@@ -30,7 +30,9 @@ end
|
|
30
30
|
|
31
31
|
defs = build_definitions(code)
|
32
32
|
|
33
|
-
defs.lookup(:
|
33
|
+
defs.lookup(:instance_method, 'example')
|
34
|
+
.is_a?(ruby_method)
|
35
|
+
.should == true
|
34
36
|
end
|
35
37
|
|
36
38
|
example 'define a class method using `class << String`' do
|
@@ -91,4 +93,4 @@ end
|
|
91
93
|
.should == true
|
92
94
|
end
|
93
95
|
end
|
94
|
-
end
|
96
|
+
end
|
metadata
CHANGED
@@ -1,14 +1,14 @@
|
|
1
1
|
--- !ruby/object:Gem::Specification
|
2
2
|
name: ruby-lint
|
3
3
|
version: !ruby/object:Gem::Version
|
4
|
-
version: 1.0.
|
4
|
+
version: 1.0.3
|
5
5
|
platform: ruby
|
6
6
|
authors:
|
7
7
|
- Yorick Peterse
|
8
8
|
autorequire:
|
9
9
|
bindir: bin
|
10
10
|
cert_chain: []
|
11
|
-
date: 2013-12-
|
11
|
+
date: 2013-12-23 00:00:00.000000000 Z
|
12
12
|
dependencies:
|
13
13
|
- !ruby/object:Gem::Dependency
|
14
14
|
name: parser
|