3939
4040total_files_size = Dir . glob ( "#{ project . base_dir } /lib/**/*.rb" ) . size
4141
42+ def stats_item ( path , line , line_content , comparison_key )
43+ {
44+ path : path . to_s ,
45+ line : line ,
46+ line_content : line_content ,
47+ comparison_key : comparison_key
48+ } . compact
49+ end
50+
51+ def ignore_item ( path , line , comment_source , ignored_source )
52+ stats_item ( path , line , nil , { type : "steep_ignore" , path : path . to_s , source : comment_source , ignored_source : ignored_source } )
53+ end
54+
55+ def rbs_item ( path , line , source , context )
56+ stats_item ( path , line , source , { type : "rbs_declaration" , path : path . to_s , context : context , source : source } )
57+ end
58+
4259# steep:ignore comments stats
4360ignore_comments = loader . each_path_in_patterns ( datadog_target . source_pattern ) . each_with_object ( [ ] ) do |path , result |
44- buffer = ::Parser ::Source ::Buffer . new ( path . to_s , 1 , source : path . read )
61+ source = path . read
62+ source_lines = source . lines
63+ buffer = ::Parser ::Source ::Buffer . new ( path . to_s , 1 , source : source )
4564 _ , comments = ::Parser ::Ruby25 . new . parse_with_comments ( buffer )
46- rbs_buffer = ::RBS ::Buffer . new ( name : path , content : path . read )
65+ rbs_buffer = ::RBS ::Buffer . new ( name : path , content : source )
4766 comments . each do |comment |
4867 ignore = ::Steep ::AST ::Ignore . parse ( comment , rbs_buffer )
4968 next if ignore . nil? || ignore . is_a? ( ::Steep ::AST ::Ignore ::IgnoreEnd )
5069
51- result << {
52- path : path . to_s ,
53- line : ignore . line
54- }
70+ ignored_source = source_lines [ ignore . line - 1 ] &.strip
71+ result << ignore_item ( path , ignore . line , comment . loc . expression . source , ignored_source )
5572 end
5673end
5774
58- def ast_traversal ( declarations , result = { } )
75+ # Collects declarations with their enclosing RBS namespace for stable comparison keys.
76+ # @param declarations [Array<RBS::AST::Declarations::Base, RBS::AST::Members::Base>]
77+ # @param result [Hash] accumulated methods and other declarations
78+ # @param context [Array<String>] enclosing Ruby namespace, e.g. ["Datadog", "Core"]
79+ def ast_traversal ( declarations , result = { } , context = [ ] )
5980 result [ :methods ] ||= [ ]
6081 result [ :others ] ||= [ ]
6182 declarations . each do |declaration |
6283 case declaration
6384 when ::RBS ::AST ::Declarations ::Module ,
6485 ::RBS ::AST ::Declarations ::Class ,
6586 ::RBS ::AST ::Declarations ::Interface
66- ast_traversal ( declaration . members , result )
87+ ast_traversal ( declaration . members , result , context + [ declaration . name . to_s ] )
6788 when ::RBS ::AST ::Declarations ::TypeAlias ,
6889 ::RBS ::AST ::Declarations ::Constant ,
6990 ::RBS ::AST ::Declarations ::Global ,
7091 ::RBS ::AST ::Members ::Var ,
7192 ::RBS ::AST ::Members ::Attribute
72- result [ :others ] << declaration
93+ result [ :others ] << { declaration : declaration , context : context }
7394 # Only this one does not have a type field
7495 when ::RBS ::AST ::Members ::MethodDefinition
75- result [ :methods ] << declaration
96+ result [ :methods ] << { declaration : declaration , context : context }
7697 end
7798 end
7899 result
@@ -177,7 +198,9 @@ def is_typed?(type, initialize: false)
177198 _ , _directives , declarations = ::RBS ::Parser . parse_signature ( buffer )
178199 filtered_declarations = ast_traversal ( declarations )
179200
180- filtered_declarations [ :methods ] . each do |method |
201+ filtered_declarations [ :methods ] . each do |entry |
202+ method = entry [ :declaration ]
203+
181204 # Skip definitions with last comment line being `untyped:accept`
182205 if method . comment &.string &.end_with? ( "untyped:accept\n " )
183206 typed_methods_size += 1
@@ -192,13 +215,15 @@ def is_typed?(type, initialize: false)
192215 when :typed
193216 typed_methods_size += 1
194217 when :untyped
195- untyped_methods << { path : sig_path . to_s , line : method . location . start_line , line_content : method . location . source }
218+ untyped_methods << rbs_item ( sig_path , method . location . start_line , method . location . source , entry [ :context ] )
196219 when :partial
197- partially_typed_methods << { path : sig_path . to_s , line : method . location . start_line , line_content : method . location . source }
220+ partially_typed_methods << rbs_item ( sig_path , method . location . start_line , method . location . source , entry [ :context ] )
198221 end
199222 end
200223
201- filtered_declarations [ :others ] . each do |declaration |
224+ filtered_declarations [ :others ] . each do |entry |
225+ declaration = entry [ :declaration ]
226+
202227 # Skip definitions with last comment line being `untyped:accept`
203228 if declaration . comment &.string &.end_with? ( "untyped:accept\n " )
204229 typed_others_size += 1
@@ -209,9 +234,9 @@ def is_typed?(type, initialize: false)
209234 when :typed , nil
210235 typed_others_size += 1
211236 when :untyped
212- untyped_others << { path : sig_path . to_s , line : declaration . location . start_line , line_content : declaration . location . source }
237+ untyped_others << rbs_item ( sig_path , declaration . location . start_line , declaration . location . source , entry [ :context ] )
213238 when :partial
214- partially_typed_others << { path : sig_path . to_s , line : declaration . location . start_line , line_content : declaration . location . source }
239+ partially_typed_others << rbs_item ( sig_path , declaration . location . start_line , declaration . location . source , entry [ :context ] )
215240 end
216241 end
217242end
0 commit comments