View | Details | Raw Unified | Return to bug 155561
Collapse All | Expand All

(-)src/org/eclipse/gmf/tests/setup/GenProjectBaseSetup.java (+11 lines)
Lines 45-50 Link Here
45
import org.eclipse.gmf.codegen.gmfgen.GenDiagram;
45
import org.eclipse.gmf.codegen.gmfgen.GenDiagram;
46
import org.eclipse.gmf.internal.common.codegen.GeneratorBase;
46
import org.eclipse.gmf.internal.common.codegen.GeneratorBase;
47
import org.eclipse.gmf.tests.CompileUtil;
47
import org.eclipse.gmf.tests.CompileUtil;
48
import org.eclipse.gmf.tests.JDTUtil;
48
import org.eclipse.gmf.tests.Plugin;
49
import org.eclipse.gmf.tests.Plugin;
49
import org.eclipse.jdt.core.IJavaProject;
50
import org.eclipse.jdt.core.IJavaProject;
50
import org.eclipse.jdt.core.IPackageFragment;
51
import org.eclipse.jdt.core.IPackageFragment;
Lines 91-96 Link Here
91
			IProject p = ResourcesPlugin.getWorkspace().getRoot().getProject(pluginID);
92
			IProject p = ResourcesPlugin.getWorkspace().getRoot().getProject(pluginID);
92
			hookProjectBuild(p);
93
			hookProjectBuild(p);
93
		}
94
		}
95
		hookJDTStatus(ResourcesPlugin.getWorkspace().getRoot().getProject(gmfEditorId));
94
		compileUtil = null;
96
		compileUtil = null;
95
	}
97
	}
96
98
Lines 196-201 Link Here
196
		}
198
		}
197
	}
199
	}
198
200
201
	protected void hookJDTStatus(IProject p) throws Exception {
202
		JDTUtil jdtUtil = new JDTUtil(p);
203
		IStatus jdtStatus = jdtUtil.collectProblems();
204
		if (!jdtStatus.isOK()) {
205
			Plugin.logError(jdtStatus.getMessage());
206
			Assert.fail(jdtStatus.getMessage());
207
		}
208
	}
209
199
	protected void hookGeneratorStatus(IStatus generatorStatus) {
210
	protected void hookGeneratorStatus(IStatus generatorStatus) {
200
		if (!generatorStatus.isOK()) {
211
		if (!generatorStatus.isOK()) {
201
			Plugin.getInstance().getLog().log(generatorStatus);
212
			Plugin.getInstance().getLog().log(generatorStatus);
(-)src/org/eclipse/gmf/tests/JDTUtil.java (+214 lines)
Added Link Here
1
/**
2
 * Copyright (c) 2006 Eclipse.org
3
 * 
4
 * All rights reserved. This program and the accompanying materials
5
 * are made available under the terms of the Eclipse Public License v1.0
6
 * which accompanies this distribution, and is available at
7
 * http://www.eclipse.org/legal/epl-v10.html
8
 *
9
 * Contributors:
10
 *    bblajer - initial API and implementation
11
 */
12
package org.eclipse.gmf.tests;
13
14
import java.text.MessageFormat;
15
16
import org.eclipse.core.resources.IProject;
17
import org.eclipse.core.runtime.IStatus;
18
import org.eclipse.core.runtime.MultiStatus;
19
import org.eclipse.core.runtime.Status;
20
import org.eclipse.jdt.core.ICompilationUnit;
21
import org.eclipse.jdt.core.IJavaElement;
22
import org.eclipse.jdt.core.IJavaProject;
23
import org.eclipse.jdt.core.IMember;
24
import org.eclipse.jdt.core.IPackageFragment;
25
import org.eclipse.jdt.core.IPackageFragmentRoot;
26
import org.eclipse.jdt.core.ISourceRange;
27
import org.eclipse.jdt.core.IType;
28
import org.eclipse.jdt.core.JavaCore;
29
import org.eclipse.jdt.core.JavaModelException;
30
31
/**
32
 * Utility that checks various assumptions on the generated code. Currently, only the correct placement of <code>&#64;generated</code> tags is checked.
33
 */
34
public class JDTUtil {
35
	private final IJavaProject myJavaProject;
36
	private ViolationAggregator myAggregator;
37
38
	private static interface IMemberProcessor {
39
		public IStatus processMember(IMember member, boolean isLocalMember) throws JavaModelException;
40
	}
41
42
	private static class ViolationAggregator {
43
		private MultiStatus myStatus = new MultiStatus(Plugin.getPluginID(), 0, "JDT Violations", null);
44
45
		public void add(IStatus status) {
46
			myStatus.merge(status);
47
		}
48
49
		public IStatus getStatus() {
50
			if (myStatus.isOK()) {
51
				return Status.OK_STATUS;
52
			}
53
			StringBuffer buffer = new StringBuffer();
54
			IStatus[] children = myStatus.getChildren();
55
			for(int i = 0; i < children.length; i++) {
56
				if (children[i].matches(myStatus.getSeverity())) {
57
					buffer.append(children[i].getMessage()).append("\n");
58
				}
59
			}
60
			return new Status(myStatus.getSeverity(), Plugin.getPluginID(), 0, buffer.toString(), null);
61
		}
62
	}
63
64
	public JDTUtil(IJavaProject javaProject) {
65
		myJavaProject = javaProject;
66
	}
67
68
	public JDTUtil(IProject p) {
69
		this(JavaCore.create(p));
70
	}
71
72
	public IStatus collectProblems() {
73
		return collectProblems(new IMemberProcessor[] {new GeneratedTagEnsurer(), new GeneratedTagAbsenceInLocalMembersEnsurer()});
74
	}
75
76
	private IStatus collectProblems(IMemberProcessor[] processors) {
77
		if (myAggregator == null) {
78
			myAggregator = new ViolationAggregator();
79
			collectProblems(myJavaProject, processors);
80
		}
81
		return myAggregator.getStatus();
82
	}
83
84
	private void collectProblems(IJavaElement jElement, IMemberProcessor[] processors) {
85
		try {
86
			switch (jElement.getElementType()) {
87
			case IJavaElement.JAVA_PROJECT:
88
				{
89
					IJavaProject jProject = (IJavaProject) jElement;
90
					IPackageFragmentRoot[] roots = jProject.getPackageFragmentRoots();
91
					for(int i = 0; i < roots.length; i++) {
92
						if (roots[i].getKind() == IPackageFragmentRoot.K_SOURCE) {
93
							collectProblems(roots[i], processors);
94
						}
95
					}
96
				}
97
				break;
98
			case IJavaElement.PACKAGE_FRAGMENT_ROOT:
99
				{
100
					IPackageFragmentRoot root = (IPackageFragmentRoot) jElement;
101
					IJavaElement[] children = root.getChildren();
102
					for(int i = 0; i < children.length; i++) {
103
						collectProblems(children[i], processors);
104
					}
105
				}
106
				break;
107
			case IJavaElement.PACKAGE_FRAGMENT:
108
				{
109
					IPackageFragment pf = (IPackageFragment) jElement;
110
					ICompilationUnit[] compilationUnits = pf.getCompilationUnits();
111
					for(int i = 0; i < compilationUnits.length; i++) {
112
						collectProblems(compilationUnits[i], processors);
113
					}
114
				}
115
				break;
116
			case IJavaElement.COMPILATION_UNIT:
117
				{
118
					ICompilationUnit compilationUnit = (ICompilationUnit) jElement;
119
					IType[] types = compilationUnit.getTypes();
120
					for(int i = 0; i < types.length; i++) {
121
						collectProblems(types[i], processors);
122
					}
123
				}
124
				break;
125
			case IJavaElement.TYPE:
126
				{
127
					IMember member = (IMember) jElement;
128
					collectProblems(member, processors, false);
129
				}
130
				break;
131
			}
132
		} catch (JavaModelException e) {
133
			myAggregator.add(e.getStatus());
134
		}
135
	}
136
137
	private void collectProblems(IMember member, IMemberProcessor[] processors, boolean isLocalMember) throws JavaModelException {
138
		for (int i = 0; i < processors.length; i++) {
139
			IStatus status = processors[i].processMember(member, isLocalMember);
140
			if (status != null && !status.isOK()) {
141
				myAggregator.add(status);
142
			}
143
		}
144
		isLocalMember |= !(member instanceof IType);
145
		IJavaElement[] children = member.getChildren();
146
		for(int i = 0; i < children.length; i++) {
147
			collectProblems((IMember) children[i], processors, isLocalMember);
148
		}
149
	}
150
151
	private abstract static class JavadocMemberProcessor implements IMemberProcessor {
152
		protected static final String GENERATED = "@generated";	//$NON-NLS-1$
153
		protected final String getJavadoc(IMember member) throws JavaModelException {
154
			ISourceRange javadocRange = member.getJavadocRange();
155
			if (javadocRange == null) {
156
				return "";	//$NON-NLS-1$
157
			}
158
			return member.getCompilationUnit().getSource().substring(javadocRange.getOffset(), javadocRange.getLength() + javadocRange.getOffset());
159
		}
160
	}
161
162
	private static class GeneratedTagEnsurer extends JavadocMemberProcessor {
163
		public IStatus processMember(IMember member, boolean isLocalMember) throws JavaModelException {
164
			if (isLocalMember) {
165
				return null;
166
			}
167
			if (member.getElementType() == IJavaElement.INITIALIZER && member.getOccurrenceCount() > 1) {
168
				return newViolation(member, "Multiple sibling initializers should be avoided in the generated code: they may not always be merged correctly");
169
			}
170
			String javadoc = getJavadoc(member);
171
			int index = javadoc.lastIndexOf(GENERATED);
172
			if (index == -1) {
173
				return newViolation(member, "@generated is missing");
174
			}
175
			if (javadoc.indexOf(GENERATED) != index) {
176
				return newViolation(member, "There is more than one @generated tag");
177
			}
178
			String afterGenerated = javadoc.substring(index + GENERATED.length()).trim();
179
			String asteriskIgnored = afterGenerated.replace('*', ' ').trim();
180
			if (asteriskIgnored.length() == 0) {
181
				return newViolation(member, "JavaDoc comment with @generated tag is not terminated properly");
182
			}
183
			switch (asteriskIgnored.charAt(0)) {
184
			case '@':
185
				//Next tag starts here, thus @generated is OK
186
				break;
187
			case '/':
188
				//Most likely, this is an end of a JavaDoc comment terminator.
189
				//TODO: check this assumption using the content of afterGenerated
190
				break;
191
			default:
192
				return newViolation(member, "@generated tag will be interpreted as @generated NOT");
193
			}
194
			return null;
195
		}
196
	}
197
198
	private static class GeneratedTagAbsenceInLocalMembersEnsurer extends JavadocMemberProcessor {
199
		public IStatus processMember(IMember member, boolean isLocalMember) throws JavaModelException {
200
			if (!isLocalMember) {
201
				return null;
202
			}
203
			String javadoc = getJavadoc(member);
204
			if (javadoc.indexOf(GENERATED) != -1) {
205
				return newViolation(member, "@generated tag in local members is misleading");
206
			}
207
			return null;
208
		}
209
	}
210
211
	private static IStatus newViolation(IMember member, String description) {
212
		return new Status(IStatus.ERROR, Plugin.getPluginID(), 0, MessageFormat.format("{0} has problem: {1}", new Object[] {member.getHandleIdentifier(), description}), null);
213
	}
214
}

Return to bug 155561