Module: Tapioca::Runtime::Trackers::RequiredAncestor

Extended by:
T::Sig, Tracker
Defined in:
lib/tapioca/runtime/trackers/required_ancestor.rb

Class Method Summary collapse

Methods included from Tracker

disable!, enabled?, extended, with_disabled_tracker

Class Method Details

.register(requiring, block) ⇒ Object



15
16
17
18
19
20
# File 'lib/tapioca/runtime/trackers/required_ancestor.rb', line 15

def register(requiring, block)
  return unless enabled?

  ancestors = @required_ancestors_map[requiring] ||= []
  ancestors << block
end

.required_ancestors_blocks_by(mod) ⇒ Object



23
24
25
# File 'lib/tapioca/runtime/trackers/required_ancestor.rb', line 23

def required_ancestors_blocks_by(mod)
  @required_ancestors_map[mod] || []
end

.required_ancestors_by(mod) ⇒ Object



28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
# File 'lib/tapioca/runtime/trackers/required_ancestor.rb', line 28

def required_ancestors_by(mod)
  blocks = required_ancestors_blocks_by(mod)
  blocks.map do |block|
    # Common return values of `block.call` here could be a Module or a Sorbet's runtime value for T.class.
    # But in reality it could be whatever the block has that can pass Sorbet's static check. Like
    #
    # ```
    # requires_ancestor { T.class_of(Foo); nil }
    # ```
    #
    # So it's not designed to be used at runtime and it's accidental that just calling `to_s` on the above
    # common values can get us the correct value to generate type signatures. (See SorbetRequiredAncestors)
    # Therefore, the return value `block.call` should be considered unreliable and treated with caution.
    T.unsafe(block.call)
  rescue NameError
    # The ancestor required doesn't exist, let's return nil and let the compiler decide what to do.
    nil
  end
end