firstWhere throws when provided orElse: null if no items matched (expectation was null returned)

The firstWhere docs say that if there’s no matching element a StateError will be thrown unless you provide an orElse argument. However I was just caught out that if I pre-filter the list with another .where() which matches no elements, a StateError is thrown regardless of the orElse:

[1]
  .where((a) => a > 10)
  .firstWhere((a) => a == 0, orElse: null);
Bad state: No element
    at Object.wrapException (<anonymous>:611:17)
    at WhereIterable.firstWhere$2$orElse (<anonymous>:1302:17)
    at Object.main (<anonymous>:1372:54)

IMO this behaviour seems wonky (and different to other similar methods from other languages I’ve used) – it means chaining wheres and then a firstWhere isn’t the same as putting all the conditions in the firstWhere (which seems to encourage a single firstWhere with a long set of conditions), however if that’s how it’s expected to be I think there should be a mention in the docs that an empty input will always throw regardless of the condition of the orElse argument.

Author: Fantashit

2 thoughts on “firstWhere throws when provided orElse: null if no items matched (expectation was null returned)

  1. The orElse parameter is a function, not a value. That’s occasionally annoying, but also strictly more powerful than passing a single value. It also allows you to actually use null as a default by calling as:

    someIterable.firstWhere(test, orElse: () => null);

Comments are closed.