package org.eclipse.emf.henshin.interpreter.giraph; import java.util.ArrayList; import java.util.Collection; import java.util.HashSet; import java.util.LinkedHashMap; import java.util.LinkedHashSet; import java.util.List; import java.util.Map; import java.util.Set; import org.eclipse.emf.common.util.EList; import org.eclipse.emf.ecore.EClass; import org.eclipse.emf.ecore.EClassifier; import org.eclipse.emf.ecore.ENamedElement; import org.eclipse.emf.ecore.EPackage; import org.eclipse.emf.ecore.EReference; import org.eclipse.emf.henshin.model.Edge; import org.eclipse.emf.henshin.model.Module; import org.eclipse.emf.henshin.model.Node; import org.eclipse.emf.henshin.model.Rule; import org.eclipse.emf.henshin.model.Unit; public class GiraphUtil { public static String getInstanceCode(Rule rule) throws Exception { StringBuffer json = new StringBuffer(); List<ENamedElement> types = new ArrayList<ENamedElement>(getTypeConstants(rule.getModule()).keySet()); for (int i=0; i<rule.getLhs().getNodes().size(); i++) { Node n = rule.getLhs().getNodes().get(i); json.append("[[" + i + "]," + types.indexOf(n.getType()) + ",["); for (int j=0; j<n.getOutgoing().size(); j++) { Edge e = n.getOutgoing().get(j); int trg = rule.getLhs().getNodes().indexOf(e.getTarget()); json.append("[[" + trg + "]," + types.indexOf(e.getType()) + "]"); if (j<n.getOutgoing().size()-1) json.append(","); } json.append("]]\n"); } return json.toString(); } public static Map<Unit,String> getUnitConstants(Unit mainUnit) { EList<Unit> units = mainUnit.getSubUnits(true); units.add(0, mainUnit); Map<Unit,String> unitConstants = new LinkedHashMap<Unit, String>(); for (Unit unit : units) { String name = (unit instanceof Rule ? "RULE" : "UNIT") + "_" + camelCase2Upper(unit.getName()); unitConstants.put(unit, name); } return unitConstants; } public static Map<ENamedElement,String> getTypeConstants(Module module) { // Check if we need the package name: boolean needPackage = false; Set<String> classNames = new HashSet<String>(); for (EPackage pack : module.getImports()) { for (EClassifier classifier : pack.getEClassifiers()) { if (classifier instanceof EClass) { if (classNames.contains(classifier.getName())) { needPackage = true; break; } classNames.add(classifier.getName()); } } } // Generate the names: Map<ENamedElement,String> typeConstants = new LinkedHashMap<ENamedElement, String>(); for (EPackage pack : module.getImports()) { for (EClassifier classifier : pack.getEClassifiers()) { if (!(classifier instanceof EClass)) { continue; } String name = "TYPE_"; if (needPackage) { name = name + camelCase2Upper(pack.getName()) + "_"; } name = name + camelCase2Upper(classifier.getName()); typeConstants.put(classifier, name); for (EReference ref : ((EClass) classifier).getEReferences()) { typeConstants.put(ref, name + "_" + camelCase2Upper(ref.getName())); } } } return typeConstants; } public static Collection<Rule> collectRules(Unit unit) { Set<Rule> rules = new LinkedHashSet<Rule>(); if (unit instanceof Rule) { rules.add((Rule) unit); } for (Unit subUnit : unit.getSubUnits(true)) { if (subUnit instanceof Rule) { rules.add((Rule) subUnit); } } return rules; } public static String getNodeName(Node node) { return node.getName()!=null && node.getName().trim().length()>0 ? "\""+node.getName()+"\"" : "" + node.getGraph().getNodes().indexOf(node); } private static String camelCase2Upper(String s) { String r = ""; boolean u = false; for (int i=0; i<s.length(); i++) { char c = s.charAt(i); char C = Character.toUpperCase(c); if (Character.isUpperCase(c)) { r = r + (u ? ("_"+C) : C); } else { u = true; r = r + C; } } return r; } public static Map<Rule,GiraphRuleData> generateRuleData(Unit mainUnit) throws Exception { Map<Rule,GiraphRuleData> data = new LinkedHashMap<Rule,GiraphRuleData>(); for (Rule rule : collectRules(mainUnit)) { data.put(rule, new GiraphRuleData(rule)); } return data; } public static List<EClass> getValidTypes(Node node, Module module) { Set<ENamedElement> allTypes = getTypeConstants(module).keySet(); List<EClass> types = new ArrayList<EClass>(); for (ENamedElement type : allTypes) { if (type instanceof EClass) { if (type==node.getType() || ((EClass) type).getEAllSuperTypes().contains(node.getType())) { types.add((EClass) type); } } } return types; } }