class Steep::TypeInference::SendArgs
def block_pass_arg
def block_pass_arg node = arguments.find {|node| node.type == :block_pass } block = method_type.block BlockPassArg.new(node: node, block: block) end
def each
def each if block_given? errors = [] positional_count = 0 positional_arg.tap do |args| while (value, args = args.next()) yield value case value when PositionalArgs::SplatArg type = value.type case type when nil raise when AST::Types::Tuple ts, args = args.consume(type.types.size, node: value.node) case ts when Array ty = AST::Types::Tuple.new(types: ts.map(&:type)) yield PositionalArgs::NodeTypePair.new(node: value.node, type: ty) when PositionalArgs::UnexpectedArg errors << ts yield ts end else if t = args.uniform_type args.following_args.each do |node| yield PositionalArgs::NodeTypePair.new(node: node, type: t) end else args.following_args.each do |node| arg = PositionalArgs::UnexpectedArg.new(node: node) yield arg errors << arg end end break end when PositionalArgs::UnexpectedArg, PositionalArgs::MissingArg errors << value end end end keyword_args.tap do |args| while (a, args = args.next) case a when KeywordArgs::MissingKeyword errors << a when KeywordArgs::UnexpectedKeyword errors << a end yield a case a when KeywordArgs::SplatArg case type = a.type when nil raise when AST::Types::Record keys = type.elements.keys ts, args = args.consume_keys(keys, node: a.node) case ts when KeywordArgs::UnexpectedKeyword yield ts errors << ts when Array record = AST::Types::Record.new(elements: Hash[keys.zip(ts)]) yield KeywordArgs::ArgTypePairs.new(pairs: [[a.node, record]]) end else args = args.update(index: args.index + 1) if args.rest_type type = AST::Builtin::Hash.instance_type(AST::Builtin::Symbol.instance_type, args.possible_value_type) yield KeywordArgs::ArgTypePairs.new(pairs: [[a.node, type]]) else yield KeywordArgs::UnexpectedKeyword.new(keyword: nil, node: a.node) end end end end end pass = block_pass_arg # if pass.node # yield pass # end diagnostics = [] missing_keywords = [] errors.each do |error| case error when KeywordArgs::UnexpectedKeyword diagnostics << Diagnostic::Ruby::UnexpectedKeywordArgument.new( node: error.node, method_type: method_type, method_name: method_name ) when KeywordArgs::MissingKeyword missing_keywords.push(*error.keywords) when PositionalArgs::UnexpectedArg diagnostics << Diagnostic::Ruby::UnexpectedPositionalArgument.new( node: error.node, method_type: method_type, method_name: method_name ) when PositionalArgs::MissingArg diagnostics << Diagnostic::Ruby::InsufficientPositionalArguments.new( node: node, method_name: method_name, method_type: method_type ) end end unless missing_keywords.empty? diagnostics << Diagnostic::Ruby::InsufficientKeywordArguments.new( node: node, method_name: method_name, method_type: method_type, missing_keywords: missing_keywords ) end diagnostics else enum_for :each end end
def initialize(node:, arguments:, method_name:, method_type:)
def initialize(node:, arguments:, method_name:, method_type:) @node = node @arguments = arguments @method_type = method_type @method_name = method_name end
def keyword_args
def keyword_args KeywordArgs.new( kwarg_nodes: kwargs_node&.children || [], keyword_params: keyword_params ) end
def keyword_params
def keyword_params method_type.type.params.keyword_params end
def kwargs_node
def kwargs_node unless keyword_params.empty? arguments.find {|node| node.type == :kwargs } end end
def positional_arg
def positional_arg args = if keyword_params.empty? arguments.take_while {|node| node.type != :block_pass } else arguments.take_while {|node| node.type != :kwargs && node.type != :block_pass } end PositionalArgs.new(args: args, index: 0, positional_params: positional_params) end
def positional_params
def positional_params method_type.type.params.positional_params end