/******************************************************************************* | |
* Copyright (c) 2007, 2021 Borland Software Corporation and others. | |
* | |
* All rights reserved. This program and the accompanying materials | |
* are made available under the terms of the Eclipse Public License v2.0 | |
* which accompanies this distribution, and is available at | |
* http://www.eclipse.org/legal/epl-v20.html | |
* | |
* Contributors: | |
* Borland Software Corporation - initial API and implementation | |
* Christopher Gerking - bug 537041 | |
*******************************************************************************/ | |
package org.eclipse.m2m.tests.qvt.oml.util; | |
import java.io.File; | |
import java.io.IOException; | |
import java.io.OutputStream; | |
import java.io.PrintWriter; | |
import java.lang.reflect.Field; | |
import java.lang.reflect.Method; | |
import java.net.URL; | |
import java.util.ArrayList; | |
import java.util.Collection; | |
import java.util.Collections; | |
import java.util.HashMap; | |
import java.util.HashSet; | |
import java.util.LinkedHashSet; | |
import java.util.List; | |
import java.util.Map; | |
import java.util.Set; | |
import org.eclipse.core.resources.IFile; | |
import org.eclipse.core.resources.IMarker; | |
import org.eclipse.core.resources.IProject; | |
import org.eclipse.core.resources.IResource; | |
import org.eclipse.core.resources.IResourceVisitor; | |
import org.eclipse.core.resources.IWorkspaceDescription; | |
import org.eclipse.core.resources.IWorkspaceRunnable; | |
import org.eclipse.core.resources.IncrementalProjectBuilder; | |
import org.eclipse.core.resources.ResourcesPlugin; | |
import org.eclipse.core.runtime.CoreException; | |
import org.eclipse.core.runtime.FileLocator; | |
import org.eclipse.core.runtime.IProgressMonitor; | |
import org.eclipse.core.runtime.Platform; | |
import org.eclipse.emf.common.util.URI; | |
import org.eclipse.emf.common.util.WrappedException; | |
import org.eclipse.emf.ecore.EObject; | |
import org.eclipse.emf.ecore.EPackage; | |
import org.eclipse.emf.ecore.resource.Resource; | |
import org.eclipse.emf.ecore.resource.ResourceSet; | |
import org.eclipse.emf.ecore.resource.impl.ExtensibleURIConverterImpl; | |
import org.eclipse.emf.ecore.resource.impl.ResourceSetImpl; | |
import org.eclipse.jface.preference.IPreferenceStore; | |
import org.eclipse.m2m.internal.qvt.oml.common.MdaException; | |
import org.eclipse.m2m.internal.qvt.oml.common.io.FileUtil; | |
import org.eclipse.m2m.internal.qvt.oml.compiler.BlackboxUnitResolver; | |
import org.eclipse.m2m.internal.qvt.oml.compiler.CompiledUnit; | |
import org.eclipse.m2m.internal.qvt.oml.compiler.PlatformNamespaceUriResourceMap; | |
import org.eclipse.m2m.internal.qvt.oml.compiler.QVTOCompiler; | |
import org.eclipse.m2m.internal.qvt.oml.compiler.QvtCompilerOptions; | |
import org.eclipse.m2m.internal.qvt.oml.compiler.UnitProxy; | |
import org.eclipse.m2m.internal.qvt.oml.evaluator.QvtRuntimeException; | |
import org.eclipse.m2m.internal.qvt.oml.expressions.Module; | |
import org.eclipse.m2m.tests.qvt.oml.AllTests; | |
import org.eclipse.m2m.tests.qvt.oml.RuntimeWorkspaceSetup; | |
import org.eclipse.ui.plugin.AbstractUIPlugin; | |
import org.junit.Assert; | |
import org.osgi.framework.Bundle; | |
import junit.framework.TestCase; | |
/** | |
* @author vrepeshko | |
*/ | |
public class TestUtil extends Assert { | |
private TestUtil() {} | |
static Set<CompiledUnit> collectAllCompiledModules(CompiledUnit unit, Set<CompiledUnit> result) { | |
result.add(unit); | |
for (CompiledUnit imported : unit.getCompiledImports()) { | |
collectAllCompiledModules(imported, result); | |
} | |
return result; | |
} | |
public static void assertPersistableAST(Module module, URI targetUri) { | |
OutputStream os = null; | |
try { | |
os = new ExtensibleURIConverterImpl().createOutputStream(targetUri); | |
module.eResource().save(os, Collections.emptyMap()); | |
} catch (Exception e) { | |
TestCase.fail("Failed to serialize AST: " + e.getMessage()); //$NON-NLS-1$ | |
} finally { | |
if(os != null) { | |
try { | |
os.close(); | |
} catch (IOException e) { | |
e.printStackTrace(); | |
} | |
} | |
} | |
} | |
public static void assertAllPersistableAST(CompiledUnit compiledModule) { | |
Collection<CompiledUnit> all = collectAllCompiledModules(compiledModule, new HashSet<CompiledUnit>()); | |
HashMap<CompiledUnit, Resource> resourceMap = new HashMap<CompiledUnit, Resource>(); | |
for (CompiledUnit nextModule : all) { | |
if(!BlackboxUnitResolver.isBlackboxUnitURI(nextModule.getURI())) { | |
resourceMap.put(nextModule, confineInResource(nextModule)); | |
} | |
} | |
for (Map.Entry<CompiledUnit, Resource> nextUnit : resourceMap.entrySet()) { | |
assertPersistableAST(nextUnit.getKey(), nextUnit.getValue()); | |
} | |
} | |
private static Resource confineInResource(CompiledUnit unit) { | |
URI uri = unit.getURI().appendFileExtension("xmi"); //$NON-NLS-1$ | |
Resource res = null; | |
for (Module nextModule : unit.getModules()) { | |
if(res == null) { | |
res = nextModule.eResource(); | |
res.setURI(uri); | |
} | |
res.getContents().add(nextModule); | |
} | |
assertNotNull("A resource must be bound to AST Module: " + uri, res); //$NON-NLS-1$ | |
return res; | |
} | |
private static Resource assertPersistableAST(CompiledUnit module, Resource res) { | |
try { | |
res.save(null); | |
} catch (Exception e) { | |
System.err.print(module.getURI()); | |
e.printStackTrace(); | |
fail("Invalid module AST for serialization" + e.getLocalizedMessage()); //$NON-NLS-1$ | |
} | |
assertTrue(new ExtensibleURIConverterImpl().exists(res.getURI(), Collections.emptyMap())); | |
return res; | |
} | |
public static Set<CompiledUnit> compileModules(String srcContainer, String[] modulePaths) { | |
TestModuleResolver testResolver = TestModuleResolver.createTestPluginResolver(srcContainer); | |
QVTOCompiler compiler = new QVTOCompiler(); | |
QvtCompilerOptions options = new QvtCompilerOptions(); | |
options.setGenerateCompletionData(true); | |
UnitProxy[] sourceFiles = new UnitProxy[modulePaths.length]; | |
int pos = 0; | |
for (String nextModulePath : modulePaths) { | |
sourceFiles[pos] = testResolver.resolveUnit(nextModulePath); | |
pos++; | |
} | |
CompiledUnit[] result; | |
Set<CompiledUnit> modules; | |
try { | |
result = compiler.compile(sourceFiles, options, (IProgressMonitor)null); | |
modules = new LinkedHashSet<CompiledUnit>(); | |
for (CompiledUnit nextResult : result) { | |
assertEquals(nextResult.getURI() + " must not have compilation error", //$NON-NLS-1$ | |
0, nextResult.getErrors().size()); | |
modules.add(nextResult); | |
} | |
} catch (MdaException e) { | |
fail("Compilation errors: " + e.getMessage()); | |
return null; // never gets here | |
} | |
return modules; | |
} | |
public static QVTOCompiler createTestPluginQvtCompiler(String sourceContainerPath) { | |
return new QVTOCompiler(); | |
} | |
public static void turnOffAutoBuilding() throws CoreException { | |
IWorkspaceDescription workspaceDescription = ResourcesPlugin.getWorkspace().getDescription(); | |
workspaceDescription.setAutoBuilding(false); | |
ResourcesPlugin.getWorkspace().setDescription(workspaceDescription); | |
} | |
public static void turnOnAutoBuilding() throws CoreException { | |
IWorkspaceDescription workspaceDescription = ResourcesPlugin.getWorkspace().getDescription(); | |
workspaceDescription.setAutoBuilding(true); | |
ResourcesPlugin.getWorkspace().setDescription(workspaceDescription); | |
} | |
public static void copyFolder(final IProject project, final String folderName) throws Exception { | |
File sourceFolder = getPluginRelativeFolder(folderName); | |
File destFolder = new File(project.getLocation().toString()); | |
FileUtil.copyFolder(sourceFolder, destFolder); | |
// System.out.println("source: " + sourceFolder.getAbsolutePath()); | |
// System.out.println("dest: " + destFolder.getAbsolutePath()); | |
project.refreshLocal(IResource.DEPTH_INFINITE, null); | |
} | |
public static File getPluginRelativeFolder(final String folderName) throws IOException { | |
return getPluginRelativeFile(AllTests.BUNDLE_ID, folderName); | |
} | |
public static File getPluginRelativeFile(String plugin, String folderName) throws IOException { | |
Bundle bundle = Platform.getBundle(plugin); | |
URL url = bundle.getEntry(folderName); | |
if(url == null) { | |
throw new RuntimeException("File " + folderName + " not found in " + plugin); //$NON-NLS-1$ //$NON-NLS-2$ | |
} | |
File file = new File(FileLocator.toFileURL(url).getPath()).getCanonicalFile(); | |
return file; | |
} | |
public static void deleteJavaFiles(final IProject project) throws CoreException { | |
IWorkspaceRunnable runnable = new IWorkspaceRunnable() { | |
public void run(IProgressMonitor monitor) throws CoreException { | |
final List<IFile> filesToDelete = new ArrayList<IFile>(); | |
project.accept(new IResourceVisitor() { | |
public boolean visit(final IResource resource) { | |
if(resource.getType() == IResource.FILE) { | |
String extension = resource.getFileExtension(); | |
if("java".equals(extension) || "class".equals(extension)) { //$NON-NLS-1$ //$NON-NLS-2$ | |
IFile file = (IFile) resource; | |
filesToDelete.add(file); | |
} | |
return false; | |
} | |
return true; | |
} | |
}); | |
for (IFile file : filesToDelete) { | |
try { | |
file.delete(true, null); | |
} | |
catch(Exception e) {} | |
} | |
} | |
}; | |
project.getWorkspace().run(runnable, null); | |
} | |
public static void buildProject(final IProject project) throws CoreException { | |
buildProject(project, IncrementalProjectBuilder.FULL_BUILD); | |
} | |
public static void buildProject(final IProject project, final int kind) throws CoreException { | |
project.build(kind, null); | |
List<String> errors = getBuildErrors(project); | |
assertTrue("Build failed for " + project + ": " + errors, errors.isEmpty()); //$NON-NLS-1$ //$NON-NLS-2$ | |
} | |
public static List<String> getBuildErrors(final IProject project) throws CoreException { | |
IMarker[] markers = project.findMarkers( | |
// IJavaModelMarker.JAVA_MODEL_PROBLEM_MARKER, false, | |
IMarker.PROBLEM, true, | |
IResource.DEPTH_INFINITE); | |
List<String> errors = new ArrayList<String>(); | |
for(int i = 0; i < markers.length; i++) { | |
IMarker marker = markers[i]; | |
if(RuntimeWorkspaceSetup.getInstance().getIsDevLaunchMode() && | |
"plugin.xml".equals(marker.getResource().getName()) && //$NON-NLS-1$ | |
marker.getResource().getParent() == project) { | |
continue; | |
} | |
if(marker.getAttribute(IMarker.SEVERITY, 0) == IMarker.SEVERITY_ERROR) { | |
String message = marker.getResource().getName() + | |
" " + marker.getAttribute(IMarker.LINE_NUMBER, "") + //$NON-NLS-1$ //$NON-NLS-2$ | |
": " + marker.getAttribute(IMarker.MESSAGE, "") + //$NON-NLS-1$ //$NON-NLS-2$ | |
" " + marker.getAttribute(IMarker.LOCATION, ""); //$NON-NLS-1$ //$NON-NLS-2$ | |
errors.add(message); | |
System.err.println(message); | |
} | |
} | |
return errors; | |
} | |
public static void logQVTStackTrace(QvtRuntimeException e) { | |
PrintWriter pw = new PrintWriter(System.err); | |
pw.println("QVT stacktrace:"); //$NON-NLS-1$ | |
e.printQvtStackTrace(pw); | |
pw.flush(); | |
} | |
public static void suppressGitPrefixPopUp() { // Workaround BUG 390479 | |
try { | |
Class<?> activatorClass = Class.forName("org.eclipse.egit.ui.Activator"); | |
try { | |
Class<?> preferencesClass = Class.forName("org.eclipse.egit.ui.UIPreferences"); | |
Field field = preferencesClass.getField("SHOW_GIT_PREFIX_WARNING"); | |
String name = (String)field.get(null); | |
Method getDefaultMethod = activatorClass.getMethod("getDefault"); | |
AbstractUIPlugin activator = (AbstractUIPlugin) getDefaultMethod.invoke(null); | |
IPreferenceStore store = activator.getPreferenceStore(); | |
store.setValue(name, false); | |
} | |
catch (Exception e) { | |
e.printStackTrace(); | |
} | |
} | |
catch (ClassNotFoundException e) { | |
} | |
} | |
public interface UriProvider { | |
URI getModelUri(String model); | |
} | |
public static ResourceSet getMetamodelResolutionRS(ResourceSet resSet, List<URI> metamodels, UriProvider uriProv) { | |
if (metamodels.isEmpty()) { | |
return resSet; | |
} | |
EPackage.Registry packageRegistry = resSet.getPackageRegistry(); | |
for (URI ecoreFileURI : metamodels) { | |
URI absoluteURI = ecoreFileURI; | |
if(ecoreFileURI.isRelative()) { | |
absoluteURI = uriProv.getModelUri(ecoreFileURI.toString()); | |
} | |
EPackage metamodelPackage = null; | |
try { | |
Resource ecoreResource = resSet.getResource(absoluteURI, true); | |
if(!ecoreResource.getContents().isEmpty()) { | |
EObject obj = ecoreResource.getContents().get(0); | |
if(obj instanceof EPackage) { | |
metamodelPackage = (EPackage) obj; | |
} | |
} | |
} catch (WrappedException e) { | |
TestCase.fail("Failed to load metamodel EPackage. " + e.getMessage()); //$NON-NLS-1$ | |
} | |
if(metamodelPackage == null) { | |
TestCase.fail("No metamodel EPackage available in " + absoluteURI); //$NON-NLS-1$ | |
} | |
packageRegistry.put(metamodelPackage.getNsURI(), metamodelPackage); | |
} | |
if (!metamodels.isEmpty() && resSet instanceof ResourceSetImpl) { | |
((ResourceSetImpl) resSet).setURIResourceMap(new PlatformNamespaceUriResourceMap(resSet)); | |
} | |
return resSet; | |
} | |
} |