oi
Oi: checked IO a stream can carry, failed unchecked
IoFunction and IoConsumer let a stream map through and end in IO: each is a Function or Consumer whose work throws IOException, rethrown as UncheckedIOException.
Rationale
Why. A stream's Function and Consumer cannot throw IOException, yet reading or writing a file is often the step a stream needs.
Key Concepts
Checked IO in a chain
Role. A lambda cast to IoFunction<T, R> or IoConsumer<T> implements io, which may throw IOException, and is the Function or Consumer a stream's map or forEach takes.
Pattern. Template Method
How It Works
Guarantees. An IOException thrown by io leaves apply or accept as an UncheckedIOException whose cause is that IOException. No method takes null and IoFunction never returns it, declared with contrax's @PreCondition(IsNotNull.class) and @PostCondition(IsNotNull.class).
Lane
Purpose. Mapping through and ending a stream in IO, where any IO failure stops the stream.
Alternative. A loop with its own try/catch, when one element's IO failure is recovered from and the rest go on.
Usage
Without oi: a try/catch in every lambda
places.stream()
.map(place -> {
try {
return place.toRealPath();
} catch (final IOException failed) {
throw new UncheckedIOException(failed);
}
})
.forEach(place -> {
try {
Files.delete(place);
} catch (final IOException failed) {
throw new UncheckedIOException(failed);
}
});With oi: the lambda is cast, and throws
places.stream()
.map((IoFunction<Path, Path>) Path::toRealPath)
.forEach((IoConsumer<Path>) Files::delete);Dependencies
software.visionary:junit-closure:2026.09.17at Testing
Views
Drawn from the release. A link in a view opens its source at the release tag.