@Test public void testQuery() throws Exception { final PackageBuilder builder = new PackageBuilder(); final PackageDescr packageDescr = new PackageDescr("p1"); final QueryDescr queryDescr = new QueryDescr("query1"); queryDescr.addParameter("String", "$type"); packageDescr.addRule(queryDescr); final AndDescr lhs = new AndDescr(); queryDescr.setLhs(lhs); final PatternDescr pattern = new PatternDescr(Cheese.class.getName(), "stilton"); lhs.addDescr(pattern); pattern.addConstraint(new ExprConstraintDescr("type == $type")); // Another query, no parameters QueryDescr queryDescr2 = new QueryDescr("query2"); packageDescr.addRule(queryDescr2); AndDescr lhs2 = new AndDescr(); queryDescr2.setLhs(lhs2); PatternDescr pattern2 = new PatternDescr(Cheese.class.getName()); lhs2.addDescr(pattern2); builder.addPackage(packageDescr); assertLength(0, builder.getErrors().getErrors()); KnowledgeBase kbase = KnowledgeBaseFactory.newKnowledgeBase(); kbase.addKnowledgePackages( Arrays.asList(new KnowledgePackage[] {new KnowledgePackageImp(builder.getPackage())})); final KieSession session = kbase.newStatefulKnowledgeSession(); session.insert(new Cheese("stilton", 15)); QueryResults results = session.getQueryResults("query1", "stilton"); assertEquals(1, results.size()); Object object = results.iterator().next().get("stilton"); assertEquals(new Cheese("stilton", 15), object); results = session.getQueryResults("query1", new Object[] {"cheddar"}); assertEquals(0, results.size()); session.insert(new Cheese("dolcelatte", 20)); results = session.getQueryResults("query2", new Object[] {}); assertEquals(2, results.size()); }
public Object end(final String uri, final String localName, final ExtensibleXmlParser parser) throws SAXException { final Element element = parser.endElementBuilder(); final FromDescr fromDescr = (FromDescr) parser.getCurrent(); Object parent = parser.getParent(); final PatternDescr patternDescr = (PatternDescr) parent; final ConditionalElementDescr parentDescr = (ConditionalElementDescr) parser.getParent(1); if (element.getElementsByTagName("expression").getLength() > 0) { patternDescr.setSource(fromDescr); } return fromDescr; }
public Object end(final String uri, final String localName, final ExtensibleXmlParser parser) throws SAXException { final Element element = parser.endElementBuilder(); final AccumulateDescr accumulateDescr = (AccumulateDescr) parser.getCurrent(); final Object parent = parser.getParent(); if (parent.getClass().getName().equals(FromDescr.class.getName())) { final PatternDescr result = (PatternDescr) parser.getParent(1); result.setSource(accumulateDescr); } else if (parent instanceof ConditionalElementDescr) { final ConditionalElementDescr parentDescr = (ConditionalElementDescr) parent; parentDescr.addDescr(accumulateDescr); } return accumulateDescr; }
@SuppressWarnings("unchecked") public RuleConditionElement build( RuleBuildContext context, BaseDescr descr, Pattern prefixPattern, Query query) { PatternDescr patternDescr = (PatternDescr) descr; Declaration[] params = query.getParameters(); List<BaseDescr> args = (List<BaseDescr>) patternDescr.getDescrs(); List<Integer> declrIndexes = new ArrayList<Integer>(); List<Integer> varIndexes = new ArrayList<Integer>(); List<Object> arguments = new ArrayList<Object>(params.length); for (int i = 0; i < params.length; i++) { // as these could be set in any order, initialise first, to allow setting later. arguments.add(null); } List<Declaration> requiredDeclarations = new ArrayList<Declaration>(); ObjectType argsObjectType = ClassObjectType.ObjectArray_ObjectType; InternalReadAccessor arrayReader = new SelfReferenceClassFieldReader(Object[].class, "this"); Pattern pattern = new Pattern(context.getNextPatternId(), 0, argsObjectType, null); // Deal with the constraints, both positional and bindings for (int i = 0, length = args.size(); i < length; i++) { BaseDescr base = args.get(i); String expression = null; boolean isPositional = false; boolean isBinding = false; BindingDescr bind = null; ConstraintConnectiveDescr result = null; if (base instanceof BindingDescr) { bind = (BindingDescr) base; expression = bind.getVariable() + (bind.isUnification() ? " := " : " : ") + bind.getExpression(); isBinding = true; } else { if (base instanceof ExprConstraintDescr) { ExprConstraintDescr ecd = (ExprConstraintDescr) base; expression = ecd.getExpression(); isPositional = ecd.getType() == ExprConstraintDescr.Type.POSITIONAL; } else { expression = base.getText(); } result = parseExpression(context, patternDescr, expression); if (result == null) { // error, can't parse expression. context.addError( new DescrBuildError( context.getParentDescr(), descr, null, "Unable to parse constraint: \n" + expression)); continue; } isBinding = result.getDescrs().size() == 1 && result.getDescrs().get(0) instanceof BindingDescr; if (isBinding) { bind = (BindingDescr) result.getDescrs().get(0); } } if ((!isPositional) && (!isBinding)) { // error, can't have non binding slots. context.addError( new DescrBuildError( context.getParentDescr(), descr, null, "Query's must use positional or bindings, not field constraints:\n" + expression)); continue; } else if (isPositional && isBinding) { // error, can't have positional binding slots. context.addError( new DescrBuildError( context.getParentDescr(), descr, null, "Query's can't use positional bindings:\n" + expression)); continue; } else if (isPositional) { processPositional( context, query, params, declrIndexes, varIndexes, arguments, requiredDeclarations, arrayReader, pattern, base, expression, result); } else { // it is binding processBinding( context, descr, params, declrIndexes, varIndexes, arguments, requiredDeclarations, arrayReader, pattern, bind, result); } } Declaration[] declrsArray = requiredDeclarations.toArray(new Declaration[requiredDeclarations.size()]); int[] declrIndexArray = new int[declrIndexes.size()]; for (int i = 0; i < declrsArray.length; i++) { declrIndexArray[i] = declrIndexes.get(i); } int[] varIndexesArray = new int[varIndexes.size()]; for (int i = 0; i < varIndexesArray.length; i++) { varIndexesArray[i] = varIndexes.get(i); } return new QueryElement( pattern, query.getName(), arguments.toArray(new Object[arguments.size()]), declrsArray, declrIndexArray, varIndexesArray, !patternDescr.isQuery()); }
public void visitPatternDescr(final PatternDescr descr) { this.patternContext = true; this.template = new String(); StringBuilder localString = new StringBuilder(); if (descr.getDescrs() != Collections.EMPTY_LIST) { if (descr.getIdentifier() != null) { localString.append( "<pattern identifier=\"" + descr.getIdentifier() + "\" object-type=\"" + descr.getObjectType() + "\" >" + XmlDumper.eol + processDescrList(descr.getDescrs()) + XmlDumper.eol); } else { localString.append( "<pattern object-type=\"" + descr.getObjectType() + "\" >" + XmlDumper.eol + processDescrList(descr.getDescrs()) + XmlDumper.eol); } } else { if (descr.getIdentifier() != null) { localString.append( "<pattern identifier=\"" + descr.getIdentifier() + "\" object-type=\"" + descr.getObjectType() + "\" >" + XmlDumper.eol); ; } else { localString.append( "<pattern object-type=\"" + descr.getObjectType() + "\" >" + XmlDumper.eol); } } if (descr.getSource() != null) { visit(descr.getSource()); localString.append(this.template); } localString.append("</pattern>" + XmlDumper.eol); this.template = localString.toString(); this.patternContext = false; }
@Test public void testRuleWithQuery() throws Exception { final PackageBuilder builder = new PackageBuilder(); final PackageDescr packageDescr = new PackageDescr("p1"); QueryDescr queryDescr = new QueryDescr("query1"); queryDescr.addParameter("String", "$name"); queryDescr.addParameter("int", "$age"); queryDescr.addParameter("String", "$likes"); packageDescr.addRule(queryDescr); AndDescr lhs = new AndDescr(); queryDescr.setLhs(lhs); PatternDescr pattern = new PatternDescr(Person.class.getName()); lhs.addDescr(pattern); pattern.addConstraint(new BindingDescr("$name", "name", true)); pattern.addConstraint(new BindingDescr("$age", "age", true)); pattern.addConstraint(new BindingDescr("$likes", "likes", true)); RuleDescr ruleDescr = new RuleDescr("rule-1"); packageDescr.addRule(ruleDescr); lhs = new AndDescr(); ruleDescr.setLhs(lhs); pattern = new PatternDescr(Cheese.class.getName()); lhs.addDescr(pattern); pattern.addConstraint(new BindingDescr("$type", "type")); pattern = new PatternDescr("query1"); pattern.setQuery(true); lhs.addDescr(pattern); ExprConstraintDescr expr = new ExprConstraintDescr("'bobba'"); expr.setPosition(0); expr.setType(Type.POSITIONAL); pattern.addConstraint(expr); expr = new ExprConstraintDescr("$age"); expr.setPosition(1); expr.setType(Type.POSITIONAL); pattern.addConstraint(expr); expr = new ExprConstraintDescr("$type"); expr.setPosition(2); expr.setType(Type.POSITIONAL); pattern.addConstraint(expr); ruleDescr.setConsequence("System.out.println(\"age: \" + $age);"); builder.addPackage(packageDescr); assertLength(0, builder.getErrors().getErrors()); KnowledgeBase kbase = KnowledgeBaseFactory.newKnowledgeBase(); kbase.addKnowledgePackages( Arrays.asList(new KnowledgePackage[] {new KnowledgePackageImp(builder.getPackage())})); final KieSession session = kbase.newStatefulKnowledgeSession(); session.insert(new Person("bobba", "stilton", 90)); session.insert(new Person("bobba", "brie", 80)); session.insert(new Person("bobba", "brie", 75)); session.insert(new Person("darth", "brie", 100)); session.insert(new Person("luke", "brie", 25)); session.insert(new Cheese("brie", 25)); session.fireAllRules(); }