rubocop-rbs_inline 1.5.5 → 1.6.0

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 CHANGED
@@ -1,7 +1,7 @@
1
1
  ---
2
2
  SHA256:
3
- metadata.gz: 5c49186b8eccbf2e04581f828318839da5405951bf81833fc895eca366d850b8
4
- data.tar.gz: 6e56027b2905e92da5bbc9ec5f16cfb92027f9a6fce03f15ff9a23b40fb95929
3
+ metadata.gz: 13356ee2ff7161f55fabd910db6c5baf0e49a9c45baf4f45cb056c0dd530d1bc
4
+ data.tar.gz: 02fa848f90ced8e1262cdb7fca6fc17f62472594f374b03ce103ebfb978aac15
5
5
  SHA512:
6
- metadata.gz: dda3647518169c8fc20fd69e240c762315a7d2483c8bf58a771cb3f3287f366a1dce929a5fc456e2d48c4ad3b8e0a78cc062c6895cb2159738d6326100586fb8
7
- data.tar.gz: 254f949c7b20a84c115ccbae0b10c23dbcf082ad56065170cb048a25a143eb42d6a3733fa12b85dc315c7b79c2d30c1e45bf3f6af2a620c9a2e7844e1eb8271b
6
+ metadata.gz: 60d860bb7082c040502b9bbba4cdf00ca265f9cc2cb5a7df9a71b597f50241fb722f9c0e234db67eecccf0e9f75611fbc92099fbd76eb063372953b79ac9a259
7
+ data.tar.gz: ffa3593debf4c47cfb605f4da9f6e23615d628253044eb05da335cdf4019535e1f3bf676c55de6ed4290c49c58b17f2fd50a6056c99d6eba4165fcd4ed5a58f4
data/CHANGELOG.md CHANGED
@@ -1,5 +1,15 @@
1
1
  # Changelog
2
2
 
3
+ ## 1.6.0 (2026-07-05)
4
+
5
+ ### Changes
6
+
7
+ - All cops now exclude `spec/**/*` and `test/**/*` by default. Override with `Exclude: []` per cop to lint annotations in test code.
8
+
9
+ ### Bug Fixes
10
+
11
+ - **Style/RbsInline/UntypedInstanceVariable**: No longer reports a false positive for class instance variables (assigned inside `class << self` or `def self.foo`) that have a `# @rbs self.@name: Type` annotation.
12
+
3
13
  ## 1.5.5 (2026-05-19)
4
14
 
5
15
  ### Bug Fixes
data/CLAUDE.md CHANGED
@@ -20,7 +20,8 @@ bundle exec rake rubocop:autocorrect # safe autocorrect
20
20
  bundle exec rake rubocop:autocorrect_all # all autocorrect
21
21
 
22
22
  # Type check
23
- bundle exec rake rbs:check # runs steep check
23
+ bundle exec rake steep # runs steep check
24
+ bundle exec rake rbs:validate # validates RBS signatures
24
25
 
25
26
  # Default rake task (runs specs, rubocop, and type check)
26
27
  bundle exec rake
data/Rakefile CHANGED
@@ -5,7 +5,9 @@ require 'rubocop/rake_task'
5
5
 
6
6
  RuboCop::RakeTask.new
7
7
 
8
- task default: %i[spec rubocop rbs:check]
8
+ task default: :ci
9
+
10
+ task ci: %i[rubocop spec steep rbs:validate]
9
11
 
10
12
  require 'rspec/core/rake_task'
11
13
 
@@ -33,9 +35,23 @@ task :new_cop, [:cop] do |_task, args|
33
35
  end
34
36
 
35
37
  namespace :rbs do
36
- desc 'Do type check using Steep'
37
- task :check do
38
+ desc 'Install RBS signatures'
39
+ task :install do
40
+ sh 'bundle', 'exec', 'rbs', 'collection', 'install', '--frozen'
41
+ end
42
+
43
+ desc 'Generate RBS files'
44
+ task :generate do
45
+ sh 'rbs-inline', '--opt-out', '--output=sig', 'lib'
46
+ end
47
+
48
+ desc 'Validate RBS files'
49
+ task validate: 'rbs:install' do
38
50
  sh 'rbs', '-Isig', 'validate'
39
- sh 'bundle', 'exec', 'steep', 'check'
40
51
  end
41
52
  end
53
+
54
+ desc 'Run Steep type checker'
55
+ task steep: 'rbs:install' do
56
+ sh 'bundle', 'exec', 'steep', 'check'
57
+ end
data/config/default.yml CHANGED
@@ -2,41 +2,65 @@ Style/RbsInline/DataClassCommentAlignment:
2
2
  Description: "Checks that `#:` inline type annotations in `Data.define` blocks are aligned."
3
3
  Enabled: true
4
4
  VersionAdded: '1.5.0'
5
+ Exclude:
6
+ - 'spec/**/*'
7
+ - 'test/**/*'
5
8
 
6
9
  Style/RbsInline/DataDefineWithBlock:
7
10
  Description: "Checks for `Data.define` calls with a block, which RBS::Inline does not parse."
8
11
  Enabled: true
9
12
  VersionAdded: '1.5.0'
13
+ Exclude:
14
+ - 'spec/**/*'
15
+ - 'test/**/*'
10
16
 
11
17
  Style/RbsInline/EmbeddedRbsSpacing:
12
18
  Description: 'Checks that `@rbs!` comments (embedded RBS) are followed by a blank line.'
13
19
  Enabled: true
14
20
  VersionAdded: '1.5.0'
21
+ Exclude:
22
+ - 'spec/**/*'
23
+ - 'test/**/*'
15
24
 
16
25
  Style/RbsInline/InvalidComment:
17
26
  Description: "Checks the rbs-inline annotation comment is valid."
18
27
  Enabled: true
19
28
  VersionAdded: "1.0.0"
29
+ Exclude:
30
+ - 'spec/**/*'
31
+ - 'test/**/*'
20
32
 
21
33
  Style/RbsInline/InvalidTypes:
22
34
  Description: "Checks the rbs-inline annotation comment uses valid types."
23
35
  Enabled: true
24
36
  VersionAdded: "1.0.0"
37
+ Exclude:
38
+ - 'spec/**/*'
39
+ - 'test/**/*'
25
40
 
26
41
  Style/RbsInline/KeywordSeparator:
27
42
  Description: "Checks the rbs-inline annotation comment does not use a separator after the keywords."
28
43
  Enabled: true
29
44
  VersionAdded: "1.0.0"
45
+ Exclude:
46
+ - 'spec/**/*'
47
+ - 'test/**/*'
30
48
 
31
49
  Style/RbsInline/MethodCommentSpacing:
32
50
  Description: 'Checks that method-related `@rbs` annotations are placed immediately before method definitions.'
33
51
  Enabled: true
34
52
  VersionAdded: '1.5.0'
53
+ Exclude:
54
+ - 'spec/**/*'
55
+ - 'test/**/*'
35
56
 
36
57
  Style/RbsInline/MissingDataClassAnnotation:
37
58
  Description: "Checks that `Data.define` attributes have inline type annotations."
38
59
  Enabled: true
39
60
  VersionAdded: '1.5.0'
61
+ Exclude:
62
+ - 'spec/**/*'
63
+ - 'test/**/*'
40
64
 
41
65
  Style/RbsInline/MissingTypeAnnotation:
42
66
  Description: "Checks that method definitions and attr_* declarations have RBS inline type annotations."
@@ -49,22 +73,34 @@ Style/RbsInline/MissingTypeAnnotation:
49
73
  - method_type_signature
50
74
  - method_type_signature_or_return_annotation
51
75
  Visibility: all
76
+ Exclude:
77
+ - 'spec/**/*'
78
+ - 'test/**/*'
52
79
 
53
80
  Style/RbsInline/ParametersSeparator:
54
81
  Description: "Checks the rbs-inline annotation comment uses a separator to parameters"
55
82
  Enabled: true
56
83
  VersionAdded: "1.0.0"
84
+ Exclude:
85
+ - 'spec/**/*'
86
+ - 'test/**/*'
57
87
 
58
88
  Style/RbsInline/RedundantAnnotationWithSkip:
59
89
  Description: "Checks for redundant type annotations when `@rbs skip` or `@rbs override` is present."
60
90
  Enabled: true
61
91
  SafeAutoCorrect: false
62
92
  VersionAdded: '1.5.0'
93
+ Exclude:
94
+ - 'spec/**/*'
95
+ - 'test/**/*'
63
96
 
64
97
  Style/RbsInline/RedundantInstanceVariableAnnotation:
65
98
  Description: "Checks for redundant `@rbs` instance variable type annotation when `attr_*` with an inline type annotation is already defined."
66
99
  Enabled: true
67
100
  VersionAdded: '1.5.0'
101
+ Exclude:
102
+ - 'spec/**/*'
103
+ - 'test/**/*'
68
104
 
69
105
  Style/RbsInline/RedundantTypeAnnotation:
70
106
  Description: "Checks for redundant type annotations when multiple type specifications exist for the same method definition."
@@ -76,6 +112,9 @@ Style/RbsInline/RedundantTypeAnnotation:
76
112
  - method_type_signature
77
113
  - doc_style
78
114
  - doc_style_and_return_annotation
115
+ Exclude:
116
+ - 'spec/**/*'
117
+ - 'test/**/*'
79
118
 
80
119
  Style/RbsInline/RequireRbsInlineComment:
81
120
  Description: "Checks the presence or absence of `# rbs_inline: enabled` magic comment."
@@ -85,18 +124,30 @@ Style/RbsInline/RequireRbsInlineComment:
85
124
  SupportedStyles:
86
125
  - always
87
126
  - never
127
+ Exclude:
128
+ - 'spec/**/*'
129
+ - 'test/**/*'
88
130
 
89
131
  Style/RbsInline/UnmatchedAnnotations:
90
132
  Description: "Checks the rbs-inline annotation comment is surely matched."
91
133
  Enabled: true
92
134
  VersionAdded: "1.0.0"
135
+ Exclude:
136
+ - 'spec/**/*'
137
+ - 'test/**/*'
93
138
 
94
139
  Style/RbsInline/UntypedInstanceVariable:
95
140
  Description: "Checks that instance variables in classes/modules have RBS type annotations."
96
141
  Enabled: true
97
142
  VersionAdded: '1.5.0'
143
+ Exclude:
144
+ - 'spec/**/*'
145
+ - 'test/**/*'
98
146
 
99
147
  Style/RbsInline/VariableCommentSpacing:
100
148
  Description: 'Checks that `@rbs` variable comments are followed by a blank line.'
101
149
  Enabled: true
102
150
  VersionAdded: '1.5.0'
151
+ Exclude:
152
+ - 'spec/**/*'
153
+ - 'test/**/*'
@@ -10,6 +10,8 @@ module RuboCop
10
10
  #
11
11
  # Instance variables must either have a `# @rbs @ivar: Type` annotation
12
12
  # or be covered by a typed `attr_reader/writer/accessor` declaration.
13
+ # Class-level (singleton) instance variables, assigned inside `class << self`
14
+ # or `def self.x`, must be annotated with `# @rbs self.@ivar: Type` instead.
13
15
  #
14
16
  # Only instance variables that are **assigned** within the class/module are checked.
15
17
  # Read-only references are ignored because the variable may be defined in a parent class.
@@ -47,30 +49,49 @@ module RuboCop
47
49
  # end
48
50
  # end
49
51
  #
50
- class UntypedInstanceVariable < Base
52
+ # # good (class-level ivar annotated with `self.@`)
53
+ # class Foo
54
+ # # @rbs self.@instance: Foo
55
+ #
56
+ # def self.instance
57
+ # @instance ||= new
58
+ # end
59
+ # end
60
+ #
61
+ class UntypedInstanceVariable < Base # rubocop:disable Metrics/ClassLength
51
62
  include ASTUtils
52
63
  include CommentParser
53
64
  include RangeHelp
54
65
 
55
- MSG = 'Instance variable `%<name>s` is not typed. ' \
56
- 'Add `# @rbs %<name>s: Type` or use `attr_* :%<bare_name>s #: Type`.'
66
+ MSG_IVAR = 'Instance variable `%<name>s` is not typed. ' \
67
+ 'Add `# @rbs %<name>s: Type` or use `attr_* :%<bare_name>s #: Type`.'
68
+ MSG_CIVAR = 'Class instance variable `%<name>s` is not typed. ' \
69
+ 'Add `# @rbs self.%<name>s: Type` or use `attr_* :%<bare_name>s #: Type`.'
57
70
 
58
71
  ATTR_METHODS = %i[attr_reader attr_writer attr_accessor].freeze
59
72
 
60
- # @rbs! type scope = { typed_ivars: Set[Symbol], assigned_ivars: Hash[Symbol, RuboCop::AST::Node] }
73
+ # @rbs! type scope = {
74
+ # typed_ivars: Set[Symbol],
75
+ # typed_class_ivars: Set[Symbol],
76
+ # assigned_ivars: Hash[Symbol, RuboCop::AST::Node],
77
+ # assigned_class_ivars: Hash[Symbol, RuboCop::AST::Node],
78
+ # singleton_depth: Integer
79
+ # }
61
80
 
62
81
  attr_reader :scope_stack #: Array[scope]
63
82
  attr_reader :ivar_type_annotations #: Hash[Integer, Symbol]
83
+ attr_reader :civar_type_annotations #: Hash[Integer, Symbol]
64
84
 
65
85
  def on_new_investigation #: void
66
86
  parse_comments
67
87
  @scope_stack = []
68
- @ivar_type_annotations = collect_ivar_type_annotations
88
+ @ivar_type_annotations, @civar_type_annotations = collect_ivar_type_annotations
69
89
  push_scope
70
90
  end
71
91
 
72
92
  def on_investigation_end #: void
73
93
  ivar_type_annotations.each_value { |name| current_scope[:typed_ivars] << name }
94
+ civar_type_annotations.each_value { |name| current_scope[:typed_class_ivars] << name }
74
95
  report_offenses
75
96
  pop_scope
76
97
  end
@@ -91,10 +112,26 @@ module RuboCop
91
112
 
92
113
  alias after_module after_class
93
114
 
115
+ # @rbs _node: RuboCop::AST::Node
116
+ def on_sclass(_node) #: void
117
+ current_scope[:singleton_depth] += 1
118
+ end
119
+ alias on_defs on_sclass
120
+
121
+ # @rbs _node: RuboCop::AST::Node
122
+ def after_sclass(_node) #: void
123
+ current_scope[:singleton_depth] -= 1
124
+ end
125
+ alias after_defs after_sclass
126
+
94
127
  # @rbs node: RuboCop::AST::Node
95
128
  def on_ivasgn(node) #: void
96
129
  name = node.children.first #: Symbol
97
- current_scope[:assigned_ivars][name] ||= node
130
+ if singleton_context?
131
+ current_scope[:assigned_class_ivars][name] ||= node
132
+ else
133
+ current_scope[:assigned_ivars][name] ||= node
134
+ end
98
135
  end
99
136
 
100
137
  # @rbs node: RuboCop::AST::SendNode
@@ -113,16 +150,23 @@ module RuboCop
113
150
 
114
151
  # @rbs node: RuboCop::AST::SendNode
115
152
  def register_attr_ivars(node) #: void
153
+ typed = singleton_context? ? current_scope[:typed_class_ivars] : current_scope[:typed_ivars]
116
154
  node.arguments.each do |arg|
117
155
  case arg
118
156
  when RuboCop::AST::SymbolNode, RuboCop::AST::StrNode
119
- current_scope[:typed_ivars] << :"@#{arg.value}"
157
+ typed << :"@#{arg.value}"
120
158
  end
121
159
  end
122
160
  end
123
161
 
124
162
  def push_scope #: void
125
- scope_stack.push({ typed_ivars: Set.new, assigned_ivars: {} })
163
+ scope_stack.push({
164
+ typed_ivars: Set.new,
165
+ typed_class_ivars: Set.new,
166
+ assigned_ivars: {},
167
+ assigned_class_ivars: {},
168
+ singleton_depth: 0
169
+ })
126
170
  end
127
171
 
128
172
  def pop_scope #: void
@@ -133,6 +177,10 @@ module RuboCop
133
177
  scope_stack.last || raise
134
178
  end
135
179
 
180
+ def singleton_context? #: bool
181
+ current_scope[:singleton_depth].positive?
182
+ end
183
+
136
184
  # @rbs node: RuboCop::AST::Node
137
185
  def collect_typed_ivars_for_scope(node) #: void
138
186
  class_start = node.location.line
@@ -140,24 +188,45 @@ module RuboCop
140
188
  ivar_type_annotations.reject! do |line, name|
141
189
  current_scope[:typed_ivars] << name if line.between?(class_start, class_end)
142
190
  end
191
+ civar_type_annotations.reject! do |line, name|
192
+ current_scope[:typed_class_ivars] << name if line.between?(class_start, class_end)
193
+ end
143
194
  end
144
195
 
145
- def collect_ivar_type_annotations #: Hash[Integer, Symbol] # rubocop:disable Metrics/CyclomaticComplexity
146
- parsed_comments.flat_map { |r| r.each_annotation.to_a }.filter_map do |ann|
196
+ def collect_ivar_type_annotations #: [Hash[Integer, Symbol], Hash[Integer, Symbol]]
197
+ ivar = {} #: Hash[Integer, Symbol]
198
+ civar = {} #: Hash[Integer, Symbol]
199
+ parsed_comments.flat_map { |r| r.each_annotation.to_a }.each do |ann|
147
200
  next unless ann.is_a?(RBS::Inline::AST::Annotations::IvarType)
148
- next if ann.class_instance
149
201
 
150
- line = ann.source.comments.first&.location&.start_line || 0
151
- [line, ann.name]
152
- end.to_h
202
+ if ann.class_instance
203
+ civar[annotation_line(ann)] = ann.name
204
+ else
205
+ ivar[annotation_line(ann)] = ann.name
206
+ end
207
+ end
208
+ [ivar, civar]
209
+ end
210
+
211
+ # @rbs ann: RBS::Inline::AST::Annotations::IvarType
212
+ def annotation_line(ann) #: Integer
213
+ ann.source.comments.first&.location&.start_line || 0
153
214
  end
154
215
 
155
216
  def report_offenses #: void
156
- current_scope[:assigned_ivars].each do |name, node|
157
- next if current_scope[:typed_ivars].include?(name)
217
+ report_untyped(current_scope[:assigned_ivars], current_scope[:typed_ivars], MSG_IVAR)
218
+ report_untyped(current_scope[:assigned_class_ivars], current_scope[:typed_class_ivars], MSG_CIVAR)
219
+ end
220
+
221
+ # @rbs assigned: Hash[Symbol, RuboCop::AST::Node]
222
+ # @rbs typed: Set[Symbol]
223
+ # @rbs message_template: String
224
+ def report_untyped(assigned, typed, message_template) #: void
225
+ assigned.each do |name, node|
226
+ next if typed.include?(name)
158
227
 
159
228
  bare_name = name.to_s.delete_prefix('@')
160
- add_offense(name_location(node), message: format(MSG, name:, bare_name:))
229
+ add_offense(name_location(node), message: format(message_template, name:, bare_name:))
161
230
  end
162
231
  end
163
232
  end
@@ -2,6 +2,6 @@
2
2
 
3
3
  module RuboCop
4
4
  module RbsInline
5
- VERSION = '1.5.5'
5
+ VERSION = '1.6.0'
6
6
  end
7
7
  end
@@ -6,7 +6,7 @@ gems:
6
6
  source:
7
7
  type: git
8
8
  name: ruby/gem_rbs_collection
9
- revision: 81fa8bd0617286078617a62b6a3229cebfd4af23
9
+ revision: 5689759efdc7875d533e8e5b2376b4ab89472e36
10
10
  remote: https://github.com/ruby/gem_rbs_collection.git
11
11
  repo_dir: gems
12
12
  - name: diff-lcs
@@ -14,7 +14,7 @@ gems:
14
14
  source:
15
15
  type: git
16
16
  name: ruby/gem_rbs_collection
17
- revision: 81fa8bd0617286078617a62b6a3229cebfd4af23
17
+ revision: 5689759efdc7875d533e8e5b2376b4ab89472e36
18
18
  remote: https://github.com/ruby/gem_rbs_collection.git
19
19
  repo_dir: gems
20
20
  - name: fileutils
@@ -30,7 +30,7 @@ gems:
30
30
  source:
31
31
  type: git
32
32
  name: ruby/gem_rbs_collection
33
- revision: 81fa8bd0617286078617a62b6a3229cebfd4af23
33
+ revision: 5689759efdc7875d533e8e5b2376b4ab89472e36
34
34
  remote: https://github.com/ruby/gem_rbs_collection.git
35
35
  repo_dir: gems
36
36
  - name: logger
@@ -38,7 +38,7 @@ gems:
38
38
  source:
39
39
  type: git
40
40
  name: ruby/gem_rbs_collection
41
- revision: 81fa8bd0617286078617a62b6a3229cebfd4af23
41
+ revision: 5689759efdc7875d533e8e5b2376b4ab89472e36
42
42
  remote: https://github.com/ruby/gem_rbs_collection.git
43
43
  repo_dir: gems
44
44
  - name: monitor
@@ -54,7 +54,7 @@ gems:
54
54
  source:
55
55
  type: git
56
56
  name: ruby/gem_rbs_collection
57
- revision: 81fa8bd0617286078617a62b6a3229cebfd4af23
57
+ revision: 5689759efdc7875d533e8e5b2376b4ab89472e36
58
58
  remote: https://github.com/ruby/gem_rbs_collection.git
59
59
  repo_dir: gems
60
60
  - name: parser
@@ -62,7 +62,7 @@ gems:
62
62
  source:
63
63
  type: git
64
64
  name: ruby/gem_rbs_collection
65
- revision: 81fa8bd0617286078617a62b6a3229cebfd4af23
65
+ revision: 5689759efdc7875d533e8e5b2376b4ab89472e36
66
66
  remote: https://github.com/ruby/gem_rbs_collection.git
67
67
  repo_dir: gems
68
68
  - name: prism
@@ -74,7 +74,7 @@ gems:
74
74
  source:
75
75
  type: git
76
76
  name: ruby/gem_rbs_collection
77
- revision: 81fa8bd0617286078617a62b6a3229cebfd4af23
77
+ revision: 5689759efdc7875d533e8e5b2376b4ab89472e36
78
78
  remote: https://github.com/ruby/gem_rbs_collection.git
79
79
  repo_dir: gems
80
80
  - name: rake
@@ -82,7 +82,7 @@ gems:
82
82
  source:
83
83
  type: git
84
84
  name: ruby/gem_rbs_collection
85
- revision: 81fa8bd0617286078617a62b6a3229cebfd4af23
85
+ revision: 5689759efdc7875d533e8e5b2376b4ab89472e36
86
86
  remote: https://github.com/ruby/gem_rbs_collection.git
87
87
  repo_dir: gems
88
88
  - name: rbs
@@ -102,7 +102,7 @@ gems:
102
102
  source:
103
103
  type: git
104
104
  name: ruby/gem_rbs_collection
105
- revision: 81fa8bd0617286078617a62b6a3229cebfd4af23
105
+ revision: 5689759efdc7875d533e8e5b2376b4ab89472e36
106
106
  remote: https://github.com/ruby/gem_rbs_collection.git
107
107
  repo_dir: gems
108
108
  - name: rubocop
@@ -110,7 +110,7 @@ gems:
110
110
  source:
111
111
  type: git
112
112
  name: ruby/gem_rbs_collection
113
- revision: 81fa8bd0617286078617a62b6a3229cebfd4af23
113
+ revision: 5689759efdc7875d533e8e5b2376b4ab89472e36
114
114
  remote: https://github.com/ruby/gem_rbs_collection.git
115
115
  repo_dir: gems
116
116
  - name: rubocop-ast
@@ -118,7 +118,7 @@ gems:
118
118
  source:
119
119
  type: git
120
120
  name: ruby/gem_rbs_collection
121
- revision: 81fa8bd0617286078617a62b6a3229cebfd4af23
121
+ revision: 5689759efdc7875d533e8e5b2376b4ab89472e36
122
122
  remote: https://github.com/ruby/gem_rbs_collection.git
123
123
  repo_dir: gems
124
124
  - name: strscan
@@ -8,6 +8,8 @@ module RuboCop
8
8
  #
9
9
  # Instance variables must either have a `# @rbs @ivar: Type` annotation
10
10
  # or be covered by a typed `attr_reader/writer/accessor` declaration.
11
+ # Class-level (singleton) instance variables, assigned inside `class << self`
12
+ # or `def self.x`, must be annotated with `# @rbs self.@ivar: Type` instead.
11
13
  #
12
14
  # Only instance variables that are **assigned** within the class/module are checked.
13
15
  # Read-only references are ignored because the variable may be defined in a parent class.
@@ -44,6 +46,15 @@ module RuboCop
44
46
  # @baz
45
47
  # end
46
48
  # end
49
+ #
50
+ # # good (class-level ivar annotated with `self.@`)
51
+ # class Foo
52
+ # # @rbs self.@instance: Foo
53
+ #
54
+ # def self.instance
55
+ # @instance ||= new
56
+ # end
57
+ # end
47
58
  class UntypedInstanceVariable < Base
48
59
  include ASTUtils
49
60
 
@@ -51,16 +62,20 @@ module RuboCop
51
62
 
52
63
  include RangeHelp
53
64
 
54
- MSG: ::String
65
+ MSG_IVAR: ::String
66
+
67
+ MSG_CIVAR: ::String
55
68
 
56
69
  ATTR_METHODS: untyped
57
70
 
58
- type scope = { typed_ivars: Set[Symbol], assigned_ivars: Hash[Symbol, RuboCop::AST::Node] }
71
+ type scope = { typed_ivars: Set[Symbol], typed_class_ivars: Set[Symbol], assigned_ivars: Hash[Symbol, RuboCop::AST::Node], assigned_class_ivars: Hash[Symbol, RuboCop::AST::Node], singleton_depth: Integer }
59
72
 
60
73
  attr_reader scope_stack: Array[scope]
61
74
 
62
75
  attr_reader ivar_type_annotations: Hash[Integer, Symbol]
63
76
 
77
+ attr_reader civar_type_annotations: Hash[Integer, Symbol]
78
+
64
79
  def on_new_investigation: () -> void
65
80
 
66
81
  def on_investigation_end: () -> void
@@ -75,6 +90,16 @@ module RuboCop
75
90
 
76
91
  alias after_module after_class
77
92
 
93
+ # @rbs _node: RuboCop::AST::Node
94
+ def on_sclass: (untyped _node) -> void
95
+
96
+ alias on_defs on_sclass
97
+
98
+ # @rbs _node: RuboCop::AST::Node
99
+ def after_sclass: (untyped _node) -> void
100
+
101
+ alias after_defs after_sclass
102
+
78
103
  # @rbs node: RuboCop::AST::Node
79
104
  def on_ivasgn: (RuboCop::AST::Node node) -> void
80
105
 
@@ -95,12 +120,22 @@ module RuboCop
95
120
 
96
121
  def current_scope: () -> scope
97
122
 
123
+ def singleton_context?: () -> bool
124
+
98
125
  # @rbs node: RuboCop::AST::Node
99
126
  def collect_typed_ivars_for_scope: (RuboCop::AST::Node node) -> void
100
127
 
101
- def collect_ivar_type_annotations: () -> Hash[Integer, Symbol]
128
+ def collect_ivar_type_annotations: () -> [ Hash[Integer, Symbol], Hash[Integer, Symbol] ]
129
+
130
+ # @rbs ann: RBS::Inline::AST::Annotations::IvarType
131
+ def annotation_line: (RBS::Inline::AST::Annotations::IvarType ann) -> Integer
102
132
 
103
133
  def report_offenses: () -> void
134
+
135
+ # @rbs assigned: Hash[Symbol, RuboCop::AST::Node]
136
+ # @rbs typed: Set[Symbol]
137
+ # @rbs message_template: String
138
+ def report_untyped: (Hash[Symbol, RuboCop::AST::Node] assigned, Set[Symbol] typed, String message_template) -> void
104
139
  end
105
140
  end
106
141
  end
metadata CHANGED
@@ -1,14 +1,14 @@
1
1
  --- !ruby/object:Gem::Specification
2
2
  name: rubocop-rbs_inline
3
3
  version: !ruby/object:Gem::Version
4
- version: 1.5.5
4
+ version: 1.6.0
5
5
  platform: ruby
6
6
  authors:
7
7
  - Takeshi KOMIYA
8
8
  autorequire:
9
9
  bindir: exe
10
10
  cert_chain: []
11
- date: 2026-05-19 00:00:00.000000000 Z
11
+ date: 2026-07-05 00:00:00.000000000 Z
12
12
  dependencies:
13
13
  - !ruby/object:Gem::Dependency
14
14
  name: lint_roller