sord 0.9.0 → 3.0.0.beta.2

Sign up to get free protection for your applications and to get access to all the features.
Files changed (44) hide show
  1. checksums.yaml +4 -4
  2. data/.github/ISSUE_TEMPLATE/bug_report.md +0 -0
  3. data/.github/ISSUE_TEMPLATE/feature-request.md +0 -0
  4. data/.gitignore +0 -0
  5. data/.parlour +6 -2
  6. data/.rspec +0 -0
  7. data/.travis.yml +0 -0
  8. data/CHANGELOG.md +58 -0
  9. data/CODE_OF_CONDUCT.md +0 -0
  10. data/Gemfile +0 -0
  11. data/LICENSE.txt +0 -0
  12. data/README.md +76 -43
  13. data/Rakefile +26 -7
  14. data/exe/sord +48 -6
  15. data/lib/sord.rb +1 -1
  16. data/lib/sord/generator.rb +592 -0
  17. data/lib/sord/logging.rb +0 -0
  18. data/lib/sord/parlour_plugin.rb +24 -3
  19. data/lib/sord/resolver.rb +0 -0
  20. data/lib/sord/type_converter.rb +71 -63
  21. data/lib/sord/version.rb +1 -1
  22. data/rbi/sord.rbi +210 -30
  23. data/sord.gemspec +3 -3
  24. metadata +15 -34
  25. data/lib/sord/rbi_generator.rb +0 -300
  26. data/sorbet/config +0 -0
  27. data/sorbet/rbi/gems/docile.rbi +0 -31
  28. data/sorbet/rbi/gems/parlour.rbi +0 -214
  29. data/sorbet/rbi/gems/rainbow.rbi +0 -117
  30. data/sorbet/rbi/gems/rake.rbi +0 -643
  31. data/sorbet/rbi/gems/rspec-core.rbi +0 -1658
  32. data/sorbet/rbi/gems/rspec-expectations.rbi +0 -389
  33. data/sorbet/rbi/gems/rspec-mocks.rbi +0 -823
  34. data/sorbet/rbi/gems/rspec-support.rbi +0 -268
  35. data/sorbet/rbi/gems/rspec.rbi +0 -14
  36. data/sorbet/rbi/gems/simplecov-html.rbi +0 -30
  37. data/sorbet/rbi/gems/simplecov.rbi +0 -225
  38. data/sorbet/rbi/gems/sorbet-runtime.rbi +0 -670
  39. data/sorbet/rbi/gems/yard.rbi +0 -310
  40. data/sorbet/rbi/hidden-definitions/errors.txt +0 -9285
  41. data/sorbet/rbi/hidden-definitions/hidden.rbi +0 -26604
  42. data/sorbet/rbi/sorbet-typed/lib/bundler/all/bundler.rbi +0 -8575
  43. data/sorbet/rbi/sorbet-typed/lib/ruby/all/open3.rbi +0 -111
  44. data/sorbet/rbi/sorbet-typed/lib/ruby/all/resolv.rbi +0 -543
@@ -16,7 +16,7 @@ Gem::Specification.new do |spec|
16
16
  # Specify which files should be added to the gem when it is released.
17
17
  # The `git ls-files -z` loads the files in the RubyGem that have been added into git.
18
18
  spec.files = Dir.chdir(File.expand_path('..', __FILE__)) do
19
- `git ls-files -z`.split("\x0").reject { |f| f.match(%r{^(test|spec|features)/}) }
19
+ `git ls-files -z`.split("\x0").reject { |f| f.match(%r{^(test|spec|features|sorbet)/}) }
20
20
  end
21
21
  spec.bindir = "exe"
22
22
  spec.executables = spec.files.grep(%r{^exe/}) { |f| File.basename(f) }
@@ -24,8 +24,8 @@ Gem::Specification.new do |spec|
24
24
 
25
25
  spec.add_dependency 'yard'
26
26
  spec.add_dependency 'sorbet-runtime'
27
- spec.add_dependency 'commander', '~> 4.4'
28
- spec.add_dependency 'parlour', '~> 0.6.1'
27
+ spec.add_dependency 'commander', '~> 4.5'
28
+ spec.add_dependency 'parlour', '5.0.0.beta.6'
29
29
 
30
30
  spec.add_development_dependency "bundler", "~> 2.0"
31
31
  spec.add_development_dependency "rake", "~> 10.0"
metadata CHANGED
@@ -1,14 +1,14 @@
1
1
  --- !ruby/object:Gem::Specification
2
2
  name: sord
3
3
  version: !ruby/object:Gem::Version
4
- version: 0.9.0
4
+ version: 3.0.0.beta.2
5
5
  platform: ruby
6
6
  authors:
7
7
  - Aaron Christiansen
8
- autorequire:
8
+ autorequire:
9
9
  bindir: exe
10
10
  cert_chain: []
11
- date: 2019-08-09 00:00:00.000000000 Z
11
+ date: 2020-10-05 00:00:00.000000000 Z
12
12
  dependencies:
13
13
  - !ruby/object:Gem::Dependency
14
14
  name: yard
@@ -44,28 +44,28 @@ dependencies:
44
44
  requirements:
45
45
  - - "~>"
46
46
  - !ruby/object:Gem::Version
47
- version: '4.4'
47
+ version: '4.5'
48
48
  type: :runtime
49
49
  prerelease: false
50
50
  version_requirements: !ruby/object:Gem::Requirement
51
51
  requirements:
52
52
  - - "~>"
53
53
  - !ruby/object:Gem::Version
54
- version: '4.4'
54
+ version: '4.5'
55
55
  - !ruby/object:Gem::Dependency
56
56
  name: parlour
57
57
  requirement: !ruby/object:Gem::Requirement
58
58
  requirements:
59
- - - "~>"
59
+ - - '='
60
60
  - !ruby/object:Gem::Version
61
- version: 0.6.1
61
+ version: 5.0.0.beta.6
62
62
  type: :runtime
63
63
  prerelease: false
64
64
  version_requirements: !ruby/object:Gem::Requirement
65
65
  requirements:
66
- - - "~>"
66
+ - - '='
67
67
  - !ruby/object:Gem::Version
68
- version: 0.6.1
68
+ version: 5.0.0.beta.6
69
69
  - !ruby/object:Gem::Dependency
70
70
  name: bundler
71
71
  requirement: !ruby/object:Gem::Requirement
@@ -136,7 +136,7 @@ dependencies:
136
136
  - - ">="
137
137
  - !ruby/object:Gem::Version
138
138
  version: '0'
139
- description:
139
+ description:
140
140
  email:
141
141
  - aaronc20000@gmail.com
142
142
  executables:
@@ -158,38 +158,19 @@ files:
158
158
  - Rakefile
159
159
  - exe/sord
160
160
  - lib/sord.rb
161
+ - lib/sord/generator.rb
161
162
  - lib/sord/logging.rb
162
163
  - lib/sord/parlour_plugin.rb
163
- - lib/sord/rbi_generator.rb
164
164
  - lib/sord/resolver.rb
165
165
  - lib/sord/type_converter.rb
166
166
  - lib/sord/version.rb
167
167
  - rbi/sord.rbi
168
- - sorbet/config
169
- - sorbet/rbi/gems/docile.rbi
170
- - sorbet/rbi/gems/parlour.rbi
171
- - sorbet/rbi/gems/rainbow.rbi
172
- - sorbet/rbi/gems/rake.rbi
173
- - sorbet/rbi/gems/rspec-core.rbi
174
- - sorbet/rbi/gems/rspec-expectations.rbi
175
- - sorbet/rbi/gems/rspec-mocks.rbi
176
- - sorbet/rbi/gems/rspec-support.rbi
177
- - sorbet/rbi/gems/rspec.rbi
178
- - sorbet/rbi/gems/simplecov-html.rbi
179
- - sorbet/rbi/gems/simplecov.rbi
180
- - sorbet/rbi/gems/sorbet-runtime.rbi
181
- - sorbet/rbi/gems/yard.rbi
182
- - sorbet/rbi/hidden-definitions/errors.txt
183
- - sorbet/rbi/hidden-definitions/hidden.rbi
184
- - sorbet/rbi/sorbet-typed/lib/bundler/all/bundler.rbi
185
- - sorbet/rbi/sorbet-typed/lib/ruby/all/open3.rbi
186
- - sorbet/rbi/sorbet-typed/lib/ruby/all/resolv.rbi
187
168
  - sord.gemspec
188
169
  homepage: https://github.com/AaronC81/sord
189
170
  licenses:
190
171
  - MIT
191
172
  metadata: {}
192
- post_install_message:
173
+ post_install_message:
193
174
  rdoc_options: []
194
175
  require_paths:
195
176
  - lib
@@ -200,12 +181,12 @@ required_ruby_version: !ruby/object:Gem::Requirement
200
181
  version: '0'
201
182
  required_rubygems_version: !ruby/object:Gem::Requirement
202
183
  requirements:
203
- - - ">="
184
+ - - ">"
204
185
  - !ruby/object:Gem::Version
205
- version: '0'
186
+ version: 1.3.1
206
187
  requirements: []
207
188
  rubygems_version: 3.0.3
208
- signing_key:
189
+ signing_key:
209
190
  specification_version: 4
210
191
  summary: Generate Sorbet RBI files from YARD documentation
211
192
  test_files: []
@@ -1,300 +0,0 @@
1
- # typed: true
2
- require 'yard'
3
- require 'sord/type_converter'
4
- require 'sord/logging'
5
- require 'parlour'
6
- require 'rainbow'
7
-
8
- module Sord
9
- # Converts the current working directory's YARD registry into an RBI file.
10
- class RbiGenerator
11
- # @return [Integer] The number of objects this generator has processed so
12
- # far.
13
- def object_count
14
- @namespace_count + @method_count
15
- end
16
-
17
- # @return [Array<Array(String, YARD::CodeObjects::Base, Integer)>] The
18
- # errors encountered by by the generator. Each element is of the form
19
- # [message, item, line].
20
- attr_reader :warnings
21
-
22
- # Create a new RBI generator.
23
- # @param [Hash] options
24
- # @option options [Integer] break_params
25
- # @option options [Boolean] replace_errors_with_untyped
26
- # @option options [Boolean] replace_unresolved_with_untyped
27
- # @option options [Boolean] comments
28
- # @option options [Parlour::RbiGenerator] generator
29
- # @option options [Parlour::RbiGenerator::Namespace] root
30
- # @return [void]
31
- def initialize(options)
32
- @parlour = options[:parlour] || Parlour::RbiGenerator.new
33
- @current_object = options[:root] || @parlour.root
34
-
35
- @namespace_count = 0
36
- @method_count = 0
37
- @warnings = []
38
-
39
- @replace_errors_with_untyped = options[:replace_errors_with_untyped]
40
- @replace_unresolved_with_untyped = options[:replace_unresolved_with_untyped]
41
-
42
- # Hook the logger so that messages are added as comments to the RBI file
43
- Logging.add_hook do |type, msg, item|
44
- @current_object.add_comment_to_next_child("sord #{type} - #{msg}")
45
- end if options[:comments]
46
-
47
- # Hook the logger so that warnings are collected
48
- Logging.add_hook do |type, msg, item|
49
- # TODO: is it possible to get line numbers here?
50
- warnings << [msg, item, 0] if type == :warn
51
- end
52
- end
53
-
54
- # Increment the namespace counter.
55
- # @return [void]
56
- def count_namespace
57
- @namespace_count += 1
58
- end
59
-
60
- # Increment the method counter.
61
- # @return [void]
62
- def count_method
63
- @method_count += 1
64
- end
65
-
66
- # Given a YARD CodeObject, add lines defining its mixins (that is, extends
67
- # and includes) to the current RBI file. Returns the number of mixins.
68
- # @param [YARD::CodeObjects::Base] item
69
- # @return [Integer]
70
- def add_mixins(item)
71
- item.instance_mixins.reverse_each do |i|
72
- @current_object.create_include(i.path.to_s)
73
- end
74
- item.class_mixins.reverse_each do |e|
75
- @current_object.create_extend(e.path.to_s)
76
- end
77
-
78
- item.instance_mixins.length + item.class_mixins.length
79
- end
80
-
81
- # Given a YARD NamespaceObject, add lines defining constants.
82
- # @param [YARD::CodeObjects::NamespaceObject] item
83
- # @return [void]
84
- def add_constants(item)
85
- item.constants.each do |constant|
86
- # Take a constant (like "A::B::CONSTANT"), split it on each '::', and
87
- # set the constant name to the last string in the array.
88
- constant_name = constant.to_s.split('::').last
89
-
90
- # Add the constant to the current object being generated.
91
- @current_object.create_constant(constant_name, value: "T.let(#{constant.value}, T.untyped)")
92
- end
93
- end
94
-
95
- # Given a YARD NamespaceObject, add lines defining its methods and their
96
- # signatures to the current RBI file.
97
- # @param [YARD::CodeObjects::NamespaceObject] item
98
- # @return [void]
99
- def add_methods(item)
100
- item.meths(inherited: false).each do |meth|
101
- count_method
102
-
103
- # If the method is an alias, skip it so we don't define it as a
104
- # separate method. Sorbet will handle it automatically.
105
- if meth.is_alias?
106
- next
107
- end
108
-
109
- # This is better than iterating over YARD's "@param" tags directly
110
- # because it includes parameters without documentation
111
- # (The gsubs allow for better splat-argument compatibility)
112
- parameter_names_and_defaults_to_tags = meth.parameters.map do |name, default|
113
- [[name, default], meth.tags('param')
114
- .find { |p| p.name&.gsub('*', '')&.gsub(':', '') == name.gsub('*', '').gsub(':', '') }]
115
- end.to_h
116
-
117
- parameter_types = parameter_names_and_defaults_to_tags.map do |name_and_default, tag|
118
- name = name_and_default.first
119
-
120
- if tag
121
- TypeConverter.yard_to_sorbet(tag.types, meth, @replace_errors_with_untyped, @replace_unresolved_with_untyped)
122
- elsif name.start_with? '&'
123
- # Find yieldparams and yieldreturn
124
- yieldparams = meth.tags('yieldparam')
125
- yieldreturn = meth.tag('yieldreturn')&.types
126
- yieldreturn = nil if yieldreturn&.length == 1 &&
127
- yieldreturn&.first&.downcase == 'void'
128
-
129
- # Create strings
130
- params_string = yieldparams.map do |param|
131
- "#{param.name.gsub('*', '')}: #{TypeConverter.yard_to_sorbet(param.types, meth, @replace_errors_with_untyped, @replace_unresolved_with_untyped)}" unless param.name.nil?
132
- end.join(', ')
133
- return_string = TypeConverter.yard_to_sorbet(yieldreturn, meth, @replace_errors_with_untyped, @replace_unresolved_with_untyped)
134
-
135
- # Create proc types, if possible
136
- if yieldparams.empty? && yieldreturn.nil?
137
- 'T.untyped'
138
- elsif yieldreturn.nil?
139
- "T.proc#{params_string.empty? ? '' : ".params(#{params_string})"}.void"
140
- else
141
- "T.proc#{params_string.empty? ? '' : ".params(#{params_string})"}.returns(#{return_string})"
142
- end
143
- elsif meth.path.end_with? '='
144
- # Look for the matching getter method
145
- getter_path = meth.path[0...-1]
146
- getter = item.meths.find { |m| m.path == getter_path }
147
-
148
- unless getter
149
- if parameter_names_and_defaults_to_tags.length == 1 \
150
- && meth.tags('param').length == 1 \
151
- && meth.tag('param').types
152
-
153
- Logging.infer("argument name in single @param inferred as #{parameter_names_and_defaults_to_tags.first.first.first.inspect}", meth)
154
- next TypeConverter.yard_to_sorbet(meth.tag('param').types, meth, @replace_errors_with_untyped, @replace_unresolved_with_untyped)
155
- else
156
- Logging.omit("no YARD type given for #{name.inspect}, using T.untyped", meth)
157
- next 'T.untyped'
158
- end
159
- end
160
-
161
- inferred_type = TypeConverter.yard_to_sorbet(
162
- getter.tags('return').flat_map(&:types), meth, @replace_errors_with_untyped, @replace_unresolved_with_untyped)
163
-
164
- Logging.infer("inferred type of parameter #{name.inspect} as #{inferred_type} using getter's return type", meth)
165
- inferred_type
166
- else
167
- # Is this the only argument, and was a @param specified without an
168
- # argument name? If so, infer it
169
- if parameter_names_and_defaults_to_tags.length == 1 \
170
- && meth.tags('param').length == 1 \
171
- && meth.tag('param').types
172
-
173
- Logging.infer("argument name in single @param inferred as #{parameter_names_and_defaults_to_tags.first.first.first.inspect}", meth)
174
- TypeConverter.yard_to_sorbet(meth.tag('param').types, meth, @replace_errors_with_untyped, @replace_unresolved_with_untyped)
175
- else
176
- Logging.omit("no YARD type given for #{name.inspect}, using T.untyped", meth)
177
- 'T.untyped'
178
- end
179
- end
180
- end
181
-
182
- return_tags = meth.tags('return')
183
- returns = if return_tags.length == 0
184
- Logging.omit("no YARD return type given, using T.untyped", meth)
185
- 'T.untyped'
186
- elsif return_tags.length == 1 && return_tags&.first&.types&.first&.downcase == "void"
187
- nil
188
- else
189
- TypeConverter.yard_to_sorbet(meth.tag('return').types, meth, @replace_errors_with_untyped, @replace_unresolved_with_untyped)
190
- end
191
-
192
- parlour_params = parameter_names_and_defaults_to_tags
193
- .zip(parameter_types)
194
- .map do |((name, default), _), type|
195
- # If the default is "nil" but the type is not nilable, then it
196
- # should become nilable
197
- # (T.untyped can include nil, so don't alter that)
198
- type = "T.nilable(#{type})" \
199
- if default == 'nil' && !type.start_with?('T.nilable') && type != 'T.untyped'
200
- Parlour::RbiGenerator::Parameter.new(
201
- name.to_s,
202
- type: type,
203
- default: default
204
- )
205
- end
206
-
207
- @current_object.create_method(
208
- meth.name.to_s,
209
- parameters: parlour_params,
210
- returns: returns,
211
- class_method: meth.scope == :class
212
- )
213
- end
214
- end
215
-
216
- # Given a YARD NamespaceObject, add lines defining its mixins, methods
217
- # and children to the RBI file.
218
- # @param [YARD::CodeObjects::NamespaceObject] item
219
- # @return [void]
220
- def add_namespace(item)
221
- count_namespace
222
-
223
- superclass = nil
224
- superclass = item.superclass.path.to_s if item.type == :class && item.superclass.to_s != "Object"
225
-
226
- parent = @current_object
227
- @current_object = item.type == :class \
228
- ? parent.create_class(item.name.to_s, superclass: superclass)
229
- : parent.create_module(item.name.to_s)
230
-
231
- add_mixins(item)
232
- add_methods(item)
233
- add_constants(item)
234
-
235
- item.children.select { |x| [:class, :module].include?(x.type) }
236
- .each { |child| add_namespace(child) }
237
-
238
- @current_object = parent
239
- end
240
-
241
- # Populates the RBI generator with the contents of the YARD registry. You
242
- # must load the YARD registry first!
243
- # @return [void]
244
- def populate
245
- # Generate top-level modules, which recurses to all modules
246
- YARD::Registry.root.children
247
- .select { |x| [:class, :module].include?(x.type) }
248
- .each { |child| add_namespace(child) }
249
- end
250
-
251
- # Populates the RBI generator with the contents of the YARD registry, then
252
- # uses the loaded Parlour::RbiGenerator to generate the RBI file. You must
253
- # load the YARD registry first!
254
- # @return [void]
255
- def generate
256
- populate
257
- @parlour.rbi
258
- end
259
-
260
- # Loads the YARD registry, populates the RBI file, and prints any relevant
261
- # final logs.
262
- # @return [void]
263
- def run
264
- # Get YARD ready
265
- YARD::Registry.load!
266
-
267
- # Populate the RBI
268
- populate
269
-
270
- if object_count.zero?
271
- Logging.warn("No objects processed.")
272
- Logging.warn("Have you definitely generated the YARD documentation for this project?")
273
- Logging.warn("Run `yard` to generate docs.")
274
- end
275
-
276
- Logging.done("Processed #{object_count} objects (#{@namespace_count} namespaces and #{@method_count} methods)")
277
-
278
- Logging.hooks.clear
279
-
280
- unless warnings.empty?
281
- Logging.warn("There were #{warnings.length} important warnings in the RBI file, listed below.")
282
- if @replace_errors_with_untyped
283
- Logging.warn("The types which caused them have been replaced with T.untyped.")
284
- else
285
- Logging.warn("The types which caused them have been replaced with SORD_ERROR_ constants.")
286
- end
287
- Logging.warn("Please edit the file to fix these errors.")
288
- Logging.warn("Alternatively, edit your YARD documentation so that your types are valid and re-run Sord.")
289
- warnings.each do |(msg, item, _)|
290
- puts " (#{Rainbow(item&.path).bold}) #{msg}"
291
- end
292
- end
293
- rescue
294
- Logging.error($!)
295
- $@.each do |line|
296
- puts " #{line}"
297
- end
298
- end
299
- end
300
- end
File without changes
@@ -1,31 +0,0 @@
1
- # This file is autogenerated. Do not edit it by hand. Regenerate it with:
2
- # srb rbi gems
3
-
4
- # typed: true
5
- #
6
- # If you would like to make changes to this file, great! Please create the gem's shim here:
7
- #
8
- # https://github.com/sorbet/sorbet-typed/new/master?filename=lib/docile/all/docile.rbi
9
- #
10
- # docile-1.3.2
11
- module Docile
12
- def dsl_eval(dsl, *args, &block); end
13
- def dsl_eval_immutable(dsl, *args, &block); end
14
- def dsl_eval_with_block_return(dsl, *args, &block); end
15
- def self.dsl_eval(dsl, *args, &block); end
16
- def self.dsl_eval_immutable(dsl, *args, &block); end
17
- def self.dsl_eval_with_block_return(dsl, *args, &block); end
18
- extend Docile::Execution
19
- end
20
- module Docile::Execution
21
- def exec_in_proxy_context(dsl, proxy_type, *args, &block); end
22
- def self.exec_in_proxy_context(dsl, proxy_type, *args, &block); end
23
- end
24
- class Docile::FallbackContextProxy
25
- def initialize(receiver, fallback); end
26
- def instance_variables; end
27
- def method_missing(method, *args, &block); end
28
- end
29
- class Docile::ChainingFallbackContextProxy < Docile::FallbackContextProxy
30
- def method_missing(method, *args, &block); end
31
- end