net.jqwik.engine.properties.arbitraries.LazyArbitrary Maven / Gradle / Ivy
package net.jqwik.engine.properties.arbitraries;
import java.util.*;
import java.util.function.*;
import net.jqwik.api.*;
import net.jqwik.api.configurators.*;
import net.jqwik.api.providers.*;
import org.jspecify.annotations.*;
public class LazyArbitrary implements Arbitrary, SelfConfiguringArbitrary {
private final Supplier extends Arbitrary> arbitrarySupplier;
private final List> configurations = new ArrayList<>();
private @Nullable Arbitrary arbitrary;
public LazyArbitrary(Supplier extends Arbitrary> arbitrarySupplier) {
this.arbitrarySupplier = arbitrarySupplier;
}
@Override
public RandomGenerator generator(int genSize) {
return getArbitrary().generator(genSize);
}
@Override
public RandomGenerator generatorWithEmbeddedEdgeCases(int genSize) {
// This is actually right. Don't use getArbitrary().generatorWithEmbeddedEdgeCases() directly
return getArbitrary().generator(genSize, true);
}
private Arbitrary getArbitrary() {
if (this.arbitrary == null) {
Arbitrary rawArbitrary = arbitrarySupplier.get();
for (Tuple.Tuple2 configuration : configurations) {
ArbitraryConfigurator configurator = configuration.get1();
TypeUsage targetType = configuration.get2();
rawArbitrary = SelfConfiguringArbitrary.configure(rawArbitrary, configurator, targetType);
}
this.arbitrary = rawArbitrary;
}
return this.arbitrary;
}
@Override
public Optional> exhaustive(long maxNumberOfSamples) {
return getArbitrary().exhaustive(maxNumberOfSamples);
}
@Override
public EdgeCases edgeCases(int maxEdgeCases) {
// Cannot be delegated to getArbitrary() due to possible recursion
return EdgeCases.none();
}
@Override
public Arbitrary configure(ArbitraryConfigurator configurator, TypeUsage targetType) {
configurations.add(Tuple.of(configurator, targetType));
return this;
}
}