001: /*
002: * Copyright 2006-2007, Unitils.org
003: *
004: * Licensed under the Apache License, Version 2.0 (the "License");
005: * you may not use this file except in compliance with the License.
006: * You may obtain a copy of the License at
007: *
008: * http://www.apache.org/licenses/LICENSE-2.0
009: *
010: * Unless required by applicable law or agreed to in writing, software
011: * distributed under the License is distributed on an "AS IS" BASIS,
012: * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
013: * See the License for the specific language governing permissions and
014: * limitations under the License.
015: */
016: package org.unitils.reflectionassert;
017:
018: import junit.framework.AssertionFailedError;
019: import org.junit.Test;
020:
021: import java.util.ArrayList;
022: import java.util.List;
023:
024: /**
025: * Tests for correct handling of traversed instances pairs in ReflectionAssert.
026: * <p/>
027: * Special thanks to Dmitry Sidorenko, who first rported this issue and also indicated how to solve it.
028: *
029: * @author Dmitry Sidorenko
030: * @author Tim Ducheyne
031: * @author Filip Neven
032: */
033: public class ReflectionAssertTraversedInstanceTest {
034:
035: /**
036: * Test comparing objects with two lists which have intersecting list elements
037: * <p/>
038: * When traversing first collection child1 and child2 are marked as already compared. Child1 and child2 were found
039: * not equal, but the reflection assert class only stores the fact that they were already traversed, not the
040: * outcome (not equal). When traversing second collection, child1 and child2 are compared again but because they were
041: * already once compared, they are found equal. Which is ofcourse incorrect.
042: * <p/>
043: * The reflection assert class has been changed to also remember the outcome of traversed instance pairs.
044: */
045: @Test
046: public void doubleCheckTest() {
047: Parent root1 = new Parent("root");
048: Parent root2 = new Parent("root");
049:
050: Parent child1 = new Parent("child1");
051: Parent child2 = new Parent("child2");
052:
053: // Adding children in forward order to first root
054: root1.getChildren1().add(child1);
055: root1.getChildren1().add(child2);
056:
057: // Adding children in reverse order to second root
058: root2.getChildren1().add(child2);
059: root2.getChildren1().add(child1);
060:
061: // Adding children in forward order to first root
062: root1.getChildren2().add(child1);
063: root1.getChildren2().add(child2);
064:
065: // Adding children in reverse order to second root
066: root2.getChildren2().add(child2);
067: root2.getChildren2().add(child1);
068:
069: ReflectionAssert.assertLenEquals(root1, root2);
070: }
071:
072: /**
073: * Test comparing objects with two lists which have intersecting list elements
074: * <p/>
075: * Same as doubleCheckTest(), but showing a case when assert should actually fail, but it doesn't.
076: * This test case is highly dependent on order of fields in collection returned by {@link Class#getDeclaredFields()}
077: */
078: @Test(expected=AssertionFailedError.class)
079: public void doubleCheckTestShouldFail() {
080: Parent root1 = new Parent("root");
081: Parent root2 = new Parent("root");
082:
083: Parent child1 = new Parent("child1");
084: Parent child2 = new Parent("child2");
085:
086: // Adding children in forward order to first root
087: root1.getChildren1().add(child1);
088: root1.getChildren1().add(child2);
089:
090: // Adding children in reverse order to second root
091: root2.getChildren1().add(child2);
092: root2.getChildren1().add(child1);
093:
094: // Adding children in forward order to first root
095: root1.getChildren2().add(child1);
096:
097: // Adding children in reverse order to second root
098: root2.getChildren2().add(child2);
099:
100: // Should fail
101: ReflectionAssert.assertLenEquals(root1, root2);
102: }
103:
104: /**
105: * Test class with to child lists.
106: */
107: private class Parent {
108:
109: private String name;
110:
111: private List<Parent> children1;
112: private List<Parent> children2;
113:
114: public Parent(String name) {
115: this .name = name;
116: children1 = new ArrayList<Parent>();
117: children2 = new ArrayList<Parent>();
118: }
119:
120: public List<Parent> getChildren1() {
121: return children1;
122: }
123:
124: public List<Parent> getChildren2() {
125: return children2;
126: }
127:
128: public String toString() {
129: return name;
130: }
131: }
132:
133: }
|