sorbet
sorbet copied to clipboard
T.cast is not "useless" when used to narrow an untyped type
Input
# typed: strict
extend T::Sig
class A; end
class B < A; end
my_b = T.let(B.new, B)
original = T.let({}, T::Hash[Symbol, String])
a = T.cast(original, T::Hash[Symbol, T.untyped])
a = T.let(original, T::Hash[Symbol, T.untyped])
a = T.cast('string', T.untyped)
a = T.let('string', T.untyped)
Observed output
editor.rb:10: T.cast is useless because T::Hash[Symbol, String] is already a subtype of T::Hash[Symbol, T.untyped] https://srb.help/7015
10 |a = T.cast(original, T::Hash[Symbol, T.untyped])
^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
Got T::Hash[Symbol, String] originating from:
editor.rb:9:
9 |original = T.let({}, T::Hash[Symbol, String])
^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
Autocorrect: Use -a to autocorrect
editor.rb:10: Replace with original
10 |a = T.cast(original, T::Hash[Symbol, T.untyped])
^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
editor.rb:12: Please use T.unsafe to cast to T.untyped https://srb.help/7015
12 |a = T.cast('string', T.untyped)
^^^^^^^^^^^^^^^^^^^^^^^^^^^
Autocorrect: Use -a to autocorrect
editor.rb:12: Replace with T.unsafe('string')
12 |a = T.cast('string', T.untyped)
^^^^^^^^^^^^^^^^^^^^^^^^^^^
Errors: 2
Expected behavior
In this case, the type specified in the T.cast
is better than the untyped Hash.
Sorbet should suggest changing the T.cast
to T.let
instead of removing the T.cast
entirely.
Another example
Input
# typed: true
class Foo
extend T::Sig
sig {
params(
proc: T.nilable(T.proc.params(foo: String, bar: String).void)
).void
}
def initialize(proc: nil)
if proc.nil?
proc = T.let(->(foo,bar) {}, T.proc.params(foo: String, bar: String).void)
end
@proc = proc
end
end
Observed output
No errors! Great job.