Turned on checkstyle

This commit is contained in:
Marcin Grzejszczak
2019-02-01 15:48:32 +01:00
parent 94e9b8f2f8
commit e4b08a083c
268 changed files with 5114 additions and 3993 deletions

View File

@@ -1,5 +1,5 @@
/*
* Copyright 2017 the original author or authors.
* Copyright 2012-2019 the original author or authors.
*
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
@@ -15,10 +15,6 @@
*/
package org.springframework.cloud.function.compiler;
import static org.assertj.core.api.Assertions.assertThat;
import static org.junit.Assert.assertEquals;
import static org.junit.Assert.assertTrue;
import java.io.File;
import java.io.FileInputStream;
import java.io.FileOutputStream;
@@ -35,21 +31,25 @@ import java.util.jar.JarInputStream;
import java.util.jar.JarOutputStream;
import java.util.zip.ZipEntry;
import ch.qos.logback.classic.Level;
import ch.qos.logback.classic.Logger;
import ch.qos.logback.classic.LoggerContext;
import org.junit.Test;
import org.slf4j.LoggerFactory;
import org.springframework.cloud.function.compiler.java.CompilationResult;
import org.springframework.cloud.function.compiler.java.RuntimeJavaCompiler;
import org.springframework.cloud.function.core.FunctionFactoryUtils;
import ch.qos.logback.classic.Level;
import ch.qos.logback.classic.Logger;
import ch.qos.logback.classic.LoggerContext;
import static org.assertj.core.api.Assertions.assertThat;
import static org.junit.Assert.assertEquals;
import static org.junit.Assert.assertTrue;
/**
* Tests that verify dependency resolution. Dependencies can be resolved against simple
* Tests that verify dependency resolution. Dependencies can be resolved against simple
* classpath entries or against classes under BOOT-INF/classes or in a nested jar under
* under BOOT-INF/lib. Finding classes in those locations enables compilation
* against a packaged boot jar.
* under BOOT-INF/lib. Finding classes in those locations enables compilation against a
* packaged boot jar.
*
* @author Andy Clement
*/
@@ -57,9 +57,10 @@ public class CompilerDependencyResolutionTests {
@Test
public void compilingTestClass() throws Exception {
ClassDescriptor t1 = compile("Test1","package com.test;\npublic class Test1 { public static String doit() { return \"T1\";}}\n");
ClassDescriptor t1 = compile("Test1",
"package com.test;\npublic class Test1 { public static String doit() { return \"T1\";}}\n");
String result = (String) t1.clazz.getDeclaredMethod("doit").invoke(null);
assertEquals("T1",result);
assertEquals("T1", result);
}
@Test
@@ -69,122 +70,130 @@ public class CompilerDependencyResolutionTests {
File jar = JarBuilder.create().addEntries(t1, t2).getJar();
assertJarContents(jar, t1, t2);
}
/**
* Doesn't actually verify the caching helps but can be useful to run to see
* current numbers.
* Doesn't actually verify the caching helps but can be useful to run to see current
* numbers.
*/
@Test
public void speedtest() {
LoggerContext loggerContext = (LoggerContext) LoggerFactory.getILoggerFactory();
Logger rootLogger = loggerContext.getLogger("org.springframework.cloud.function.compiler");
Logger rootLogger = loggerContext
.getLogger("org.springframework.cloud.function.compiler");
rootLogger.setLevel(Level.ERROR);
// 10 uses of a single function compiler:
long stime = System.currentTimeMillis();
FunctionCompiler<String,String> fc = new FunctionCompiler<String, String>(String.class.getName());
for (int i=0;i<5;i++) {
FunctionCompiler<String, String> fc = new FunctionCompiler<String, String>(
String.class.getName());
for (int i = 0; i < 5; i++) {
stime = System.currentTimeMillis();
CompiledFunctionFactory<Function<String, String>> result =
fc.compile("foos", "flux -> flux.map(v -> v.toUpperCase())", "Flux<String>", "Flux<String>");
assertThat(FunctionFactoryUtils.isFluxFunction(result.getFactoryMethod())).isTrue();
System.out.println("Reusing FunctionCompiler: #"+(i+1)+" = "+(System.currentTimeMillis()-stime)+"ms");
CompiledFunctionFactory<Function<String, String>> result = fc.compile("foos",
"flux -> flux.map(v -> v.toUpperCase())", "Flux<String>",
"Flux<String>");
assertThat(FunctionFactoryUtils.isFluxFunction(result.getFactoryMethod()))
.isTrue();
System.out.println("Reusing FunctionCompiler: #" + (i + 1) + " = "
+ (System.currentTimeMillis() - stime) + "ms");
}
// 3 separate FunctionCompilers:
stime = System.currentTimeMillis();
CompiledFunctionFactory<Function<String, String>> compiled = new FunctionCompiler<String, String>(
String.class.getName()).compile("foos", "flux -> flux.map(v -> v.toUpperCase())", "Flux<String>",
String.class.getName()).compile("foos",
"flux -> flux.map(v -> v.toUpperCase())", "Flux<String>",
"Flux<String>");
assertThat(FunctionFactoryUtils.isFluxFunction(compiled.getFactoryMethod())).isTrue();
assertThat(FunctionFactoryUtils.isFluxFunction(compiled.getFactoryMethod()))
.isTrue();
long etime = System.currentTimeMillis();
long time1 = (etime - stime);
System.out.println("New FunctionCompiler: "+time1+"ms");
stime = System.currentTimeMillis();
compiled = new FunctionCompiler<String, String>(String.class.getName()).compile("foos",
"flux -> flux.map(v -> v.toUpperCase())", "Flux<String>", "Flux<String>");
assertThat(FunctionFactoryUtils.isFluxFunction(compiled.getFactoryMethod())).isTrue();
etime = System.currentTimeMillis();
long time2 = (etime - stime);
System.out.println("New FunctionCompiler: "+time2+"ms");
System.out.println("New FunctionCompiler: " + time1 + "ms");
stime = System.currentTimeMillis();
compiled = new FunctionCompiler<String, String>(String.class.getName()).compile("foos",
"flux -> flux.map(v -> v.toUpperCase())", "Flux<String>", "Flux<String>");
assertThat(FunctionFactoryUtils.isFluxFunction(compiled.getFactoryMethod())).isTrue();
compiled = new FunctionCompiler<String, String>(String.class.getName()).compile(
"foos", "flux -> flux.map(v -> v.toUpperCase())", "Flux<String>",
"Flux<String>");
assertThat(FunctionFactoryUtils.isFluxFunction(compiled.getFactoryMethod()))
.isTrue();
etime = System.currentTimeMillis();
long time2 = (etime - stime);
System.out.println("New FunctionCompiler: " + time2 + "ms");
stime = System.currentTimeMillis();
compiled = new FunctionCompiler<String, String>(String.class.getName()).compile(
"foos", "flux -> flux.map(v -> v.toUpperCase())", "Flux<String>",
"Flux<String>");
assertThat(FunctionFactoryUtils.isFluxFunction(compiled.getFactoryMethod()))
.isTrue();
etime = System.currentTimeMillis();
long time3 = (etime - stime);
System.out.println("New FunctionCompiler: "+time3+"ms");
System.out.println("New FunctionCompiler: " + time3 + "ms");
}
@Test
public void usingJarNoPackageDecl() throws Exception {
ClassDescriptor tx = compile("TestX","public class TestX { public static String doit() { return \"TX\";}}\n");
ClassDescriptor tx = compile("TestX",
"public class TestX { public static String doit() { return \"TX\";}}\n");
File jar = JarBuilder.create().addEntry(tx).getJar();
assertJarContents(jar, tx);
CompilationResult result = new RuntimeJavaCompiler().compile("A",
"public class A {\n" +
" public static Object run() {\n" +
" return new TestX();\n" +
" }\n" +
"}",
jar.toURI().toString());
assertTrue("Should be no problems: "+result.getCompilationMessages(), result.getCompilationMessages().isEmpty());
try (URLClassLoader cl = new TestClassLoader(tx,descriptorFromResult(result))) {
"public class A {\n" + " public static Object run() {\n"
+ " return new TestX();\n" + " }\n" + "}",
jar.toURI().toString());
assertTrue("Should be no problems: " + result.getCompilationMessages(),
result.getCompilationMessages().isEmpty());
try (URLClassLoader cl = new TestClassLoader(tx, descriptorFromResult(result))) {
Class<?> class1 = cl.loadClass("A");
Object invoke = class1.getDeclaredMethod("run").invoke(null);
assertEquals(tx.name, invoke.getClass().getName());
}
}
// A class with no package declaration is placed under BOOT-INF/classes/ in a jar that is then used for resolution
// A class with no package declaration is placed under BOOT-INF/classes/ in a jar that
// is then used for resolution
@Test
public void usingJarNoPackageDeclBootInfClasses() throws Exception {
ClassDescriptor t1 = compile("TestX","public class TestX { public static String doit() { return \"TX\";}}\n");
File jar = JarBuilder.create().addEntryWithPrefix("BOOT-INF/classes/",t1).getJar();
ClassDescriptor t1 = compile("TestX",
"public class TestX { public static String doit() { return \"TX\";}}\n");
File jar = JarBuilder.create().addEntryWithPrefix("BOOT-INF/classes/", t1)
.getJar();
assertJarContents(jar, "BOOT-INF/classes/", t1);
CompilationResult result = new RuntimeJavaCompiler().compile("A",
"public class A {\n" +
" public static Object run() {\n" +
" return new TestX();\n" +
" }\n" +
"}",
jar.toURI().toString());
assertTrue("Should be no problems: "+result.getCompilationMessages(), result.getCompilationMessages().isEmpty());
try (URLClassLoader cl = new TestClassLoader(t1,descriptorFromResult(result))) {
"public class A {\n" + " public static Object run() {\n"
+ " return new TestX();\n" + " }\n" + "}",
jar.toURI().toString());
assertTrue("Should be no problems: " + result.getCompilationMessages(),
result.getCompilationMessages().isEmpty());
try (URLClassLoader cl = new TestClassLoader(t1, descriptorFromResult(result))) {
Class<?> class1 = cl.loadClass("A");
Object invoke = class1.getDeclaredMethod("run").invoke(null);
assertEquals(t1.name, invoke.getClass().getName());
}
}
// A class with no package declaration is placed in a jar which is then placed under
// under BOOT-INF/lib/ in a jar that is then used for resolution
@Test
public void usingJarNoPackageDeclNestedBootInfLib() throws Exception {
ClassDescriptor t1 = compile("TestX","public class TestX { public static String doit() { return \"TX\";}}\n");
ClassDescriptor t1 = compile("TestX",
"public class TestX { public static String doit() { return \"TX\";}}\n");
File jar = JarBuilder.create().addEntry(t1).getJar();
assertJarContents(jar, t1);
// Now stick that jar in another jar!
File jar2 = JarBuilder.create().addEntry("BOOT-INF/lib/inner.jar",jar).getJar();
File jar2 = JarBuilder.create().addEntry("BOOT-INF/lib/inner.jar", jar).getJar();
CompilationResult result = new RuntimeJavaCompiler().compile("A",
"public class A {\n" +
" public static Object run() {\n" +
" return new TestX();\n" +
" }\n" +
"}",
jar2.toURI().toString());
assertTrue("Should be no problems: "+result.getCompilationMessages(), result.getCompilationMessages().isEmpty());
try (URLClassLoader cl = new TestClassLoader(t1,descriptorFromResult(result))) {
"public class A {\n" + " public static Object run() {\n"
+ " return new TestX();\n" + " }\n" + "}",
jar2.toURI().toString());
assertTrue("Should be no problems: " + result.getCompilationMessages(),
result.getCompilationMessages().isEmpty());
try (URLClassLoader cl = new TestClassLoader(t1, descriptorFromResult(result))) {
Class<?> class1 = cl.loadClass("A");
Object invoke = class1.getDeclaredMethod("run").invoke(null);
assertEquals(t1.name, invoke.getClass().getName());
}
}
// Build a jar containing a type with a package declaration and building against it
@Test
public void usingJarWithPackageDecl() throws Exception {
@@ -192,15 +201,13 @@ public class CompilerDependencyResolutionTests {
File jar = JarBuilder.create().addEntry(t1).getJar();
assertJarContents(jar, t1);
CompilationResult result = new RuntimeJavaCompiler().compile("A",
"import " + t1.name.replace('$', '.') + ";\n" +
"public class A {\n" +
" public static Object run() {\n" +
" return new Test1();\n" +
" }\n" +
"}",
jar.toURI().toString());
assertTrue("Should be no problems: "+result.getCompilationMessages(), result.getCompilationMessages().isEmpty());
try (URLClassLoader cl = new TestClassLoader(t1,descriptorFromResult(result))) {
"import " + t1.name.replace('$', '.') + ";\n" + "public class A {\n"
+ " public static Object run() {\n" + " return new Test1();\n"
+ " }\n" + "}",
jar.toURI().toString());
assertTrue("Should be no problems: " + result.getCompilationMessages(),
result.getCompilationMessages().isEmpty());
try (URLClassLoader cl = new TestClassLoader(t1, descriptorFromResult(result))) {
Class<?> class1 = cl.loadClass("A");
Object invoke = class1.getDeclaredMethod("run").invoke(null);
assertEquals(t1.name, invoke.getClass().getName());
@@ -211,24 +218,22 @@ public class CompilerDependencyResolutionTests {
public void usingJarWithPackageDeclBootInfClasses() throws Exception {
// Here the dependencies are under BOOT-INF/classes in the jar
ClassDescriptor t1 = getTestClass("1");
File jar = JarBuilder.create().addEntryWithPrefix("BOOT-INF/classes/",t1).getJar();
File jar = JarBuilder.create().addEntryWithPrefix("BOOT-INF/classes/", t1)
.getJar();
assertJarContents(jar, "BOOT-INF/classes/", t1);
CompilationResult result = new RuntimeJavaCompiler().compile("A",
"import " + t1.name.replace('$', '.') + ";\n" +
"public class A {\n" +
" public static Object run() {\n" +
" return new Test1();\n" +
" }\n" +
"}",
jar.toURI().toString());
assertTrue("Should be no problems: "+result.getCompilationMessages(), result.getCompilationMessages().isEmpty());
try (URLClassLoader cl = new TestClassLoader(t1,descriptorFromResult(result))) {
"import " + t1.name.replace('$', '.') + ";\n" + "public class A {\n"
+ " public static Object run() {\n" + " return new Test1();\n"
+ " }\n" + "}",
jar.toURI().toString());
assertTrue("Should be no problems: " + result.getCompilationMessages(),
result.getCompilationMessages().isEmpty());
try (URLClassLoader cl = new TestClassLoader(t1, descriptorFromResult(result))) {
Class<?> class1 = cl.loadClass("A");
Object invoke = class1.getDeclaredMethod("run").invoke(null);
assertEquals(t1.name, invoke.getClass().getName());
}
}
@Test
public void usingJarWithPackageDeclNestedBootInfLib() throws Exception {
@@ -237,17 +242,15 @@ public class CompilerDependencyResolutionTests {
File jar = JarBuilder.create().addEntry(t1).getJar();
assertJarContents(jar, t1);
// Now stick that jar in another jar!
File jar2 = JarBuilder.create().addEntry("BOOT-INF/lib/inner.jar",jar).getJar();
File jar2 = JarBuilder.create().addEntry("BOOT-INF/lib/inner.jar", jar).getJar();
CompilationResult result = new RuntimeJavaCompiler().compile("A",
"import " + t1.name.replace('$', '.') + ";\n" +
"public class A {\n" +
" public static Object run() {\n" +
" return new Test1();\n" +
" }\n" +
"}",
jar2.toURI().toString());
assertTrue("Should be no problems: "+result.getCompilationMessages(), result.getCompilationMessages().isEmpty());
try (URLClassLoader cl = new TestClassLoader(t1,descriptorFromResult(result))) {
"import " + t1.name.replace('$', '.') + ";\n" + "public class A {\n"
+ " public static Object run() {\n" + " return new Test1();\n"
+ " }\n" + "}",
jar2.toURI().toString());
assertTrue("Should be no problems: " + result.getCompilationMessages(),
result.getCompilationMessages().isEmpty());
try (URLClassLoader cl = new TestClassLoader(t1, descriptorFromResult(result))) {
Class<?> class1 = cl.loadClass("A");
Object invoke = class1.getDeclaredMethod("run").invoke(null);
assertEquals(t1.name, invoke.getClass().getName());
@@ -255,67 +258,42 @@ public class CompilerDependencyResolutionTests {
}
// ---
// Simple classloader that can load from descriptors
class TestClassLoader extends URLClassLoader {
ClassDescriptor[] descriptors;
public TestClassLoader(ClassDescriptor... descriptors) {
super(new URL[0], TestClassLoader.class.getClassLoader());
this.descriptors = descriptors;
}
@Override
protected Class<?> findClass(String name) throws ClassNotFoundException {
for (ClassDescriptor descriptor: descriptors) {
if (descriptor.name.equals(name)) {
return defineClass(descriptor.name, descriptor.bytes, 0, descriptor.bytes.length);
}
}
return super.findClass(name);
}
}
// Simple holder for the result of compilation
static class ClassDescriptor {
final String name;
final byte[] bytes;
final Class<?> clazz;
public ClassDescriptor(String name, byte[] bytes, Class<?> clazz) {
this.name = name;
this.bytes = bytes;
this.clazz = clazz;
}
}
private ClassDescriptor descriptorFromResult(CompilationResult result) {
Class<?> clazz = result.getCompiledClasses().get(0);
return new ClassDescriptor(clazz.getName(),result.getClassBytes(clazz.getName()),clazz);
return new ClassDescriptor(clazz.getName(), result.getClassBytes(clazz.getName()),
clazz);
}
private ClassDescriptor compile(String className, String classSourceCode) {
CompilationResult compile = new RuntimeJavaCompiler().compile(className, classSourceCode);
assertTrue("Should be empty: \n"+compile.getCompilationMessages(), compile.getCompilationMessages().isEmpty());
CompilationResult compile = new RuntimeJavaCompiler().compile(className,
classSourceCode);
assertTrue("Should be empty: \n" + compile.getCompilationMessages(),
compile.getCompilationMessages().isEmpty());
Class<?> clazz = compile.getCompiledClasses().get(0);
return new ClassDescriptor(clazz.getName(),compile.getClassBytes(clazz.getName()), compile.getCompiledClasses().get(0));
return new ClassDescriptor(clazz.getName(),
compile.getClassBytes(clazz.getName()),
compile.getCompiledClasses().get(0));
}
private ClassDescriptor getTestClass(String suffix) {
try {
return compile("Test"+suffix,"package com.test;\npublic class Test"+suffix+" { public static String doit() { return \"T"+suffix+"\";}}\n");
} catch (Exception e) {
return compile("Test" + suffix,
"package com.test;\npublic class Test" + suffix
+ " { public static String doit() { return \"T" + suffix
+ "\";}}\n");
}
catch (Exception e) {
throw new IllegalStateException(e);
}
}
private void assertJarContents(File jar, ClassDescriptor... classdescriptors) {
assertJarContents(jar, "", classdescriptors);
}
private void assertJarContents(File jar, String prefix, ClassDescriptor... classDescriptors) {
private void assertJarContents(File jar, String prefix,
ClassDescriptor... classDescriptors) {
List<String> clazzes = new ArrayList<>();
for (ClassDescriptor classDescriptor : classDescriptors) {
clazzes.add(prefix + classDescriptor.name.replace('.', '/') + ".class");
@@ -335,7 +313,8 @@ public class CompilerDependencyResolutionTests {
fn.accept(nextJarEntry);
}
jarInputStream.close();
} catch (IOException ioe) {
}
catch (IOException ioe) {
ioe.printStackTrace();
}
}
@@ -348,31 +327,55 @@ public class CompilerDependencyResolutionTests {
});
}
// Simple holder for the result of compilation
static class ClassDescriptor {
final String name;
final byte[] bytes;
final Class<?> clazz;
public ClassDescriptor(String name, byte[] bytes, Class<?> clazz) {
this.name = name;
this.bytes = bytes;
this.clazz = clazz;
}
}
static class JarBuilder {
File jarFile;
JarOutputStream jos;
private JarBuilder() {
try {
File newJar = File.createTempFile("test", ".jar");
jarFile = newJar.getAbsoluteFile();
this.jarFile = newJar.getAbsoluteFile();
newJar.delete();
jos = new JarOutputStream(new FileOutputStream(jarFile));
jarFile.deleteOnExit();
} catch (IOException e) {
this.jos = new JarOutputStream(new FileOutputStream(this.jarFile));
this.jarFile.deleteOnExit();
}
catch (IOException e) {
throw new IllegalStateException("Unexpected problem creating file", e);
}
}
public static JarBuilder create() {
return new JarBuilder();
}
public JarBuilder addEntry(String entryName, File entryContentFile) {
try {
ZipEntry ze = new ZipEntry(entryName);
jos.putNextEntry(ze);
jos.write(loadBytes(entryContentFile));
jos.closeEntry();
this.jos.putNextEntry(ze);
this.jos.write(loadBytes(entryContentFile));
this.jos.closeEntry();
return this;
} catch (IOException e) {
}
catch (IOException e) {
throw new IllegalStateException(e);
}
}
@@ -386,7 +389,8 @@ public class CompilerDependencyResolutionTests {
if (bs == null) {
bs = new byte[readCount];
System.arraycopy(buf, 0, bs, 0, readCount);
} else {
}
else {
byte[] newbs = new byte[bs.length + readCount];
System.arraycopy(bs, 0, newbs, 0, bs.length);
System.arraycopy(buf, 0, newbs, bs.length, readCount);
@@ -394,7 +398,8 @@ public class CompilerDependencyResolutionTests {
}
}
return bs;
} catch (IOException ioe) {
}
catch (IOException ioe) {
throw new IllegalStateException(ioe);
}
}
@@ -414,26 +419,47 @@ public class CompilerDependencyResolutionTests {
try {
String n = holder.name.replace('.', '/') + ".class";
ZipEntry ze = new ZipEntry(prefix + n);
jos.putNextEntry(ze);
jos.write(holder.bytes);
jos.closeEntry();
this.jos.putNextEntry(ze);
this.jos.write(holder.bytes);
this.jos.closeEntry();
return this;
} catch (IOException e) {
}
catch (IOException e) {
throw new IllegalStateException(e);
}
}
public static JarBuilder create() {
return new JarBuilder();
}
private File getJar() {
try {
jos.close();
} catch (IOException e) {
this.jos.close();
}
catch (IOException e) {
throw new IllegalStateException("Unable to close jar", e);
}
return jarFile;
return this.jarFile;
}
}
// Simple classloader that can load from descriptors
class TestClassLoader extends URLClassLoader {
ClassDescriptor[] descriptors;
public TestClassLoader(ClassDescriptor... descriptors) {
super(new URL[0], TestClassLoader.class.getClassLoader());
this.descriptors = descriptors;
}
@Override
protected Class<?> findClass(String name) throws ClassNotFoundException {
for (ClassDescriptor descriptor : this.descriptors) {
if (descriptor.name.equals(name)) {
return defineClass(descriptor.name, descriptor.bytes, 0,
descriptor.bytes.length);
}
}
return super.findClass(name);
}
}

View File

@@ -1,5 +1,5 @@
/*
* Copyright 2016-2017 the original author or authors.
* Copyright 2012-2019 the original author or authors.
*
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
@@ -35,14 +35,16 @@ public class ConsumerCompilerTests {
CompiledFunctionFactory<Consumer<String>> compiled = new ConsumerCompiler<String>(
String.class.getName()).compile("foos",
"flux -> flux.subscribe(System.out::println)", "Flux<String>");
assertThat(FunctionFactoryUtils.isFluxConsumer(compiled.getFactoryMethod())).isTrue();
assertThat(FunctionFactoryUtils.isFluxConsumer(compiled.getFactoryMethod()))
.isTrue();
}
@Test
public void consumesString() {
CompiledFunctionFactory<Consumer<String>> compiled = new ConsumerCompiler<String>(
String.class.getName()).compile("foos", "System.out::println", "String");
assertThat(FunctionFactoryUtils.isFluxConsumer(compiled.getFactoryMethod())).isFalse();
assertThat(FunctionFactoryUtils.isFluxConsumer(compiled.getFactoryMethod()))
.isFalse();
}
}

View File

@@ -1,5 +1,5 @@
/*
* Copyright 2016-2017 the original author or authors.
* Copyright 2012-2019 the original author or authors.
*
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
@@ -34,15 +34,19 @@ public class FunctionCompilerTests {
public void transformsFluxString() {
CompiledFunctionFactory<Function<String, String>> compiled = new FunctionCompiler<String, String>(
String.class.getName()).compile("foos",
"flux -> flux.map(v -> v.toUpperCase())", "Flux<String>", "Flux<String>");
assertThat(FunctionFactoryUtils.isFluxFunction(compiled.getFactoryMethod())).isTrue();
"flux -> flux.map(v -> v.toUpperCase())", "Flux<String>",
"Flux<String>");
assertThat(FunctionFactoryUtils.isFluxFunction(compiled.getFactoryMethod()))
.isTrue();
}
@Test
public void transformsString() {
CompiledFunctionFactory<Function<String, String>> compiled = new FunctionCompiler<String, String>(
String.class.getName()).compile("foos", "v -> v.toUpperCase()", "String", "String");
assertThat(FunctionFactoryUtils.isFluxFunction(compiled.getFactoryMethod())).isFalse();
String.class.getName()).compile("foos", "v -> v.toUpperCase()", "String",
"String");
assertThat(FunctionFactoryUtils.isFluxFunction(compiled.getFactoryMethod()))
.isFalse();
assertThat(compiled.getResult().apply("hello")).isEqualTo("HELLO");
}

View File

@@ -1,5 +1,5 @@
/*
* Copyright 2016-2017 the original author or authors.
* Copyright 2012-2019 the original author or authors.
*
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
@@ -36,15 +36,16 @@ public class SupplierCompilerTests {
CompiledFunctionFactory<Supplier<String>> compiled = new SupplierCompiler<String>(
String.class.getName()).compile("foos",
"() -> Flux.just(\"foo\", \"bar\")", "Flux<String>");
assertThat(FunctionFactoryUtils.isFluxSupplier(compiled.getFactoryMethod())).isTrue();
assertThat(FunctionFactoryUtils.isFluxSupplier(compiled.getFactoryMethod()))
.isTrue();
}
@Test
public void supppliesString() {
CompiledFunctionFactory<Supplier<String>> compiled = new SupplierCompiler<String>(
String.class.getName()).compile("foos",
"() -> \"foo\"", "String");
assertThat(FunctionFactoryUtils.isFluxSupplier(compiled.getFactoryMethod())).isFalse();
String.class.getName()).compile("foos", "() -> \"foo\"", "String");
assertThat(FunctionFactoryUtils.isFluxSupplier(compiled.getFactoryMethod()))
.isFalse();
assertThat(compiled.getResult().get()).isEqualTo("foo");
}
@@ -52,9 +53,11 @@ public class SupplierCompilerTests {
public void supppliesFluxStreamString() {
CompiledFunctionFactory<Supplier<Flux<String>>> compiled = new SupplierCompiler<Flux<String>>(
String.class.getName()).compile("foos",
"() -> Flux.interval(Duration.ofMillis(1000)).map(Object::toString)",
"Flux<String>");
assertThat(FunctionFactoryUtils.isFluxSupplier(compiled.getFactoryMethod())).isTrue();
"() -> Flux.interval(Duration.ofMillis(1000)).map(Object::toString)",
"Flux<String>");
assertThat(FunctionFactoryUtils.isFluxSupplier(compiled.getFactoryMethod()))
.isTrue();
assertThat(compiled.getResult().get().blockFirst()).isEqualTo("0");
}
}

View File

@@ -1,5 +1,5 @@
/*
* Copyright 2017 the original author or authors.
* Copyright 2012-2019 the original author or authors.
*
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
@@ -16,9 +16,6 @@
package org.springframework.cloud.function.compiler.java;
import static org.junit.Assert.assertEquals;
import static org.junit.Assert.assertTrue;
import java.io.File;
import java.util.List;
import java.util.Locale;
@@ -26,6 +23,9 @@ import java.util.function.Supplier;
import org.junit.Test;
import static org.junit.Assert.assertEquals;
import static org.junit.Assert.assertTrue;
/**
* @author Andy Clement
*/
@@ -39,27 +39,30 @@ public class RuntimeJavaCompilerTests {
List<CompilationMessage> compilationMessages = cr.getCompilationMessages();
assertTrue(compilationMessages.isEmpty());
}
@Test
public void missingType() throws Exception {
Locale.setDefault(Locale.ENGLISH);
RuntimeJavaCompiler rjc = new RuntimeJavaCompiler();
CompilationResult cr = rjc.compile("A",
"public class A implements java.util.function.Supplier { "+
" public String get() {\n"+
" ExpressionParser parser = new SpelExpressionParser();\n" +
" Expression exp = parser.parseExpression(\"'Hello World'\");\n" +
" String message = (String) exp.getValue();"+
" return message;\n"+
" }\n"+
"}");
CompilationResult cr = rjc.compile("A",
"public class A implements java.util.function.Supplier { "
+ " public String get() {\n"
+ " ExpressionParser parser = new SpelExpressionParser();\n"
+ " Expression exp = parser.parseExpression(\"'Hello World'\");\n"
+ " String message = (String) exp.getValue();"
+ " return message;\n" + " }\n" + "}");
List<CompilationMessage> compilationMessages = cr.getCompilationMessages();
assertEquals(3,compilationMessages.size());
assertTrue(compilationMessages.get(0).getMessage().contains("cannot find symbol"));
assertTrue(compilationMessages.get(0).getMessage().contains("class ExpressionParser"));
assertTrue(compilationMessages.get(1).getMessage().contains("cannot find symbol"));
assertTrue(compilationMessages.get(1).getMessage().contains("class SpelExpressionParser"));
assertTrue(compilationMessages.get(2).getMessage().contains("cannot find symbol"));
assertEquals(3, compilationMessages.size());
assertTrue(
compilationMessages.get(0).getMessage().contains("cannot find symbol"));
assertTrue(compilationMessages.get(0).getMessage()
.contains("class ExpressionParser"));
assertTrue(
compilationMessages.get(1).getMessage().contains("cannot find symbol"));
assertTrue(compilationMessages.get(1).getMessage()
.contains("class SpelExpressionParser"));
assertTrue(
compilationMessages.get(2).getMessage().contains("cannot find symbol"));
assertTrue(compilationMessages.get(2).getMessage().contains("class Expression"));
}
@@ -67,57 +70,57 @@ public class RuntimeJavaCompilerTests {
public void okWithImportedDependencies() throws Exception {
RuntimeJavaCompiler rjc = new RuntimeJavaCompiler();
CompilationResult cr = rjc.compile("A",
"import org.springframework.expression.*;\n"+
"import org.springframework.expression.spel.standard.*;\n"+
"public class A implements java.util.function.Supplier {\n"+
" public String get() {\n"+
" ExpressionParser parser = new SpelExpressionParser();\n" +
" Expression exp = parser.parseExpression(\"'Hello World'\");\n" +
" String message = (String) exp.getValue();\n"+
" return message;\n"+
" }\n"+
"}","maven://org.springframework:spring-expression:4.3.9.RELEASE");
"import org.springframework.expression.*;\n"
+ "import org.springframework.expression.spel.standard.*;\n"
+ "public class A implements java.util.function.Supplier {\n"
+ " public String get() {\n"
+ " ExpressionParser parser = new SpelExpressionParser();\n"
+ " Expression exp = parser.parseExpression(\"'Hello World'\");\n"
+ " String message = (String) exp.getValue();\n"
+ " return message;\n" + " }\n" + "}",
"maven://org.springframework:spring-expression:4.3.9.RELEASE");
List<CompilationMessage> compilationMessages = cr.getCompilationMessages();
assertTrue(compilationMessages.isEmpty());
try (SimpleClassLoader cl = new SimpleClassLoader(this.getClass().getClassLoader())) {
Class<?> clazz = cl.defineClass("A",cr.getClassBytes("A"));
try (SimpleClassLoader cl = new SimpleClassLoader(
this.getClass().getClassLoader())) {
Class<?> clazz = cl.defineClass("A", cr.getClassBytes("A"));
Supplier<String> supplier = (Supplier<String>) clazz.newInstance();
assertEquals("Hello World",supplier.get());
assertEquals("Hello World", supplier.get());
}
}
@Test
public void okWithImportedDependencies2() throws Exception {
RuntimeJavaCompiler rjc = new RuntimeJavaCompiler();
String source =
"import org.joda.time.*;\n"+
"public class A implements java.util.function.Supplier {\n"+
" public String get() {\n"+
" DateTime dt = new DateTime();\n" +
" int month = dt.getMonthOfYear();\n"+
" return String.valueOf(month>0);\n"+
" }\n"+
"}";
CompilationResult cr = rjc.compile("A", source, "maven://joda-time:joda-time:2.9.9");
String source = "import org.joda.time.*;\n"
+ "public class A implements java.util.function.Supplier {\n"
+ " public String get() {\n" + " DateTime dt = new DateTime();\n"
+ " int month = dt.getMonthOfYear();\n"
+ " return String.valueOf(month>0);\n" + " }\n" + "}";
CompilationResult cr = rjc.compile("A", source,
"maven://joda-time:joda-time:2.9.9");
List<CompilationMessage> compilationMessages = cr.getCompilationMessages();
assertTrue(compilationMessages.isEmpty());
List<File> resolvedAdditionalDependencies = cr.getResolvedAdditionalDependencies();
try (SimpleClassLoader cl = new SimpleClassLoader(resolvedAdditionalDependencies, this.getClass().getClassLoader())) {
Class<?> clazz = cl.defineClass("A",cr.getClassBytes("A"));
List<File> resolvedAdditionalDependencies = cr
.getResolvedAdditionalDependencies();
try (SimpleClassLoader cl = new SimpleClassLoader(resolvedAdditionalDependencies,
this.getClass().getClassLoader())) {
Class<?> clazz = cl.defineClass("A", cr.getClassBytes("A"));
Supplier<String> supplier = (Supplier<String>) clazz.newInstance();
assertEquals("true",supplier.get());
assertEquals("true", supplier.get());
}
cr = rjc.compile("A", source,
"maven://org.springframework:spring-expression:4.3.9.RELEASE",
"maven://joda-time:joda-time:2.9.9");
compilationMessages = cr.getCompilationMessages();
assertTrue(compilationMessages.isEmpty());
resolvedAdditionalDependencies = cr.getResolvedAdditionalDependencies();
try (SimpleClassLoader cl = new SimpleClassLoader(resolvedAdditionalDependencies, this.getClass().getClassLoader())) {
Class<?> clazz = cl.defineClass("A",cr.getClassBytes("A"));
try (SimpleClassLoader cl = new SimpleClassLoader(resolvedAdditionalDependencies,
this.getClass().getClassLoader())) {
Class<?> clazz = cl.defineClass("A", cr.getClassBytes("A"));
Supplier<String> supplier = (Supplier<String>) clazz.newInstance();
assertEquals("true",supplier.get());
assertEquals("true", supplier.get());
}
}
@@ -125,34 +128,45 @@ public class RuntimeJavaCompilerTests {
public void dependencyResolution() throws Exception {
// Failure:
RuntimeJavaCompiler rjc = new RuntimeJavaCompiler();
CompilationResult cr = rjc.compile("A",
"public class A {}",
"maven://org.springframework:spring-expression2:4.3.9.RELEASE"); // extra '2' in there
CompilationResult cr = rjc.compile("A", "public class A {}",
"maven://org.springframework:spring-expression2:4.3.9.RELEASE"); // extra
// '2'
// in
// there
List<CompilationMessage> compilationMessages = cr.getCompilationMessages();
assertEquals(1,compilationMessages.size());
// ERROR:org.eclipse.aether.resolution.ArtifactResolutionException: Could not find artifact org.springframework:spring-expression2:jar:4.3.9.RELEASE in spring-snapshots (https://repo.spring.io/libs-snapshot)
assertTrue(compilationMessages.get(0).getMessage().contains("Could not find artifact org.springframework:spring-expression2:jar:4.3.9.RELEASE"));
assertEquals(1, compilationMessages.size());
// ERROR:org.eclipse.aether.resolution.ArtifactResolutionException: Could not find
// artifact org.springframework:spring-expression2:jar:4.3.9.RELEASE in
// spring-snapshots (https://repo.spring.io/libs-snapshot)
assertTrue(compilationMessages.get(0).getMessage().contains(
"Could not find artifact org.springframework:spring-expression2:jar:4.3.9.RELEASE"));
// Failure:
rjc = new RuntimeJavaCompiler();
cr = rjc.compile("A",
"public class A {}",
"trouble://org.springframework:spring-expression:4.3.9.RELEASE"); // rogue prefix (should be "maven:")
cr = rjc.compile("A", "public class A {}",
"trouble://org.springframework:spring-expression:4.3.9.RELEASE"); // rogue
// prefix
// (should
// be
// "maven:")
compilationMessages = cr.getCompilationMessages();
assertEquals(1,compilationMessages.size());
assertTrue(compilationMessages.get(0).toString(),compilationMessages.get(0).getMessage().contains("Unrecognized dependency: "));
assertEquals(1, compilationMessages.size());
assertTrue(compilationMessages.get(0).toString(), compilationMessages.get(0)
.getMessage().contains("Unrecognized dependency: "));
// Success
rjc = new RuntimeJavaCompiler();
cr = rjc.compile("A",
"public class A {}",
"maven://joda-time:joda-time:2.9.9");
cr = rjc.compile("A", "public class A {}", "maven://joda-time:joda-time:2.9.9");
compilationMessages = cr.getCompilationMessages();
assertEquals(0,compilationMessages.size());
List<File> resolvedAdditionalDependencies = cr.getResolvedAdditionalDependencies();
assertEquals(0, compilationMessages.size());
List<File> resolvedAdditionalDependencies = cr
.getResolvedAdditionalDependencies();
assertEquals(1, resolvedAdditionalDependencies.size());
assertTrue("Expected this to end with 'joda-time-2.9.9.jar': "+resolvedAdditionalDependencies.get(0).toString(),
resolvedAdditionalDependencies.get(0).toString().endsWith("joda-time-2.9.9.jar"));
assertTrue(
"Expected this to end with 'joda-time-2.9.9.jar': "
+ resolvedAdditionalDependencies.get(0).toString(),
resolvedAdditionalDependencies.get(0).toString()
.endsWith("joda-time-2.9.9.jar"));
}
}

View File

@@ -1,5 +1,5 @@
/*
* Copyright 2016-2017 the original author or authors.
* Copyright 2012-2019 the original author or authors.
*
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
@@ -21,6 +21,7 @@ import java.util.function.Function;
import java.util.function.Supplier;
import org.junit.Test;
import reactor.core.publisher.Flux;
import org.springframework.cloud.function.compiler.CompiledFunctionFactory;
import org.springframework.cloud.function.compiler.ConsumerCompiler;
@@ -32,8 +33,6 @@ import org.springframework.core.io.ByteArrayResource;
import static org.assertj.core.api.Assertions.assertThat;
import reactor.core.publisher.Flux;
/**
* @author Dave Syer
* @author Oleg Zhurakousky
@@ -44,11 +43,14 @@ public class ByteCodeLoadingFunctionTests {
public void compileConsumer() throws Exception {
CompiledFunctionFactory<Consumer<String>> compiled = new ConsumerCompiler<String>(
String.class.getName()).compile("foos", "System.out::println", "String");
ByteArrayResource resource = new ByteArrayResource(compiled.getGeneratedClassBytes(), "foos");
ByteCodeLoadingConsumer<String> consumer = new ByteCodeLoadingConsumer<>(resource);
ByteArrayResource resource = new ByteArrayResource(
compiled.getGeneratedClassBytes(), "foos");
ByteCodeLoadingConsumer<String> consumer = new ByteCodeLoadingConsumer<>(
resource);
consumer.afterPropertiesSet();
assertThat(consumer instanceof FunctionFactoryMetadata);
assertThat(FunctionFactoryUtils.isFluxConsumer(consumer.getFactoryMethod())).isFalse();
assertThat(FunctionFactoryUtils.isFluxConsumer(consumer.getFactoryMethod()))
.isFalse();
consumer.accept("foo");
}
@@ -56,35 +58,48 @@ public class ByteCodeLoadingFunctionTests {
public void compileSupplier() throws Exception {
CompiledFunctionFactory<Supplier<String>> compiled = new SupplierCompiler<String>(
String.class.getName()).compile("foos", "() -> \"foo\"", "String");
ByteArrayResource resource = new ByteArrayResource(compiled.getGeneratedClassBytes(), "foos");
ByteCodeLoadingSupplier<String> supplier = new ByteCodeLoadingSupplier<>(resource);
ByteArrayResource resource = new ByteArrayResource(
compiled.getGeneratedClassBytes(), "foos");
ByteCodeLoadingSupplier<String> supplier = new ByteCodeLoadingSupplier<>(
resource);
supplier.afterPropertiesSet();
assertThat(supplier instanceof FunctionFactoryMetadata);
assertThat(FunctionFactoryUtils.isFluxSupplier(supplier.getFactoryMethod())).isFalse();
assertThat(FunctionFactoryUtils.isFluxSupplier(supplier.getFactoryMethod()))
.isFalse();
assertThat(supplier.get()).isEqualTo("foo");
}
@Test
public void compileFunction() throws Exception {
CompiledFunctionFactory<Function<String, String>> compiled = new FunctionCompiler<String, String>(
String.class.getName()).compile("foos", "v -> v.toUpperCase()", "String", "String");
ByteArrayResource resource = new ByteArrayResource(compiled.getGeneratedClassBytes(), "foos");
ByteCodeLoadingFunction<String, String> function = new ByteCodeLoadingFunction<>(resource);
String.class.getName()).compile("foos", "v -> v.toUpperCase()", "String",
"String");
ByteArrayResource resource = new ByteArrayResource(
compiled.getGeneratedClassBytes(), "foos");
ByteCodeLoadingFunction<String, String> function = new ByteCodeLoadingFunction<>(
resource);
function.afterPropertiesSet();
assertThat(function instanceof FunctionFactoryMetadata);
assertThat(FunctionFactoryUtils.isFluxFunction(function.getFactoryMethod())).isFalse();
assertThat(FunctionFactoryUtils.isFluxFunction(function.getFactoryMethod()))
.isFalse();
assertThat(function.apply("foo")).isEqualTo("FOO");
}
@Test
public void compileFluxFunction() throws Exception {
CompiledFunctionFactory<Function<Flux<String>, Flux<String>>> compiled = new FunctionCompiler<Flux<String>, Flux<String>>(
String.class.getName()).compile("foos", "flux -> flux.map(v -> v.toUpperCase())", "Flux<String>", "Flux<String>");
ByteArrayResource resource = new ByteArrayResource(compiled.getGeneratedClassBytes(), "foos");
ByteCodeLoadingFunction<Flux<String>, Flux<String>> function = new ByteCodeLoadingFunction<>(resource);
String.class.getName()).compile("foos",
"flux -> flux.map(v -> v.toUpperCase())", "Flux<String>",
"Flux<String>");
ByteArrayResource resource = new ByteArrayResource(
compiled.getGeneratedClassBytes(), "foos");
ByteCodeLoadingFunction<Flux<String>, Flux<String>> function = new ByteCodeLoadingFunction<>(
resource);
function.afterPropertiesSet();
assertThat(function instanceof FunctionFactoryMetadata);
assertThat(FunctionFactoryUtils.isFluxFunction(function.getFactoryMethod())).isTrue();
assertThat(FunctionFactoryUtils.isFluxFunction(function.getFactoryMethod()))
.isTrue();
assertThat(function.apply(Flux.just("foo")).blockFirst()).isEqualTo("FOO");
}
}

View File

@@ -1,5 +1,5 @@
/*
* Copyright 2017 the original author or authors.
* Copyright 2012-2019 the original author or authors.
*
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
@@ -28,12 +28,11 @@ import java.util.stream.Collectors;
import java.util.stream.Stream;
import org.reactivestreams.Publisher;
import reactor.core.publisher.Flux;
import org.springframework.util.ObjectUtils;
import org.springframework.util.ReflectionUtils;
import reactor.core.publisher.Flux;
/**
* <p>
* Miscellaneous utility operations to interrogate functional components (beans)
@@ -54,6 +53,7 @@ import reactor.core.publisher.Flux;
public abstract class FunctionFactoryUtils {
private static final String FLUX_CLASS_NAME = Flux.class.getName();
private static final String PUBLISHER_CLASS_NAME = Publisher.class.getName();
private FunctionFactoryUtils() {
@@ -142,4 +142,5 @@ public abstract class FunctionFactoryUtils {
&& Stream.of(types).allMatch(type -> type.startsWith(FLUX_CLASS_NAME)
|| type.startsWith(PUBLISHER_CLASS_NAME));
}
}

View File

@@ -1,5 +1,5 @@
/*
* Copyright 2016-2017 the original author or authors.
* Copyright 2012-2019 the original author or authors.
*
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
@@ -23,13 +23,12 @@ import java.util.function.Supplier;
import org.junit.Test;
import org.reactivestreams.Publisher;
import reactor.core.publisher.Flux;
import org.springframework.util.ReflectionUtils;
import static org.assertj.core.api.Assertions.assertThat;
import reactor.core.publisher.Flux;
/**
* @author Dave Syer
*
@@ -38,15 +37,17 @@ public class FunctionFactoryUtilsTests {
@Test
public void isFluxConsumer() {
Method method = ReflectionUtils.findMethod(FunctionFactoryUtilsTests.class, "fluxConsumer");
Method method = ReflectionUtils.findMethod(FunctionFactoryUtilsTests.class,
"fluxConsumer");
assertThat(FunctionFactoryUtils.isFluxConsumer(method)).isTrue();
assertThat(FunctionFactoryUtils.isFluxSupplier(method)).isFalse();
assertThat(FunctionFactoryUtils.isFluxFunction(method)).isFalse();
}
@Test
public void isFluxSupplier() {
Method method = ReflectionUtils.findMethod(FunctionFactoryUtilsTests.class, "fluxSupplier");
Method method = ReflectionUtils.findMethod(FunctionFactoryUtilsTests.class,
"fluxSupplier");
assertThat(FunctionFactoryUtils.isFluxSupplier(method)).isTrue();
assertThat(FunctionFactoryUtils.isFluxConsumer(method)).isFalse();
assertThat(FunctionFactoryUtils.isFluxFunction(method)).isFalse();
@@ -54,20 +55,22 @@ public class FunctionFactoryUtilsTests {
@Test
public void isFluxFunction() {
Method method = ReflectionUtils.findMethod(FunctionFactoryUtilsTests.class, "fluxFunction");
Method method = ReflectionUtils.findMethod(FunctionFactoryUtilsTests.class,
"fluxFunction");
assertThat(FunctionFactoryUtils.isFluxFunction(method)).isTrue();
assertThat(FunctionFactoryUtils.isFluxSupplier(method)).isFalse();
assertThat(FunctionFactoryUtils.isFluxConsumer(method)).isFalse();
}
@Test
public void isReactiveFunction() {
Method method = ReflectionUtils.findMethod(FunctionFactoryUtilsTests.class, "reactiveFunction");
Method method = ReflectionUtils.findMethod(FunctionFactoryUtilsTests.class,
"reactiveFunction");
assertThat(FunctionFactoryUtils.isFluxFunction(method)).isTrue();
assertThat(FunctionFactoryUtils.isFluxSupplier(method)).isFalse();
assertThat(FunctionFactoryUtils.isFluxConsumer(method)).isFalse();
}
public Function<Flux<Foo>, Flux<Foo>> fluxFunction() {
return foos -> foos.map(foo -> new Foo());
}
@@ -83,7 +86,9 @@ public class FunctionFactoryUtilsTests {
public Consumer<Flux<Foo>> fluxConsumer() {
return flux -> flux.subscribe(System.out::println);
}
class Foo {}
class Foo {
}
}