Истекшие задания activiti выбрасывают исключение при запуске сервера-Grails


Это относится к заданиям таймера рабочего процесса activiti в приложении grails.

При запуске приложения grails с истекшими заданиями исключение создается для обычных функций grails, таких как log и методы классов домена.

Например:

Caused by: groovy.lang.MissingPropertyException: No such property: log for class: com.service.common.UtilityService
    at org.codehaus.groovy.runtime.ScriptBytecodeAdapter.unwrap(ScriptBytecodeAdapter.java:49)
    at org.codehaus.groovy.runtime.callsite.PogoMetaClassGetPropertySite.getProperty(PogoMetaClassGetPropertySite.java:50)
    at org.codehaus.groovy.runtime.callsite.AbstractCallSite.callGroovyObjectGetProperty(AbstractCallSite.java:239)
    at com.service.common.UtilityService.insertToQueue(UtilityService.groovy:370)
    at sun.reflect.NativeMethodAccessorImpl.invoke0(Native Method)
    at sun.reflect.NativeMethodAccessorImpl.invoke(NativeMethodAccessorImpl.java:39)
    at sun.reflect.DelegatingMethodAccessorImpl.invoke(DelegatingMethodAccessorImpl.java:25)
    at java.lang.reflect.Method.invoke(Method.java:597)
    at org.activiti.engine.impl.javax.el.BeanELResolver.invoke(BeanELResolver.java:479)
    ... 71 more

Это происходит в среде разработки, запускающей приложение из Spring STS. Мы используем плагин activiti 5.8.2 для grails (1.3.6)

После полного запуска веб-приложения задания (расписание на время после запуска) выполняются правильно, и никакое исключение отсутствующего свойства не выбрасывается.

Несмотря на то, что мы можем исправить проблему отсутствующего свойства для журнала, используя вместо этого private static final log = LogFactory.getLog(this), тогда любая ссылка на доменные классы вызовет ошибку, например, с помощью метода get или find.

Например:

Caused by: groovy.lang.MissingMethodException: No signature of method: static com.domain.wr.WorkRequest.read() is applicable for argument types: (java.lang.String) values: [44700]
Possible solutions: getId(), getAt(java.lang.String), setId(java.lang.Long), grep(java.lang.Object), each(groovy.lang.Closure), find(groovy.lang.Closure)
    at groovy.lang.MetaClassImpl.invokeStaticMissingMethod(MetaClassImpl.java:1357)
    at groovy.lang.MetaClassImpl.invokeStaticMethod(MetaClassImpl.java:1343)
    at groovy.lang.ExpandoMetaClass.invokeStaticMethod(ExpandoMetaClass.java:1082)
    at org.codehaus.groovy.runtime.callsite.StaticMetaClassSite.call(StaticMetaClassSite.java:50)
    at org.codehaus.groovy.runtime.callsite.CallSiteArray.defaultCall(CallSiteArray.java:40)
    at org.codehaus.groovy.runtime.callsite.AbstractCallSite.call(AbstractCallSite.java:116)
    at org.codehaus.groovy.runtime.callsite.AbstractCallSite.call(AbstractCallSite.java:124)
    at com.service.common.UtilityService.insertToQueue(UtilityService.groovy:373)
    at sun.reflect.NativeMethodAccessorImpl.invoke0(Native Method)
    at sun.reflect.NativeMethodAccessorImpl.invoke(NativeMethodAccessorImpl.java:39)
    at sun.reflect.DelegatingMethodAccessorImpl.invoke(DelegatingMethodAccessorImpl.java:25)
    at java.lang.reflect.Method.invoke(Method.java:597)
    at org.activiti.engine.impl.javax.el.BeanELResolver.invoke(BeanELResolver.java:479)
    ... 71 more

Конфигурация Activiti

Конфигурация.заводной

// Added by the Grails Activiti plugin:
activiti {
      processEngineName = "activiti-engine-default"
      databaseType = "oracle"
      deploymentName = appName
      history = "audit" // "none", "activity", "audit" or "full"
      sessionUsernameKey = "username"
      useFormKey = true
      deploymentResources = ["classpath:activiti/escalation/WorkRequest.bpmn20.xml"]

}

Конфигурация.свойства

activiti.processEngineName =activiti-engine-default
activiti.databaseSchemaUpdate =true 
activiti.jobExecutorActivate =true
activiti.mailServerHost = "mail1.net"
activiti.mailServerPort = 25
activiti.mailServerUsername = ""
activiti.mailServerPassword = ""
activiti.mailServerDefaultFrom = ""

Это убивает мое приложение, поскольку время простоя делает рабочий процесс непригодным для выполнения задач таймера.

2 3

2 ответа:

У меня была более или менее та же проблема, и в нашем случае она была вызвана Activiti, начинающей выполнение заданий до завершения впрыска пружины. Вот почему это происходит только при запуске: задание обращается к свойствам, которых еще нет.

Вы можете подтвердить, что вы находитесь в той же ситуации, увеличив RETRIES_ в таблице ACT_RU_JOB после завершения загрузки приложения и посмотреть, успешно ли выполняются задания.

Если это ваш случай, я думаю, что единственный вариант-это чтобы обновить плагин и если все еще не удается, создать ошибку.

Этот вопрос был решен.
1) Изменить Конфигурацию.Groovy и отключить активити при запуске

 activiti {
          processEngineName = "activiti-engine-default"
          databaseType = "oracle"
          disabled = true
          deploymentName = appName
          sessionUsernameKey = "username"
          useFormKey = true
          deploymentResources = []
    }

2) Добавьте инициализацию объектов Activiti в метод init пользовательского BootStrap

def init = { servletContext ->

    org.springframework.context.ApplicationContext ctx = ServletContextHolder.getServletContext().getAttribute(GrailsApplicationAttributes.APPLICATION_CONTEXT)
    def bb = new grails.spring.BeanBuilder(ctx)
    bb.beans {
        //println "Activiti Process Engine Initialization..."
        customDbIdGenerator(com.mycompany.activiti.customDbIdGenerator){
            idBlockSize=CH.config.activiti.idBlockSize?:100
        }
        processEngineConfiguration(org.activiti.spring.SpringProcessEngineConfiguration) {
            processEngineName = CH.config.activiti.processEngineName?:ActivitiConstants.DEFAULT_PROCESS_ENGINE_NAME
            databaseType = CH.config.activiti.databaseType?:ActivitiConstants.DEFAULT_DATABASE_TYPE
            databaseSchemaUpdate = CH.config.activiti.databaseSchemaUpdate ? CH.config.activiti.databaseSchemaUpdate.toString() : ActivitiConstants.DEFAULT_DATABASE_SCHEMA_UPDATE
            deploymentName = CH.config.activiti.deploymentName?:ActivitiConstants.DEFAULT_DEPLOYMENT_NAME
            deploymentResources = CH.config.activiti.deploymentResources?:ActivitiConstants.DEFAULT_DEPLOYMENT_RESOURCES
            jobExecutorActivate = CH.config.activiti.jobExecutorActivate?:ActivitiConstants.DEFAULT_JOB_EXECUTOR_ACTIVATE
                  history = CH.config.activiti.history?:ActivitiConstants.DEFAULT_HISTORY
            mailServerHost = CH.config.activiti.mailServerHost?:ActivitiConstants.DEFAULT_MAIL_SERVER_HOST
            mailServerPort = CH.config.activiti.mailServerPort?:ActivitiConstants.DEFAULT_MAIL_SERVER_PORT
            mailServerUsername = CH.config.activiti.mailServerUsername
            mailServerPassword = CH.config.activiti.mailServerPassword
            mailServerDefaultFrom = CH.config.activiti.mailServerDefaultFrom?:ActivitiConstants.DEFAULT_MAIL_SERVER_FROM
            dataSource = ref("dataSource")
            transactionManager = ref("transactionManager")
            idGenerator= ref("customDbIdGenerator")
        }

          processEngine(org.activiti.spring.ProcessEngineFactoryBean) {
              processEngineConfiguration = ref("processEngineConfiguration")
          }

        runtimeService(processEngine:"getRuntimeService")
        repositoryService(processEngine:"getRepositoryService")
        taskService(processEngine:"getTaskService")
        managementService(processEngine:"getManagementService")
        identityService(processEngine:"getIdentityService")
        historyService(processEngine:"getHistoryService")
        formService(processEngine:"getFormService")

        activitiService(org.grails.activiti.ActivitiService) {
            runtimeService = ref("runtimeService")
            taskService = ref("taskService")
            identityService = ref("identityService")
            formService = ref("formService")
        }
    }
    println "## Registering Beans ##";
    bb.registerBeans(ctx);
    ctx.getBean("processEngine");

    println "Bean Count2 "+ctx.getBeanDefinitionCount();
}

Обратите внимание, что используемый генератор идентификаторов DB является пользовательским и может быть заменен на генератор по умолчанию.