================================================================================
Function definitions end keywords
================================================================================

function f()
endf

function f()
endf

function f()
endfu

function f()
endfunction

--------------------------------------------------------------------------------

(script_file
  (function_definition
    (function_declaration
      (identifier)
      (parameters)))
  (function_definition
    (function_declaration
      (identifier)
      (parameters)))
  (function_definition
    (function_declaration
      (identifier)
      (parameters)))
  (function_definition
    (function_declaration
      (identifier)
      (parameters))))

================================================================================
Function definition without body
================================================================================

function foo()
endf

--------------------------------------------------------------------------------

(script_file
  (function_definition
    (function_declaration
      (identifier)
      (parameters))))

================================================================================
Function definition with body
================================================================================

function foo()
	let bar = 31
endf

--------------------------------------------------------------------------------

(script_file
  (function_definition
    (function_declaration
      (identifier)
      (parameters))
    (body
      (let_statement
        (identifier)
        (integer_literal)))))

================================================================================
Function with args
================================================================================

function foo(a, b)
endf

--------------------------------------------------------------------------------

(script_file
  (function_definition
    (function_declaration
      (identifier)
      (parameters
        (identifier)
        (identifier)))))

================================================================================
Function with default args
================================================================================

function foo(a, b = 10)
endf

--------------------------------------------------------------------------------

(script_file
  (function_definition
    (function_declaration
      name: (identifier)
      parameters: (parameters
        (identifier)
        (default_parameter
          name: (identifier)
          value: (integer_literal))))))

================================================================================
Function only default
================================================================================

function foo(a=1, b=2)
endf

--------------------------------------------------------------------------------

(script_file
  (function_definition
    (function_declaration
      name: (identifier)
      parameters: (parameters
        (default_parameter
          name: (identifier)
          value: (integer_literal))
        (default_parameter
          name: (identifier)
          value: (integer_literal))))))

================================================================================
Function default spread
================================================================================

function foo(a=1, ...)
endf

--------------------------------------------------------------------------------

(script_file
  (function_definition
    (function_declaration
      name: (identifier)
      parameters: (parameters
        (default_parameter
          name: (identifier)
          value: (integer_literal))
        (spread)))))

================================================================================
Function with args and spread
================================================================================

function foo(a, b, ...)
endf

--------------------------------------------------------------------------------

(script_file
  (function_definition
    (function_declaration
      (identifier)
      (parameters
        (identifier)
        (identifier)
        (spread)))))

================================================================================
Function with spread
================================================================================

function foo(...)
endf

--------------------------------------------------------------------------------

(script_file
  (function_definition
    (function_declaration
      (identifier)
      (parameters
        (spread)))))

================================================================================
Script local function
================================================================================

function <SID>foo()
endfunction

--------------------------------------------------------------------------------

(script_file
  (function_definition
    (function_declaration
      (scoped_identifier
        (scope)
        (identifier))
      (parameters))))

================================================================================
Function return integer
================================================================================

function foo()
  return 1
endfunction

--------------------------------------------------------------------------------

(script_file
  (function_definition
    (function_declaration
      (identifier)
      (parameters))
    (body
      (return_statement
        (integer_literal)))))

================================================================================
Function empty return
================================================================================

function foo()
  return
endfunction

--------------------------------------------------------------------------------

(script_file
  (function_definition
    (function_declaration
      (identifier)
      (parameters))
    (body
      (return_statement))))

================================================================================
Function with definition arguments
:skip
================================================================================

function foo() dict abort range closure
  return
endfunction

function foo() abort dict range closure
  return
endfunction

--------------------------------------------------------------------------------

(script_file
  (function_definition
    (function_declaration
      (identifier)
      (parameters))
    (body
      (return_statement)))
  (function_definition
    (function_declaration
      (identifier)
      (parameters))
    (body
      (return_statement))))

================================================================================
:fun-y function
================================================================================

fun bar()
  return
endfunction

--------------------------------------------------------------------------------

(script_file
  (function_definition
    (function_declaration
      (identifier)
      (parameters))
    (body
      (return_statement))))

================================================================================
Function def with comment
================================================================================

fun foo() " This is function foo
  echo "bar"
endfunction

--------------------------------------------------------------------------------

(script_file
  (function_definition
    (function_declaration
      (identifier)
      (parameters))
    (comment)
    (body
      (echo_statement
        (string_literal)))))

================================================================================
function with curly-brace
================================================================================

fun my_func_{func_end}()
endfunction

--------------------------------------------------------------------------------

(script_file
  (function_definition
    (function_declaration
      (identifier
        (curly_braces_name
          (identifier)))
      (parameters))))

================================================================================
Basic anonymous function
================================================================================

function mydict.return_thing()
  return 'thing'
endfunction

--------------------------------------------------------------------------------

(script_file
  (function_definition
    (function_declaration
      name: (field_expression
        value: (identifier)
        field: (identifier))
      parameters: (parameters))
    (body
      (return_statement
        (string_literal)))))

================================================================================
Anonymous function with curly-brace
================================================================================

function {some_dict}.len()
  return len(self)
endfunction

--------------------------------------------------------------------------------

(script_file
  (function_definition
    (function_declaration
      name: (field_expression
        value: (identifier
          (curly_braces_name
            (identifier)))
        field: (identifier))
      parameters: (parameters))
    (body
      (return_statement
        (call_expression
          function: (identifier)
          (identifier))))))

================================================================================
Anonymous function bound to a script-local variable
================================================================================

function <SID>var.field()
endfunction

--------------------------------------------------------------------------------

(script_file
  (function_definition
    (function_declaration
      name: (field_expression
        value: (scoped_identifier
          (scope)
          (identifier))
        field: (identifier))
      parameters: (parameters))))

================================================================================
Anonymous function bound to an element of a list
================================================================================

func persons[0].full_name()
  return 'Ms. Jackson'
endfunc

--------------------------------------------------------------------------------

(script_file
  (function_definition
    (function_declaration
      name: (field_expression
        value: (index_expression
          value: (identifier)
          index: (integer_literal))
        field: (identifier))
      parameters: (parameters))
    (body
      (return_statement
        (string_literal)))))

================================================================================
Function definitions with bang
================================================================================

function! Fn_1() abort
endfunction

function! s:fn_2() abort
endfunction

--------------------------------------------------------------------------------

(script_file
  (function_definition
    (bang)
    (function_declaration
      name: (identifier)
      parameters: (parameters)))
  (function_definition
    (bang)
    (function_declaration
      name: (scoped_identifier
        (scope)
        (identifier))
      parameters: (parameters))))
