let $fixture = $args[0]
printf "%s" "pub struct Item { n: Integer }; pub fn Item::next_item(): Integer | () { if \$self.n == 0 { return () }; \$self.n = \$self.n - 1; \$self.n }; pub fn make(): Item { Item(n: 2) }" -> "${fixture}/custom.shy"
check_repl ["id": "ITERATOR", "name": "ITERATOR", "steps": [
["struct Counter { n: Integer }; let \$counter = Counter(n: 2)", "quiet", ""],
["fn Counter::next_item(): Integer | () { if \$self.n == 0 { return () }; \$self.n = \$self.n - 1; \$self.n }", "quiet", ""],
["for \$x in \$counter { echo \$x }; echo \$counter.n", "output", "1\n0\n2"],
["fn consume(\$c: Counter) { for \$x in \$c { echo \$x } }", "quiet", ""],
["fn Counter::next_item(): Integer | () { 1 / 0 }", "quiet", ""],
["for \$x in \$counter { echo wrong }", "error", "Arithmetic error"],
["echo \$counter.n", "output", "2"],
["consume \$counter", "output", "1\n0"],
["fn Counter::next_item(): Integer { 1 }", "error", "must declare a return type"],
["for \$x in \$counter {}", "error", "Arithmetic error"],
["fn Counter::next_item(): [Integer, String] | () { if \$self.n == 0 { return () }; \$self.n = \$self.n - 1; [\$self.n,\"v\"] }", "quiet", ""],
["for (\$n,\$s) in \$counter { echo \$n \$s }; echo \$counter.n", "output", "1 v\n0 v\n2"],
["for (\$a,\$b,\$c) in \$counter {}", "error", "Array destructuring expected 3"],
["echo \$counter.n", "output", "2"],
["import custom::{ Item }; let \$item = custom::make; for \$n in \$item { echo \$n }; echo \$item.n", "output", "1\n0\n2"],
["let \$a = [1,2]; let \$next = `\$a.next_item; echo (\$next) (\$next) (\$next)", "output", "1 2 ()"],
["for (\$a,\$b) in [\"a\": 3] { echo \$a \$b }", "output", "a 3"]
], "exit": 0]