/******************************************************************************* * Copyright (c) 2006-2012 * Software Technology Group, Dresden University of Technology * DevBoost GmbH, Berlin, Amtsgericht Charlottenburg, HRB 140026 * * 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: * Software Technology Group - TU Dresden, Germany; * DevBoost GmbH - Berlin, Germany * - initial API and implementation ******************************************************************************/ package org.emftext.language.mecore.resource.mecore.analysis.types; import java.util.LinkedHashMap; import java.util.Map; import org.eclipse.emf.ecore.EClassifier; import org.eclipse.emf.ecore.EDataType; import org.eclipse.emf.ecore.EObject; import org.eclipse.emf.ecore.EPackage; import org.eclipse.emf.ecore.EcorePackage; import org.eclipse.emf.ecore.util.EcoreUtil; import org.emftext.language.mecore.MClass; import org.emftext.language.mecore.MDataType; import org.emftext.language.mecore.MEcoreType; import org.emftext.language.mecore.MEnum; import org.emftext.language.mecore.MImport; import org.emftext.language.mecore.MPackage; import org.emftext.language.mecore.MType; import org.emftext.language.mecore.MecoreFactory; import org.emftext.language.mecore.resource.mecore.IMecoreReferenceResolveResult; public class TypeResolver { private Map<EClassifier, MDataType> dataTypeMap = new LinkedHashMap<EClassifier, MDataType>(); public void resolve(String identifier, EObject container, boolean resolveFuzzy, final IMecoreReferenceResolveResult<MType> result) { EObject root = EcoreUtil.getRootContainer(container); for (EClassifier eClassifier : EcorePackage.eINSTANCE.getEClassifiers()) { if (eClassifier instanceof EDataType) { if (checkClassifier(identifier, resolveFuzzy, result, eClassifier, "")) { return; } } } if (!result.wasResolved() || resolveFuzzy) { // search in imported packages if (root instanceof MPackage) { MPackage mPackage = (MPackage) root; for (MImport mImport : mPackage.getImports()) { EPackage ePackage = mImport.getImportedPackage(); String prefix = mImport.getPrefix() + "."; if (searchInEPackage(identifier, prefix, ePackage, resolveFuzzy, result)) { return; } } } // search in Ecore package (imported by default) searchInEPackage(identifier, "", EcorePackage.eINSTANCE, resolveFuzzy, result); } } private boolean searchInEPackage(String identifier, String prefix, EPackage ePackage, boolean resolveFuzzy, final IMecoreReferenceResolveResult<MType> result) { for (EClassifier eClassifier : ePackage.getEClassifiers()) { if (checkClassifier(identifier, resolveFuzzy, result, eClassifier, prefix)) { return true; } } // TODO handle nested packages return false; } private boolean checkClassifier(String identifier, boolean resolveFuzzy, final IMecoreReferenceResolveResult<MType> result, EClassifier eClassifier, String prefix) { String name = prefix + eClassifier.getName(); if (identifier.equals(name) || resolveFuzzy) { if (eClassifier instanceof EDataType) { result.addMapping(name, getMDataType((EDataType) eClassifier)); } else if (eClassifier instanceof EClassifier) { result.addMapping(name, createMEcoreType((EClassifier) eClassifier)); } if (!resolveFuzzy) { return true; } } return false; } private MType getMDataType(EDataType eDataType) { if (!dataTypeMap.containsKey(eDataType)) { MDataType mDataType = MecoreFactory.eINSTANCE.createMDataType(); mDataType.setEDataType(eDataType); dataTypeMap.put(eDataType, mDataType); } return dataTypeMap.get(eDataType); } private MEcoreType createMEcoreType(EClassifier eClassifier) { MEcoreType mEcoreType = MecoreFactory.eINSTANCE.createMEcoreType(); mEcoreType.setEcoreType(eClassifier); return mEcoreType; } public String deResolve(MType element) { if (element instanceof MClass) { return ((MClass) element).getName(); } else if (element instanceof MEnum) { return ((MEnum) element).getName(); } else if (element instanceof MDataType) { MDataType mDataType = (MDataType) element; return mDataType.getEDataType().getName(); } else if (element instanceof MEcoreType) { MEcoreType mEcoreType = (MEcoreType) element; return mEcoreType.getEcoreType().getName(); } return null; } }