001 package com.hammurapi.review.util;
002
003 import java.lang.annotation.Annotation;
004 import java.lang.reflect.Method;
005 import java.util.LinkedList;
006
007 import org.eclipse.emf.ecore.util.EcoreUtil;
008
009 import com.hammurapi.config.bootstrap.ConfigurationException;
010 import com.hammurapi.config.runtime.FactoryConfig;
011 import com.hammurapi.config.util.ConfigUtil;
012 import com.hammurapi.flow.Flow;
013 import com.hammurapi.flow.Node;
014 import com.hammurapi.reasoning.impl.RuleSetToFlowCompiler;
015 import com.hammurapi.reasoning.spi.Infer;
016 import com.hammurapi.reasoning.spi.model.ModelFactory;
017 import com.hammurapi.reasoning.spi.model.Rule;
018 import com.hammurapi.reasoning.spi.model.RuleSet;
019 import com.hammurapi.review.Inspect;
020 import com.hammurapi.review.Inspector;
021 import com.hammurapi.review.InspectorCategory;
022 import com.hammurapi.review.InspectorSet;
023
024 /**
025 * This class compiles inspector set definition to a flow definition to be used by
026 * Hammurapi Rules engine for inferring observations from model elements.
027 * @author Pavel Vlasov
028 *
029 */
030 public class InspectorSetCompiler extends RuleSetToFlowCompiler {
031
032 /**
033 * Compiles inspector set to flow.
034 * @param source
035 * @param contextClassLoader
036 * @param contextUrl
037 * @param tokens
038 * @param profilePath
039 * @return
040 * @throws ConfigurationException
041 */
042 public Flow compile(InspectorSet source, FactoryConfig factoryConfig) throws ConfigurationException {
043 return compile(compile(source), factoryConfig);
044 }
045
046 private RuleSet compile(InspectorSet source) throws ConfigurationException {
047 RuleSet ret = ModelFactory.eINSTANCE.createRuleSet();
048 InspectorSet inspectorSet = (InspectorSet) EcoreUtil.copy(source);
049
050 // Bases
051 for (InspectorSet base: inspectorSet.getBase()) {
052 ret.getBase().add(compile(base));
053 }
054
055 ConfigUtil.pump(inspectorSet, ret);
056
057 // Inspectors
058 for (Inspector inspector: inspectorSet.getInspectors()) {
059 if (inspector.isEnabled() && inspector.isRuntime()) {
060 Rule rule = ModelFactory.eINSTANCE.createRule();
061 ret.getRule().add(rule);
062 ConfigUtil.pump(inspector, rule);
063 ConfigUtil.addScalarProperty(rule, "severity", inspector.getSeverity(), false);
064 LinkedList<String> cl = new LinkedList<String>();
065 for (InspectorCategory c = inspector.getCategory(); c!=null; c = c.getParentCategory()) {
066 cl.addFirst(c.getName());
067 }
068 for (String cn: cl) {
069 ConfigUtil.addScalarProperty(rule, "category", cn, false);
070 }
071 }
072 }
073
074 return ret;
075 }
076
077 @Override
078 protected Node createInferenceMethodNode(
079 RuleSet ruleSet,
080 Rule rule,
081 Method method, Flow owner) {
082 Node ret = createNode(owner, InspectorMethodNode.class);
083 ConfigUtil.addScalarProperty(ret, "inspectorName", rule.getName(), true);
084 return ret;
085 }
086
087 @Override
088 protected Infer getInferAnnotation(Method method) {
089 final Inspect inspect = method.getAnnotation(Inspect.class);
090 if (inspect==null) {
091 return null;
092 }
093
094 return new Infer() {
095
096 @Override
097 public int priority() {
098 return 0;
099 }
100
101 @Override
102 public Class<?>[] value() {
103 return inspect.value();
104 }
105
106 @Override
107 public Class<? extends Annotation> annotationType() {
108 return Infer.class;
109 }
110
111 };
112 }
113
114 }