BJ-413 Ft/add composed function (#11)

* Add identifier for rules
This commit is contained in:
Kostya 2019-03-29 10:18:14 +03:00 committed by GitHub
parent 8b339fca65
commit 10ead498a3
No known key found for this signature in database
GPG Key ID: 4AEE18F83AFDEB23
6 changed files with 46 additions and 19 deletions

View File

@ -5,7 +5,7 @@ parse
;
fraud_rule
: RULE_BLOCK expression RETURN result (CATCH_ERROR catch_result)? SCOL
: RULE_BLOCK (IDENTIFIER ':')? expression RETURN result (CATCH_ERROR catch_result)? SCOL
;
expression

View File

@ -13,5 +13,11 @@ import java.util.List;
public class ResultModel {
private ResultStatus resultStatus;
private String ruleChecked;
private List<String> notificationsRule;
public ResultModel(ResultStatus resultStatus, List<String> notificationsRule) {
this.resultStatus = resultStatus;
this.notificationsRule = notificationsRule;
}
}

View File

@ -0,0 +1,17 @@
package com.rbkmoney.fraudo.utils;
import com.rbkmoney.fraudo.FraudoParser;
import lombok.AccessLevel;
import lombok.NoArgsConstructor;
@NoArgsConstructor(access = AccessLevel.PRIVATE)
public class RuleKeyGenerator {
public static String generateRuleKey(FraudoParser.Fraud_ruleContext fraudRuleContext) {
if (fraudRuleContext.IDENTIFIER() != null && !fraudRuleContext.IDENTIFIER().getText().isEmpty()) {
return fraudRuleContext.IDENTIFIER().getText();
}
return String.valueOf(fraudRuleContext.getRuleIndex());
}
}

View File

@ -6,6 +6,7 @@ import com.rbkmoney.fraudo.constant.ResultStatus;
import com.rbkmoney.fraudo.exception.NotImplementedOperatorException;
import com.rbkmoney.fraudo.exception.UnknownResultException;
import com.rbkmoney.fraudo.model.ResultModel;
import com.rbkmoney.fraudo.utils.RuleKeyGenerator;
import com.rbkmoney.fraudo.utils.TextUtil;
import lombok.RequiredArgsConstructor;
@ -21,7 +22,7 @@ public class FastFraudVisitorImpl extends FraudoBaseVisitor<Object> {
private final CustomFuncVisitorImpl customFuncVisitor;
@Override
public Object visitFraud_rule(com.rbkmoney.fraudo.FraudoParser.Fraud_ruleContext ctx) {
public Object visitFraud_rule(FraudoParser.Fraud_ruleContext ctx) {
try {
if (asBoolean(ctx.expression())) {
return ResultStatus.getByValue((String) super.visit(ctx.result()));
@ -36,28 +37,29 @@ public class FastFraudVisitorImpl extends FraudoBaseVisitor<Object> {
}
@Override
public Object visitParse(com.rbkmoney.fraudo.FraudoParser.ParseContext ctx) {
public Object visitParse(FraudoParser.ParseContext ctx) {
List<String> notifications = new ArrayList<>();
for (com.rbkmoney.fraudo.FraudoParser.Fraud_ruleContext fraud_ruleContext : ctx.fraud_rule()) {
ResultStatus result = (ResultStatus) visitFraud_rule(fraud_ruleContext);
for (FraudoParser.Fraud_ruleContext fraudRuleContext : ctx.fraud_rule()) {
ResultStatus result = (ResultStatus) visitFraud_rule(fraudRuleContext);
String key = RuleKeyGenerator.generateRuleKey(fraudRuleContext);
if (result != null && ResultStatus.NOTIFY.equals(result)) {
notifications.add(String.valueOf(fraud_ruleContext.getRuleIndex()));
notifications.add(key);
} else if (result != null && !ResultStatus.NORMAL.equals(result)) {
return new ResultModel(result, notifications);
return new ResultModel(result, key, notifications);
} else if (result == null) {
throw new UnknownResultException(fraud_ruleContext.getText());
throw new UnknownResultException(fraudRuleContext.getText());
}
}
return new ResultModel(ResultStatus.NORMAL, notifications);
}
@Override
public Object visitResult(com.rbkmoney.fraudo.FraudoParser.ResultContext ctx) {
public Object visitResult(FraudoParser.ResultContext ctx) {
return ctx.getText();
}
@Override
public Object visitDecimalExpression(com.rbkmoney.fraudo.FraudoParser.DecimalExpressionContext ctx) {
public Object visitDecimalExpression(FraudoParser.DecimalExpressionContext ctx) {
return Double.valueOf(ctx.DECIMAL().getText());
}
@ -67,17 +69,17 @@ public class FastFraudVisitorImpl extends FraudoBaseVisitor<Object> {
}
@Override
public Object visitNotExpression(com.rbkmoney.fraudo.FraudoParser.NotExpressionContext ctx) {
public Object visitNotExpression(FraudoParser.NotExpressionContext ctx) {
return !((Boolean) this.visit(ctx.expression()));
}
@Override
public Object visitParenExpression(com.rbkmoney.fraudo.FraudoParser.ParenExpressionContext ctx) {
public Object visitParenExpression(FraudoParser.ParenExpressionContext ctx) {
return super.visit(ctx.expression());
}
@Override
public Object visitComparatorExpression(com.rbkmoney.fraudo.FraudoParser.ComparatorExpressionContext ctx) {
public Object visitComparatorExpression(FraudoParser.ComparatorExpressionContext ctx) {
if (ctx.op.EQ() != null) {
return this.visit(ctx.left).equals(this.visit(ctx.right));
} else if (ctx.op.LE() != null) {
@ -93,7 +95,7 @@ public class FastFraudVisitorImpl extends FraudoBaseVisitor<Object> {
}
@Override
public Object visitBinaryExpression(com.rbkmoney.fraudo.FraudoParser.BinaryExpressionContext ctx) {
public Object visitBinaryExpression(FraudoParser.BinaryExpressionContext ctx) {
if (ctx.op.AND() != null) {
return asBoolean(ctx.left) && asBoolean(ctx.right);
} else if (ctx.op.OR() != null) {
@ -103,12 +105,12 @@ public class FastFraudVisitorImpl extends FraudoBaseVisitor<Object> {
}
@Override
public Object visitBoolExpression(com.rbkmoney.fraudo.FraudoParser.BoolExpressionContext ctx) {
public Object visitBoolExpression(FraudoParser.BoolExpressionContext ctx) {
return Boolean.valueOf(ctx.getText());
}
@Override
public Object visitCount(com.rbkmoney.fraudo.FraudoParser.CountContext ctx) {
public Object visitCount(FraudoParser.CountContext ctx) {
return countVisitor.visitCount(ctx);
}
@ -172,11 +174,11 @@ public class FastFraudVisitorImpl extends FraudoBaseVisitor<Object> {
return customFuncVisitor.visitAmount(ctx);
}
private boolean asBoolean(com.rbkmoney.fraudo.FraudoParser.ExpressionContext ctx) {
private boolean asBoolean(FraudoParser.ExpressionContext ctx) {
return (boolean) visit(ctx);
}
private double asDouble(com.rbkmoney.fraudo.FraudoParser.ExpressionContext ctx) {
private double asDouble(FraudoParser.ExpressionContext ctx) {
return (double) visit(ctx);
}
}

View File

@ -67,6 +67,7 @@ public class FraudoTest {
InputStream resourceAsStream = FraudoTest.class.getResourceAsStream("/rules/decline.frd");
ResultModel result = parseAndVisit(resourceAsStream);
Assert.assertEquals(ResultStatus.DECLINE, result.getResultStatus());
Assert.assertEquals("test_11", result.getRuleChecked());
}
@Test
@ -98,6 +99,7 @@ public class FraudoTest {
com.rbkmoney.fraudo.FraudoParser.ParseContext parseContext = getParseContext(resourceAsStream);
ResultModel result = invokeParse(parseContext);
Assert.assertEquals(ResultStatus.DECLINE, result.getResultStatus());
Assert.assertEquals("1", result.getRuleChecked());
Mockito.when(countAggregator.count(anyObject(), any(), anyLong())).thenReturn(9);
Mockito.when(countAggregator.countError(anyObject(), any(), anyLong(), anyString())).thenReturn(6);

View File

@ -1,2 +1,2 @@
rule: 3 > 2 AND 1 = 1
rule:test_11: 3 > 2 AND 1 = 1
-> decline;