inch 0.2.3 → 0.3.0.rc1

Sign up to get free protection for your applications and to get access to all the features.
Files changed (111) hide show
  1. checksums.yaml +4 -4
  2. data/.simplecov +7 -0
  3. data/TODOS.md +0 -5
  4. data/config/defaults.rb +26 -1
  5. data/inch.gemspec +1 -0
  6. data/lib/inch.rb +2 -1
  7. data/lib/inch/api.rb +34 -0
  8. data/lib/inch/api/filter.rb +17 -0
  9. data/lib/inch/api/get.rb +30 -0
  10. data/lib/inch/api/list.rb +10 -0
  11. data/lib/inch/api/options/base.rb +45 -0
  12. data/lib/inch/api/options/filter.rb +25 -0
  13. data/lib/inch/api/options/suggest.rb +36 -0
  14. data/lib/inch/api/stats.rb +7 -0
  15. data/lib/inch/api/suggest.rb +110 -0
  16. data/lib/inch/cli.rb +4 -1
  17. data/lib/inch/cli/command/base.rb +1 -17
  18. data/lib/inch/cli/command/base_list.rb +3 -63
  19. data/lib/inch/cli/command/base_object.rb +6 -28
  20. data/lib/inch/cli/command/list.rb +3 -2
  21. data/lib/inch/cli/command/options/base.rb +1 -1
  22. data/lib/inch/cli/command/options/base_list.rb +4 -2
  23. data/lib/inch/cli/command/options/suggest.rb +9 -8
  24. data/lib/inch/cli/command/output/base.rb +9 -11
  25. data/lib/inch/cli/command/output/list.rb +2 -2
  26. data/lib/inch/cli/command/output/show.rb +2 -10
  27. data/lib/inch/cli/command/output/stats.rb +4 -3
  28. data/lib/inch/cli/command/output/suggest.rb +5 -5
  29. data/lib/inch/cli/command/stats.rb +4 -3
  30. data/lib/inch/cli/command/suggest.rb +4 -94
  31. data/lib/inch/code_object.rb +2 -2
  32. data/lib/inch/code_object/converter.rb +89 -0
  33. data/lib/inch/code_object/provider.rb +36 -0
  34. data/lib/inch/code_object/provider/yard.rb +19 -0
  35. data/lib/inch/code_object/provider/yard/docstring.rb +106 -0
  36. data/lib/inch/code_object/provider/yard/nodoc_helper.rb +93 -0
  37. data/lib/inch/code_object/provider/yard/object.rb +55 -0
  38. data/lib/inch/code_object/provider/yard/object/base.rb +262 -0
  39. data/lib/inch/code_object/provider/yard/object/class_object.rb +12 -0
  40. data/lib/inch/code_object/provider/yard/object/constant_object.rb +12 -0
  41. data/lib/inch/code_object/provider/yard/object/method_object.rb +126 -0
  42. data/lib/inch/code_object/provider/yard/object/method_parameter_object.rb +88 -0
  43. data/lib/inch/code_object/provider/yard/object/module_object.rb +12 -0
  44. data/lib/inch/code_object/provider/yard/object/namespace_object.rb +47 -0
  45. data/lib/inch/code_object/provider/yard/parser.rb +54 -0
  46. data/lib/inch/code_object/proxy.rb +5 -3
  47. data/lib/inch/code_object/proxy/base.rb +103 -110
  48. data/lib/inch/code_object/proxy/class_object.rb +0 -1
  49. data/lib/inch/code_object/proxy/method_object.rb +20 -99
  50. data/lib/inch/code_object/proxy/method_parameter_object.rb +15 -39
  51. data/lib/inch/code_object/proxy/namespace_object.rb +7 -18
  52. data/lib/inch/codebase.rb +19 -0
  53. data/lib/inch/codebase/objects.rb +73 -0
  54. data/lib/inch/codebase/objects_filter.rb +61 -0
  55. data/lib/inch/codebase/proxy.rb +22 -0
  56. data/lib/inch/config.rb +8 -1
  57. data/lib/inch/evaluation.rb +5 -7
  58. data/lib/inch/evaluation/file.rb +1 -1
  59. data/lib/inch/evaluation/grade.rb +1 -1
  60. data/lib/inch/evaluation/object_schema.rb +3 -1
  61. data/lib/inch/evaluation/priority_range.rb +44 -0
  62. data/lib/inch/evaluation/proxy.rb +25 -0
  63. data/lib/inch/evaluation/proxy/base.rb +146 -0
  64. data/lib/inch/evaluation/proxy/class_object.rb +8 -0
  65. data/lib/inch/evaluation/proxy/constant_object.rb +19 -0
  66. data/lib/inch/evaluation/proxy/method_object.rb +65 -0
  67. data/lib/inch/evaluation/proxy/module_object.rb +8 -0
  68. data/lib/inch/evaluation/proxy/namespace_object.rb +27 -0
  69. data/lib/inch/evaluation/role/base.rb +19 -0
  70. data/lib/inch/evaluation/role/constant.rb +16 -0
  71. data/lib/inch/evaluation/role/method.rb +22 -0
  72. data/lib/inch/evaluation/role/method_parameter.rb +31 -1
  73. data/lib/inch/evaluation/role/namespace.rb +15 -0
  74. data/lib/inch/evaluation/role/object.rb +24 -0
  75. data/lib/inch/rake/suggest.rb +1 -0
  76. data/lib/inch/utils/read_write_methods.rb +44 -0
  77. data/lib/inch/{cli → utils}/weighted_list.rb +1 -1
  78. data/lib/inch/version.rb +1 -1
  79. data/test/fixtures/simple/lib/broken.rb +8 -0
  80. data/test/inch/api/filter_test.rb +51 -0
  81. data/test/inch/api/get_test.rb +22 -0
  82. data/test/inch/api/list_test.rb +15 -0
  83. data/test/inch/api/options/base_test.rb +30 -0
  84. data/test/inch/api/stats_test.rb +15 -0
  85. data/test/inch/api/suggest_test.rb +26 -0
  86. data/test/inch/cli/command/list_test.rb +2 -1
  87. data/test/inch/code_object/converter_test.rb +29 -0
  88. data/test/inch/code_object/{docstring_test.rb → provider/yard/docstring_test.rb} +13 -13
  89. data/test/inch/code_object/{nodoc_helper_test.rb → provider/yard/nodoc_helper_test.rb} +6 -6
  90. data/test/inch/code_object/provider/yard_test.rb +11 -0
  91. data/test/inch/code_object/provider_test.rb +9 -0
  92. data/test/inch/code_object/proxy/method_object_test.rb +22 -22
  93. data/test/inch/code_object/proxy_test.rb +10 -10
  94. data/test/inch/codebase/objects_test.rb +28 -0
  95. data/test/inch/codebase/proxy_test.rb +17 -0
  96. data/test/inch/evaluation/role/base_test.rb +71 -0
  97. data/test/inch/{cli → utils}/weighted_list_test.rb +2 -2
  98. data/test/shared/base_list.rb +73 -0
  99. data/test/test_helper.rb +0 -95
  100. metadata +89 -24
  101. data/lib/inch/code_object/docstring.rb +0 -102
  102. data/lib/inch/code_object/nodoc_helper.rb +0 -107
  103. data/lib/inch/evaluation/base.rb +0 -157
  104. data/lib/inch/evaluation/class_object.rb +0 -6
  105. data/lib/inch/evaluation/constant_object.rb +0 -33
  106. data/lib/inch/evaluation/method_object.rb +0 -105
  107. data/lib/inch/evaluation/module_object.rb +0 -6
  108. data/lib/inch/evaluation/namespace_object.rb +0 -52
  109. data/lib/inch/evaluation/read_write_methods.rb +0 -21
  110. data/lib/inch/source_parser.rb +0 -62
  111. data/test/inch/source_parser_test.rb +0 -23
@@ -1,102 +0,0 @@
1
- module Inch
2
- module CodeObject
3
- class Docstring
4
- def initialize(text)
5
- @text = text.to_s
6
- end
7
-
8
- def empty?
9
- @text.strip.empty?
10
- end
11
-
12
- def contains_code_example?
13
- !code_examples.empty?
14
- end
15
-
16
- def code_examples
17
- @code_examples ||= parse_code_examples
18
- end
19
-
20
- def describes_parameter?(name)
21
- describe_parameter_regexps(name).any? do |pattern|
22
- @text.index(pattern)
23
- end
24
- end
25
-
26
- def mentions_parameter?(name)
27
- mention_parameter_regexps(name).any? do |pattern|
28
- @text.index(pattern)
29
- end
30
- end
31
-
32
- def mentions_return?
33
- @text.lines.to_a.last =~ /^Returns\ /
34
- end
35
-
36
- def describes_return?
37
- @text.lines.to_a.last =~ /^Returns\ (\w+\s){2,}/
38
- end
39
-
40
- def parse_code_examples
41
- code_examples = []
42
- example = nil
43
- @text.lines.each_with_index do |line, index|
44
- if line =~/^\s*+$/
45
- code_examples << example if example
46
- example = []
47
- elsif line =~/^\ {2,}\S+/
48
- example << line if example
49
- else
50
- code_examples << example if example
51
- example = nil
52
- end
53
- end
54
- code_examples << example if example
55
- code_examples.delete_if(&:empty?).map(&:join)
56
- end
57
-
58
- private
59
-
60
- def mention_parameter_patterns(name)
61
- [
62
- "+#{name}+",
63
- "+#{name}+::",
64
- "<tt>#{name}</tt>",
65
- "<tt>#{name}</tt>::",
66
- "#{name}::",
67
- /^#{name}\ \-\ /
68
- ]
69
- end
70
-
71
- def describe_parameter_extra_regexps(name)
72
- [
73
- "#{name}::",
74
- "+#{name}+::",
75
- "<tt>#{name}</tt>::",
76
- ].map do |pattern|
77
- r = pattern.is_a?(Regexp) ? pattern : Regexp.escape(pattern)
78
- /#{r}\n\ {2,}.+/m
79
- end
80
- end
81
-
82
- def describe_parameter_regexps(name)
83
- same_line_regexps = mention_parameter_patterns(name).map do |pattern|
84
- r = pattern.is_a?(Regexp) ? pattern : Regexp.escape(pattern)
85
- /^#{r}\s?\S+/
86
- end
87
- same_line_regexps + describe_parameter_extra_regexps(name)
88
- end
89
-
90
- def mention_parameter_regexps(name)
91
- mention_parameter_patterns(name).map do |pattern|
92
- if pattern.is_a?(Regexp)
93
- pattern
94
- else
95
- r = Regexp.escape(pattern)
96
- /\W#{r}\W/
97
- end
98
- end
99
- end
100
- end
101
- end
102
- end
@@ -1,107 +0,0 @@
1
- module Inch
2
- module CodeObject
3
- module NodocHelper
4
-
5
- # Returns true if the code object is somehow marked not to be
6
- # documented.
7
- #
8
- # @note Doesnot recognize ":startdoc:" and ":stopdoc:"
9
- #
10
- def nodoc?
11
- private_tag? || nodoc_comment?
12
- end
13
-
14
- NO_DOC_REGEX = /#\s*\:nodoc\:/
15
- NO_DOC_ALL_REGEX = /#\s*\:nodoc\:\s*all/
16
- DOC_REGEX = /#\s*\:doc\:/
17
-
18
- def nodoc_comment?
19
- explicit_nodoc_comment? || implicit_nodoc_comment?
20
- end
21
-
22
- def explicit_nodoc_comment?
23
- declarations.any? { |str| str =~ NO_DOC_REGEX }
24
- end
25
-
26
- def explicit_nodoc_all_comment?
27
- declarations.any? { |str| str =~ NO_DOC_ALL_REGEX }
28
- end
29
-
30
- def explicit_doc_comment?
31
- declarations.any? { |str| str =~ DOC_REGEX }
32
- end
33
-
34
- def implicit_nodoc_all_comment?
35
- if parent
36
- parent.explicit_nodoc_all_comment? ||
37
- parent.implicit_nodoc_all_comment?
38
- end
39
- end
40
-
41
- def implicit_nodoc_comment?
42
- return false if explicit_doc_comment?
43
-
44
- if parent
45
- return false if parent.explicit_doc_comment?
46
-
47
- if namespace?
48
- if parent.explicit_nodoc_all_comment?
49
- return true
50
- else
51
- return parent.implicit_nodoc_all_comment?
52
- end
53
- else
54
- if parent.explicit_nodoc_comment?
55
- return true
56
- else
57
- return parent.implicit_nodoc_all_comment?
58
- end
59
- end
60
- end
61
- end
62
-
63
- # Returns all lines in all files declaring the object
64
- #
65
- # @example
66
- # declarations # => ["class Base # :nodoc:", "class Foo < Base"]
67
- #
68
- # @return [Array<String>]
69
- def declarations
70
- @declarations ||= files.map do |(filename, line_no)|
71
- get_line_no(filename, line_no)
72
- end
73
- end
74
-
75
- # Returns all files declaring the object in the form of an Array of
76
- # Arrays containing the filename and the line number of their
77
- # declaration.
78
- #
79
- # @example
80
- # files # => [["lib/inch.rb", 3],
81
- # ["lib/inch/cli.rb", 1],
82
- # ["lib/inch/version.rb", 1],
83
- #
84
- # @return [Array<Array(String, Fixnum)>]
85
- def files
86
- object.files
87
- rescue YARD::CodeObjects::ProxyMethodError
88
- # this error is raised by YARD
89
- # see broken.rb in test fixtures
90
- []
91
- end
92
-
93
- # Returns a +line_number+ from a file
94
- #
95
- # @param filename [String]
96
- # @param line_number [Fixnum]
97
- # @return [String]
98
- def get_line_no(filename, line_number)
99
- f = File.open(filename)
100
- line_number.times{f.gets}
101
- result = $_
102
- f.close
103
- result
104
- end
105
- end
106
- end
107
- end
@@ -1,157 +0,0 @@
1
- module Inch
2
- module Evaluation
3
- # @abstract
4
- class Base
5
- extend Forwardable
6
-
7
- MIN_SCORE = 0
8
- MAX_SCORE = 100
9
-
10
- TAGGED_SCORE = 20 # assigned per unconsidered tag
11
-
12
- # @return [CodeObject::Proxy::Base]
13
- attr_accessor :object
14
-
15
- attr_reader :min_score, :max_score
16
-
17
- # @param object [CodeObject::Proxy::Base]
18
- def initialize(object)
19
- self.object = object
20
- @roles = []
21
- evaluate
22
- end
23
-
24
- # Evaluates the objects and assigns roles
25
- # @abstract
26
- def evaluate
27
- end
28
-
29
- # @return [Float]
30
- def max_score
31
- arr = @roles.map(&:max_score).compact
32
- [MAX_SCORE].concat(arr).min
33
- end
34
-
35
- # @return [Float]
36
- def min_score
37
- arr = @roles.map(&:min_score).compact
38
- [MIN_SCORE].concat(arr).max
39
- end
40
-
41
- # @return [Float]
42
- def score
43
- value = @roles.inject(0) { |sum,r| sum + r.score.to_f }
44
- if value < min_score
45
- min_score
46
- elsif value > max_score
47
- max_score
48
- else
49
- value
50
- end
51
- end
52
-
53
- # @return [Fixnum]
54
- def priority
55
- @roles.inject(0) { |sum,r| sum + r.priority.to_i }
56
- end
57
-
58
- # @return [Array<Evaluation::Role::Base>]
59
- def roles
60
- @roles
61
- end
62
-
63
- class << self
64
- attr_reader :criteria_map
65
-
66
- # Defines the weights during evaluation for different criteria
67
- #
68
- # MethodObject.criteria do
69
- # docstring 0.5
70
- # parameters 0.4
71
- # return_type 0.1
72
- #
73
- # if object.constructor?
74
- # parameters 0.5
75
- # return_type 0.0
76
- # end
77
- # end
78
- #
79
- # @return [void]
80
- def criteria(&block)
81
- @criteria_map ||= {}
82
- @criteria_map[to_s] ||= ObjectSchema.new(&block)
83
- end
84
- end
85
-
86
- protected
87
-
88
- def add_role(role)
89
- @roles << role
90
- end
91
-
92
- def criteria
93
- @criteria ||= begin
94
- c = self.class.criteria_map[self.class.to_s]
95
- c.evaluate(object)
96
- c
97
- end
98
- end
99
-
100
- def eval_visibility
101
- if object.in_root?
102
- add_role Role::Object::InRoot.new(object)
103
- end
104
- if object.public?
105
- add_role Role::Object::Public.new(object)
106
- end
107
- if object.protected?
108
- add_role Role::Object::Protected.new(object)
109
- end
110
- if object.private?
111
- add_role Role::Object::Private.new(object)
112
- end
113
- end
114
-
115
- def eval_doc
116
- if object.has_doc?
117
- add_role Role::Object::WithDoc.new(object, score_for(:docstring))
118
- else
119
- add_role Role::Object::WithoutDoc.new(object, score_for(:docstring))
120
- end
121
- if object.nodoc?
122
- add_role Role::Object::TaggedAsNodoc.new(object)
123
- end
124
- end
125
-
126
- def eval_code_example
127
- if object.has_code_example?
128
- if object.has_multiple_code_examples?
129
- add_role Role::Object::WithMultipleCodeExamples.new(object, score_for(:code_example_multi))
130
- else
131
- add_role Role::Object::WithCodeExample.new(object, score_for(:code_example_single))
132
- end
133
- else
134
- add_role Role::Object::WithoutCodeExample.new(object, score_for(:code_example_single))
135
- end
136
- end
137
-
138
- def eval_tags
139
- if object.api_tag?
140
- if object.private_api_tag?
141
- add_role Role::Object::TaggedAsPrivateAPI.new(object)
142
- else
143
- add_role Role::Object::TaggedAsAPI.new(object)
144
- end
145
- end
146
- if object.has_unconsidered_tags?
147
- count = object.unconsidered_tags.size
148
- add_role Role::Object::Tagged.new(object, score_for(:unconsidered_tag) * count)
149
- end
150
- end
151
-
152
- def score_for(criteria_name)
153
- criteria.send(criteria_name) * MAX_SCORE
154
- end
155
- end
156
- end
157
- end
@@ -1,6 +0,0 @@
1
- module Inch
2
- module Evaluation
3
- class ClassObject < NamespaceObject
4
- end
5
- end
6
- end
@@ -1,33 +0,0 @@
1
- module Inch
2
- module Evaluation
3
- class ConstantObject < Base
4
- def evaluate
5
- eval_doc
6
- eval_visibility
7
- end
8
-
9
- def eval_doc
10
- if object.has_doc?
11
- add_role Role::Constant::WithDoc.new(object, score_for(:docstring))
12
- else
13
- add_role Role::Constant::WithoutDoc.new(object, score_for(:docstring))
14
- end
15
- if object.nodoc?
16
- add_role Role::Constant::TaggedAsNodoc.new(object)
17
- end
18
- end
19
-
20
- def eval_visibility
21
- if object.in_root?
22
- add_role Role::Constant::InRoot.new(object)
23
- end
24
- if object.public?
25
- add_role Role::Constant::Public.new(object)
26
- end
27
- if object.private?
28
- add_role Role::Constant::Private.new(object)
29
- end
30
- end
31
- end
32
- end
33
- end
@@ -1,105 +0,0 @@
1
- module Inch
2
- module Evaluation
3
- class MethodObject < Base
4
- def evaluate
5
- eval_doc
6
- eval_code_example
7
- eval_visibility
8
- eval_tags
9
-
10
- eval_parameters
11
- eval_return_type
12
- eval_method
13
- end
14
-
15
- private
16
-
17
- def eval_method
18
- if object.constructor?
19
- add_role Role::Method::Constructor.new(object)
20
- end
21
- if object.getter?
22
- add_role Role::Method::Getter.new(object)
23
- end
24
- if object.setter?
25
- add_role Role::Method::Setter.new(object)
26
- end
27
- if object.overridden?
28
- add_role Role::Method::Overridden.new(object, object.overridden_method.score)
29
- end
30
- if object.has_many_lines?
31
- add_role Role::Method::WithManyLines.new(object)
32
- end
33
- if object.bang_name?
34
- add_role Role::Method::WithBangName.new(object)
35
- end
36
- if object.questioning_name?
37
- add_role Role::Method::WithQuestioningName.new(object)
38
- end
39
- if object.has_alias?
40
- add_role Role::Method::HasAlias.new(object)
41
- end
42
- end
43
-
44
- def eval_parameters
45
- if object.has_parameters?
46
- eval_all_parameters
47
- else
48
- eval_no_parameters
49
- end
50
- end
51
-
52
- def eval_no_parameters
53
- if score > min_score
54
- add_role Role::Method::WithoutParameters.new(object, score_for(:parameters))
55
- end
56
- end
57
-
58
- def eval_all_parameters
59
- params = object.parameters
60
- per_param = score_for(:parameters) / params.size
61
- params.each do |param|
62
- if param.mentioned?
63
- if param.wrongly_mentioned?
64
- add_role Role::MethodParameter::WithWrongMention.new(param, -score_for(:parameters))
65
- else
66
- add_role Role::MethodParameter::WithMention.new(param, per_param * 0.5)
67
- end
68
- else
69
- add_role Role::MethodParameter::WithoutMention.new(param, per_param * 0.5)
70
- end
71
- if param.typed?
72
- add_role Role::MethodParameter::WithType.new(param, per_param * 0.5)
73
- else
74
- add_role Role::MethodParameter::WithoutType.new(param, per_param * 0.5)
75
- end
76
- if param.bad_name?
77
- add_role Role::MethodParameter::WithBadName.new(param)
78
- end
79
- if param.block?
80
- add_role Role::MethodParameter::Block.new(param)
81
- end
82
- if param.splat?
83
- add_role Role::MethodParameter::Splat.new(param)
84
- end
85
- end
86
- if object.has_many_parameters?
87
- add_role Role::Method::WithManyParameters.new(object)
88
- end
89
- end
90
-
91
- def eval_return_type
92
- if object.return_mentioned?
93
- add_role Role::Method::WithReturnType.new(object, score_for(:return_type))
94
- else
95
- add_role Role::Method::WithoutReturnType.new(object, score_for(:return_type))
96
- end
97
- if object.return_described?
98
- add_role Role::Method::WithReturnDescription.new(object, score_for(:return_description))
99
- else
100
- add_role Role::Method::WithoutReturnDescription.new(object, score_for(:return_description))
101
- end
102
- end
103
- end
104
- end
105
- end