#432 Injector - prevent static field injection, add more tests

This commit is contained in:
ljacqu
2016-04-30 10:44:32 +02:00
parent 2c491803d3
commit 908399e271
14 changed files with 211 additions and 45 deletions
@@ -10,6 +10,7 @@ import fr.xephi.authme.initialization.samples.Duration;
import fr.xephi.authme.initialization.samples.FieldInjectionWithAnnotations;
import fr.xephi.authme.initialization.samples.InvalidClass;
import fr.xephi.authme.initialization.samples.InvalidPostConstruct;
import fr.xephi.authme.initialization.samples.InvalidStaticFieldInjection;
import fr.xephi.authme.initialization.samples.PostConstructTestClass;
import fr.xephi.authme.initialization.samples.ProvidedClass;
import fr.xephi.authme.initialization.samples.Size;
@@ -34,7 +35,7 @@ public class AuthMeServiceInitializerTest {
@Before
public void setInitializer() {
initializer = new AuthMeServiceInitializer(ALLOWED_PACKAGE);
initializer.register(new ProvidedClass(""));
initializer.register(ProvidedClass.class, new ProvidedClass(""));
}
@Test
@@ -128,7 +129,7 @@ public class AuthMeServiceInitializerTest {
@Test(expected = RuntimeException.class)
public void shouldThrowForSecondRegistration() {
// given / when / then
initializer.register(new ProvidedClass(""));
initializer.register(ProvidedClass.class, new ProvidedClass(""));
}
@Test(expected = RuntimeException.class)
@@ -152,15 +153,6 @@ public class AuthMeServiceInitializerTest {
initializer.register(String.class, null);
}
@Test(expected = RuntimeException.class)
public void shouldThrowForRegisterOfType() {
// given / when / then
// this most likely means that the second argument was forgotten, so throw an error and force
// the API user to use the explicit register(Class.class, String.class) if really, really desired
// (Though for such generic types, an annotation would be a lot better)
initializer.register(String.class);
}
@Test
public void shouldExecutePostConstructMethod() {
// given
@@ -215,7 +207,7 @@ public class AuthMeServiceInitializerTest {
@Test(expected = RuntimeException.class)
public void shouldThrowForAlreadyRegisteredClass() {
// given
initializer.register(new BetaManager());
initializer.register(BetaManager.class, new BetaManager());
// when / then
initializer.register(BetaManager.class, new BetaManager());
@@ -233,4 +225,10 @@ public class AuthMeServiceInitializerTest {
assertThat(singletonScoped, not(sameInstance(requestScoped)));
}
@Test(expected = RuntimeException.class)
public void shouldThrowForStaticFieldInjection() {
// given / when / then
initializer.newInstance(InvalidStaticFieldInjection.class);
}
}
@@ -0,0 +1,81 @@
package fr.xephi.authme.initialization;
import fr.xephi.authme.initialization.samples.AlphaService;
import fr.xephi.authme.initialization.samples.ClassWithAnnotations;
import fr.xephi.authme.initialization.samples.Duration;
import fr.xephi.authme.initialization.samples.GammaService;
import fr.xephi.authme.initialization.samples.InvalidClass;
import fr.xephi.authme.initialization.samples.ProvidedClass;
import fr.xephi.authme.initialization.samples.Size;
import org.junit.Test;
import static org.hamcrest.Matchers.arrayContaining;
import static org.hamcrest.Matchers.equalTo;
import static org.hamcrest.Matchers.not;
import static org.hamcrest.Matchers.nullValue;
import static org.junit.Assert.assertThat;
/**
* Test for {@link ConstructorInjection}.
*/
public class ConstructorInjectionTest {
@Test
public void shouldReturnDependencies() {
// given
Injection<ClassWithAnnotations> injection = ConstructorInjection.provide(ClassWithAnnotations.class).get();
// when
Class<?>[] dependencies = injection.getDependencies();
Class<?>[] annotations = injection.getDependencyAnnotations();
// then
assertThat(dependencies, arrayContaining(int.class, GammaService.class, long.class));
assertThat(annotations, arrayContaining((Class<?>) Size.class, null, Duration.class));
}
@Test
public void shouldInstantiate() {
// given
GammaService gammaService = new GammaService(
AlphaService.newInstance(new ProvidedClass("")));
Injection<ClassWithAnnotations> injection = ConstructorInjection.provide(ClassWithAnnotations.class).get();
// when
ClassWithAnnotations instance = injection.instantiateWith(-112, gammaService, 19L);
// then
assertThat(instance, not(nullValue()));
assertThat(instance.getSize(), equalTo(-112));
assertThat(instance.getGammaService(), equalTo(gammaService));
assertThat(instance.getDuration(), equalTo(19L));
}
@Test(expected = NullPointerException.class)
public void shouldThrowForNullValue() {
// given
Injection<ClassWithAnnotations> injection = ConstructorInjection.provide(ClassWithAnnotations.class).get();
// when / then
injection.instantiateWith(-112, null, 12L);
}
@Test(expected = RuntimeException.class)
public void shouldThrowUponInstantiationError() {
// given
AlphaService alphaService = AlphaService.newInstance(new ProvidedClass(""));
Injection<InvalidClass> injection = ConstructorInjection.provide(InvalidClass.class).get();
// when
injection.instantiateWith(alphaService, 5);
}
@Test
public void shouldReturnNullForNoConstructorInjection() {
// given / when
Injection<FieldInjection> injection = ConstructorInjection.provide(FieldInjection.class).get();
// then
assertThat(injection, nullValue());
}
}
@@ -1,15 +1,19 @@
package fr.xephi.authme.initialization;
import fr.xephi.authme.initialization.samples.AlphaService;
import fr.xephi.authme.initialization.samples.BadFieldInjection;
import fr.xephi.authme.initialization.samples.BetaManager;
import fr.xephi.authme.initialization.samples.ClassWithAnnotations;
import fr.xephi.authme.initialization.samples.Duration;
import fr.xephi.authme.initialization.samples.FieldInjectionWithAnnotations;
import fr.xephi.authme.initialization.samples.GammaService;
import fr.xephi.authme.initialization.samples.InvalidStaticFieldInjection;
import fr.xephi.authme.initialization.samples.ProvidedClass;
import fr.xephi.authme.initialization.samples.Size;
import org.junit.Test;
import javax.inject.Inject;
import static org.hamcrest.Matchers.arrayContaining;
import static org.hamcrest.Matchers.not;
import static org.hamcrest.Matchers.nullValue;
@@ -51,4 +55,61 @@ public class FieldInjectionTest {
assertThat(betaManager.getDependencies(), arrayContaining(providedClass, gammaService, alphaService));
}
@Test
public void shouldProvideNullForImpossibleFieldInjection() {
// given / when
FieldInjection<BadFieldInjection> injection = FieldInjection.provide(BadFieldInjection.class).get();
// then
assertThat(injection, nullValue());
}
@Test(expected = RuntimeException.class)
public void shouldForwardExceptionDuringInstantiation() {
// given
FieldInjection<ThrowingConstructor> injection = FieldInjection.provide(ThrowingConstructor.class).get();
// when / when
injection.instantiateWith(new ProvidedClass(""));
}
@Test(expected = RuntimeException.class)
public void shouldThrowForInvalidFieldValue() {
// given
ProvidedClass providedClass = new ProvidedClass("");
AlphaService alphaService = AlphaService.newInstance(providedClass);
GammaService gammaService = new GammaService(alphaService);
FieldInjection<BetaManager> injection = FieldInjection.provide(BetaManager.class).get();
// when / then
// Correct order is provided, gamma, alpha
injection.instantiateWith(providedClass, alphaService, gammaService);
}
@Test(expected = NullPointerException.class)
public void shouldThrowForNullValue() {
// given
ProvidedClass providedClass = new ProvidedClass("");
AlphaService alphaService = AlphaService.newInstance(providedClass);
FieldInjection<BetaManager> injection = FieldInjection.provide(BetaManager.class).get();
// when / then
// Correct order is provided, gamma, alpha
injection.instantiateWith(providedClass, null, alphaService);
}
@Test(expected = RuntimeException.class)
public void shouldThrowForStaticFieldInjection() {
// given / when / then
FieldInjection.provide(InvalidStaticFieldInjection.class).get();
}
private static class ThrowingConstructor {
@Inject
private ProvidedClass providedClass;
public ThrowingConstructor() {
throw new UnsupportedOperationException("Exception in constructor");
}
}
}
@@ -5,7 +5,7 @@ import javax.inject.Inject;
/**
* Classes with circular dependencies.
*/
public class CircularClasses {
public abstract class CircularClasses {
public static final class Circular1 {
@Inject
@@ -3,7 +3,7 @@ package fr.xephi.authme.initialization.samples;
import javax.inject.Inject;
/**
* Sample - class dependent on alpha and provided.
* Sample - class dependent on alpha service.
*/
public class GammaService {
@@ -6,7 +6,7 @@ import javax.inject.Inject;
/**
* Class with invalid @PostConstruct method.
*/
public class InvalidPostConstruct {
public abstract class InvalidPostConstruct {
public static final class WithParams {
@Inject
@@ -0,0 +1,17 @@
package fr.xephi.authme.initialization.samples;
import javax.inject.Inject;
/**
* Sample class - attempted field injection on a static member.
*/
public class InvalidStaticFieldInjection {
@Inject
private ProvidedClass providedClass;
@Inject
protected static AlphaService alphaService;
InvalidStaticFieldInjection() { }
}
@@ -4,7 +4,7 @@ import javax.annotation.PostConstruct;
import javax.inject.Inject;
/**
* Sample class for testing the execution of the @PostConstruct method.
* Sample class for testing the execution of @PostConstruct methods.
*/
public class PostConstructTestClass {