class IRB::TypeCompletion::Types::SingletonType::InstanceType::UnionType

Constants

BOOLEAN

Attributes

types[R]

Public Class Methods

[](*types) click to toggle source
# File irb/type_completion/types.rb, line 269
def self.[](*types)
  type = new(*types)
  if type.types.empty?
    OBJECT
  elsif type.types.size == 1
    type.types.first
  else
    type
  end
end
_match_free_variable(vars, rbs_type, value, accumulator) click to toggle source
# File irb/type_completion/types.rb, line 385
def self._match_free_variable(vars, rbs_type, value, accumulator)
  case [rbs_type, value]
  in [RBS::Types::Variable,]
    (accumulator[rbs_type.name] ||= []) << value if vars.include? rbs_type.name
  in [RBS::Types::ClassInstance, InstanceType]
    names = rbs_builder.build_singleton(rbs_type.name).type_params
    names.zip(rbs_type.args).each do |name, arg|
      v = value.params[name]
      _match_free_variable vars, arg, v, accumulator if v
    end
  in [RBS::Types::Tuple, InstanceType] if value.klass == Array
    v = value.params[:Elem]
    rbs_type.types.each do |t|
      _match_free_variable vars, t, v, accumulator
    end
  in [RBS::Types::Record, InstanceType] if value.klass == Hash
    # TODO
  in [RBS::Types::Interface,]
    definition = rbs_builder.build_interface rbs_type.name
    convert = {}
    definition.type_params.zip(rbs_type.args).each do |from, arg|
      convert[from] = arg.name if arg.is_a? RBS::Types::Variable
    end
    return if convert.empty?
    ac = {}
    definition.methods.each do |method_name, method|
      return_type = method_return_type value, method_name
      method.defs.each do |method_def|
        interface_return_type = method_def.type.type.return_type
        _match_free_variable convert, interface_return_type, return_type, ac
      end
    end
    convert.each do |from, to|
      values = ac[from]
      (accumulator[to] ||= []).concat values if values
    end
  else
  end
end
array_of(*types) click to toggle source
# File irb/type_completion/types.rb, line 288
def self.array_of(*types)
  type = types.size >= 2 ? UnionType[*types] : types.first || OBJECT
  InstanceType.new Array, Elem: type
end
from_rbs_type(return_type, self_type, extra_vars = {}) click to toggle source
# File irb/type_completion/types.rb, line 293
def self.from_rbs_type(return_type, self_type, extra_vars = {})
  case return_type
  when RBS::Types::Bases::Self
    self_type
  when RBS::Types::Bases::Bottom, RBS::Types::Bases::Nil
    NIL
  when RBS::Types::Bases::Any, RBS::Types::Bases::Void
    OBJECT
  when RBS::Types::Bases::Class
    self_type.transform do |type|
      case type
      in SingletonType
        InstanceType.new(self_type.module_or_class.is_a?(Class) ? Class : Module)
      in InstanceType
        SingletonType.new type.klass
      end
    end
    UnionType[*types]
  when RBS::Types::Bases::Bool
    BOOLEAN
  when RBS::Types::Bases::Instance
    self_type.transform do |type|
      if type.is_a?(SingletonType) && type.module_or_class.is_a?(Class)
        InstanceType.new type.module_or_class
      else
        OBJECT
      end
    end
  when RBS::Types::Union
    UnionType[*return_type.types.map { from_rbs_type _1, self_type, extra_vars }]
  when RBS::Types::Proc
    PROC
  when RBS::Types::Tuple
    elem = UnionType[*return_type.types.map { from_rbs_type _1, self_type, extra_vars }]
    InstanceType.new Array, Elem: elem
  when RBS::Types::Record
    InstanceType.new Hash, K: SYMBOL, V: OBJECT
  when RBS::Types::Literal
    InstanceType.new return_type.literal.class
  when RBS::Types::Variable
    if extra_vars.key? return_type.name
      extra_vars[return_type.name]
    elsif self_type.is_a? InstanceType
      self_type.params[return_type.name] || OBJECT
    elsif self_type.is_a? UnionType
      types = self_type.types.filter_map do |t|
        t.params[return_type.name] if t.is_a? InstanceType
      end
      UnionType[*types]
    else
      OBJECT
    end
  when RBS::Types::Optional
    UnionType[from_rbs_type(return_type.type, self_type, extra_vars), NIL]
  when RBS::Types::Alias
    case return_type.name.name
    when :int
      INTEGER
    when :boolish
      BOOLEAN
    when :string
      STRING
    else
      # TODO: ???
      OBJECT
    end
  when RBS::Types::Interface
    # unimplemented
    OBJECT
  when RBS::Types::ClassInstance
    klass = return_type.name.to_namespace.path.reduce(Object) { _1.const_get _2 }
    if return_type.args
      args = return_type.args.map { from_rbs_type _1, self_type, extra_vars }
      names = rbs_builder.build_singleton(return_type.name).type_params
      params = names.map.with_index { [_1, args[_2] || OBJECT] }.to_h
    end
    InstanceType.new klass, params || {}
  end
end
match_free_variables(vars, types, values) click to toggle source
# File irb/type_completion/types.rb, line 377
def self.match_free_variables(vars, types, values)
  accumulator = {}
  types.zip values do |t, v|
    _match_free_variable(vars, t, v, accumulator) if v
  end
  accumulator.transform_values { UnionType[*_1] }
end
method_return_bottom?(method) click to toggle source
# File irb/type_completion/types.rb, line 373
def self.method_return_bottom?(method)
  method.type.return_type.is_a? RBS::Types::Bases::Bottom
end
new(*types) click to toggle source
# File irb/type_completion/types.rb, line 234
def initialize(*types)
  @types = []
  singletons = []
  instances = {}
  collect = -> type do
    case type
    in UnionType
      type.types.each(&collect)
    in InstanceType
      params = (instances[type.klass] ||= {})
      type.params.each do |k, v|
        (params[k] ||= []) << v
      end
    in SingletonType
      singletons << type
    end
  end
  types.each(&collect)
  @types = singletons.uniq + instances.map do |klass, params|
    InstanceType.new(klass, params.transform_values { |v| UnionType[*v] })
  end
end

Public Instance Methods

all_methods() click to toggle source
# File irb/type_completion/types.rb, line 281
      def all_methods() = @types.flat_map(&:all_methods).uniq
      def constants() = @types.flat_map(&:constants).uniq
      def inspect() = @types.map(&:inspect).join(' | ')
    end

    BOOLEAN = UnionType[TRUE, FALSE]

    def self.array_of(*types)
      type = types.size >= 2 ? UnionType[*types] : types.first || OBJECT
      InstanceType.new Array, Elem: type
    end

    def self.from_rbs_type(return_type, self_type, extra_vars = {})
      case return_type
      when RBS::Types::Bases::Self
        self_type
      when RBS::Types::Bases::Bottom, RBS::Types::Bases::Nil
        NIL
      when RBS::Types::Bases::Any, RBS::Types::Bases::Void
        OBJECT
      when RBS::Types::Bases::Class
        self_type.transform do |type|
          case type
          in SingletonType
            InstanceType.new(self_type.module_or_class.is_a?(Class) ? Class : Module)
          in InstanceType
            SingletonType.new type.klass
          end
        end
        UnionType[*types]
      when RBS::Types::Bases::Bool
        BOOLEAN
      when RBS::Types::Bases::Instance
        self_type.transform do |type|
          if type.is_a?(SingletonType) && type.module_or_class.is_a?(Class)
            InstanceType.new type.module_or_class
          else
            OBJECT
          end
        end
      when RBS::Types::Union
        UnionType[*return_type.types.map { from_rbs_type _1, self_type, extra_vars }]
      when RBS::Types::Proc
        PROC
      when RBS::Types::Tuple
        elem = UnionType[*return_type.types.map { from_rbs_type _1, self_type, extra_vars }]
        InstanceType.new Array, Elem: elem
      when RBS::Types::Record
        InstanceType.new Hash, K: SYMBOL, V: OBJECT
      when RBS::Types::Literal
        InstanceType.new return_type.literal.class
      when RBS::Types::Variable
        if extra_vars.key? return_type.name
          extra_vars[return_type.name]
        elsif self_type.is_a? InstanceType
          self_type.params[return_type.name] || OBJECT
        elsif self_type.is_a? UnionType
          types = self_type.types.filter_map do |t|
            t.params[return_type.name] if t.is_a? InstanceType
          end
          UnionType[*types]
        else
          OBJECT
        end
      when RBS::Types::Optional
        UnionType[from_rbs_type(return_type.type, self_type, extra_vars), NIL]
      when RBS::Types::Alias
        case return_type.name.name
        when :int
          INTEGER
        when :boolish
          BOOLEAN
        when :string
          STRING
        else
          # TODO: ???
          OBJECT
        end
      when RBS::Types::Interface
        # unimplemented
        OBJECT
      when RBS::Types::ClassInstance
        klass = return_type.name.to_namespace.path.reduce(Object) { _1.const_get _2 }
        if return_type.args
          args = return_type.args.map { from_rbs_type _1, self_type, extra_vars }
          names = rbs_builder.build_singleton(return_type.name).type_params
          params = names.map.with_index { [_1, args[_2] || OBJECT] }.to_h
        end
        InstanceType.new klass, params || {}
      end
    end

    def self.method_return_bottom?(method)
      method.type.return_type.is_a? RBS::Types::Bases::Bottom
    end

    def self.match_free_variables(vars, types, values)
      accumulator = {}
      types.zip values do |t, v|
        _match_free_variable(vars, t, v, accumulator) if v
      end
      accumulator.transform_values { UnionType[*_1] }
    end

    def self._match_free_variable(vars, rbs_type, value, accumulator)
      case [rbs_type, value]
      in [RBS::Types::Variable,]
        (accumulator[rbs_type.name] ||= []) << value if vars.include? rbs_type.name
      in [RBS::Types::ClassInstance, InstanceType]
        names = rbs_builder.build_singleton(rbs_type.name).type_params
        names.zip(rbs_type.args).each do |name, arg|
          v = value.params[name]
          _match_free_variable vars, arg, v, accumulator if v
        end
      in [RBS::Types::Tuple, InstanceType] if value.klass == Array
        v = value.params[:Elem]
        rbs_type.types.each do |t|
          _match_free_variable vars, t, v, accumulator
        end
      in [RBS::Types::Record, InstanceType] if value.klass == Hash
        # TODO
      in [RBS::Types::Interface,]
        definition = rbs_builder.build_interface rbs_type.name
        convert = {}
        definition.type_params.zip(rbs_type.args).each do |from, arg|
          convert[from] = arg.name if arg.is_a? RBS::Types::Variable
        end
        return if convert.empty?
        ac = {}
        definition.methods.each do |method_name, method|
          return_type = method_return_type value, method_name
          method.defs.each do |method_def|
            interface_return_type = method_def.type.type.return_type
            _match_free_variable convert, interface_return_type, return_type, ac
          end
        end
        convert.each do |from, to|
          values = ac[from]
          (accumulator[to] ||= []).concat values if values
        end
      else
      end
    end
  end
end
constants() click to toggle source
# File irb/type_completion/types.rb, line 282
    def constants() = @types.flat_map(&:constants).uniq
    def inspect() = @types.map(&:inspect).join(' | ')
  end

  BOOLEAN = UnionType[TRUE, FALSE]

  def self.array_of(*types)
    type = types.size >= 2 ? UnionType[*types] : types.first || OBJECT
    InstanceType.new Array, Elem: type
  end

  def self.from_rbs_type(return_type, self_type, extra_vars = {})
    case return_type
    when RBS::Types::Bases::Self
      self_type
    when RBS::Types::Bases::Bottom, RBS::Types::Bases::Nil
      NIL
    when RBS::Types::Bases::Any, RBS::Types::Bases::Void
      OBJECT
    when RBS::Types::Bases::Class
      self_type.transform do |type|
        case type
        in SingletonType
          InstanceType.new(self_type.module_or_class.is_a?(Class) ? Class : Module)
        in InstanceType
          SingletonType.new type.klass
        end
      end
      UnionType[*types]
    when RBS::Types::Bases::Bool
      BOOLEAN
    when RBS::Types::Bases::Instance
      self_type.transform do |type|
        if type.is_a?(SingletonType) && type.module_or_class.is_a?(Class)
          InstanceType.new type.module_or_class
        else
          OBJECT
        end
      end
    when RBS::Types::Union
      UnionType[*return_type.types.map { from_rbs_type _1, self_type, extra_vars }]
    when RBS::Types::Proc
      PROC
    when RBS::Types::Tuple
      elem = UnionType[*return_type.types.map { from_rbs_type _1, self_type, extra_vars }]
      InstanceType.new Array, Elem: elem
    when RBS::Types::Record
      InstanceType.new Hash, K: SYMBOL, V: OBJECT
    when RBS::Types::Literal
      InstanceType.new return_type.literal.class
    when RBS::Types::Variable
      if extra_vars.key? return_type.name
        extra_vars[return_type.name]
      elsif self_type.is_a? InstanceType
        self_type.params[return_type.name] || OBJECT
      elsif self_type.is_a? UnionType
        types = self_type.types.filter_map do |t|
          t.params[return_type.name] if t.is_a? InstanceType
        end
        UnionType[*types]
      else
        OBJECT
      end
    when RBS::Types::Optional
      UnionType[from_rbs_type(return_type.type, self_type, extra_vars), NIL]
    when RBS::Types::Alias
      case return_type.name.name
      when :int
        INTEGER
      when :boolish
        BOOLEAN
      when :string
        STRING
      else
        # TODO: ???
        OBJECT
      end
    when RBS::Types::Interface
      # unimplemented
      OBJECT
    when RBS::Types::ClassInstance
      klass = return_type.name.to_namespace.path.reduce(Object) { _1.const_get _2 }
      if return_type.args
        args = return_type.args.map { from_rbs_type _1, self_type, extra_vars }
        names = rbs_builder.build_singleton(return_type.name).type_params
        params = names.map.with_index { [_1, args[_2] || OBJECT] }.to_h
      end
      InstanceType.new klass, params || {}
    end
  end

  def self.method_return_bottom?(method)
    method.type.return_type.is_a? RBS::Types::Bases::Bottom
  end

  def self.match_free_variables(vars, types, values)
    accumulator = {}
    types.zip values do |t, v|
      _match_free_variable(vars, t, v, accumulator) if v
    end
    accumulator.transform_values { UnionType[*_1] }
  end

  def self._match_free_variable(vars, rbs_type, value, accumulator)
    case [rbs_type, value]
    in [RBS::Types::Variable,]
      (accumulator[rbs_type.name] ||= []) << value if vars.include? rbs_type.name
    in [RBS::Types::ClassInstance, InstanceType]
      names = rbs_builder.build_singleton(rbs_type.name).type_params
      names.zip(rbs_type.args).each do |name, arg|
        v = value.params[name]
        _match_free_variable vars, arg, v, accumulator if v
      end
    in [RBS::Types::Tuple, InstanceType] if value.klass == Array
      v = value.params[:Elem]
      rbs_type.types.each do |t|
        _match_free_variable vars, t, v, accumulator
      end
    in [RBS::Types::Record, InstanceType] if value.klass == Hash
      # TODO
    in [RBS::Types::Interface,]
      definition = rbs_builder.build_interface rbs_type.name
      convert = {}
      definition.type_params.zip(rbs_type.args).each do |from, arg|
        convert[from] = arg.name if arg.is_a? RBS::Types::Variable
      end
      return if convert.empty?
      ac = {}
      definition.methods.each do |method_name, method|
        return_type = method_return_type value, method_name
        method.defs.each do |method_def|
          interface_return_type = method_def.type.type.return_type
          _match_free_variable convert, interface_return_type, return_type, ac
        end
      end
      convert.each do |from, to|
        values = ac[from]
        (accumulator[to] ||= []).concat values if values
      end
    else
    end
  end
end
inspect() click to toggle source
# File irb/type_completion/types.rb, line 283
  def inspect() = @types.map(&:inspect).join(' | ')
end
methods() click to toggle source
# File irb/type_completion/types.rb, line 280
        def methods() = @types.flat_map(&:methods).uniq
        def all_methods() = @types.flat_map(&:all_methods).uniq
        def constants() = @types.flat_map(&:constants).uniq
        def inspect() = @types.map(&:inspect).join(' | ')
      end

      BOOLEAN = UnionType[TRUE, FALSE]

      def self.array_of(*types)
        type = types.size >= 2 ? UnionType[*types] : types.first || OBJECT
        InstanceType.new Array, Elem: type
      end

      def self.from_rbs_type(return_type, self_type, extra_vars = {})
        case return_type
        when RBS::Types::Bases::Self
          self_type
        when RBS::Types::Bases::Bottom, RBS::Types::Bases::Nil
          NIL
        when RBS::Types::Bases::Any, RBS::Types::Bases::Void
          OBJECT
        when RBS::Types::Bases::Class
          self_type.transform do |type|
            case type
            in SingletonType
              InstanceType.new(self_type.module_or_class.is_a?(Class) ? Class : Module)
            in InstanceType
              SingletonType.new type.klass
            end
          end
          UnionType[*types]
        when RBS::Types::Bases::Bool
          BOOLEAN
        when RBS::Types::Bases::Instance
          self_type.transform do |type|
            if type.is_a?(SingletonType) && type.module_or_class.is_a?(Class)
              InstanceType.new type.module_or_class
            else
              OBJECT
            end
          end
        when RBS::Types::Union
          UnionType[*return_type.types.map { from_rbs_type _1, self_type, extra_vars }]
        when RBS::Types::Proc
          PROC
        when RBS::Types::Tuple
          elem = UnionType[*return_type.types.map { from_rbs_type _1, self_type, extra_vars }]
          InstanceType.new Array, Elem: elem
        when RBS::Types::Record
          InstanceType.new Hash, K: SYMBOL, V: OBJECT
        when RBS::Types::Literal
          InstanceType.new return_type.literal.class
        when RBS::Types::Variable
          if extra_vars.key? return_type.name
            extra_vars[return_type.name]
          elsif self_type.is_a? InstanceType
            self_type.params[return_type.name] || OBJECT
          elsif self_type.is_a? UnionType
            types = self_type.types.filter_map do |t|
              t.params[return_type.name] if t.is_a? InstanceType
            end
            UnionType[*types]
          else
            OBJECT
          end
        when RBS::Types::Optional
          UnionType[from_rbs_type(return_type.type, self_type, extra_vars), NIL]
        when RBS::Types::Alias
          case return_type.name.name
          when :int
            INTEGER
          when :boolish
            BOOLEAN
          when :string
            STRING
          else
            # TODO: ???
            OBJECT
          end
        when RBS::Types::Interface
          # unimplemented
          OBJECT
        when RBS::Types::ClassInstance
          klass = return_type.name.to_namespace.path.reduce(Object) { _1.const_get _2 }
          if return_type.args
            args = return_type.args.map { from_rbs_type _1, self_type, extra_vars }
            names = rbs_builder.build_singleton(return_type.name).type_params
            params = names.map.with_index { [_1, args[_2] || OBJECT] }.to_h
          end
          InstanceType.new klass, params || {}
        end
      end

      def self.method_return_bottom?(method)
        method.type.return_type.is_a? RBS::Types::Bases::Bottom
      end

      def self.match_free_variables(vars, types, values)
        accumulator = {}
        types.zip values do |t, v|
          _match_free_variable(vars, t, v, accumulator) if v
        end
        accumulator.transform_values { UnionType[*_1] }
      end

      def self._match_free_variable(vars, rbs_type, value, accumulator)
        case [rbs_type, value]
        in [RBS::Types::Variable,]
          (accumulator[rbs_type.name] ||= []) << value if vars.include? rbs_type.name
        in [RBS::Types::ClassInstance, InstanceType]
          names = rbs_builder.build_singleton(rbs_type.name).type_params
          names.zip(rbs_type.args).each do |name, arg|
            v = value.params[name]
            _match_free_variable vars, arg, v, accumulator if v
          end
        in [RBS::Types::Tuple, InstanceType] if value.klass == Array
          v = value.params[:Elem]
          rbs_type.types.each do |t|
            _match_free_variable vars, t, v, accumulator
          end
        in [RBS::Types::Record, InstanceType] if value.klass == Hash
          # TODO
        in [RBS::Types::Interface,]
          definition = rbs_builder.build_interface rbs_type.name
          convert = {}
          definition.type_params.zip(rbs_type.args).each do |from, arg|
            convert[from] = arg.name if arg.is_a? RBS::Types::Variable
          end
          return if convert.empty?
          ac = {}
          definition.methods.each do |method_name, method|
            return_type = method_return_type value, method_name
            method.defs.each do |method_def|
              interface_return_type = method_def.type.type.return_type
              _match_free_variable convert, interface_return_type, return_type, ac
            end
          end
          convert.each do |from, to|
            values = ac[from]
            (accumulator[to] ||= []).concat values if values
          end
        else
        end
      end
    end
  end
end
nillable?() click to toggle source
# File irb/type_completion/types.rb, line 261
def nillable?
  types.any?(&:nillable?)
end
nonnillable() click to toggle source
# File irb/type_completion/types.rb, line 265
def nonnillable
  UnionType[*types.reject { _1.is_a?(InstanceType) && _1.klass == NilClass }]
end
transform(&block) click to toggle source
# File irb/type_completion/types.rb, line 257
def transform(&block)
  UnionType[*types.map(&block)]
end