Skip to main content
summaryrefslogtreecommitdiffstats
blob: a6bc4ab150dc8f707b932e3bbd59cc2d7209ed08 (plain) (blame)
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
/**
 * Copyright (c) 2013 Obeo.
 * All rights reserved. This program and the accompanying materials
 * are made available under the terms of the Eclipse Public License v1.0
 * which accompanies this distribution, and is available at
 * http://www.eclipse.org/legal/epl-v10.html
 * 
 * Contributors:
 *     Obeo - initial API and implementation
 */
package org.eclipse.emf.compare.tests.diff;

import static junit.framework.Assert.assertEquals;
import static junit.framework.Assert.assertTrue;

import com.google.common.collect.Lists;

import java.util.List;

import org.eclipse.emf.common.util.BasicMonitor;
import org.eclipse.emf.common.util.URI;
import org.eclipse.emf.compare.Comparison;
import org.eclipse.emf.compare.Diff;
import org.eclipse.emf.compare.DifferenceKind;
import org.eclipse.emf.compare.EMFCompare;
import org.eclipse.emf.compare.merge.BatchMerger;
import org.eclipse.emf.compare.merge.IBatchMerger;
import org.eclipse.emf.compare.merge.IMerger;
import org.eclipse.emf.compare.scope.IComparisonScope;
import org.eclipse.emf.compare.tests.nodes.Node;
import org.eclipse.emf.compare.tests.nodes.NodesFactory;
import org.eclipse.emf.ecore.xmi.XMIResource;
import org.eclipse.emf.ecore.xmi.impl.XMIResourceImpl;
import org.junit.Before;
import org.junit.Ignore;
import org.junit.Test;

/**
 * This will specifically make sure that merging two large lists never takes more than a set amount of time.
 * <p>
 * I have a list (S1) on the left side that contains 2000 elements. Its counterpart on the right side (S2) has
 * 200 elements, only 100 of which are not differences (i.e. : also present in S1). We'll make sure that
 * merging these two lists is fast enough (through test timeouts).
 * </p>
 * 
 * @author <a href="mailto:laurent.goubet@obeo.fr">Laurent Goubet</a>
 */
@SuppressWarnings("nls")
public class LCSPerformanceTest {
	private XMIResource left;

	private XMIResource right;

	@Before
	public void setup() {
		left = new XMIResourceImpl(URI.createURI("left.xmi"));
		right = new XMIResourceImpl(URI.createURI("right.xmi"));

		createNode(left, 2000, 0, 1);
		createNode(right, 200, 0, 1901);
	}

	@Test
	public void checkTestData() {
		assertTrue(left.getContents().size() == 1);
		final Node leftRoot = (Node)left.getContents().get(0);
		assertTrue(leftRoot.eContents().size() == 2000);

		assertTrue(right.getContents().size() == 1);
		final Node rightRoot = (Node)right.getContents().get(0);
		assertTrue(rightRoot.eContents().size() == 200);

		IComparisonScope scope = EMFCompare.createDefaultScope(left, right);
		Comparison comparison = EMFCompare.builder().build().compare(scope);

		final List<Diff> additions = Lists.newArrayList();
		final List<Diff> deletions = Lists.newArrayList();

		for (Diff difference : comparison.getDifferences()) {
			if (difference.getKind() == DifferenceKind.ADD) {
				additions.add(difference);
			} else {
				deletions.add(difference);
			}
		}

		assertEquals(Integer.valueOf(1900), Integer.valueOf(additions.size()));
		assertEquals(Integer.valueOf(100), Integer.valueOf(deletions.size()));
	}

	/**
	 * Will fail if {@link #checkTestData()} does.
	 * <p>
	 * The real assertion here is that this should never take more than 40 seconds to execute. We have 1900
	 * additions to merge, accounting for as many LCS computations.
	 * </p>
	 * <p>
	 * Note that this test should run in less than 30 seconds... we give it a little leeway with a 40 seconds
	 * time out.
	 * </p>
	 * <p>
	 * Ignored for now : the build machine is much too slow and does not execute this even when left 60s to do
	 * so.
	 * </p>
	 */
	@Ignore
	@Test(timeout = 40000)
	public void copyLeftToRight() {
		IComparisonScope scope = EMFCompare.createDefaultScope(left, right);
		Comparison comparison = EMFCompare.builder().build().compare(scope);

		final IMerger.Registry registry = IMerger.RegistryImpl.createStandaloneInstance();
		final IBatchMerger merger = new BatchMerger(registry);
		merger.copyAllLeftToRight(comparison.getDifferences(), new BasicMonitor());

		comparison = EMFCompare.builder().build().compare(scope);
		assertTrue(comparison.getDifferences().isEmpty());
	}

	/**
	 * Will fail if {@link #checkTestData()} does.
	 * <p>
	 * The real assertion here is that this should never take more than 3 seconds to execute : we're resetting
	 * all differences so there are only 100 "slow" ones : resetting deletions need the LCS computation.
	 * </p>
	 * <p>
	 * Ignored for now : the build machine is much too slow.
	 * </p>
	 */
	@Ignore
	@Test(timeout = 3000)
	public void copyRightToLeft() {
		IComparisonScope scope = EMFCompare.createDefaultScope(left, right);
		Comparison comparison = EMFCompare.builder().build().compare(scope);

		final IMerger.Registry registry = IMerger.RegistryImpl.createStandaloneInstance();
		final IBatchMerger merger = new BatchMerger(registry);
		merger.copyAllRightToLeft(comparison.getDifferences(), new BasicMonitor());

		comparison = EMFCompare.builder().build().compare(scope);
		assertTrue(comparison.getDifferences().isEmpty());
	}

	private void createNode(XMIResource resource, int childCount, int nodeId, int idGap) {
		resource.eSetDeliver(false);
		Node node = NodesFactory.eINSTANCE.createNode();
		node.setName("node" + nodeId);
		resource.getContents().add(node);
		resource.setID(node, Integer.toString(nodeId));
		int childId = nodeId + Math.max(1, idGap);
		for (int i = 0; i < childCount; i++) {
			Node child = NodesFactory.eINSTANCE.createNode();
			child.setName("node" + childId);
			node.getContainmentRef1().add(child);
			resource.setID(child, Integer.toString(childId));
			childId++;
		}
		resource.eSetDeliver(true);
	}
}

Back to the top