pact-jvm: AmqpTarget doesn't find @PactVerifyProvider annotation

I’m running a simple message provider test:

@RunWith(PactRunner.class)
@Provider("userservice")
@PactFolder("../pact-message-consumer/target/pacts")
@SpringBootTest
public class MessageProviderTest {

	@TestTarget
	public final Target target = new AmqpTarget(Collections.singletonList("io.reflectoring"));

	@PactVerifyProvider("a user created message")
	public String verifyUserCreatedMessage() {
		return "{\"testParam1\": \"value1\",\"testParam2\": \"value2\"}";
	}
}

Executing this test results in

Failures:

0) a user created message
      No annotated methods were found for interaction 'a user created message'. You need to provide a method annotated with @PactVerifyProvider("a user created message") that returns the message contents.

The cause for this is that the Reflections call in ProviderVerifier#verifyResponseByInvokingProviderMethods doesn’t find the @PactVerifyProvider annotation on my test method. There must be something wrong with the setup of the Reflections instance (class loader?).

When I’m using the following code snippet from a test, the annotation is found:

Reflections r = new Reflections(ClasspathHelper.forPackage("io.reflectoring"), new MethodAnnotationsScanner());
Set<Method> methods = r.getMethodsAnnotatedWith(PactVerifyProvider.class);

About this issue

  • Original URL
  • State: closed
  • Created 6 years ago
  • Comments: 20 (13 by maintainers)

Commits related to this issue

Most upvoted comments

@eranberg I was experiencing the same issue but with 3.6.4. I found that after upgrading maven-surefire-plugin, everything started to work:

<plugin>
    <groupId>org.apache.maven.plugins</groupId>
    <artifactId>maven-surefire-plugin</artifactId>
    <version>2.22.1</version>
    <configuration>
        <useSystemClassLoader>false</useSystemClassLoader>
    </configuration>
</plugin>

Intermediate versions may work, however I didn’t look into it.

Had this issue as well. My issue is that I am using Java 11. Upgraded to pact-jvm-consumer-junit version 4.0.0-beta.2 and I have provider verification working again.

Thanks @jon-ruckwood I will update the docs to specify that version as a minimum.

@PMT87 @gumartinm You need to set the Maven Surefire plugin to use an isolated class loader. For example:

             <plugin>
                <groupId>org.apache.maven.plugins</groupId>
                <artifactId>maven-surefire-plugin</artifactId>
                <configuration>
                    <useSystemClassLoader>false</useSystemClassLoader>
                </configuration>
            </plugin>

@eranberg have a look at https://github.com/uglyog/pact-maven-amqp-test, it is a simple project that works with Maven 3.5. You’ll need to compare it to yours to work out what the issue is.

@uglyog I still couldn’t get it to work, even when overriding the projectClasspath field. Must be some issue with the classloader.

I can get it to work when overriding the whole usage of Reflections (i.e. subclassing AmqpTarget and ProviderVerifier, but that is a very ugly workaround (see here).

Instead of using a specific classloader, I simply use Reflections r = new Reflections(packages, new MethodAnnotationsScanner()); to scan the classpath for annotations.

Why does ProviderVerifier use a specific class loader? Wouldn’t it make sense to use the Reflections default as I did above?