diff --git a/pom.xml b/pom.xml
index ffeef667e8..440704f8eb 100644
--- a/pom.xml
+++ b/pom.xml
@@ -66,7 +66,6 @@
2.12.2
0.8.8
1.6.0
- 1.3.0
1.8.22
1.9.4
diff --git a/spring-cloud-contract-verifier/pom.xml b/spring-cloud-contract-verifier/pom.xml
index ff9ed4d9c7..79559def3e 100644
--- a/spring-cloud-contract-verifier/pom.xml
+++ b/spring-cloud-contract-verifier/pom.xml
@@ -247,12 +247,6 @@
spring-boot-starter-jersey
test
-->
-
- org.mdkt.compiler
- InMemoryJavaCompiler
- ${InMemoryJavaCompiler.version}
- test
-
jetty-ee10-servlet
org.eclipse.jetty.ee10
diff --git a/spring-cloud-contract-verifier/src/test/groovy/org/springframework/cloud/contract/verifier/builder/MockMvcMethodBodyBuilderWithMatchersSpec.groovy b/spring-cloud-contract-verifier/src/test/groovy/org/springframework/cloud/contract/verifier/builder/MockMvcMethodBodyBuilderWithMatchersSpec.groovy
index c14890632e..fabb3242f7 100644
--- a/spring-cloud-contract-verifier/src/test/groovy/org/springframework/cloud/contract/verifier/builder/MockMvcMethodBodyBuilderWithMatchersSpec.groovy
+++ b/spring-cloud-contract-verifier/src/test/groovy/org/springframework/cloud/contract/verifier/builder/MockMvcMethodBodyBuilderWithMatchersSpec.groovy
@@ -17,7 +17,6 @@
package org.springframework.cloud.contract.verifier.builder
import org.junit.Rule
-import org.mdkt.compiler.CompilationException
import spock.lang.Issue
import spock.lang.Shared
import spock.lang.Specification
@@ -238,7 +237,7 @@ class MockMvcMethodBodyBuilderWithMatchersSpec extends Specification implements
try {
SyntaxChecker.tryToCompileWithoutCompileStatic(methodBuilderName, test)
}
- catch (CompilationException classFormatError) {
+ catch (Exception classFormatError) {
String output = classFormatError.message
assert output.contains('cannot find symbol')
assert output.contains('assertThatValueIsANumber')
diff --git a/spring-cloud-contract-verifier/src/test/groovy/org/springframework/cloud/contract/verifier/util/SyntaxChecker.groovy b/spring-cloud-contract-verifier/src/test/groovy/org/springframework/cloud/contract/verifier/util/SyntaxChecker.groovy
index ceb01b0187..f24d45fdaf 100644
--- a/spring-cloud-contract-verifier/src/test/groovy/org/springframework/cloud/contract/verifier/util/SyntaxChecker.groovy
+++ b/spring-cloud-contract-verifier/src/test/groovy/org/springframework/cloud/contract/verifier/util/SyntaxChecker.groovy
@@ -19,6 +19,16 @@ package org.springframework.cloud.contract.verifier.util
import java.lang.reflect.Method
import javax.inject.Inject
+import javax.tools.Diagnostic
+import javax.tools.DiagnosticCollector
+import javax.tools.FileObject
+import javax.tools.ForwardingJavaFileManager
+import javax.tools.JavaCompiler
+import javax.tools.JavaFileManager
+import javax.tools.JavaFileObject
+import javax.tools.SimpleJavaFileObject
+import javax.tools.StandardJavaFileManager
+import javax.tools.ToolProvider
import javax.ws.rs.client.Entity
import javax.ws.rs.client.WebTarget
import javax.ws.rs.core.Response
@@ -35,7 +45,6 @@ import org.codehaus.groovy.control.customizers.ASTTransformationCustomizer
import org.codehaus.groovy.control.customizers.ImportCustomizer
import org.junit.Rule
import org.junit.Test
-import org.mdkt.compiler.InMemoryJavaCompiler
import org.w3c.dom.Document
import org.xml.sax.InputSource
@@ -46,6 +55,7 @@ import org.springframework.cloud.contract.verifier.messaging.internal.ContractVe
import org.springframework.cloud.contract.verifier.messaging.internal.ContractVerifierObjectMapper
import org.springframework.cloud.contract.verifier.messaging.util.ContractVerifierMessagingUtil
import org.springframework.util.ReflectionUtils
+
/**
* checking the syntax of produced scripts
*/
@@ -110,8 +120,7 @@ private void test(String test) {
try {
if (builderName.toLowerCase().contains("spock")) {
tryToCompileGroovy(builderName, test)
- }
- else {
+ } else {
tryToCompileJava(builderName, test)
}
} catch (Throwable t) {
@@ -125,8 +134,7 @@ private void test(String test) {
if (builderName.toLowerCase().contains("spock")) {
Script script = tryToCompileGroovy(builderName, test)
script.invokeMethod("validate_method()", null)
- }
- else {
+ } else {
Class clazz = tryToCompileJava(builderName, test)
Method method = ReflectionUtils.findMethod(clazz, "validate_method")
method.invoke(clazz.newInstance())
@@ -141,8 +149,7 @@ private void test(String test) {
static void tryToCompileWithoutCompileStatic(String builderName, String test) {
if (builderName.toLowerCase().contains("spock")) {
tryToCompileGroovy(builderName, test, false)
- }
- else {
+ } else {
tryToCompileJava(builderName, test)
}
}
@@ -162,7 +169,7 @@ private void test(String test) {
private static String updatedTest(String test, String className) {
test.replaceAll("class FooTest", "class " + className)
- .replaceAll("import javax.ws.rs.core.Response", "import javax.ws.rs.core.Response; import javax.ws.rs.client.WebTarget;")
+ .replaceAll("import javax.ws.rs.core.Response", "import javax.ws.rs.core.Response; import javax.ws.rs.client.WebTarget;")
}
private static GString getStaticImports(String builderName) {
@@ -176,15 +183,43 @@ private void test(String test) {
String className = className(test)
String fqnClassName = "com.example.${className}"
test = test.replaceAll("class FooTest", "class " + className)
- .replaceAll("import javax.ws.rs.core.Response", "import javax.ws.rs.core.Response; import javax.ws.rs.client.WebTarget;")
+ .replaceAll("import javax.ws.rs.core.Response", "import javax.ws.rs.core.Response; import javax.ws.rs.client.WebTarget;")
return compileJava(fqnClassName, test)
}
- private static Class> compileJava(String fqnClassName, String test) {
- return InMemoryJavaCompiler.newInstance()
- .ignoreWarnings()
- .compile(fqnClassName, test)
+ @CompileStatic
+ private static Class> compileJava(String fqnClassName, String sourceCode) {
+ JavaCompiler compiler = ToolProvider.getSystemJavaCompiler()
+ DiagnosticCollector diagnostics = new DiagnosticCollector<>()
+ InMemoryClassLoader classLoader = new InMemoryClassLoader()
+ StandardJavaFileManager standardFileManager = compiler.getStandardFileManager(diagnostics, null, null)
+ JavaFileManager fileManager = new InMemoryFileManager(standardFileManager, classLoader)
+ JavaFileObject javaFile = new InMemorySourceFile(fqnClassName, sourceCode)
+ JavaCompiler.CompilationTask task = compiler.getTask(
+ new StringWriter(),
+ fileManager,
+ diagnostics,
+ null,
+ null,
+ Collections.singletonList(javaFile)
+ )
+
+ boolean success = task.call()
+ if (!success) {
+ StringBuilder errorMsg = new StringBuilder("Compilation failed:")
+ for (Diagnostic extends JavaFileObject> diagnostic : diagnostics.getDiagnostics()) {
+ errorMsg.append("\nLine ").append(diagnostic.getLineNumber())
+ .append(": ").append(diagnostic.getMessage(null))
+ }
+ throw new IllegalStateException(errorMsg.toString())
+ }
+
+ try {
+ return classLoader.loadClass(fqnClassName)
+ } catch (ClassNotFoundException e) {
+ throw new IllegalStateException("Failed to load compiled class", e)
+ }
}
private static String className(String test) {
@@ -210,4 +245,81 @@ private void test(String test) {
return true
}
+ @CompileStatic
+ private static class InMemorySourceFile extends SimpleJavaFileObject {
+ private final String sourceCode
+
+ InMemorySourceFile(String className, String sourceCode) {
+ super(URI.create("string:///" + className.replace('.', '/') + Kind.SOURCE.extension),
+ Kind.SOURCE)
+ this.sourceCode = sourceCode
+ }
+
+ @Override
+ CharSequence getCharContent(boolean ignoreEncodingErrors) {
+ return sourceCode
+ }
+ }
+
+ @CompileStatic
+ private static class InMemoryClassLoader extends ClassLoader {
+ private final Map classData = new HashMap<>()
+
+ void addClass(String name, byte[] data) {
+ classData.put(name, data)
+ }
+
+ @Override
+ protected Class> findClass(String name) throws ClassNotFoundException {
+ byte[] data = classData.get(name)
+ if (data == null) {
+ throw new ClassNotFoundException(name)
+ }
+ return defineClass(name, data, 0, data.length)
+ }
+ }
+
+ @CompileStatic
+ private static class InMemoryFileManager extends ForwardingJavaFileManager {
+ private final InMemoryClassLoader classLoader
+
+ InMemoryFileManager(StandardJavaFileManager fileManager, InMemoryClassLoader classLoader) {
+ super(fileManager)
+ this.classLoader = classLoader
+ }
+
+ @Override
+ JavaFileObject getJavaFileForOutput(Location location,
+ String className,
+ JavaFileObject.Kind kind,
+ FileObject sibling) {
+ return new InMemoryClassFile(className, classLoader)
+ }
+ }
+
+ @CompileStatic
+ private static class InMemoryClassFile extends SimpleJavaFileObject {
+ private final String className
+ private final InMemoryClassLoader classLoader
+ private final ByteArrayOutputStream outputStream = new ByteArrayOutputStream()
+
+ InMemoryClassFile(String className, InMemoryClassLoader classLoader) {
+ super(URI.create("byte:///" + className.replace('.', '/') + Kind.CLASS.extension),
+ Kind.CLASS)
+ this.className = className
+ this.classLoader = classLoader
+ }
+
+ @Override
+ OutputStream openOutputStream() {
+ outputStream.reset()
+ return new FilterOutputStream(outputStream) {
+ @Override
+ void close() throws IOException {
+ super.close()
+ classLoader.addClass(className, outputStream.toByteArray())
+ }
+ }
+ }
+ }
}