首页 > 解决方案 > 我不明白为什么 drools 规则会产生错误

问题描述

我是流口水的初学者。我有两种类似的代码。

第一个代码正在工作查找。但是第二个代码不起作用。

我不明白为什么这段代码不同。

请检查此问题。

规则文件 - 工作查找

 rule "VoLTE Validate Rule"
 dialect "mvel"
 when
      $uBody : VoLTEBody()
 then
       ArrayList ltErrorCd = new ArrayList();
       ErrorCD_Intl uErrCdOut = new ErrorCD_Intl("0001", "10", 1, "IMSI");
       ltErrorCd.add(uErrCdOut);

       String[] ltErrCd = new String[5];
       ErrorCD_Intl eachErrorCd = ltErrorCd.get(0);
       ltErrCd[0] = new String(eachErrorCd.sErrCd);
 end

规则文件 - 不工作

  rule "VoLTE Validate Rule"
  dialect "mvel"
  when
       $uBody : VoLTEBody()
  then
       ArrayList ltErrorCd = new ArrayList();
       ErrorCD_Intl uErrCdOut = new ErrorCD_Intl("0001", "10", 1, "IMSI");
       ltErrorCd.add(uErrCdOut);

       String[] ltErrCd = new String[5];
       for (int i=0; i<ltErrorCd.size(); i++) {
            ErrorCd_Intl eachErrorCd = ltErrorCd.get(i);
            ltErrCd[i] = new String(eachErrorCd.sErrCd);
       }
   end

错误

   Caused by: org.mvel2.PropertyAccessException: [Error: unable to resolve method: org.drools.core.base.DefaultKnowledgeHelper.eachErrorCd() [arglength=0]]
   [Near : {... rCd[i] = new String(eachErrorCd.sErrCd); ....}]
                                    ^

ErrorCD_Intl 类

 public class ErrorCD_Intl {
        public String sErrCd;
        public String sErrLevelDivCd;
        public int    iErrPriority;
        public String sOldErrCd;

 }

标签: drools

解决方案


This is a shortcoming of the MVEL language. It simplifies property navigation by allowing you to write eachErrorCd.sErrCd but it expects the class to actually have a getter methods for the field (getSErrCd()).

In situations where the field in the object is public, MVEL will still prefer to access the property via its getter method.

The getter method is obviously missing in your class therefore the expression fails. The error message doesn't help in identifying the cause, I admit.

You have two options to fix the issue:

  1. Add the getter method. Its name should probably be getSErrCd().
  2. Switch to java dialect. In this case, you'll have to add generic type arguments to the ArrayList:

    ArrayList<ErrorCD_Intl> ltErrorCd = new ArrayList<>();
    

P.S. I don't understand why the error doesn't occur if you do the same thing outside a for-loop.


推荐阅读