Search in sources :

Example 11 with AccumulateDescr

use of org.drools.compiler.lang.descr.AccumulateDescr in project drools by kiegroup.

the class FromCollectVisitor method trasformFromCollectToCollectList.

public void trasformFromCollectToCollectList(PatternDescr pattern, CollectDescr collectDescr) {
    // The inner pattern of the "from collect" needs to be processed to have the binding
    final PatternDescr collectDescrInputPattern = collectDescr.getInputPattern();
    collectDescrInputPattern.accept(parentVisitor);
    final AccumulateDescr accumulateDescr = new AccumulateDescr();
    accumulateDescr.setInputPattern(collectDescrInputPattern);
    accumulateDescr.addFunction("collectList", null, false, new String[] { collectDescrInputPattern.getIdentifier() });
    final PatternDescr transformedPatternDescr = new PatternDescr(pattern.getObjectType());
    for (BaseDescr o : pattern.getConstraint().getDescrs()) {
        transformedPatternDescr.addConstraint(o);
    }
    transformedPatternDescr.setSource(accumulateDescr);
    transformedPatternDescr.accept(parentVisitor);
}
Also used : PatternDescr(org.drools.compiler.lang.descr.PatternDescr) BaseDescr(org.drools.compiler.lang.descr.BaseDescr) AccumulateDescr(org.drools.compiler.lang.descr.AccumulateDescr)

Example 12 with AccumulateDescr

use of org.drools.compiler.lang.descr.AccumulateDescr in project drools by kiegroup.

the class ModelGeneratorVisitor method visit.

@Override
public void visit(PatternDescr descr) {
    final PatternSourceDescr patternSource = descr.getSource();
    if (patternSource != null && patternSource instanceof CollectDescr) {
        fromCollectVisitor.trasformFromCollectToCollectList(descr, (CollectDescr) patternSource);
    } else {
        if (patternSource instanceof AccumulateDescr) {
            AccumulateDescr accSource = (AccumulateDescr) patternSource;
            if (accSource.getFunctions().isEmpty() || accSource.getFunctions().get(0).getBind() == null) {
                patternVisitor.visit(descr).buildPattern();
                accumulateVisitor.visit(accSource, descr);
            } else {
                accumulateVisitor.visit(accSource, descr);
                patternVisitor.visit(descr).buildPattern();
            }
        } else {
            patternVisitor.visit(descr).buildPattern();
        }
    }
}
Also used : CollectDescr(org.drools.compiler.lang.descr.CollectDescr) PatternSourceDescr(org.drools.compiler.lang.descr.PatternSourceDescr) AccumulateDescr(org.drools.compiler.lang.descr.AccumulateDescr)

Example 13 with AccumulateDescr

use of org.drools.compiler.lang.descr.AccumulateDescr in project drools by kiegroup.

the class AccumulateVisitor method visit.

public void visit(AccumulateDescr descr, PatternDescr basePattern) {
    final MethodCallExpr accumulateDSL = new MethodCallExpr(null, "accumulate");
    context.addExpression(accumulateDSL);
    final MethodCallExpr accumulateExprs = new MethodCallExpr(null, "and");
    accumulateDSL.addArgument(accumulateExprs);
    context.pushExprPointer(accumulateExprs::addArgument);
    BaseDescr input = descr.getInputPattern() == null ? descr.getInput() : descr.getInputPattern();
    boolean inputPatternHasConstraints = (input instanceof PatternDescr) && (!((PatternDescr) input).getConstraint().getDescrs().isEmpty());
    input.accept(modelGeneratorVisitor);
    if (accumulateExprs.getArguments().isEmpty()) {
        accumulateDSL.remove(accumulateExprs);
    } else if (accumulateExprs.getArguments().size() == 1) {
        accumulateDSL.setArgument(0, accumulateExprs.getArguments().get(0));
    }
    if (!descr.getFunctions().isEmpty()) {
        for (AccumulateDescr.AccumulateFunctionCallDescr function : descr.getFunctions()) {
            final Optional<NewBinding> optNewBinding = visit(context, function, accumulateDSL, basePattern, inputPatternHasConstraints);
            processNewBinding(optNewBinding);
        }
    } else if (descr.getFunctions().isEmpty() && descr.getInitCode() != null) {
        // LEGACY: Accumulate with inline custom code
        if (input instanceof PatternDescr) {
            visitAccInlineCustomCode(context, descr, accumulateDSL, basePattern, (PatternDescr) input);
        } else {
            throw new UnsupportedOperationException("I was expecting input to be of type PatternDescr. " + input);
        }
    } else {
        throw new UnsupportedOperationException("Unknown type of Accumulate.");
    }
    context.popExprPointer();
    postVisit();
}
Also used : PatternDescr(org.drools.compiler.lang.descr.PatternDescr) BaseDescr(org.drools.compiler.lang.descr.BaseDescr) AccumulateDescr(org.drools.compiler.lang.descr.AccumulateDescr) MethodCallExpr(org.drools.javaparser.ast.expr.MethodCallExpr)

Example 14 with AccumulateDescr

use of org.drools.compiler.lang.descr.AccumulateDescr in project drools by kiegroup.

the class AccumulateVisitor method visitAccInlineCustomCode.

/**
 * By design this legacy accumulate (with inline custome code) visitor supports only with 1-and-only binding in the accumulate code/expressions.
 */
protected void visitAccInlineCustomCode(RuleContext context2, AccumulateDescr descr, MethodCallExpr accumulateDSL, PatternDescr basePattern, PatternDescr inputDescr) {
    context.pushExprPointer(accumulateDSL::addArgument);
    final MethodCallExpr functionDSL = new MethodCallExpr(null, "accFunction");
    String code = null;
    try {
        code = new String(IoUtils.readBytesFromInputStream(this.getClass().getResourceAsStream("/AccumulateInlineFunction.java")));
    } catch (IOException e1) {
        e1.printStackTrace();
        throw new RuntimeException("Unable to locate template.");
    }
    String targetClassName = StringUtil.toId(context2.getRuleDescr().getName()) + "Accumulate" + descr.getLine();
    code = code.replaceAll("AccumulateInlineFunction", targetClassName);
    CompilationUnit templateCU = JavaParser.parse(code);
    ClassOrInterfaceDeclaration templateClass = templateCU.getClassByName(targetClassName).orElseThrow(() -> new RuntimeException("Template did not contain expected type definition."));
    ClassOrInterfaceDeclaration templateContextClass = templateClass.getMembers().stream().filter(m -> m instanceof ClassOrInterfaceDeclaration && ((ClassOrInterfaceDeclaration) m).getNameAsString().equals("ContextData")).map(ClassOrInterfaceDeclaration.class::cast).findFirst().orElseThrow(() -> new RuntimeException("Template did not contain expected type definition."));
    List<String> contextFieldNames = new ArrayList<>();
    MethodDeclaration initMethod = templateClass.getMethodsByName("init").get(0);
    BlockStmt initBlock = JavaParser.parseBlock("{" + descr.getInitCode() + "}");
    for (Statement stmt : initBlock.getStatements()) {
        if (stmt instanceof ExpressionStmt && ((ExpressionStmt) stmt).getExpression() instanceof VariableDeclarationExpr) {
            VariableDeclarationExpr vdExpr = (VariableDeclarationExpr) ((ExpressionStmt) stmt).getExpression();
            for (VariableDeclarator vd : vdExpr.getVariables()) {
                contextFieldNames.add(vd.getNameAsString());
                templateContextClass.addField(vd.getType(), vd.getNameAsString(), Modifier.PUBLIC);
                if (vd.getInitializer().isPresent()) {
                    Expression initializer = vd.getInitializer().get();
                    Expression target = new FieldAccessExpr(new NameExpr("data"), vd.getNameAsString());
                    Statement initStmt = new ExpressionStmt(new AssignExpr(target, initializer, AssignExpr.Operator.ASSIGN));
                    initMethod.getBody().get().addStatement(initStmt);
                }
            }
        } else {
            // add as-is.
            initMethod.getBody().get().addStatement(stmt);
        }
    }
    Type singleAccumulateType = JavaParser.parseType("java.lang.Object");
    MethodDeclaration accumulateMethod = templateClass.getMethodsByName("accumulate").get(0);
    BlockStmt actionBlock = JavaParser.parseBlock("{" + descr.getActionCode() + "}");
    Collection<String> allNamesInActionBlock = collectNamesInBlock(context2, actionBlock);
    if (allNamesInActionBlock.size() == 1) {
        String nameExpr = allNamesInActionBlock.iterator().next();
        accumulateMethod.getParameter(1).setName(nameExpr);
        singleAccumulateType = context2.getDeclarationById(nameExpr).get().getType();
    } else {
        new LegacyAccumulate(context, descr, basePattern).build();
        return;
    }
    writeAccumulateMethod(contextFieldNames, singleAccumulateType, accumulateMethod, actionBlock);
    // <result expression>: this is a semantic expression in the selected dialect that is executed after all source objects are iterated.
    MethodDeclaration resultMethod = templateClass.getMethodsByName("getResult").get(0);
    Type returnExpressionType = JavaParser.parseType("java.lang.Object");
    Expression returnExpression = JavaParser.parseExpression(descr.getResultCode());
    if (returnExpression instanceof NameExpr) {
        returnExpression = new EnclosedExpr(returnExpression);
    }
    rescopeNamesToNewScope(new NameExpr("data"), contextFieldNames, returnExpression);
    resultMethod.getBody().get().addStatement(new ReturnStmt(returnExpression));
    MethodDeclaration getResultTypeMethod = templateClass.getMethodsByName("getResultType").get(0);
    getResultTypeMethod.getBody().get().addStatement(new ReturnStmt(new ClassExpr(returnExpressionType)));
    if (descr.getReverseCode() != null) {
        MethodDeclaration supportsReverseMethod = templateClass.getMethodsByName("supportsReverse").get(0);
        supportsReverseMethod.getBody().get().addStatement(JavaParser.parseStatement("return true;"));
        MethodDeclaration reverseMethod = templateClass.getMethodsByName("reverse").get(0);
        BlockStmt reverseBlock = JavaParser.parseBlock("{" + descr.getReverseCode() + "}");
        Collection<String> allNamesInReverseBlock = collectNamesInBlock(context2, reverseBlock);
        if (allNamesInReverseBlock.size() == 1) {
            reverseMethod.getParameter(1).setName(allNamesInReverseBlock.iterator().next());
        } else {
            new LegacyAccumulate(context, descr, basePattern).build();
            return;
        }
        writeAccumulateMethod(contextFieldNames, singleAccumulateType, reverseMethod, reverseBlock);
    } else {
        MethodDeclaration supportsReverseMethod = templateClass.getMethodsByName("supportsReverse").get(0);
        supportsReverseMethod.getBody().get().addStatement(JavaParser.parseStatement("return false;"));
        MethodDeclaration reverseMethod = templateClass.getMethodsByName("reverse").get(0);
        reverseMethod.getBody().get().addStatement(JavaParser.parseStatement("throw new UnsupportedOperationException(\"This function does not support reverse.\");"));
    }
    // add resulting accumulator class into the package model
    this.packageModel.addGeneratedPOJO(templateClass);
    functionDSL.addArgument(new ClassExpr(JavaParser.parseType(targetClassName)));
    functionDSL.addArgument(new NameExpr(toVar(inputDescr.getIdentifier())));
    final String bindingId = basePattern.getIdentifier();
    final MethodCallExpr asDSL = new MethodCallExpr(functionDSL, "as");
    asDSL.addArgument(new NameExpr(toVar(bindingId)));
    accumulateDSL.addArgument(asDSL);
    context.popExprPointer();
}
Also used : Expression(org.drools.javaparser.ast.expr.Expression) ModelGeneratorVisitor(org.drools.modelcompiler.builder.generator.visitor.ModelGeneratorVisitor) DeclarationSpec(org.drools.modelcompiler.builder.generator.DeclarationSpec) DrlxParseUtil(org.drools.modelcompiler.builder.generator.DrlxParseUtil) JavaParser(org.drools.javaparser.JavaParser) BinaryExpr(org.drools.javaparser.ast.expr.BinaryExpr) DrlxParseUtil.toType(org.drools.modelcompiler.builder.generator.DrlxParseUtil.toType) AccumulateUtil(org.drools.compiler.rule.builder.util.AccumulateUtil) AccumulateFunction(org.kie.api.runtime.rule.AccumulateFunction) DrlxParseUtil.forceCastForName(org.drools.modelcompiler.builder.generator.DrlxParseUtil.forceCastForName) FieldAccessExpr(org.drools.javaparser.ast.expr.FieldAccessExpr) ExpressionStmt(org.drools.javaparser.ast.stmt.ExpressionStmt) DrlxParseUtil.toVar(org.drools.modelcompiler.builder.generator.DrlxParseUtil.toVar) ConstraintParser(org.drools.modelcompiler.builder.generator.drlxparse.ConstraintParser) Statement(org.drools.javaparser.ast.stmt.Statement) PackageModel(org.drools.modelcompiler.builder.PackageModel) Parameter(org.drools.javaparser.ast.body.Parameter) Collection(java.util.Collection) ClassExpr(org.drools.javaparser.ast.expr.ClassExpr) NameExpr(org.drools.javaparser.ast.expr.NameExpr) VariableDeclarationExpr(org.drools.javaparser.ast.expr.VariableDeclarationExpr) UnknownType(org.drools.javaparser.ast.type.UnknownType) List(java.util.List) TypedExpression(org.drools.modelcompiler.builder.generator.TypedExpression) Optional(java.util.Optional) DrlxParseFail(org.drools.modelcompiler.builder.generator.drlxparse.DrlxParseFail) DrlxParseResult(org.drools.modelcompiler.builder.generator.drlxparse.DrlxParseResult) AbstractExpressionBuilder(org.drools.modelcompiler.builder.generator.expression.AbstractExpressionBuilder) DrlxParseSuccess(org.drools.modelcompiler.builder.generator.drlxparse.DrlxParseSuccess) DrlxParseUtil.rescopeNamesToNewScope(org.drools.modelcompiler.builder.generator.DrlxParseUtil.rescopeNamesToNewScope) ReturnStmt(org.drools.javaparser.ast.stmt.ReturnStmt) BlockStmt(org.drools.javaparser.ast.stmt.BlockStmt) ArrayList(java.util.ArrayList) AssignExpr(org.drools.javaparser.ast.expr.AssignExpr) IoUtils(org.drools.core.util.IoUtils) MethodCallExpr(org.drools.javaparser.ast.expr.MethodCallExpr) StringUtil(org.drools.modelcompiler.util.StringUtil) MethodDeclaration(org.drools.javaparser.ast.body.MethodDeclaration) LambdaExpr(org.drools.javaparser.ast.expr.LambdaExpr) ClassOrInterfaceDeclaration(org.drools.javaparser.ast.body.ClassOrInterfaceDeclaration) EnclosedExpr(org.drools.javaparser.ast.expr.EnclosedExpr) AccumulateDescr(org.drools.compiler.lang.descr.AccumulateDescr) VariableDeclarator(org.drools.javaparser.ast.body.VariableDeclarator) IOException(java.io.IOException) BaseDescr(org.drools.compiler.lang.descr.BaseDescr) CompilationUnit(org.drools.javaparser.ast.CompilationUnit) Type(org.drools.javaparser.ast.type.Type) PatternDescr(org.drools.compiler.lang.descr.PatternDescr) RuleContext(org.drools.modelcompiler.builder.generator.RuleContext) Collectors.toList(java.util.stream.Collectors.toList) ParseResultVisitor(org.drools.modelcompiler.builder.generator.drlxparse.ParseResultVisitor) Modifier(org.drools.javaparser.ast.Modifier) ClassOrInterfaceDeclaration(org.drools.javaparser.ast.body.ClassOrInterfaceDeclaration) ArrayList(java.util.ArrayList) NameExpr(org.drools.javaparser.ast.expr.NameExpr) ExpressionStmt(org.drools.javaparser.ast.stmt.ExpressionStmt) VariableDeclarator(org.drools.javaparser.ast.body.VariableDeclarator) AssignExpr(org.drools.javaparser.ast.expr.AssignExpr) FieldAccessExpr(org.drools.javaparser.ast.expr.FieldAccessExpr) CompilationUnit(org.drools.javaparser.ast.CompilationUnit) VariableDeclarationExpr(org.drools.javaparser.ast.expr.VariableDeclarationExpr) MethodDeclaration(org.drools.javaparser.ast.body.MethodDeclaration) Statement(org.drools.javaparser.ast.stmt.Statement) BlockStmt(org.drools.javaparser.ast.stmt.BlockStmt) IOException(java.io.IOException) DrlxParseUtil.toType(org.drools.modelcompiler.builder.generator.DrlxParseUtil.toType) UnknownType(org.drools.javaparser.ast.type.UnknownType) Type(org.drools.javaparser.ast.type.Type) Expression(org.drools.javaparser.ast.expr.Expression) TypedExpression(org.drools.modelcompiler.builder.generator.TypedExpression) ClassExpr(org.drools.javaparser.ast.expr.ClassExpr) EnclosedExpr(org.drools.javaparser.ast.expr.EnclosedExpr) ReturnStmt(org.drools.javaparser.ast.stmt.ReturnStmt) MethodCallExpr(org.drools.javaparser.ast.expr.MethodCallExpr)

Example 15 with AccumulateDescr

use of org.drools.compiler.lang.descr.AccumulateDescr in project drools by kiegroup.

the class PatternVisitor method visit.

public DSLNode visit(PatternDescr pattern) {
    String className = pattern.getObjectType();
    List<? extends BaseDescr> constraintDescrs = pattern.getConstraint().getDescrs();
    String queryName = "query_" + pattern.getObjectType();
    final MethodDeclaration queryMethod = packageModel.getQueryMethod(queryName);
    // Expression is a query, get bindings from query parameter type
    if (queryMethod != null) {
        return new Query(context, packageModel, pattern, constraintDescrs, queryName);
    }
    String queryDef = toQueryDef(pattern.getObjectType());
    if (packageModel.getQueryDefWithType().containsKey(queryDef)) {
        return new QueryCall(context, packageModel, pattern, queryDef);
    }
    if (pattern.getIdentifier() == null && pattern.getObjectType().equals("Object") && pattern.getSource() instanceof AccumulateDescr) {
        if (context.isPatternDSL()) {
            return new PatternAccumulateConstraint(context, packageModel, pattern, ((AccumulateDescr) pattern.getSource()), constraintDescrs);
        } else {
            return new FlowAccumulateConstraint(context, packageModel, pattern, ((AccumulateDescr) pattern.getSource()), constraintDescrs);
        }
    }
    final boolean allConstraintsPositional = areAllConstraintsPositional(constraintDescrs);
    final Class<?> patternType = getClassFromContext(context.getTypeResolver(), className);
    if (context.isPatternDSL()) {
        return new PatternDSLPattern(context, packageModel, pattern, constraintDescrs, patternType, allConstraintsPositional);
    } else {
        return new FlowDSLPattern(context, packageModel, pattern, constraintDescrs, patternType, allConstraintsPositional);
    }
}
Also used : MethodDeclaration(org.drools.javaparser.ast.body.MethodDeclaration) AccumulateDescr(org.drools.compiler.lang.descr.AccumulateDescr)

Aggregations

AccumulateDescr (org.drools.compiler.lang.descr.AccumulateDescr)28 PatternDescr (org.drools.compiler.lang.descr.PatternDescr)19 PackageDescr (org.drools.compiler.lang.descr.PackageDescr)15 RuleDescr (org.drools.compiler.lang.descr.RuleDescr)15 Test (org.junit.Test)15 AccumulateFunctionCallDescr (org.drools.compiler.lang.descr.AccumulateDescr.AccumulateFunctionCallDescr)5 ArrayList (java.util.ArrayList)4 BaseDescr (org.drools.compiler.lang.descr.BaseDescr)4 Accumulate (org.drools.core.rule.Accumulate)4 List (java.util.List)3 AndDescr (org.drools.compiler.lang.descr.AndDescr)3 CollectDescr (org.drools.compiler.lang.descr.CollectDescr)3 InputStreamReader (java.io.InputStreamReader)2 KnowledgeBuilderConfigurationImpl (org.drools.compiler.builder.impl.KnowledgeBuilderConfigurationImpl)2 KnowledgeBuilderImpl (org.drools.compiler.builder.impl.KnowledgeBuilderImpl)2 DialectCompiletimeRegistry (org.drools.compiler.compiler.DialectCompiletimeRegistry)2 XmlPackageReader (org.drools.compiler.compiler.xml.XmlPackageReader)2 FromDescr (org.drools.compiler.lang.descr.FromDescr)2 RuleBuildContext (org.drools.compiler.rule.builder.RuleBuildContext)2 RuleConditionBuilder (org.drools.compiler.rule.builder.RuleConditionBuilder)2