zoukankan      html  css  js  c++  java
  • Drools使用注意事项

    使用场景:

    public void doCustomer() {
    //
    People people = new People();
    people.setName("哒");
    people.setSex(1);
    people.setDrlType("people");
    //
    KieServices kieServices = KieServices.Factory.get();
    StatelessKieSession kieSession = kieServices.getKieClasspathContainer().newStatelessKieSession("my-test");
    List<Command> commands = new ArrayList<>();
    KieCommands kieCommands = kieServices.getCommands();
    commands.add(kieCommands.newInsert(people, "input"));

    ExecutionResults execute = kieSession.execute(kieCommands.newBatchExecution(commands));

    }
    项目中,有两个地方调用doCustomer方法,一个是rabbitMq的监听类,一个是Controller接口处
    这两处的调用,由于当前线程的上下文加载器不同,导致只能有其中一处的调用正常,另外一个报错

    异常问题:

    抛出异常There's already another KieContainer created from a different ClassLoader

    解决方案:

    通过分析源码,发现:
    // 使用Holder内部类的方式,创建了一个单例对象
    KieServices kieServices = KieServices.Factory.get();

    // 使用Volatile + Double-Check的方式,创建了一个单例对象;
    KieContainer kieContainer = kieServices.getKieClasspathContainer(); 但是,代码中,会校验classLoader != classpathClassLoader ???

    前者为当前线程上下文类加载器,后者为第一次创建KieContainer的线程类加载器这么一分析,发现是两处的调用,线程上下文加载器不一致导致的报错。
    解决办法之一,就是,在项目启动的时候,初始化 KieServices 和 KieContainer 对象
    或者
    KieServices kieServices = KieServices.Factory.get();
    StatelessKieSession kieSession = kieServices.getKieClasspathContainer(this.getClass().getClassLoader()).newStatelessKieSession("my-test");
  • 相关阅读:
    【258】雅思口语常用话
    【256】◀▶IEW-答案
    UITabBarController 标签栏控制器
    枚举
    HDU3631:Shortest Path(Floyd)
    让Barebox正确引导Tiny6410的linux内核
    调度子系统2_核心调度器
    12.10 公司面试总结
    X265编译中C2220错误的解决办法
    JSP元素和标签
  • 原文地址:https://www.cnblogs.com/kobe-lin/p/14141756.html
Copyright © 2011-2022 走看看