Gosu reference

Gosu Blocks and Collections

GuidewireTraining.com faculty · Updated

Definition: A block in Gosu is an anonymous function (Gosu's equivalent of a Java lambda) written with a backslash, such as \ x -> x * 2. Blocks are passed to collection methods like where, map and firstWhere to filter, transform and search lists without writing explicit loops.

Block syntax

A block starts with a backslash, lists its parameters, then an arrow and the body.

var double = \ x : int -> x * 2
print(double(21))           // 42

// Multiple statements use braces and an explicit return
var describe = \ name : String -> {
  var trimmed = name.trim()
  return "Hello, ${trimmed}"
}

When a block is passed to a method, Gosu usually infers the parameter type, so you can leave it out:

var names = {"Asha", "Ravi", "Meera"}
var longNames = names.where(\ n -> n.length() > 4)

Block types

A variable or parameter that holds a block has a block type, written with the block keyword:

function applyTwice(f : block(x : int) : int, value : int) : int {
  return f(f(value))
}
print(applyTwice(\ x -> x + 3, 10))   // 16

Common collection methods

Method What it does Example
where Keeps elements that match vehicles.where(\ v -> v.Year >= 2023)
map Transforms each element vehicles.map(\ v -> v.Make)
firstWhere First match, or null drivers.firstWhere(\ d -> d.Excluded)
hasMatch True if any element matches drivers.hasMatch(\ d -> d.Age < 25)
allMatch True if every element matches vehicles.allMatch(\ v -> v.Vin != null)
countWhere Counts matches claims.countWhere(\ c -> c.State == TC_OPEN)
sum Adds a numeric value per element vehicles.sum(\ v -> v.CostNew)
each Runs a side effect per element contacts.each(\ c -> print(c.DisplayName))
toSet / toList Converts the result vehicles.map(\ v -> v.Make).toSet()

Methods can be chained, which keeps rules short and readable:

var youngDriverMakes = period.PersonalAutoLine.Vehicles
  .where(\ v -> v.Drivers.hasMatch(\ d -> d.PolicyDriver.Age < 25))
  .map(\ v -> v.Make)
  .toSet()

Capturing variables

A block can use variables from the code around it:

var minYear = 2020
var recent = vehicles.where(\ v -> v.Year >= minYear)

When to use a loop instead

Use a for loop when you need to exit early, update several variables, or when a block chain becomes hard to read. Readability matters more than brevity in code that others will maintain.

Common mistakes

  • Calling a collection method on a possibly null array or list (use ?. or check for null first).
  • Using where(...).first() when firstWhere(...) states the intent more clearly.
  • Running database queries inside a block that executes for every element of a large collection.
  • Using map to perform side effects instead of each.

Troubleshooting

Compile error that the block's parameter type cannot be inferred.
Declare the parameter type explicitly, for example \ v : PersonalVehicle -> v.Year.
NullPointerException inside a block.
An element or a property on it is null. Use the null-safe ?. operator inside the block, or filter nulls first with where(\ x -> x != null).
A block-heavy rule runs slowly.
Look for queries or expensive property calls inside the block and move them outside, or filter earlier so the block runs on fewer elements.

Examples are simplified for learning. Check exact APIs and behaviour against the documentation for your InsuranceSuite release.