Skip to content

Commit

Permalink
Added failing tests for BeforeTry member variables
Browse files Browse the repository at this point in the history
  • Loading branch information
jlink committed Mar 18, 2023
1 parent ef6122a commit 091a7b8
Show file tree
Hide file tree
Showing 5 changed files with 115 additions and 3 deletions.
7 changes: 4 additions & 3 deletions api/src/main/java/net/jqwik/api/lifecycle/BeforeTry.java
Original file line number Diff line number Diff line change
Expand Up @@ -7,10 +7,11 @@
import static org.apiguardian.api.API.Status.*;

/**
* Annotate methods of a container class with {@code @BeforeTry}
* to have them run once before each try - the actual invocation of the property
* Annotate methods or member variables of a container class with {@code @BeforeTry}.
* Annotated methods will then be run once before each try - the actual invocation of the property
* method with generated parameters - including properties of
* embedded containers.
* Annotated members will be freshly initialized before each try.
*
* <p>{@code @BeforeTry} methods are inherited from superclasses
* and implemented interfaces as long as they are not <em>hidden</em>
Expand All @@ -28,7 +29,7 @@
*
* @see AfterTry
*/
@Target({ElementType.ANNOTATION_TYPE, ElementType.METHOD})
@Target({ElementType.FIELD, ElementType.ANNOTATION_TYPE, ElementType.METHOD})
@Retention(RetentionPolicy.RUNTIME)
@API(status = MAINTAINED, since = "1.4.0")
public @interface BeforeTry {
Expand Down
3 changes: 3 additions & 0 deletions engine/src/main/java/net/jqwik/engine/hooks/Hooks.java
Original file line number Diff line number Diff line change
Expand Up @@ -24,6 +24,9 @@ public static class AroundProperty {
public static class AroundTry {
// Should run close to property method
public static final int TRY_LIFECYCLE_METHODS_PROXIMITY = -10;

// Should run first thing
public static final int BEFORE_TRY_MEMBERS_PROXIMITY = -100;
}

}
Original file line number Diff line number Diff line change
@@ -0,0 +1,63 @@
package net.jqwik.engine.hooks.lifecycle;

import java.lang.reflect.*;
import java.util.*;

import org.junit.platform.engine.support.hierarchical.*;

import net.jqwik.api.lifecycle.*;
import net.jqwik.engine.hooks.*;
import net.jqwik.engine.support.*;

public class BeforeTryMembersHook implements AroundTryHook {

private void beforeTry(TryLifecycleContext context) {
System.out.println("initialize before try members");
// List<Method> beforeTryMethods = LifecycleMethods.findBeforeTryMethods(context.containerClass());
// callTryMethods(beforeTryMethods, context);
}

private void callTryMethods(List<Method> methods, TryLifecycleContext context) {
Object testInstance = context.testInstance();
ThrowableCollector throwableCollector = new ThrowableCollector(ignore -> false);
for (Method method : methods) {
Object[] parameters = MethodParameterResolver.resolveParameters(method, context);
throwableCollector.execute(() -> callMethod(method, testInstance, parameters));
}
throwableCollector.assertEmpty();
}

private void callMethod(Method method, Object target, Object[] parameters) {
JqwikReflectionSupport.invokeMethodPotentiallyOuter(method, target, parameters);
}

private void afterTry(TryLifecycleContext context) {
List<Method> afterTryMethods = LifecycleMethods.findAfterTryMethods(context.containerClass());
callTryMethods(afterTryMethods, context);
}

@Override
public PropagationMode propagateTo() {
return PropagationMode.ALL_DESCENDANTS;
}

@Override
public boolean appliesTo(Optional<AnnotatedElement> element) {
return element.map(e -> e instanceof Method).orElse(false);
}

@Override
public int aroundTryProximity() {
return Hooks.AroundTry.BEFORE_TRY_MEMBERS_PROXIMITY;
}

@Override
public TryExecutionResult aroundTry(TryLifecycleContext context, TryExecutor aTry, List<Object> parameters) {
beforeTry(context);
try {
return aTry.execute(parameters);
} finally {
afterTry(context);
}
}
}
Original file line number Diff line number Diff line change
Expand Up @@ -2,6 +2,7 @@ net.jqwik.engine.hooks.lifecycle.AutoCloseableHook
net.jqwik.engine.hooks.lifecycle.ContainerLifecycleMethodsHook
net.jqwik.engine.hooks.lifecycle.PropertyLifecycleMethodsHook
net.jqwik.engine.hooks.lifecycle.TryLifecycleMethodsHook
net.jqwik.engine.hooks.lifecycle.BeforeTryMembersHook
net.jqwik.engine.hooks.DisabledHook
net.jqwik.engine.hooks.statistics.StatisticsHook
net.jqwik.engine.hooks.ResolveReporterHook
Original file line number Diff line number Diff line change
@@ -0,0 +1,44 @@
package net.jqwik.engine.execution.lifecycle;

import org.assertj.core.api.*;

import net.jqwik.api.*;
import net.jqwik.api.constraints.*;
import net.jqwik.api.lifecycle.*;

class BeforeTryOnMemberVariableTests {

@BeforeTry
private int member = 41;

@BeforeTry
void testBefore() {
System.out.println("before try outer");
}

@Property(tries = 10)
void beforeTryOnMember(@ForAll @IntRange(min = 1, max = 100) int addend) {
Assertions.assertThat(member).isEqualTo(41);
member = member + addend;
}

@Group
class InnerTests {

@BeforeTry
private int innerMember = 42;

@BeforeTry
void testBeforeInner() {
System.out.println("before try inner");
}

@Property(tries = 10)
void beforeTryOnMemberInInnerGroup(@ForAll @IntRange(min = 1, max = 100) int addend) {
Assertions.assertThat(member).isEqualTo(41);
member = member + addend;
Assertions.assertThat(innerMember).isEqualTo(42);
innerMember = innerMember + addend;
}
}
}

0 comments on commit 091a7b8

Please sign in to comment.