Class: RBI::Type Abstract
- Inherits:
-
Object
- Object
- RBI::Type
- Defined in:
- lib/rbi/type.rb,
lib/rbi/rbs_printer.rb,
lib/rbi/type_parser.rb,
lib/rbi/type_visitor.rb
Overview
The base class for all RBI types.
Defined Under Namespace
Classes: All, Any, Anything, AttachedClass, Boolean, Class, ClassOf, Composite, Error, Generic, Module, Nilable, NoReturn, Proc, SelfType, Shape, Simple, Tuple, TypeAlias, TypeParameter, Untyped, Visitor, Void
Class Method Summary collapse
-
.all(type1, type2, *types) ⇒ Object
Builds a type that represents an intersection of multiple types like
T.all(String, Integer). -
.any(type1, type2, *types) ⇒ Object
Builds a type that represents a union of multiple types like
T.any(String, Integer). -
.anything ⇒ Object
Builds a type that represents
T.anything. -
.attached_class ⇒ Object
Builds a type that represents
T.attached_class. -
.boolean ⇒ Object
Builds a type that represents
T::Boolean. -
.class_of(type, type_parameter = nil) ⇒ Object
Builds a type that represents the singleton class of another type like
T.class_of(Foo). -
.generic(name, *params) ⇒ Object
Builds a type that represents a generic type like
T::Array[String]orT::Hash[Symbol, Integer]. -
.nilable(type) ⇒ Object
Builds a type that represents a nilable of another type like
T.nilable(String). -
.noreturn ⇒ Object
Builds a type that represents
T.noreturn. -
.parse_node(node) ⇒ Object
: (Prism::Node node) -> Type.
-
.parse_string(string) ⇒ Object
: (String string) -> Type.
-
.proc ⇒ Object
Builds a type that represents a proc type like
T.proc.void. -
.self_type ⇒ Object
Builds a type that represents
T.self_type. -
.shape(types = {}) ⇒ Object
Builds a type that represents a shape type like
{name: String, age: Integer}. -
.simple(name) ⇒ Object
Builds a simple type like
Stringor::Foo::Bar. -
.t_class(type) ⇒ Object
Builds a type that represents the class of another type like
T::Class[Foo]. -
.t_module(type) ⇒ Object
Builds a type that represents the module of another type like
T::Module[Foo]. -
.tuple(*types) ⇒ Object
Builds a type that represents a tuple type like
[String, Integer]. -
.type_alias(name, aliased_type) ⇒ Object
Builds a type that represents a type alias like
MyTypeAlias. -
.type_parameter(name) ⇒ Object
Builds a type that represents a type parameter like
T.type_parameter(:U). -
.untyped ⇒ Object
Builds a type that represents
T.untyped. -
.void ⇒ Object
Builds a type that represents
void.
Instance Method Summary collapse
-
#==(other) ⇒ Object
abstract
: (BasicObject) -> bool.
-
#eql?(other) ⇒ Boolean
: (BasicObject other) -> bool.
-
#hash ⇒ Object
: -> Integer.
-
#initialize ⇒ Type
constructor
: -> void.
-
#nilable ⇒ Object
Returns a new type that is
nilableif it is not already. -
#nilable? ⇒ Boolean
Returns whether the type is nilable.
-
#non_nilable ⇒ Object
Returns the non-nilable version of the type.
-
#normalize ⇒ Object
abstract
Returns a normalized version of the type.
-
#rbs_string ⇒ Object
: -> String.
-
#simplify ⇒ Object
abstract
Returns a simplified version of the type.
-
#to_rbi ⇒ Object
abstract
: -> String.
-
#to_s ⇒ Object
: -> String.
Constructor Details
#initialize ⇒ Type
: -> void
993 994 995 |
# File 'lib/rbi/type.rb', line 993 def initialize @nilable = false #: bool end |
Class Method Details
.all(type1, type2, *types) ⇒ Object
Builds a type that represents an intersection of multiple types like T.all(String, Integer).
Note that this method transforms types such as T.all(String, String) into String, so
it may return something other than a All.
: (Type type1, Type type2, *Type types) -> Type
929 930 931 |
# File 'lib/rbi/type.rb', line 929 def all(type1, type2, *types) All.new([type1, type2, *types]).simplify end |
.any(type1, type2, *types) ⇒ Object
Builds a type that represents a union of multiple types like T.any(String, Integer).
Note that this method transforms types such as T.any(String, NilClass) into T.nilable(String), so
it may return something other than a Any.
: (Type type1, Type type2, *Type types) -> Type
938 939 940 |
# File 'lib/rbi/type.rb', line 938 def any(type1, type2, *types) Any.new([type1, type2, *types]).simplify end |
.anything ⇒ Object
Builds a type that represents T.anything.
: -> Anything
854 855 856 |
# File 'lib/rbi/type.rb', line 854 def anything Anything.new end |
.attached_class ⇒ Object
Builds a type that represents T.attached_class.
: -> AttachedClass
860 861 862 |
# File 'lib/rbi/type.rb', line 860 def attached_class AttachedClass.new end |
.boolean ⇒ Object
Builds a type that represents T::Boolean.
: -> Boolean
866 867 868 |
# File 'lib/rbi/type.rb', line 866 def boolean Boolean.new end |
.class_of(type, type_parameter = nil) ⇒ Object
Builds a type that represents the singleton class of another type like T.class_of(Foo).
: (Simple type, ?Type? type_parameter) -> ClassOf
910 911 912 |
# File 'lib/rbi/type.rb', line 910 def class_of(type, type_parameter = nil) ClassOf.new(type, type_parameter) end |
.generic(name, *params) ⇒ Object
Builds a type that represents a generic type like T::Array[String] or T::Hash[Symbol, Integer].
: (String name, *(Type | Array) params) -> Generic
946 947 948 |
# File 'lib/rbi/type.rb', line 946 def generic(name, *params) Generic.new(name, *params.flatten) end |
.nilable(type) ⇒ Object
Builds a type that represents a nilable of another type like T.nilable(String).
Note that this method transforms types such as T.nilable(T.untyped) into T.untyped, so
it may return something other than a RBI::Type::Nilable.
: (Type type) -> Type
919 920 921 922 |
# File 'lib/rbi/type.rb', line 919 def nilable(type) nilable = Nilable.new(type) nilable.simplify end |
.noreturn ⇒ Object
Builds a type that represents T.noreturn.
: -> NoReturn
872 873 874 |
# File 'lib/rbi/type.rb', line 872 def noreturn NoReturn.new end |
.parse_node(node) ⇒ Object
: (Prism::Node node) -> Type
26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 |
# File 'lib/rbi/type_parser.rb', line 26 def parse_node(node) case node when Prism::ConstantReadNode, Prism::ConstantPathNode parse_constant(node) when Prism::ConstantWriteNode, Prism::ConstantPathWriteNode parse_constant_assignment(node) when Prism::CallNode parse_call(node) when Prism::ArrayNode parse_tuple(node) when Prism::HashNode, Prism::KeywordHashNode parse_shape(node) when Prism::ParenthesesNode body = node.body raise Error, "Expected exactly 1 child, got 0" unless body.is_a?(Prism::StatementsNode) children = body.body raise Error, "Expected exactly 1 child, got #{children.size}" unless children.size == 1 parse_node( children.first, #: as !nil ) else raise Error, "Unexpected node `#{node}`" end end |
.parse_string(string) ⇒ Object
: (String string) -> Type
10 11 12 13 14 15 16 17 18 19 20 21 22 23 |
# File 'lib/rbi/type_parser.rb', line 10 def parse_string(string) result = Prism.parse(string) unless result.success? raise Error, result.errors.map { |e| "#{e.}." }.join(" ") end node = result.value raise Error, "Expected a type expression, got `#{node.class}`" unless node.is_a?(Prism::ProgramNode) raise Error, "Expected a type expression, got nothing" if node.statements.body.empty? raise Error, "Expected a single type expression, got `#{node.slice}`" if node.statements.body.size > 1 node = node.statements.body.first #: as !nil parse_node(node) end |
.proc ⇒ Object
Builds a type that represents a proc type like T.proc.void.
: -> Proc
980 981 982 |
# File 'lib/rbi/type.rb', line 980 def proc Proc.new end |
.self_type ⇒ Object
Builds a type that represents T.self_type.
: -> SelfType
878 879 880 |
# File 'lib/rbi/type.rb', line 878 def self_type SelfType.new end |
.shape(types = {}) ⇒ Object
Builds a type that represents a shape type like {name: String, age: Integer}.
: (?Hash[(String | Symbol), Type] types) -> Shape
972 973 974 |
# File 'lib/rbi/type.rb', line 972 def shape(types = {}) Shape.new(types) end |
.simple(name) ⇒ Object
Builds a simple type like String or ::Foo::Bar.
It raises a NameError if the name is not a valid Ruby class identifier.
: (String name) -> Simple
843 844 845 846 847 848 |
# File 'lib/rbi/type.rb', line 843 def simple(name) # TODO: should we allow creating the instance anyway and move this to a `validate!` method? raise NameError, "Invalid type name: `#{name}`" unless valid_identifier?(name) Simple.new(name) end |
.t_class(type) ⇒ Object
Builds a type that represents the class of another type like T::Class[Foo].
: (Type type) -> Class
898 899 900 |
# File 'lib/rbi/type.rb', line 898 def t_class(type) Class.new(type) end |
.t_module(type) ⇒ Object
Builds a type that represents the module of another type like T::Module[Foo].
: (Type type) -> Module
904 905 906 |
# File 'lib/rbi/type.rb', line 904 def t_module(type) Module.new(type) end |
.tuple(*types) ⇒ Object
Builds a type that represents a tuple type like [String, Integer].
: (*(Type | Array) types) -> Tuple
966 967 968 |
# File 'lib/rbi/type.rb', line 966 def tuple(*types) Tuple.new(types.flatten) end |
.type_alias(name, aliased_type) ⇒ Object
Builds a type that represents a type alias like MyTypeAlias.
: (String name, Type aliased_type) -> TypeAlias
958 959 960 |
# File 'lib/rbi/type.rb', line 958 def type_alias(name, aliased_type) TypeAlias.new(name, aliased_type) end |
.type_parameter(name) ⇒ Object
Builds a type that represents a type parameter like T.type_parameter(:U).
: (Symbol name) -> TypeParameter
952 953 954 |
# File 'lib/rbi/type.rb', line 952 def type_parameter(name) TypeParameter.new(name) end |
Instance Method Details
#==(other) ⇒ Object
: (BasicObject) -> bool
1064 |
# File 'lib/rbi/type.rb', line 1064 def ==(other) = raise NotImplementedError, "Abstract method called" |
#eql?(other) ⇒ Boolean
: (BasicObject other) -> bool
1067 1068 1069 |
# File 'lib/rbi/type.rb', line 1067 def eql?(other) self == other end |
#hash ⇒ Object
: -> Integer
1073 1074 1075 |
# File 'lib/rbi/type.rb', line 1073 def hash to_rbi.hash end |
#nilable ⇒ Object
1007 1008 1009 |
# File 'lib/rbi/type.rb', line 1007 def nilable Type.nilable(self) end |
#nilable? ⇒ Boolean
Returns whether the type is nilable. : -> bool
1034 1035 1036 |
# File 'lib/rbi/type.rb', line 1034 def nilable? is_a?(Nilable) end |
#non_nilable ⇒ Object
Returns the non-nilable version of the type. If the type is already non-nilable, it returns itself. If the type is nilable, it returns the inner type.
type = RBI::Type.nilable(RBI::Type.simple("String"))
type.to_rbi # => "::T.nilable(String)"
type.non_nilable.to_rbi # => "String"
type.non_nilable.non_nilable.to_rbi # => "String"
: -> Type
1022 1023 1024 1025 1026 1027 1028 1029 1030 |
# File 'lib/rbi/type.rb', line 1022 def non_nilable # TODO: Should this logic be moved into a builder method? case self when Nilable type else self end end |
#normalize ⇒ Object
Returns a normalized version of the type.
Normalized types are meant to be easier to process, not to read.
For example, T.any(TrueClass, FalseClass) instead of T::Boolean or
T.any(String, NilClass) instead of T.nilable(String).
This is the inverse of #simplify.
: -> Type
1048 |
# File 'lib/rbi/type.rb', line 1048 def normalize = raise NotImplementedError, "Abstract method called" |
#rbs_string ⇒ Object
: -> String
1275 1276 1277 1278 1279 |
# File 'lib/rbi/rbs_printer.rb', line 1275 def rbs_string p = TypePrinter.new p.visit(self) p.string end |
#simplify ⇒ Object
Returns a simplified version of the type.
Simplified types are meant to be easier to read, not to process.
For example, T::Boolean instead of T.any(TrueClass, FalseClass) or
T.nilable(String) instead of T.any(String, NilClass).
This is the inverse of #normalize.
: -> Type
1060 |
# File 'lib/rbi/type.rb', line 1060 def simplify = raise NotImplementedError, "Abstract method called" |
#to_rbi ⇒ Object
: -> String
1079 |
# File 'lib/rbi/type.rb', line 1079 def to_rbi = raise NotImplementedError, "Abstract method called" |
#to_s ⇒ Object
: -> String
1083 1084 1085 |
# File 'lib/rbi/type.rb', line 1083 def to_s to_rbi end |