You are viewing a plain text version of this content. The canonical link for it is here.
Posted to commits@reef.apache.org by we...@apache.org on 2015/01/23 00:46:41 UTC
[08/51] [partial] incubator-reef git commit: [REEF-93] Move java
sources to lang/java
http://git-wip-us.apache.org/repos/asf/incubator-reef/blob/53ea32cc/lang/java/reef-tang/tang/src/test/java/org/apache/reef/tang/implementation/TestClassHierarchy.java
----------------------------------------------------------------------
diff --git a/lang/java/reef-tang/tang/src/test/java/org/apache/reef/tang/implementation/TestClassHierarchy.java b/lang/java/reef-tang/tang/src/test/java/org/apache/reef/tang/implementation/TestClassHierarchy.java
new file mode 100644
index 0000000..4c4c2cd
--- /dev/null
+++ b/lang/java/reef-tang/tang/src/test/java/org/apache/reef/tang/implementation/TestClassHierarchy.java
@@ -0,0 +1,642 @@
+/**
+ * Licensed to the Apache Software Foundation (ASF) under one
+ * or more contributor license agreements. See the NOTICE file
+ * distributed with this work for additional information
+ * regarding copyright ownership. The ASF licenses this file
+ * to you under the Apache License, Version 2.0 (the
+ * "License"); you may not use this file except in compliance
+ * with the License. You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing,
+ * software distributed under the License is distributed on an
+ * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
+ * KIND, either express or implied. See the License for the
+ * specific language governing permissions and limitations
+ * under the License.
+ */
+package org.apache.reef.tang.implementation;
+
+import org.apache.reef.tang.ClassHierarchy;
+import org.apache.reef.tang.Tang;
+import org.apache.reef.tang.annotations.*;
+import org.apache.reef.tang.exceptions.ClassHierarchyException;
+import org.apache.reef.tang.exceptions.InjectionException;
+import org.apache.reef.tang.exceptions.NameResolutionException;
+import org.apache.reef.tang.types.ClassNode;
+import org.apache.reef.tang.types.ConstructorDef;
+import org.apache.reef.tang.types.Node;
+import org.apache.reef.tang.util.ReflectionUtilities;
+import org.junit.Assert;
+import org.junit.Before;
+import org.junit.Rule;
+import org.junit.Test;
+import org.junit.rules.ExpectedException;
+
+import javax.inject.Inject;
+import java.util.List;
+import java.util.Map;
+import java.util.Set;
+
+@DefaultImplementation(String.class)
+interface BadIfaceDefault {
+}
+
+interface I1 {
+}
+
+public class TestClassHierarchy {
+ public ClassHierarchy ns;
+
+ @Rule
+ public ExpectedException thrown = ExpectedException.none();
+
+ @Before
+ public void setUp() throws Exception {
+ TangImpl.reset();
+ ns = Tang.Factory.getTang().getDefaultClassHierarchy();
+ }
+
+ public String s(Class<?> c) {
+ return ReflectionUtilities.getFullName(c);
+ }
+
+ @Test
+ public void testJavaString() throws NameResolutionException {
+ ns.getNode(ReflectionUtilities.getFullName(String.class));
+ Node n = null;
+ try {
+ n = ns.getNode("java");
+ } catch (NameResolutionException e) {
+ }
+ Assert.assertNull(n);
+ try {
+ n = ns.getNode("java.lang");
+ } catch (NameResolutionException e) {
+ }
+ Assert.assertNull(n);
+ Assert.assertNotNull(ns.getNode("java.lang.String"));
+ try {
+ ns.getNode("com.microsoft");
+ Assert.fail("Didn't get expected exception");
+ } catch (NameResolutionException e) {
+
+ }
+ }
+
+ @Test
+ public void testSimpleConstructors() throws NameResolutionException {
+ ClassNode<?> cls = (ClassNode<?>) ns.getNode(s(SimpleConstructors.class));
+ Assert.assertTrue(cls.getChildren().size() == 0);
+ ConstructorDef<?> def[] = cls.getInjectableConstructors();
+ Assert.assertEquals(3, def.length);
+ }
+
+ @Test
+ public void testNamedParameterConstructors() throws NameResolutionException {
+ ns.getNode(s(NamedParameterConstructors.class));
+ }
+
+ @Test
+ public void testArray() throws NameResolutionException {
+ thrown.expect(UnsupportedOperationException.class);
+ thrown.expectMessage("No support for arrays, etc. Name was: [Ljava.lang.String;");
+ ns.getNode(s(new String[0].getClass()));
+ }
+
+ @Test
+ public void testRepeatConstructorArg() throws NameResolutionException {
+ thrown.expect(ClassHierarchyException.class);
+ thrown.expectMessage("Repeated constructor parameter detected. Cannot inject constructor org.apache.reef.tang.implementation.RepeatConstructorArg(int,int)");
+ ns.getNode(s(RepeatConstructorArg.class));
+ }
+
+ @Test
+ public void testRepeatConstructorArgClasses() throws NameResolutionException {
+ thrown.expect(ClassHierarchyException.class);
+ thrown.expectMessage("Repeated constructor parameter detected. Cannot inject constructor org.apache.reef.tang.implementation.RepeatConstructorArgClasses(org.apache.reef.tang.implementation.A,org.apache.reef.tang.implementation.A)");
+ ns.getNode(s(RepeatConstructorArgClasses.class));
+ }
+
+ @Test
+ public void testLeafRepeatedConstructorArgClasses() throws NameResolutionException {
+ ns.getNode(s(LeafRepeatedConstructorArgClasses.class));
+ }
+
+ @Test
+ public void testNamedRepeatConstructorArgClasses() throws NameResolutionException {
+ ns.getNode(s(NamedRepeatConstructorArgClasses.class));
+ }
+
+ @Test
+ public void testResolveDependencies() throws NameResolutionException {
+ ns.getNode(s(SimpleConstructors.class));
+ Assert.assertNotNull(ns.getNode(ReflectionUtilities
+ .getFullName(String.class)));
+ }
+
+ @Test
+ public void testDocumentedLocalNamedParameter() throws NameResolutionException {
+ ns.getNode(s(DocumentedLocalNamedParameter.class));
+ }
+
+ @Test
+ public void testNamedParameterTypeMismatch() throws NameResolutionException {
+ thrown.expect(ClassHierarchyException.class);
+ thrown.expectMessage("Named parameter type mismatch in org.apache.reef.tang.implementation.NamedParameterTypeMismatch. Constructor expects a java.lang.String but Foo is a java.lang.Integer");
+ ns.getNode(s(NamedParameterTypeMismatch.class));
+ }
+
+ @Test
+ public void testUnannotatedName() throws NameResolutionException {
+ thrown.expect(ClassHierarchyException.class);
+ thrown.expectMessage("Named parameter org.apache.reef.tang.implementation.UnannotatedName is missing its @NamedParameter annotation.");
+ ns.getNode(s(UnannotatedName.class));
+ }
+
+ // TODO: The next three error messages should be more specific about the underlying cause of the failure.
+ @Test
+ public void testAnnotatedNotName() throws NameResolutionException {
+ thrown.expect(ClassHierarchyException.class);
+ thrown.expectMessage("Found illegal @NamedParameter org.apache.reef.tang.implementation.AnnotatedNotName does not implement Name<?>");
+ ns.getNode(s(AnnotatedNotName.class));
+ }
+
+ @Test
+ public void testAnnotatedNameWrongInterface() throws NameResolutionException {
+ thrown.expect(ClassHierarchyException.class);
+ thrown.expectMessage("Found illegal @NamedParameter org.apache.reef.tang.implementation.AnnotatedNameWrongInterface does not implement Name<?>");
+ ns.getNode(s(AnnotatedNameWrongInterface.class));
+ }
+
+ @Test
+ public void testAnnotatedNameNotGenericInterface() throws NameResolutionException {
+ thrown.expect(ClassHierarchyException.class);
+ thrown.expectMessage("Found illegal @NamedParameter org.apache.reef.tang.implementation.AnnotatedNameNotGenericInterface does not implement Name<?>");
+ ns.getNode(s(AnnotatedNameNotGenericInterface.class));
+ }
+
+ @Test
+ public void testAnnotatedNameMultipleInterfaces() throws NameResolutionException {
+ thrown.expect(ClassHierarchyException.class);
+ thrown.expectMessage("Named parameter org.apache.reef.tang.implementation.AnnotatedNameMultipleInterfaces implements multiple interfaces. It is only allowed to implement Name<T>");
+ ns.getNode(s(AnnotatedNameMultipleInterfaces.class));
+ }
+
+ @Test
+ public void testUnAnnotatedNameMultipleInterfaces() throws NameResolutionException {
+ thrown.expect(ClassHierarchyException.class);
+ thrown.expectMessage("Named parameter org.apache.reef.tang.implementation.UnAnnotatedNameMultipleInterfaces is missing its @NamedParameter annotation.");
+ ns.getNode(s(UnAnnotatedNameMultipleInterfaces.class));
+ }
+
+ @Test
+ public void testNameWithConstructor() throws NameResolutionException {
+ thrown.expect(ClassHierarchyException.class);
+ thrown.expectMessage("Named parameter org.apache.reef.tang.implementation.NameWithConstructor has a constructor. Named parameters must not declare any constructors.");
+ ns.getNode(s(NameWithConstructor.class));
+ }
+
+ @Test
+ public void testNameWithZeroArgInject() throws NameResolutionException {
+ thrown.expect(ClassHierarchyException.class);
+ thrown.expectMessage("Named parameter org.apache.reef.tang.implementation.NameWithZeroArgInject has an injectable constructor. Named parameters must not declare any constructors.");
+ ns.getNode(s(NameWithZeroArgInject.class));
+ }
+
+ @Test
+ public void testGenericTorture1() throws NameResolutionException {
+ ns.getNode(s(GenericTorture1.class));
+ }
+
+ @Test
+ public void testGenericTorture2() throws NameResolutionException {
+ ns.getNode(s(GenericTorture2.class));
+ }
+
+ @Test
+ public void testGenericTorture3() throws NameResolutionException {
+ ns.getNode(s(GenericTorture3.class));
+ }
+
+ @Test
+ public void testGenericTorture4() throws NameResolutionException {
+ ns.getNode(s(GenericTorture4.class));
+ }
+
+ @Test
+ public void testGenericTorture5() throws NameResolutionException {
+ ns.getNode(s(GenericTorture5.class));
+ }
+
+ @Test
+ public void testGenericTorture6() throws NameResolutionException {
+ ns.getNode(s(GenericTorture6.class));
+ }
+
+ @Test
+ public void testGenericTorture7() throws NameResolutionException {
+ ns.getNode(s(GenericTorture7.class));
+ }
+
+ @Test
+ public void testGenericTorture8() throws NameResolutionException {
+ ns.getNode(s(GenericTorture8.class));
+ }
+
+ @Test
+ public void testGenericTorture9() throws NameResolutionException {
+ ns.getNode(s(GenericTorture9.class));
+ }
+
+ @Test
+ public void testGenericTorture10() throws NameResolutionException {
+ ns.getNode(s(GenericTorture10.class));
+ }
+
+ @Test
+ public void testGenericTorture11() throws NameResolutionException {
+ ns.getNode(s(GenericTorture11.class));
+ }
+
+ @Test
+ public void testGenericTorture12() throws NameResolutionException {
+ ns.getNode(s(GenericTorture12.class));
+ }
+
+ @Test
+ public void testInjectNonStaticLocalArgClass() throws NameResolutionException {
+ ns.getNode(s(InjectNonStaticLocalArgClass.class));
+ }
+
+ @Test(expected = ClassHierarchyException.class)
+ public void testInjectNonStaticLocalType() throws NameResolutionException {
+ ns.getNode(s(InjectNonStaticLocalType.class));
+ }
+
+ @Test(expected = ClassHierarchyException.class)
+ public void testConflictingShortNames() throws NameResolutionException {
+ ns.getNode(s(ShortNameFooA.class));
+ ns.getNode(s(ShortNameFooB.class));
+ }
+
+ @Test
+ public void testOKShortNames() throws NameResolutionException {
+ ns.getNode(s(ShortNameFooA.class));
+ }
+
+ @Test
+ public void testRoundTripInnerClassNames() throws ClassNotFoundException, NameResolutionException {
+ Node n = ns.getNode(s(Nested.Inner.class));
+ Class.forName(n.getFullName());
+ }
+
+ @Test
+ public void testRoundTripAnonInnerClassNames() throws ClassNotFoundException, NameResolutionException {
+ Node n = ns.getNode(s(AnonNested.x.getClass()));
+ Node m = ns.getNode(s(AnonNested.y.getClass()));
+ Assert.assertNotSame(n.getFullName(), m.getFullName());
+ Class<?> c = Class.forName(n.getFullName());
+ Class<?> d = Class.forName(m.getFullName());
+ Assert.assertNotSame(c, d);
+ }
+
+ @Test
+ public void testUnitIsInjectable() throws InjectionException, NameResolutionException {
+ ClassNode<?> n = (ClassNode<?>) ns.getNode(s(OuterUnitTH.class));
+ Assert.assertTrue(n.isUnit());
+ Assert.assertTrue(n.isInjectionCandidate());
+ }
+
+ @Test
+ public void testBadUnitDecl() throws NameResolutionException {
+ thrown.expect(ClassHierarchyException.class);
+ thrown.expectMessage("Detected explicit constructor in class enclosed in @Unit org.apache.reef.tang.implementation.OuterUnitBad$InA Such constructors are disallowed.");
+
+ ns.getNode(s(OuterUnitBad.class));
+ }
+
+ @Test
+ public void nameCantBindWrongSubclassAsDefault() throws NameResolutionException {
+ thrown.expect(ClassHierarchyException.class);
+ thrown.expectMessage("class org.apache.reef.tang.implementation.BadName defines a default class java.lang.Integer with a raw type that does not extend of its target's raw type class java.lang.String");
+
+ ns.getNode(s(BadName.class));
+ }
+
+ @Test
+ public void ifaceCantBindWrongImplAsDefault() throws NameResolutionException {
+ thrown.expect(ClassHierarchyException.class);
+ thrown.expectMessage("interface org.apache.reef.tang.implementation.BadIfaceDefault declares its default implementation to be non-subclass class java.lang.String");
+ ns.getNode(s(BadIfaceDefault.class));
+ }
+
+ @Test
+ public void testParseableDefaultClassNotOK() throws NameResolutionException {
+ thrown.expect(ClassHierarchyException.class);
+ thrown.expectMessage("Named parameter org.apache.reef.tang.implementation.BadParsableDefaultClass defines default implementation for parsable type java.lang.String");
+ ns.getNode(s(BadParsableDefaultClass.class));
+ }
+
+ @Test
+ public void testDanglingUnit() throws NameResolutionException {
+ thrown.expect(ClassHierarchyException.class);
+ thrown.expectMessage("Class org.apache.reef.tang.implementation.DanglingUnit has an @Unit annotation, but no non-static inner classes. Such @Unit annotations would have no effect, and are therefore disallowed.");
+
+ ns.getNode(s(DanglingUnit.class));
+
+ }
+
+ @Test
+ public void testNonInjectableParam() throws NameResolutionException {
+ thrown.expect(ClassHierarchyException.class);
+ thrown.expectMessage("public org.apache.reef.tang.implementation.NonInjectableParam(int) is not injectable, but it has an @Parameter annotation.");
+ ns.getNode(s(NonInjectableParam.class));
+ }
+
+}
+
+@NamedParameter(default_class = String.class)
+class BadParsableDefaultClass implements Name<String> {
+}
+
+@NamedParameter(default_class = Integer.class)
+class BadName implements Name<String> {
+}
+
+class SimpleConstructors {
+
+ @Inject
+ public SimpleConstructors() {
+ }
+
+ @Inject
+ public SimpleConstructors(int x) {
+ }
+
+ public SimpleConstructors(String x) {
+ }
+
+ @Inject
+ public SimpleConstructors(int x, String y) {
+ }
+}
+
+class NamedParameterConstructors {
+
+ @Inject
+ public NamedParameterConstructors(String x, @Parameter(X.class) String y) {
+ }
+
+ ;
+
+ @NamedParameter()
+ class X implements Name<String> {
+ }
+}
+
+class RepeatConstructorArg {
+ public
+ @Inject
+ RepeatConstructorArg(int x, int y) {
+ }
+}
+
+class A {
+}
+
+class RepeatConstructorArgClasses {
+ public
+ @Inject
+ RepeatConstructorArgClasses(A x, A y) {
+ }
+}
+
+class LeafRepeatedConstructorArgClasses {
+
+ static class A {
+ class AA {
+ }
+ }
+
+ static class B {
+ class AA {
+ }
+ }
+
+ static class C {
+ @Inject
+ C(A.AA a, B.AA b) {
+ }
+ }
+}
+
+@NamedParameter()
+class AA implements Name<A> {
+}
+
+@NamedParameter()
+class BB implements Name<A> {
+}
+
+class NamedRepeatConstructorArgClasses {
+ public
+ @Inject
+ NamedRepeatConstructorArgClasses(@Parameter(AA.class) A x,
+ @Parameter(BB.class) A y) {
+ }
+}
+
+class DocumentedLocalNamedParameter {
+
+ @Inject
+ public DocumentedLocalNamedParameter(@Parameter(Foo.class) String s) {
+ }
+
+ @NamedParameter(doc = "doc stuff", default_value = "some value")
+ final class Foo implements Name<String> {
+ }
+}
+
+class NamedParameterTypeMismatch {
+
+ @Inject
+ public NamedParameterTypeMismatch(@Parameter(Foo.class) String s) {
+ }
+
+ @NamedParameter(doc = "doc.stuff", default_value = "1")
+ final class Foo implements Name<Integer> {
+ }
+}
+
+class UnannotatedName implements Name<String> {
+}
+
+@NamedParameter(doc = "c")
+class AnnotatedNotName {
+}
+
+@NamedParameter(doc = "c")
+class AnnotatedNameWrongInterface implements I1 {
+}
+
+@SuppressWarnings("rawtypes")
+@NamedParameter(doc = "c")
+class AnnotatedNameNotGenericInterface implements Name {
+}
+
+class UnAnnotatedNameMultipleInterfaces implements Name<Object>, I1 {
+}
+
+@NamedParameter(doc = "c")
+class AnnotatedNameMultipleInterfaces implements Name<Object>, I1 {
+}
+
+@NamedParameter()
+class NameWithConstructor implements Name<Object> {
+ private NameWithConstructor(int i) {
+ }
+}
+
+@NamedParameter()
+class NameWithZeroArgInject implements Name<Object> {
+ @Inject
+ public NameWithZeroArgInject() {
+ }
+}
+
+@NamedParameter()
+class GenericTorture1 implements Name<Set<String>> {
+}
+
+@NamedParameter()
+class GenericTorture2 implements Name<Set<?>> {
+}
+
+@NamedParameter()
+class GenericTorture3 implements Name<Set<Set<String>>> {
+}
+
+@SuppressWarnings("rawtypes")
+@NamedParameter()
+class GenericTorture4 implements Name<Set<Set>> {
+}
+
+@NamedParameter()
+class GenericTorture5 implements Name<Map<Set<String>, Set<String>>> {
+}
+
+@SuppressWarnings("rawtypes")
+@NamedParameter()
+class GenericTorture6 implements Name<Map<Set, Set<String>>> {
+}
+
+@SuppressWarnings("rawtypes")
+@NamedParameter()
+class GenericTorture7 implements Name<Map<Set<String>, Set>> {
+}
+
+@NamedParameter()
+class GenericTorture8 implements Name<Map<String, String>> {
+}
+
+@SuppressWarnings("rawtypes")
+@NamedParameter()
+class GenericTorture9 implements Name<Map<Set, Set>> {
+}
+
+@NamedParameter()
+class GenericTorture10 implements Name<List<String>> {
+}
+
+@NamedParameter()
+class GenericTorture11 implements Name<List<?>> {
+}
+
+@NamedParameter()
+class GenericTorture12 implements Name<List<List<String>>> {
+}
+
+class InjectNonStaticLocalArgClass {
+ @Inject
+ InjectNonStaticLocalArgClass(NonStaticLocal x) {
+ }
+
+ class NonStaticLocal {
+ }
+}
+
+class InjectNonStaticLocalType {
+ class NonStaticLocal {
+ @Inject
+ NonStaticLocal(NonStaticLocal x) {
+ }
+ }
+}
+
+@NamedParameter(short_name = "foo")
+class ShortNameFooA implements Name<String> {
+}
+
+@NamedParameter(short_name = "foo")
+class ShortNameFooB implements Name<Integer> {
+}
+
+class Nested {
+ class Inner {
+ }
+}
+
+class AnonNested {
+ static X x = new X() {
+ @SuppressWarnings("unused")
+ int i;
+ };
+ static X y = new X() {
+ @SuppressWarnings("unused")
+ int j;
+ };
+
+ static interface X {
+ }
+}
+
+@Unit
+class OuterUnitBad {
+ class InA {
+ @Inject
+ InA() {
+ }
+ }
+
+ class InB {
+ }
+}
+
+@Unit
+class OuterUnitTH {
+ class InA {
+ }
+
+ class InB {
+ }
+}
+
+@Unit
+class DanglingUnit {
+ @Inject
+ DanglingUnit() {
+ }
+
+ static class DoesntCount {
+ }
+}
+
+class SomeName implements Name<Integer> {
+}
+
+class NonInjectableParam {
+ public NonInjectableParam(@Parameter(SomeName.class) int i) {
+ }
+}
\ No newline at end of file
http://git-wip-us.apache.org/repos/asf/incubator-reef/blob/53ea32cc/lang/java/reef-tang/tang/src/test/java/org/apache/reef/tang/implementation/java/TestConfigurationBuilder.java
----------------------------------------------------------------------
diff --git a/lang/java/reef-tang/tang/src/test/java/org/apache/reef/tang/implementation/java/TestConfigurationBuilder.java b/lang/java/reef-tang/tang/src/test/java/org/apache/reef/tang/implementation/java/TestConfigurationBuilder.java
new file mode 100644
index 0000000..7a65cd3
--- /dev/null
+++ b/lang/java/reef-tang/tang/src/test/java/org/apache/reef/tang/implementation/java/TestConfigurationBuilder.java
@@ -0,0 +1,60 @@
+/**
+ * Licensed to the Apache Software Foundation (ASF) under one
+ * or more contributor license agreements. See the NOTICE file
+ * distributed with this work for additional information
+ * regarding copyright ownership. The ASF licenses this file
+ * to you under the Apache License, Version 2.0 (the
+ * "License"); you may not use this file except in compliance
+ * with the License. You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing,
+ * software distributed under the License is distributed on an
+ * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
+ * KIND, either express or implied. See the License for the
+ * specific language governing permissions and limitations
+ * under the License.
+ */
+package org.apache.reef.tang.implementation.java;
+
+import org.apache.reef.tang.Tang;
+import org.apache.reef.tang.annotations.Name;
+import org.apache.reef.tang.annotations.NamedParameter;
+import org.apache.reef.tang.annotations.Parameter;
+import org.junit.Rule;
+import org.junit.Test;
+import org.junit.rules.ExpectedException;
+
+import javax.inject.Inject;
+
+/**
+ * TestConfigurationBuilder
+ */
+public class TestConfigurationBuilder {
+ @Rule
+ public ExpectedException thrown = ExpectedException.none();
+
+ @Test
+ public void nullStringVaueTest() {
+ thrown.expect(IllegalStateException.class);
+ thrown.expectMessage("The value null set to the named parameter is illegal: class org.apache.reef.tang.implementation.java.TestConfigurationBuilder$NamedParamterNoDefault$NamedString");
+
+ Tang.Factory.getTang().newConfigurationBuilder()
+ .bindNamedParameter(NamedParamterNoDefault.NamedString.class, (String) null)
+ .build();
+ }
+
+ static class NamedParamterNoDefault {
+ final private String str;
+
+ @Inject
+ NamedParamterNoDefault(@Parameter(NamedString.class) String str) {
+ this.str = str;
+ }
+
+ @NamedParameter()
+ class NamedString implements Name<String> {
+ }
+ }
+}
http://git-wip-us.apache.org/repos/asf/incubator-reef/blob/53ea32cc/lang/java/reef-tang/tang/src/test/java/org/apache/reef/tang/implementation/java/TestParameterParser.java
----------------------------------------------------------------------
diff --git a/lang/java/reef-tang/tang/src/test/java/org/apache/reef/tang/implementation/java/TestParameterParser.java b/lang/java/reef-tang/tang/src/test/java/org/apache/reef/tang/implementation/java/TestParameterParser.java
new file mode 100644
index 0000000..0425920
--- /dev/null
+++ b/lang/java/reef-tang/tang/src/test/java/org/apache/reef/tang/implementation/java/TestParameterParser.java
@@ -0,0 +1,245 @@
+/**
+ * Licensed to the Apache Software Foundation (ASF) under one
+ * or more contributor license agreements. See the NOTICE file
+ * distributed with this work for additional information
+ * regarding copyright ownership. The ASF licenses this file
+ * to you under the Apache License, Version 2.0 (the
+ * "License"); you may not use this file except in compliance
+ * with the License. You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing,
+ * software distributed under the License is distributed on an
+ * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
+ * KIND, either express or implied. See the License for the
+ * specific language governing permissions and limitations
+ * under the License.
+ */
+package org.apache.reef.tang.implementation.java;
+
+import org.apache.reef.tang.ExternalConstructor;
+import org.apache.reef.tang.JavaConfigurationBuilder;
+import org.apache.reef.tang.Tang;
+import org.apache.reef.tang.annotations.Name;
+import org.apache.reef.tang.annotations.NamedParameter;
+import org.apache.reef.tang.annotations.Parameter;
+import org.apache.reef.tang.exceptions.BindException;
+import org.apache.reef.tang.exceptions.InjectionException;
+import org.apache.reef.tang.formats.ParameterParser;
+import org.apache.reef.tang.util.ReflectionUtilities;
+import org.junit.Assert;
+import org.junit.Rule;
+import org.junit.Test;
+import org.junit.rules.ExpectedException;
+
+import javax.inject.Inject;
+
+public class TestParameterParser {
+
+ @Rule
+ public ExpectedException thrown = ExpectedException.none();
+
+ @Test
+ public void testParameterParser() throws BindException {
+ ParameterParser p = new ParameterParser();
+ p.addParser(FooParser.class);
+ Foo f = p.parse(Foo.class, "woot");
+ Assert.assertEquals(f.s, "woot");
+ }
+
+ @Test
+ public void testUnregisteredParameterParser() throws BindException {
+ thrown.expect(UnsupportedOperationException.class);
+ thrown.expectMessage("Don't know how to parse a org.apache.reef.tang.implementation.java.TestParameterParser$Foo");
+ ParameterParser p = new ParameterParser();
+ //p.addParser(FooParser.class);
+ Foo f = p.parse(Foo.class, "woot");
+ Assert.assertEquals(f.s, "woot");
+ }
+
+ @Test
+ public void testReturnSubclass() throws BindException {
+ ParameterParser p = new ParameterParser();
+ p.addParser(BarParser.class);
+ Bar f = (Bar) p.parse(Foo.class, "woot");
+ Assert.assertEquals(f.s, "woot");
+
+ }
+
+ @Test
+ public void testGoodMerge() throws BindException {
+ ParameterParser old = new ParameterParser();
+ old.addParser(BarParser.class);
+ ParameterParser nw = new ParameterParser();
+ nw.mergeIn(old);
+ nw.parse(Foo.class, "woot");
+ }
+
+ @Test
+ public void testGoodMerge2() throws BindException {
+ ParameterParser old = new ParameterParser();
+ old.addParser(BarParser.class);
+ ParameterParser nw = new ParameterParser();
+ nw.addParser(BarParser.class);
+ nw.mergeIn(old);
+ nw.parse(Foo.class, "woot");
+ }
+
+ @Test
+ public void testBadMerge() throws BindException {
+ thrown.expect(IllegalArgumentException.class);
+ thrown.expectMessage("Conflict detected when merging parameter parsers! To parse org.apache.reef.tang.implementation.java.TestParameterParser$Foo I have a: org.apache.reef.tang.implementation.java.TestParameterParser$FooParser the other instance has a: org.apache.reef.tang.implementation.java.TestParameterParser$BarParser");
+ ParameterParser old = new ParameterParser();
+ old.addParser(BarParser.class);
+ ParameterParser nw = new ParameterParser();
+ nw.addParser(FooParser.class);
+ nw.mergeIn(old);
+ }
+
+ @SuppressWarnings("unchecked")
+ @Test
+ public void testEndToEnd() throws BindException, InjectionException {
+ Tang tang = Tang.Factory.getTang();
+ JavaConfigurationBuilder cb = tang.newConfigurationBuilder(BarParser.class);
+ cb.bindNamedParameter(SomeNamedFoo.class, "hdfs://woot");
+ ILikeBars ilb = tang.newInjector(cb.build()).getInstance(ILikeBars.class);
+ Assert.assertNotNull(ilb);
+ }
+
+ @SuppressWarnings("unchecked")
+ @Test
+ public void testDelegatingParser() throws BindException, InjectionException, ClassNotFoundException {
+ Tang tang = Tang.Factory.getTang();
+ JavaConfigurationBuilder cb = tang.newConfigurationBuilder(TypeParser.class);
+
+ JavaConfigurationBuilder cb2 = tang.newConfigurationBuilder(cb.build());
+
+ cb2.bind(ReflectionUtilities.getFullName(ParseName.class), "a");
+
+ ParseableType t = tang.newInjector(cb2.build()).getNamedInstance(ParseName.class);
+ Assert.assertTrue(t instanceof ParseTypeA);
+
+ cb2 = tang.newConfigurationBuilder(cb.build());
+
+ cb2.bind(ReflectionUtilities.getFullName(ParseNameB.class), "b");
+ cb2.bindNamedParameter(ParseNameA.class, "a");
+ tang.newInjector(cb2.build()).getInstance(NeedsA.class);
+ tang.newInjector(cb2.build()).getInstance(NeedsB.class);
+
+ }
+
+ private static class FooParser implements ExternalConstructor<Foo> {
+ private final Foo foo;
+
+ @Inject
+ public FooParser(String s) {
+ this.foo = new Foo(s);
+ }
+
+ @Override
+ public Foo newInstance() {
+ return foo;
+ }
+ }
+
+ private static class BarParser implements ExternalConstructor<Foo> {
+ private final Bar bar;
+
+ @Inject
+ public BarParser(String s) {
+ this.bar = new Bar(s);
+ }
+
+ @Override
+ public Bar newInstance() {
+ return bar;
+ }
+ }
+
+ private static class Foo {
+ public final String s;
+
+ public Foo(String s) {
+ this.s = s;
+ }
+ }
+
+ private static class Bar extends Foo {
+ public Bar(String s) {
+ super(s);
+ }
+ }
+
+ @NamedParameter
+ private static class SomeNamedFoo implements Name<Foo> {
+ }
+
+ private static class ILikeBars {
+ @Inject
+ ILikeBars(@Parameter(SomeNamedFoo.class) Foo bar) {
+ Bar b = (Bar) bar;
+ Assert.assertEquals(b.s, "hdfs://woot");
+ }
+ }
+
+ private static class ParseableType {
+ }
+
+ private static class ParseTypeA extends ParseableType {
+
+ }
+
+ private static class ParseTypeB extends ParseableType {
+
+ }
+
+ private static class TypeParser implements ExternalConstructor<ParseableType> {
+ ParseableType instance;
+
+ @Inject
+ public TypeParser(String s) {
+ if (s.equals("a")) {
+ instance = new ParseTypeA();
+ }
+ if (s.equals("b")) {
+ instance = new ParseTypeB();
+ }
+
+ }
+
+ @Override
+ public ParseableType newInstance() {
+ return instance;
+ }
+ }
+
+ @NamedParameter()
+ private static class ParseName implements Name<ParseableType> {
+
+ }
+
+ @NamedParameter()
+ private static class ParseNameA implements Name<ParseableType> {
+
+ }
+
+ @NamedParameter()
+ private static class ParseNameB implements Name<ParseTypeB> {
+
+ }
+
+ private static class NeedsA {
+ @Inject
+ public NeedsA(@Parameter(ParseNameA.class) ParseableType a) {
+ Assert.assertTrue(a instanceof ParseTypeA);
+ }
+ }
+
+ private static class NeedsB {
+ @Inject
+ public NeedsB(@Parameter(ParseNameB.class) ParseTypeB b) {
+ Assert.assertTrue(b instanceof ParseTypeB);
+ }
+ }
+}
http://git-wip-us.apache.org/repos/asf/incubator-reef/blob/53ea32cc/lang/java/reef-tang/tang/src/test/java/org/apache/reef/tang/implementation/protobuf/TestClassHierarchyRoundTrip.java
----------------------------------------------------------------------
diff --git a/lang/java/reef-tang/tang/src/test/java/org/apache/reef/tang/implementation/protobuf/TestClassHierarchyRoundTrip.java b/lang/java/reef-tang/tang/src/test/java/org/apache/reef/tang/implementation/protobuf/TestClassHierarchyRoundTrip.java
new file mode 100644
index 0000000..238f979
--- /dev/null
+++ b/lang/java/reef-tang/tang/src/test/java/org/apache/reef/tang/implementation/protobuf/TestClassHierarchyRoundTrip.java
@@ -0,0 +1,401 @@
+/**
+ * Licensed to the Apache Software Foundation (ASF) under one
+ * or more contributor license agreements. See the NOTICE file
+ * distributed with this work for additional information
+ * regarding copyright ownership. The ASF licenses this file
+ * to you under the Apache License, Version 2.0 (the
+ * "License"); you may not use this file except in compliance
+ * with the License. You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing,
+ * software distributed under the License is distributed on an
+ * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
+ * KIND, either express or implied. See the License for the
+ * specific language governing permissions and limitations
+ * under the License.
+ */
+package org.apache.reef.tang.implementation.protobuf;
+
+import org.apache.reef.tang.Tang;
+import org.apache.reef.tang.exceptions.InjectionException;
+import org.apache.reef.tang.exceptions.NameResolutionException;
+import org.apache.reef.tang.implementation.TangImpl;
+import org.apache.reef.tang.implementation.TestClassHierarchy;
+import org.junit.Assert;
+import org.junit.Test;
+
+import java.io.File;
+import java.io.IOException;
+
+public class TestClassHierarchyRoundTrip extends TestClassHierarchy {
+
+ private void setup1() {
+ TangImpl.reset();
+ ns = Tang.Factory.getTang().getDefaultClassHierarchy();
+ }
+
+ private void setup2() {
+ TangImpl.reset();
+ ns = new ProtocolBufferClassHierarchy(ProtocolBufferClassHierarchy.serialize(ns));
+ }
+
+ private void setup3() {
+ TangImpl.reset();
+ try {
+ final File file = java.io.File.createTempFile("testProto", "bin");
+ ProtocolBufferClassHierarchy.serialize(file, ns);
+ ns = ProtocolBufferClassHierarchy.deserialize(file);
+ file.delete();
+ } catch (IOException e) {
+ Assert.fail(String.format("IOException when serialize/deserialize proto buffer file ", e));
+ }
+ }
+
+ @Test
+ @Override
+ public void testJavaString() throws NameResolutionException {
+ setup1();
+ super.testJavaString();
+ setup2();
+ super.testJavaString();
+ setup3();
+ super.testJavaString();
+ }
+
+ @Test
+ @Override
+ public void testSimpleConstructors() throws NameResolutionException {
+ setup1();
+ super.testSimpleConstructors();
+ setup2();
+ super.testSimpleConstructors();
+ setup3();
+ super.testSimpleConstructors();
+ }
+
+ @Test
+ @Override
+ public void testNamedParameterConstructors() throws NameResolutionException {
+ setup1();
+ super.testNamedParameterConstructors();
+ setup2();
+ super.testNamedParameterConstructors();
+ setup3();
+ super.testNamedParameterConstructors();
+ }
+
+ @Test
+ @Override
+ public void testArray() throws NameResolutionException {
+ setup1();
+ super.testArray();
+ setup2();
+ super.testArray();
+ setup3();
+ super.testArray();
+ }
+
+ @Test
+ @Override
+ public void testRepeatConstructorArg() throws NameResolutionException {
+ setup1();
+ super.testRepeatConstructorArg();
+ setup2();
+ super.testRepeatConstructorArg();
+ setup3();
+ super.testRepeatConstructorArg();
+ }
+
+ @Test
+ @Override
+ public void testRepeatConstructorArgClasses() throws NameResolutionException {
+ setup1();
+ super.testRepeatConstructorArgClasses();
+ setup2();
+ super.testRepeatConstructorArgClasses();
+ setup3();
+ super.testRepeatConstructorArgClasses();
+ }
+
+ @Test
+ @Override
+ public void testLeafRepeatedConstructorArgClasses() throws NameResolutionException {
+ setup1();
+ super.testLeafRepeatedConstructorArgClasses();
+ setup2();
+ super.testLeafRepeatedConstructorArgClasses();
+ setup3();
+ super.testLeafRepeatedConstructorArgClasses();
+ }
+
+ @Test
+ @Override
+ public void testNamedRepeatConstructorArgClasses() throws NameResolutionException {
+ setup1();
+ super.testNamedRepeatConstructorArgClasses();
+ setup2();
+ super.testNamedRepeatConstructorArgClasses();
+ setup3();
+ super.testNamedRepeatConstructorArgClasses();
+ }
+
+ @Test
+ @Override
+ public void testResolveDependencies() throws NameResolutionException {
+ setup1();
+ super.testResolveDependencies();
+ setup2();
+ super.testResolveDependencies();
+ setup3();
+ super.testResolveDependencies();
+ }
+
+ @Test
+ @Override
+ public void testDocumentedLocalNamedParameter() throws NameResolutionException {
+ setup1();
+ super.testDocumentedLocalNamedParameter();
+ setup2();
+ super.testDocumentedLocalNamedParameter();
+ setup3();
+ super.testDocumentedLocalNamedParameter();
+ }
+
+ @Test
+ @Override
+ public void testNamedParameterTypeMismatch() throws NameResolutionException {
+ setup1();
+ super.testNamedParameterTypeMismatch();
+ setup2();
+ super.testNamedParameterTypeMismatch();
+ setup3();
+ super.testNamedParameterTypeMismatch();
+ }
+
+ @Test
+ @Override
+ public void testUnannotatedName() throws NameResolutionException {
+ setup1();
+ super.testUnannotatedName();
+ setup2();
+ super.testUnannotatedName();
+ setup3();
+ super.testUnannotatedName();
+ }
+
+ @Test
+ @Override
+ public void testAnnotatedNotName() throws NameResolutionException {
+ setup1();
+ super.testAnnotatedNotName();
+ setup2();
+ super.testAnnotatedNotName();
+ setup3();
+ super.testAnnotatedNotName();
+ }
+
+ @Test
+ @Override
+ public void testGenericTorture1() throws NameResolutionException {
+ setup1();
+ super.testGenericTorture1();
+ setup2();
+ super.testGenericTorture1();
+ setup3();
+ super.testGenericTorture1();
+ }
+
+ @Test
+ @Override
+ public void testGenericTorture2() throws NameResolutionException {
+ setup1();
+ super.testGenericTorture2();
+ setup2();
+ super.testGenericTorture2();
+ setup3();
+ super.testGenericTorture2();
+ }
+
+ @Test
+ @Override
+ public void testGenericTorture3() throws NameResolutionException {
+ setup1();
+ super.testGenericTorture3();
+ setup2();
+ super.testGenericTorture3();
+ setup3();
+ super.testGenericTorture3();
+ }
+
+ @Test
+ @Override
+ public void testGenericTorture4() throws NameResolutionException {
+ setup1();
+ super.testGenericTorture4();
+ setup2();
+ super.testGenericTorture4();
+ setup3();
+ super.testGenericTorture4();
+ }
+
+ @Test
+ @Override
+ public void testGenericTorture5() throws NameResolutionException {
+ setup1();
+ super.testGenericTorture5();
+ setup2();
+ super.testGenericTorture5();
+ setup3();
+ super.testGenericTorture5();
+ }
+
+ @Test
+ @Override
+ public void testGenericTorture6() throws NameResolutionException {
+ setup1();
+ super.testGenericTorture6();
+ setup2();
+ super.testGenericTorture6();
+ setup3();
+ super.testGenericTorture6();
+ }
+
+ @Test
+ @Override
+ public void testGenericTorture7() throws NameResolutionException {
+ setup1();
+ super.testGenericTorture7();
+ setup2();
+ super.testGenericTorture7();
+ setup3();
+ super.testGenericTorture7();
+ }
+
+ @Test
+ @Override
+ public void testGenericTorture8() throws NameResolutionException {
+ setup1();
+ super.testGenericTorture8();
+ setup2();
+ super.testGenericTorture8();
+ setup3();
+ super.testGenericTorture8();
+ }
+
+ @Test
+ @Override
+ public void testGenericTorture9() throws NameResolutionException {
+ setup1();
+ super.testGenericTorture9();
+ setup2();
+ super.testGenericTorture9();
+ setup3();
+ super.testGenericTorture9();
+ }
+
+ @Test
+ @Override
+ public void testGenericTorture10() throws NameResolutionException {
+ setup1();
+ super.testGenericTorture10();
+ setup2();
+ super.testGenericTorture10();
+ }
+
+ @Test
+ @Override
+ public void testGenericTorture11() throws NameResolutionException {
+ setup1();
+ super.testGenericTorture11();
+ setup2();
+ super.testGenericTorture11();
+ }
+
+ @Test
+ @Override
+ public void testGenericTorture12() throws NameResolutionException {
+ setup1();
+ super.testGenericTorture12();
+ setup2();
+ super.testGenericTorture12();
+ }
+
+ @Test
+ @Override
+ public void testInjectNonStaticLocalArgClass() throws NameResolutionException {
+ setup1();
+ super.testInjectNonStaticLocalArgClass();
+ setup2();
+ super.testInjectNonStaticLocalArgClass();
+ setup3();
+ super.testInjectNonStaticLocalArgClass();
+ }
+
+ @Test
+ @Override
+ public void testOKShortNames() throws NameResolutionException {
+ setup1();
+ super.testOKShortNames();
+ setup2();
+ super.testOKShortNames();
+ setup3();
+ super.testOKShortNames();
+ }
+
+ @Test
+ @Override
+ public void testRoundTripInnerClassNames() throws NameResolutionException, ClassNotFoundException {
+ setup1();
+ super.testRoundTripInnerClassNames();
+ setup2();
+ super.testRoundTripInnerClassNames();
+ setup3();
+ super.testRoundTripInnerClassNames();
+ }
+
+ @Test
+ @Override
+ public void testUnitIsInjectable() throws NameResolutionException, InjectionException {
+ setup1();
+ super.testUnitIsInjectable();
+ setup2();
+ super.testUnitIsInjectable();
+ setup3();
+ super.testUnitIsInjectable();
+ }
+
+ @Test
+ @Override
+ public void testBadUnitDecl() throws NameResolutionException {
+ setup1();
+ super.testBadUnitDecl();
+ setup2();
+ super.testBadUnitDecl();
+ setup3();
+ super.testBadUnitDecl();
+ }
+
+ @Test
+ @Override
+ public void nameCantBindWrongSubclassAsDefault() throws NameResolutionException {
+ setup1();
+ super.nameCantBindWrongSubclassAsDefault();
+ setup2();
+ super.nameCantBindWrongSubclassAsDefault();
+ setup3();
+ super.nameCantBindWrongSubclassAsDefault();
+ }
+
+ @Test
+ @Override
+ public void ifaceCantBindWrongImplAsDefault() throws NameResolutionException {
+ setup1();
+ super.ifaceCantBindWrongImplAsDefault();
+ setup2();
+ super.ifaceCantBindWrongImplAsDefault();
+ setup3();
+ super.ifaceCantBindWrongImplAsDefault();
+ }
+}
http://git-wip-us.apache.org/repos/asf/incubator-reef/blob/53ea32cc/lang/java/reef-tang/tang/src/test/java/org/apache/reef/tang/test/AnInterface.java
----------------------------------------------------------------------
diff --git a/lang/java/reef-tang/tang/src/test/java/org/apache/reef/tang/test/AnInterface.java b/lang/java/reef-tang/tang/src/test/java/org/apache/reef/tang/test/AnInterface.java
new file mode 100644
index 0000000..6d6b6d6
--- /dev/null
+++ b/lang/java/reef-tang/tang/src/test/java/org/apache/reef/tang/test/AnInterface.java
@@ -0,0 +1,29 @@
+/**
+ * Licensed to the Apache Software Foundation (ASF) under one
+ * or more contributor license agreements. See the NOTICE file
+ * distributed with this work for additional information
+ * regarding copyright ownership. The ASF licenses this file
+ * to you under the Apache License, Version 2.0 (the
+ * "License"); you may not use this file except in compliance
+ * with the License. You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing,
+ * software distributed under the License is distributed on an
+ * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
+ * KIND, either express or implied. See the License for the
+ * specific language governing permissions and limitations
+ * under the License.
+ */
+package org.apache.reef.tang.test;
+
+import org.apache.reef.tang.annotations.DefaultImplementation;
+
+/**
+ * An interface with a default implementation
+ */
+@DefaultImplementation(AnInterfaceImplementation.class)
+interface AnInterface {
+ void aMethod();
+}
http://git-wip-us.apache.org/repos/asf/incubator-reef/blob/53ea32cc/lang/java/reef-tang/tang/src/test/java/org/apache/reef/tang/test/AnInterfaceImplementation.java
----------------------------------------------------------------------
diff --git a/lang/java/reef-tang/tang/src/test/java/org/apache/reef/tang/test/AnInterfaceImplementation.java b/lang/java/reef-tang/tang/src/test/java/org/apache/reef/tang/test/AnInterfaceImplementation.java
new file mode 100644
index 0000000..d932b37
--- /dev/null
+++ b/lang/java/reef-tang/tang/src/test/java/org/apache/reef/tang/test/AnInterfaceImplementation.java
@@ -0,0 +1,52 @@
+/**
+ * Licensed to the Apache Software Foundation (ASF) under one
+ * or more contributor license agreements. See the NOTICE file
+ * distributed with this work for additional information
+ * regarding copyright ownership. The ASF licenses this file
+ * to you under the Apache License, Version 2.0 (the
+ * "License"); you may not use this file except in compliance
+ * with the License. You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing,
+ * software distributed under the License is distributed on an
+ * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
+ * KIND, either express or implied. See the License for the
+ * specific language governing permissions and limitations
+ * under the License.
+ */
+package org.apache.reef.tang.test;
+
+import javax.inject.Inject;
+
+final class AnInterfaceImplementation implements AnInterface {
+ private final int aMagicNumber;
+
+ @Inject
+ AnInterfaceImplementation() {
+ this.aMagicNumber = 42;
+ }
+
+ @Override
+ public void aMethod() {
+
+ }
+
+ @Override
+ public boolean equals(Object o) {
+ if (this == o) return true;
+ if (o == null || getClass() != o.getClass()) return false;
+
+ AnInterfaceImplementation that = (AnInterfaceImplementation) o;
+
+ if (aMagicNumber != that.aMagicNumber) return false;
+
+ return true;
+ }
+
+ @Override
+ public int hashCode() {
+ return aMagicNumber;
+ }
+}
http://git-wip-us.apache.org/repos/asf/incubator-reef/blob/53ea32cc/lang/java/reef-tang/tang/src/test/java/org/apache/reef/tang/test/CyclicDependency.java
----------------------------------------------------------------------
diff --git a/lang/java/reef-tang/tang/src/test/java/org/apache/reef/tang/test/CyclicDependency.java b/lang/java/reef-tang/tang/src/test/java/org/apache/reef/tang/test/CyclicDependency.java
new file mode 100644
index 0000000..ca48643
--- /dev/null
+++ b/lang/java/reef-tang/tang/src/test/java/org/apache/reef/tang/test/CyclicDependency.java
@@ -0,0 +1,56 @@
+/**
+ * Licensed to the Apache Software Foundation (ASF) under one
+ * or more contributor license agreements. See the NOTICE file
+ * distributed with this work for additional information
+ * regarding copyright ownership. The ASF licenses this file
+ * to you under the Apache License, Version 2.0 (the
+ * "License"); you may not use this file except in compliance
+ * with the License. You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing,
+ * software distributed under the License is distributed on an
+ * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
+ * KIND, either express or implied. See the License for the
+ * specific language governing permissions and limitations
+ * under the License.
+ */
+package org.apache.reef.tang.test;
+
+import javax.inject.Inject;
+
+/**
+ * Part of a cyclic dependency
+ */
+final class CyclicDependency {
+ private final CyclicDependencyClassOne one;
+ private final CyclicDependencyClassTwo two;
+
+ @Inject
+ CyclicDependency(final CyclicDependencyClassOne one,
+ final CyclicDependencyClassTwo two) {
+ this.one = one;
+ this.two = two;
+ }
+
+ @Override
+ public boolean equals(Object o) {
+ if (this == o) return true;
+ if (o == null || getClass() != o.getClass()) return false;
+
+ CyclicDependency that = (CyclicDependency) o;
+
+ if (!one.equals(that.one)) return false;
+ if (!two.equals(that.two)) return false;
+
+ return true;
+ }
+
+ @Override
+ public int hashCode() {
+ int result = one.hashCode();
+ result = 31 * result + two.hashCode();
+ return result;
+ }
+}
http://git-wip-us.apache.org/repos/asf/incubator-reef/blob/53ea32cc/lang/java/reef-tang/tang/src/test/java/org/apache/reef/tang/test/CyclicDependencyClassOne.java
----------------------------------------------------------------------
diff --git a/lang/java/reef-tang/tang/src/test/java/org/apache/reef/tang/test/CyclicDependencyClassOne.java b/lang/java/reef-tang/tang/src/test/java/org/apache/reef/tang/test/CyclicDependencyClassOne.java
new file mode 100644
index 0000000..513a854
--- /dev/null
+++ b/lang/java/reef-tang/tang/src/test/java/org/apache/reef/tang/test/CyclicDependencyClassOne.java
@@ -0,0 +1,50 @@
+/**
+ * Licensed to the Apache Software Foundation (ASF) under one
+ * or more contributor license agreements. See the NOTICE file
+ * distributed with this work for additional information
+ * regarding copyright ownership. The ASF licenses this file
+ * to you under the Apache License, Version 2.0 (the
+ * "License"); you may not use this file except in compliance
+ * with the License. You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing,
+ * software distributed under the License is distributed on an
+ * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
+ * KIND, either express or implied. See the License for the
+ * specific language governing permissions and limitations
+ * under the License.
+ */
+package org.apache.reef.tang.test;
+
+import javax.inject.Inject;
+
+/**
+ * Part of a cyclic dependency
+ */
+final class CyclicDependencyClassOne {
+ private final CyclicDependencyClassTwo other;
+
+ @Inject
+ CyclicDependencyClassOne(final CyclicDependencyClassTwo other) {
+ this.other = other;
+ }
+
+ @Override
+ public boolean equals(Object o) {
+ if (this == o) return true;
+ if (o == null || getClass() != o.getClass()) return false;
+
+ CyclicDependencyClassOne that = (CyclicDependencyClassOne) o;
+
+ if (!other.equals(that.other)) return false;
+
+ return true;
+ }
+
+ @Override
+ public int hashCode() {
+ return other.hashCode();
+ }
+}
http://git-wip-us.apache.org/repos/asf/incubator-reef/blob/53ea32cc/lang/java/reef-tang/tang/src/test/java/org/apache/reef/tang/test/CyclicDependencyClassTwo.java
----------------------------------------------------------------------
diff --git a/lang/java/reef-tang/tang/src/test/java/org/apache/reef/tang/test/CyclicDependencyClassTwo.java b/lang/java/reef-tang/tang/src/test/java/org/apache/reef/tang/test/CyclicDependencyClassTwo.java
new file mode 100644
index 0000000..bfceb55
--- /dev/null
+++ b/lang/java/reef-tang/tang/src/test/java/org/apache/reef/tang/test/CyclicDependencyClassTwo.java
@@ -0,0 +1,48 @@
+/**
+ * Licensed to the Apache Software Foundation (ASF) under one
+ * or more contributor license agreements. See the NOTICE file
+ * distributed with this work for additional information
+ * regarding copyright ownership. The ASF licenses this file
+ * to you under the Apache License, Version 2.0 (the
+ * "License"); you may not use this file except in compliance
+ * with the License. You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing,
+ * software distributed under the License is distributed on an
+ * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
+ * KIND, either express or implied. See the License for the
+ * specific language governing permissions and limitations
+ * under the License.
+ */
+package org.apache.reef.tang.test;
+
+import org.apache.reef.tang.InjectionFuture;
+
+import javax.inject.Inject;
+
+/**
+ * Part of a cyclic dependency.
+ */
+final class CyclicDependencyClassTwo {
+ private final InjectionFuture<CyclicDependencyClassOne> other;
+
+ @Inject
+ CyclicDependencyClassTwo(InjectionFuture<CyclicDependencyClassOne> other) {
+ this.other = other;
+ }
+
+ @Override
+ public boolean equals(Object o) {
+ if (this == o) return true;
+ if (o == null || getClass() != o.getClass()) return false;
+
+ return true;
+ }
+
+ @Override
+ public int hashCode() {
+ return other.hashCode();
+ }
+}
http://git-wip-us.apache.org/repos/asf/incubator-reef/blob/53ea32cc/lang/java/reef-tang/tang/src/test/java/org/apache/reef/tang/test/Handler.java
----------------------------------------------------------------------
diff --git a/lang/java/reef-tang/tang/src/test/java/org/apache/reef/tang/test/Handler.java b/lang/java/reef-tang/tang/src/test/java/org/apache/reef/tang/test/Handler.java
new file mode 100644
index 0000000..864b362
--- /dev/null
+++ b/lang/java/reef-tang/tang/src/test/java/org/apache/reef/tang/test/Handler.java
@@ -0,0 +1,30 @@
+/**
+ * Licensed to the Apache Software Foundation (ASF) under one
+ * or more contributor license agreements. See the NOTICE file
+ * distributed with this work for additional information
+ * regarding copyright ownership. The ASF licenses this file
+ * to you under the Apache License, Version 2.0 (the
+ * "License"); you may not use this file except in compliance
+ * with the License. You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing,
+ * software distributed under the License is distributed on an
+ * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
+ * KIND, either express or implied. See the License for the
+ * specific language governing permissions and limitations
+ * under the License.
+ */
+package org.apache.reef.tang.test;
+
+/**
+ * An interface with a type parameter. This can be found e.g. in REEF EventHandlers.
+ *
+ * @param <T>
+ */
+interface Handler<T> {
+
+ public void process(final T value);
+
+}
http://git-wip-us.apache.org/repos/asf/incubator-reef/blob/53ea32cc/lang/java/reef-tang/tang/src/test/java/org/apache/reef/tang/test/InjectableClass.java
----------------------------------------------------------------------
diff --git a/lang/java/reef-tang/tang/src/test/java/org/apache/reef/tang/test/InjectableClass.java b/lang/java/reef-tang/tang/src/test/java/org/apache/reef/tang/test/InjectableClass.java
new file mode 100644
index 0000000..a8accb8
--- /dev/null
+++ b/lang/java/reef-tang/tang/src/test/java/org/apache/reef/tang/test/InjectableClass.java
@@ -0,0 +1,47 @@
+/**
+ * Licensed to the Apache Software Foundation (ASF) under one
+ * or more contributor license agreements. See the NOTICE file
+ * distributed with this work for additional information
+ * regarding copyright ownership. The ASF licenses this file
+ * to you under the Apache License, Version 2.0 (the
+ * "License"); you may not use this file except in compliance
+ * with the License. You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing,
+ * software distributed under the License is distributed on an
+ * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
+ * KIND, either express or implied. See the License for the
+ * specific language governing permissions and limitations
+ * under the License.
+ */
+package org.apache.reef.tang.test;
+
+import javax.inject.Inject;
+
+final class InjectableClass {
+
+ private final int magicNumber = -42;
+
+ @Inject
+ InjectableClass() {
+ }
+
+ @Override
+ public boolean equals(Object o) {
+ if (this == o) return true;
+ if (o == null || getClass() != o.getClass()) return false;
+
+ InjectableClass that = (InjectableClass) o;
+
+ if (magicNumber != that.magicNumber) return false;
+
+ return true;
+ }
+
+ @Override
+ public int hashCode() {
+ return magicNumber;
+ }
+}
http://git-wip-us.apache.org/repos/asf/incubator-reef/blob/53ea32cc/lang/java/reef-tang/tang/src/test/java/org/apache/reef/tang/test/ListInterface.java
----------------------------------------------------------------------
diff --git a/lang/java/reef-tang/tang/src/test/java/org/apache/reef/tang/test/ListInterface.java b/lang/java/reef-tang/tang/src/test/java/org/apache/reef/tang/test/ListInterface.java
new file mode 100644
index 0000000..4e8c1a0
--- /dev/null
+++ b/lang/java/reef-tang/tang/src/test/java/org/apache/reef/tang/test/ListInterface.java
@@ -0,0 +1,23 @@
+/**
+ * Licensed to the Apache Software Foundation (ASF) under one
+ * or more contributor license agreements. See the NOTICE file
+ * distributed with this work for additional information
+ * regarding copyright ownership. The ASF licenses this file
+ * to you under the Apache License, Version 2.0 (the
+ * "License"); you may not use this file except in compliance
+ * with the License. You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing,
+ * software distributed under the License is distributed on an
+ * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
+ * KIND, either express or implied. See the License for the
+ * specific language governing permissions and limitations
+ * under the License.
+ */
+package org.apache.reef.tang.test;
+
+public interface ListInterface {
+ void bMethod();
+}
http://git-wip-us.apache.org/repos/asf/incubator-reef/blob/53ea32cc/lang/java/reef-tang/tang/src/test/java/org/apache/reef/tang/test/ListInterfaceImplOne.java
----------------------------------------------------------------------
diff --git a/lang/java/reef-tang/tang/src/test/java/org/apache/reef/tang/test/ListInterfaceImplOne.java b/lang/java/reef-tang/tang/src/test/java/org/apache/reef/tang/test/ListInterfaceImplOne.java
new file mode 100644
index 0000000..3adad54
--- /dev/null
+++ b/lang/java/reef-tang/tang/src/test/java/org/apache/reef/tang/test/ListInterfaceImplOne.java
@@ -0,0 +1,55 @@
+/**
+ * Licensed to the Apache Software Foundation (ASF) under one
+ * or more contributor license agreements. See the NOTICE file
+ * distributed with this work for additional information
+ * regarding copyright ownership. The ASF licenses this file
+ * to you under the Apache License, Version 2.0 (the
+ * "License"); you may not use this file except in compliance
+ * with the License. You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing,
+ * software distributed under the License is distributed on an
+ * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
+ * KIND, either express or implied. See the License for the
+ * specific language governing permissions and limitations
+ * under the License.
+ */
+package org.apache.reef.tang.test;
+
+import javax.inject.Inject;
+
+public class ListInterfaceImplOne implements ListInterface {
+
+ private final int magicNumber;
+
+ @Inject
+ ListInterfaceImplOne() {
+ magicNumber = 31;
+ }
+
+ @Override
+ public void bMethod() {
+ }
+
+ @Override
+ public boolean equals(Object obj) {
+ if (this == obj) {
+ return true;
+ } else if (obj == null || obj.getClass() != getClass()) {
+ return false;
+ } else {
+ ListInterfaceImplOne one = (ListInterfaceImplOne) obj;
+ if (one.magicNumber != magicNumber) {
+ return false;
+ }
+ return true;
+ }
+ }
+
+ @Override
+ public int hashCode() {
+ return magicNumber;
+ }
+}
http://git-wip-us.apache.org/repos/asf/incubator-reef/blob/53ea32cc/lang/java/reef-tang/tang/src/test/java/org/apache/reef/tang/test/ListInterfaceImplTwo.java
----------------------------------------------------------------------
diff --git a/lang/java/reef-tang/tang/src/test/java/org/apache/reef/tang/test/ListInterfaceImplTwo.java b/lang/java/reef-tang/tang/src/test/java/org/apache/reef/tang/test/ListInterfaceImplTwo.java
new file mode 100644
index 0000000..1513f82
--- /dev/null
+++ b/lang/java/reef-tang/tang/src/test/java/org/apache/reef/tang/test/ListInterfaceImplTwo.java
@@ -0,0 +1,55 @@
+/**
+ * Licensed to the Apache Software Foundation (ASF) under one
+ * or more contributor license agreements. See the NOTICE file
+ * distributed with this work for additional information
+ * regarding copyright ownership. The ASF licenses this file
+ * to you under the Apache License, Version 2.0 (the
+ * "License"); you may not use this file except in compliance
+ * with the License. You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing,
+ * software distributed under the License is distributed on an
+ * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
+ * KIND, either express or implied. See the License for the
+ * specific language governing permissions and limitations
+ * under the License.
+ */
+package org.apache.reef.tang.test;
+
+import javax.inject.Inject;
+
+public class ListInterfaceImplTwo implements ListInterface {
+ private final double magicNumber;
+
+ @Inject
+ ListInterfaceImplTwo() {
+ magicNumber = 31.0;
+ }
+
+ @Override
+ public void bMethod() {
+ }
+
+ @Override
+ public boolean equals(Object obj) {
+ if (this == obj) {
+ return true;
+ } else if (obj == null || obj.getClass() != getClass()) {
+ return false;
+ } else {
+ ListInterfaceImplTwo two = (ListInterfaceImplTwo) obj;
+ if (Double.compare(two.magicNumber, magicNumber) != 0) {
+ return false;
+ }
+ return true;
+ }
+ }
+
+ @Override
+ public int hashCode() {
+ long temp = Double.doubleToLongBits(magicNumber);
+ return (int) (temp ^ (temp >>> 32));
+ }
+}
http://git-wip-us.apache.org/repos/asf/incubator-reef/blob/53ea32cc/lang/java/reef-tang/tang/src/test/java/org/apache/reef/tang/test/ListOfBaseTypes.java
----------------------------------------------------------------------
diff --git a/lang/java/reef-tang/tang/src/test/java/org/apache/reef/tang/test/ListOfBaseTypes.java b/lang/java/reef-tang/tang/src/test/java/org/apache/reef/tang/test/ListOfBaseTypes.java
new file mode 100644
index 0000000..76d0a26
--- /dev/null
+++ b/lang/java/reef-tang/tang/src/test/java/org/apache/reef/tang/test/ListOfBaseTypes.java
@@ -0,0 +1,82 @@
+/**
+ * Licensed to the Apache Software Foundation (ASF) under one
+ * or more contributor license agreements. See the NOTICE file
+ * distributed with this work for additional information
+ * regarding copyright ownership. The ASF licenses this file
+ * to you under the Apache License, Version 2.0 (the
+ * "License"); you may not use this file except in compliance
+ * with the License. You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing,
+ * software distributed under the License is distributed on an
+ * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
+ * KIND, either express or implied. See the License for the
+ * specific language governing permissions and limitations
+ * under the License.
+ */
+package org.apache.reef.tang.test;
+
+import org.apache.reef.tang.annotations.Name;
+import org.apache.reef.tang.annotations.NamedParameter;
+import org.apache.reef.tang.annotations.Parameter;
+
+import javax.inject.Inject;
+import java.util.List;
+
+final class ListOfBaseTypes {
+ private final List<Integer> integers;
+ private final List<Double> doubles;
+ private final List<String> strings;
+ private final List<Integer> moreIntegers;
+
+ @Inject
+ ListOfBaseTypes(@Parameter(Integers.class) final List<Integer> integers,
+ @Parameter(Doubles.class) final List<Double> doubles,
+ @Parameter(Strings.class) final List<String> strings,
+ @Parameter(MoreIntegers.class) final List<Integer> moreIntegers) {
+ this.integers = integers;
+ this.doubles = doubles;
+ this.strings = strings;
+ this.moreIntegers = moreIntegers;
+ }
+
+ @Override
+ public boolean equals(Object o) {
+ if (this == o) return true;
+ if (o == null || getClass() != o.getClass()) return false;
+
+ ListOfBaseTypes that = (ListOfBaseTypes) o;
+
+ if (!doubles.equals(that.doubles)) return false;
+ if (!integers.equals(that.integers)) return false;
+ if (!strings.equals(that.strings)) return false;
+
+ return true;
+ }
+
+ @Override
+ public int hashCode() {
+ int result = integers.hashCode();
+ result = 31 * result + doubles.hashCode();
+ result = 31 * result + strings.hashCode();
+ return result;
+ }
+
+ @NamedParameter
+ public static class Integers implements Name<List<Integer>> {
+ }
+
+ @NamedParameter(default_values = {"1", "2", "3"})
+ public static class MoreIntegers implements Name<List<Integer>> {
+ }
+
+ @NamedParameter
+ public static class Doubles implements Name<List<Double>> {
+ }
+
+ @NamedParameter
+ public static class Strings implements Name<List<String>> {
+ }
+}
\ No newline at end of file
http://git-wip-us.apache.org/repos/asf/incubator-reef/blob/53ea32cc/lang/java/reef-tang/tang/src/test/java/org/apache/reef/tang/test/ListOfImplementations.java
----------------------------------------------------------------------
diff --git a/lang/java/reef-tang/tang/src/test/java/org/apache/reef/tang/test/ListOfImplementations.java b/lang/java/reef-tang/tang/src/test/java/org/apache/reef/tang/test/ListOfImplementations.java
new file mode 100644
index 0000000..c1fc103
--- /dev/null
+++ b/lang/java/reef-tang/tang/src/test/java/org/apache/reef/tang/test/ListOfImplementations.java
@@ -0,0 +1,55 @@
+/**
+ * Licensed to the Apache Software Foundation (ASF) under one
+ * or more contributor license agreements. See the NOTICE file
+ * distributed with this work for additional information
+ * regarding copyright ownership. The ASF licenses this file
+ * to you under the Apache License, Version 2.0 (the
+ * "License"); you may not use this file except in compliance
+ * with the License. You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing,
+ * software distributed under the License is distributed on an
+ * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
+ * KIND, either express or implied. See the License for the
+ * specific language governing permissions and limitations
+ * under the License.
+ */
+package org.apache.reef.tang.test;
+
+import org.apache.reef.tang.annotations.Parameter;
+
+import javax.inject.Inject;
+import java.util.List;
+
+public class ListOfImplementations {
+
+ private final List<ListInterface> theInstances;
+
+ @Inject
+ ListOfImplementations(@Parameter(TestConfiguration.ListOfInstances.class) final List<ListInterface> theInstances) {
+ this.theInstances = theInstances;
+ }
+
+ @Override
+ public boolean equals(Object o) {
+ if (this == o) return true;
+ if (o == null || getClass() != o.getClass()) return false;
+
+ ListOfImplementations that = (ListOfImplementations) o;
+
+ if (!theInstances.equals(that.theInstances)) return false;
+
+ return true;
+ }
+
+ @Override
+ public int hashCode() {
+ return theInstances.hashCode();
+ }
+
+ public boolean isValid() {
+ return this.theInstances.size() == 2;
+ }
+}
http://git-wip-us.apache.org/repos/asf/incubator-reef/blob/53ea32cc/lang/java/reef-tang/tang/src/test/java/org/apache/reef/tang/test/ObjectTreeTest.java
----------------------------------------------------------------------
diff --git a/lang/java/reef-tang/tang/src/test/java/org/apache/reef/tang/test/ObjectTreeTest.java b/lang/java/reef-tang/tang/src/test/java/org/apache/reef/tang/test/ObjectTreeTest.java
new file mode 100644
index 0000000..53fb0ec
--- /dev/null
+++ b/lang/java/reef-tang/tang/src/test/java/org/apache/reef/tang/test/ObjectTreeTest.java
@@ -0,0 +1,61 @@
+/**
+ * Licensed to the Apache Software Foundation (ASF) under one
+ * or more contributor license agreements. See the NOTICE file
+ * distributed with this work for additional information
+ * regarding copyright ownership. The ASF licenses this file
+ * to you under the Apache License, Version 2.0 (the
+ * "License"); you may not use this file except in compliance
+ * with the License. You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing,
+ * software distributed under the License is distributed on an
+ * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
+ * KIND, either express or implied. See the License for the
+ * specific language governing permissions and limitations
+ * under the License.
+ */
+package org.apache.reef.tang.test;
+
+import org.apache.reef.tang.Configuration;
+import org.apache.reef.tang.Tang;
+import org.apache.reef.tang.exceptions.BindException;
+import org.apache.reef.tang.exceptions.InjectionException;
+import org.junit.Assert;
+import org.junit.Test;
+
+public class ObjectTreeTest {
+
+ public static Configuration getConfiguration() throws BindException {
+ return TestConfiguration.CONF
+ .set(TestConfiguration.OPTIONAL_STRING, TestConfiguration.OPTIONAL_STRING_VALUE)
+ .set(TestConfiguration.REQUIRED_STRING, TestConfiguration.REQUIRED_STRING_VALUE)
+ .build();
+ }
+
+ /**
+ * Configuration getter for TestConfigurationWithoutList.
+ */
+ public static Configuration getConfigurationWithoutList() throws BindException {
+ // TODO: Remove this method after #192 is fixed
+ return TestConfigurationWithoutList.CONF
+ .set(TestConfigurationWithoutList.OPTIONAL_STRING, TestConfigurationWithoutList.OPTIONAL_STRING_VALUE)
+ .set(TestConfigurationWithoutList.REQUIRED_STRING, TestConfigurationWithoutList.REQUIRED_STRING_VALUE)
+ .build();
+ }
+
+ @Test
+ public void testInstantiation() throws BindException, InjectionException {
+ final RootInterface root = Tang.Factory.getTang().newInjector(getConfiguration()).getInstance(RootInterface.class);
+ Assert.assertTrue("Object instantiation left us in an inconsistent state.", root.isValid());
+ }
+
+ @Test
+ public void testTwoInstantiations() throws BindException, InjectionException {
+ final RootInterface firstRoot = Tang.Factory.getTang().newInjector(getConfiguration()).getInstance(RootInterface.class);
+ final RootInterface secondRoot = Tang.Factory.getTang().newInjector(getConfiguration()).getInstance(RootInterface.class);
+ Assert.assertNotSame("Two instantiations of the object tree should not be the same", firstRoot, secondRoot);
+ Assert.assertEquals("Two instantiations of the object tree should be equal", firstRoot, secondRoot);
+ }
+}
http://git-wip-us.apache.org/repos/asf/incubator-reef/blob/53ea32cc/lang/java/reef-tang/tang/src/test/java/org/apache/reef/tang/test/RootImplementation.java
----------------------------------------------------------------------
diff --git a/lang/java/reef-tang/tang/src/test/java/org/apache/reef/tang/test/RootImplementation.java b/lang/java/reef-tang/tang/src/test/java/org/apache/reef/tang/test/RootImplementation.java
new file mode 100644
index 0000000..161eb67
--- /dev/null
+++ b/lang/java/reef-tang/tang/src/test/java/org/apache/reef/tang/test/RootImplementation.java
@@ -0,0 +1,166 @@
+/**
+ * Licensed to the Apache Software Foundation (ASF) under one
+ * or more contributor license agreements. See the NOTICE file
+ * distributed with this work for additional information
+ * regarding copyright ownership. The ASF licenses this file
+ * to you under the Apache License, Version 2.0 (the
+ * "License"); you may not use this file except in compliance
+ * with the License. You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing,
+ * software distributed under the License is distributed on an
+ * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
+ * KIND, either express or implied. See the License for the
+ * specific language governing permissions and limitations
+ * under the License.
+ */
+package org.apache.reef.tang.test;
+
+
+import org.apache.reef.tang.annotations.Parameter;
+
+import javax.inject.Inject;
+
+/**
+ * The root of the object graph instantiated.
+ */
+final class RootImplementation implements RootInterface {
+
+ private final String requiredString;
+ private final String optionalString;
+ private final UnitClass unit;
+ private final Handler<String> stringHandler;
+ private final Handler<Integer> integerHandler;
+ private final AnInterface anInterface;
+ private final int anInt;
+ private final double aDouble;
+ private final InjectableClass injectableClass;
+ private final SetOfImplementations setOfImplementations;
+ private final SetOfBaseTypes setOfBaseTypes;
+ private final ListOfImplementations listOfImplementations;
+ private final ListOfBaseTypes listOfBaseTypes;
+ private final CyclicDependency cyclicDependency;
+
+ @Inject
+ public RootImplementation(@Parameter(TestConfiguration.RequiredString.class) final String requiredString,
+ @Parameter(TestConfiguration.OptionalString.class) final String optionalString,
+ @Parameter(TestConfiguration.StringHandler.class) final Handler<String> stringHandler,
+ @Parameter(TestConfiguration.IntegerHandler.class) final Handler<Integer> integerHandler,
+ @Parameter(TestConfiguration.NamedParameterInteger.class) final int anInt,
+ @Parameter(TestConfiguration.NamedParameterDouble.class) double aDouble,
+ final UnitClass unit,
+ final AnInterface anInterface,
+ final InjectableClass injectableClass,
+ final SetOfImplementations setOfImplementations,
+ final SetOfBaseTypes setOfBaseTypes,
+ final ListOfImplementations listOfImplementations,
+ final ListOfBaseTypes listOfBaseTypes,
+ CyclicDependency cyclicDependency) {
+ this.requiredString = requiredString;
+ this.optionalString = optionalString;
+ this.unit = unit;
+ this.stringHandler = stringHandler;
+ this.integerHandler = integerHandler;
+ this.anInterface = anInterface;
+ this.anInt = anInt;
+ this.aDouble = aDouble;
+ this.injectableClass = injectableClass;
+ this.setOfImplementations = setOfImplementations;
+ this.setOfBaseTypes = setOfBaseTypes;
+ this.listOfImplementations = listOfImplementations;
+ this.listOfBaseTypes = listOfBaseTypes;
+ this.cyclicDependency = cyclicDependency;
+ }
+
+ @Override
+ public boolean isValid() {
+ if (!this.setOfImplementations.isValid()) {
+ return false;
+ }
+ if (!this.listOfImplementations.isValid()) {
+ return false;
+ }
+ if (!this.requiredString.equals(TestConfiguration.REQUIRED_STRING_VALUE)) {
+ return false;
+ }
+
+ if (!this.optionalString.equals(TestConfiguration.OPTIONAL_STRING_VALUE)) {
+ return false;
+ }
+
+ this.integerHandler.process(3);
+ this.stringHandler.process("three");
+ if (this.unit.getIntValue() != 3) {
+ return false;
+ }
+ if (!this.unit.getStringValue().equals("three")) {
+ return false;
+ }
+ if (this.anInterface == null) {
+ return false;
+ }
+
+ if (this.aDouble != TestConfiguration.NAMED_PARAMETER_DOUBLE_VALUE) {
+ return false;
+ }
+ if (this.anInt != TestConfiguration.NAMED_PARAMETER_INTEGER_VALUE) {
+ return false;
+ }
+
+ return true;
+ }
+
+
+ @Override
+ public boolean equals(Object o) {
+ if (this == o) return true;
+ if (o == null || getClass() != o.getClass()) return false;
+
+ RootImplementation that = (RootImplementation) o;
+
+ if (Double.compare(that.aDouble, aDouble) != 0) return false;
+ if (anInt != that.anInt) return false;
+ if (anInterface != null ? !anInterface.equals(that.anInterface) : that.anInterface != null) return false;
+ if (integerHandler != null ? !integerHandler.equals(that.integerHandler) : that.integerHandler != null)
+ return false;
+ if (optionalString != null ? !optionalString.equals(that.optionalString) : that.optionalString != null)
+ return false;
+ if (requiredString != null ? !requiredString.equals(that.requiredString) : that.requiredString != null)
+ return false;
+ if (stringHandler != null ? !stringHandler.equals(that.stringHandler) : that.stringHandler != null) return false;
+ if (unit != null ? !unit.equals(that.unit) : that.unit != null) return false;
+ if (injectableClass != null ? !injectableClass.equals(that.injectableClass) : that.injectableClass != null)
+ return false;
+ if (setOfImplementations != null ? !setOfImplementations.equals(that.setOfImplementations) : that.setOfImplementations != null)
+ return false;
+ if (setOfBaseTypes != null ? !setOfBaseTypes.equals(that.setOfBaseTypes) : that.setOfBaseTypes != null)
+ return false;
+ if (listOfImplementations != null ? !listOfImplementations.equals(that.listOfImplementations) : that
+ .listOfImplementations != null)
+ return false;
+ if (listOfBaseTypes != null ? !listOfBaseTypes.equals(that.listOfBaseTypes) : that.listOfBaseTypes != null)
+ return false;
+ if (cyclicDependency != null ? !cyclicDependency.equals(that.cyclicDependency) : that.cyclicDependency != null)
+ return false;
+
+ return true;
+ }
+
+ @Override
+ public int hashCode() {
+ int result;
+ long temp;
+ result = requiredString != null ? requiredString.hashCode() : 0;
+ result = 31 * result + (optionalString != null ? optionalString.hashCode() : 0);
+ result = 31 * result + (unit != null ? unit.hashCode() : 0);
+ result = 31 * result + (stringHandler != null ? stringHandler.hashCode() : 0);
+ result = 31 * result + (integerHandler != null ? integerHandler.hashCode() : 0);
+ result = 31 * result + (anInterface != null ? anInterface.hashCode() : 0);
+ result = 31 * result + anInt;
+ temp = Double.doubleToLongBits(aDouble);
+ result = 31 * result + (int) (temp ^ (temp >>> 32));
+ return result;
+ }
+}
http://git-wip-us.apache.org/repos/asf/incubator-reef/blob/53ea32cc/lang/java/reef-tang/tang/src/test/java/org/apache/reef/tang/test/RootImplementationWithoutList.java
----------------------------------------------------------------------
diff --git a/lang/java/reef-tang/tang/src/test/java/org/apache/reef/tang/test/RootImplementationWithoutList.java b/lang/java/reef-tang/tang/src/test/java/org/apache/reef/tang/test/RootImplementationWithoutList.java
new file mode 100644
index 0000000..6569b19
--- /dev/null
+++ b/lang/java/reef-tang/tang/src/test/java/org/apache/reef/tang/test/RootImplementationWithoutList.java
@@ -0,0 +1,155 @@
+/**
+ * Licensed to the Apache Software Foundation (ASF) under one
+ * or more contributor license agreements. See the NOTICE file
+ * distributed with this work for additional information
+ * regarding copyright ownership. The ASF licenses this file
+ * to you under the Apache License, Version 2.0 (the
+ * "License"); you may not use this file except in compliance
+ * with the License. You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing,
+ * software distributed under the License is distributed on an
+ * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
+ * KIND, either express or implied. See the License for the
+ * specific language governing permissions and limitations
+ * under the License.
+ */
+package org.apache.reef.tang.test;
+
+import org.apache.reef.tang.annotations.Parameter;
+
+import javax.inject.Inject;
+
+/**
+ * The root of the object graph without list
+ *
+ * @see org.apache.reef.tang.test.RootImplementation
+ */
+public class RootImplementationWithoutList implements RootInterface {
+ // TODO: Remove this class after #192 is fixed
+ private final String requiredString;
+ private final String optionalString;
+ private final UnitClass unit;
+ private final Handler<String> stringHandler;
+ private final Handler<Integer> integerHandler;
+ private final AnInterface anInterface;
+ private final int anInt;
+ private final double aDouble;
+ private final InjectableClass injectableClass;
+ private final SetOfImplementations setOfImplementations;
+ private final SetOfBaseTypes setOfBaseTypes;
+ private final CyclicDependency cyclicDependency;
+
+ @Inject
+ public RootImplementationWithoutList(
+ @Parameter(TestConfigurationWithoutList.RequiredString.class) final String requiredString,
+ @Parameter(TestConfigurationWithoutList.OptionalString.class) final String optionalString,
+ @Parameter(TestConfigurationWithoutList.StringHandler.class) final Handler<String> stringHandler,
+ @Parameter(TestConfigurationWithoutList.IntegerHandler.class) final Handler<Integer> integerHandler,
+ @Parameter(TestConfigurationWithoutList.NamedParameterInteger.class) final int anInt,
+ @Parameter(TestConfigurationWithoutList.NamedParameterDouble.class) double aDouble,
+ final UnitClass unit,
+ final AnInterface anInterface,
+ final InjectableClass injectableClass,
+ final SetOfImplementations setOfImplementations,
+ final SetOfBaseTypes setOfBaseTypes,
+ CyclicDependency cyclicDependency) {
+
+ this.requiredString = requiredString;
+ this.optionalString = optionalString;
+ this.unit = unit;
+ this.stringHandler = stringHandler;
+ this.integerHandler = integerHandler;
+ this.anInterface = anInterface;
+ this.anInt = anInt;
+ this.aDouble = aDouble;
+ this.injectableClass = injectableClass;
+ this.setOfImplementations = setOfImplementations;
+ this.setOfBaseTypes = setOfBaseTypes;
+ this.cyclicDependency = cyclicDependency;
+ }
+
+ @Override
+ public boolean isValid() {
+ if (!this.setOfImplementations.isValid()) {
+ return false;
+ }
+ if (!this.requiredString.equals(TestConfiguration.REQUIRED_STRING_VALUE)) {
+ return false;
+ }
+
+ if (!this.optionalString.equals(TestConfiguration.OPTIONAL_STRING_VALUE)) {
+ return false;
+ }
+
+ this.integerHandler.process(3);
+ this.stringHandler.process("three");
+ if (this.unit.getIntValue() != 3) {
+ return false;
+ }
+ if (!this.unit.getStringValue().equals("three")) {
+ return false;
+ }
+ if (this.anInterface == null) {
+ return false;
+ }
+
+ if (this.aDouble != TestConfiguration.NAMED_PARAMETER_DOUBLE_VALUE) {
+ return false;
+ }
+ if (this.anInt != TestConfiguration.NAMED_PARAMETER_INTEGER_VALUE) {
+ return false;
+ }
+
+ return true;
+ }
+
+
+ @Override
+ public boolean equals(Object o) {
+ if (this == o) return true;
+ if (o == null || getClass() != o.getClass()) return false;
+
+ RootImplementationWithoutList that = (RootImplementationWithoutList) o;
+
+ if (Double.compare(that.aDouble, aDouble) != 0) return false;
+ if (anInt != that.anInt) return false;
+ if (anInterface != null ? !anInterface.equals(that.anInterface) : that.anInterface != null) return false;
+ if (integerHandler != null ? !integerHandler.equals(that.integerHandler) : that.integerHandler != null)
+ return false;
+ if (optionalString != null ? !optionalString.equals(that.optionalString) : that.optionalString != null)
+ return false;
+ if (requiredString != null ? !requiredString.equals(that.requiredString) : that.requiredString != null)
+ return false;
+ if (stringHandler != null ? !stringHandler.equals(that.stringHandler) : that.stringHandler != null) return false;
+ if (unit != null ? !unit.equals(that.unit) : that.unit != null) return false;
+ if (injectableClass != null ? !injectableClass.equals(that.injectableClass) : that.injectableClass != null)
+ return false;
+ if (setOfImplementations != null ? !setOfImplementations.equals(that.setOfImplementations) : that.setOfImplementations != null)
+ return false;
+ if (setOfBaseTypes != null ? !setOfBaseTypes.equals(that.setOfBaseTypes) : that.setOfBaseTypes != null)
+ return false;
+ if (cyclicDependency != null ? !cyclicDependency.equals(that.cyclicDependency) : that.cyclicDependency != null)
+ return false;
+
+ return true;
+ }
+
+ @Override
+ public int hashCode() {
+ int result;
+ long temp;
+ result = requiredString != null ? requiredString.hashCode() : 0;
+ result = 31 * result + (optionalString != null ? optionalString.hashCode() : 0);
+ result = 31 * result + (unit != null ? unit.hashCode() : 0);
+ result = 31 * result + (stringHandler != null ? stringHandler.hashCode() : 0);
+ result = 31 * result + (integerHandler != null ? integerHandler.hashCode() : 0);
+ result = 31 * result + (anInterface != null ? anInterface.hashCode() : 0);
+ result = 31 * result + anInt;
+ temp = Double.doubleToLongBits(aDouble);
+ result = 31 * result + (int) (temp ^ (temp >>> 32));
+ return result;
+ }
+}
http://git-wip-us.apache.org/repos/asf/incubator-reef/blob/53ea32cc/lang/java/reef-tang/tang/src/test/java/org/apache/reef/tang/test/RootInterface.java
----------------------------------------------------------------------
diff --git a/lang/java/reef-tang/tang/src/test/java/org/apache/reef/tang/test/RootInterface.java b/lang/java/reef-tang/tang/src/test/java/org/apache/reef/tang/test/RootInterface.java
new file mode 100644
index 0000000..210726b
--- /dev/null
+++ b/lang/java/reef-tang/tang/src/test/java/org/apache/reef/tang/test/RootInterface.java
@@ -0,0 +1,31 @@
+/**
+ * Licensed to the Apache Software Foundation (ASF) under one
+ * or more contributor license agreements. See the NOTICE file
+ * distributed with this work for additional information
+ * regarding copyright ownership. The ASF licenses this file
+ * to you under the Apache License, Version 2.0 (the
+ * "License"); you may not use this file except in compliance
+ * with the License. You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing,
+ * software distributed under the License is distributed on an
+ * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
+ * KIND, either express or implied. See the License for the
+ * specific language governing permissions and limitations
+ * under the License.
+ */
+package org.apache.reef.tang.test;
+
+/**
+ * The interface for the root of the test object graph instantiated.
+ */
+public interface RootInterface {
+
+ /**
+ * @return true, if the object graph has been instantiated correctly, false otherwise.
+ */
+ public boolean isValid();
+
+}
http://git-wip-us.apache.org/repos/asf/incubator-reef/blob/53ea32cc/lang/java/reef-tang/tang/src/test/java/org/apache/reef/tang/test/RoundTripTest.java
----------------------------------------------------------------------
diff --git a/lang/java/reef-tang/tang/src/test/java/org/apache/reef/tang/test/RoundTripTest.java b/lang/java/reef-tang/tang/src/test/java/org/apache/reef/tang/test/RoundTripTest.java
new file mode 100644
index 0000000..9f012e5
--- /dev/null
+++ b/lang/java/reef-tang/tang/src/test/java/org/apache/reef/tang/test/RoundTripTest.java
@@ -0,0 +1,56 @@
+/**
+ * Licensed to the Apache Software Foundation (ASF) under one
+ * or more contributor license agreements. See the NOTICE file
+ * distributed with this work for additional information
+ * regarding copyright ownership. The ASF licenses this file
+ * to you under the Apache License, Version 2.0 (the
+ * "License"); you may not use this file except in compliance
+ * with the License. You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing,
+ * software distributed under the License is distributed on an
+ * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
+ * KIND, either express or implied. See the License for the
+ * specific language governing permissions and limitations
+ * under the License.
+ */
+package org.apache.reef.tang.test;
+
+import org.apache.reef.tang.ClassHierarchy;
+import org.apache.reef.tang.Configuration;
+import org.apache.reef.tang.Tang;
+import org.apache.reef.tang.implementation.protobuf.ProtocolBufferClassHierarchy;
+import org.junit.Assert;
+import org.junit.Test;
+
+/**
+ * Base class for roundtrip tests. The idea is that serializers implement roundTrip() and then get tested by the tests
+ * in this class.
+ */
+public abstract class RoundTripTest {
+
+ public abstract Configuration roundTrip(final Configuration configuration) throws Exception;
+
+ public abstract Configuration roundTrip(final Configuration configuration, final ClassHierarchy classHierarchy) throws Exception;
+
+ @Test
+ public void testRoundTrip() throws Exception {
+ // TODO: use 'getConfiguration' instead of 'getConfigurationWithoutList' after #192 is fixed
+ final Configuration conf = ObjectTreeTest.getConfigurationWithoutList();
+ final RootInterface before = Tang.Factory.getTang().newInjector(conf).getInstance(RootInterface.class);
+ final RootInterface after = Tang.Factory.getTang().newInjector(roundTrip(conf)).getInstance(RootInterface.class);
+ Assert.assertEquals("Configuration conversion to and from Avro datatypes failed.", before, after);
+ }
+
+ @Test
+ public void testRoundTripWithClassHierarchy() throws Exception {
+ // TODO: use 'getConfiguration' instead of 'getConfigurationWithoutList' after #192 is fixed
+ final Configuration confBefore = ObjectTreeTest.getConfigurationWithoutList();
+ final ClassHierarchy c = new ProtocolBufferClassHierarchy(ProtocolBufferClassHierarchy.serialize(confBefore.getClassHierarchy()));
+ final Configuration confAfter = roundTrip(confBefore, c);
+ Assert.assertEquals(confBefore.getNamedParameters().size(), confAfter.getNamedParameters().size());
+ //For now, we cannot use ProtocolBufferClassHierarchy to do injection
+ }
+}