I am using Activiti BPM to implement a simple workflow. This workflow sends email to users and awaits user feedback. If feedback is not received for 24 hrs, it will again send the email and await for response.
I used boundary event like this:
<boundaryEvent id="boundarytimer1" name="Timer" attachedToRef="userTask" cancelActivity="true">
<timerEventDefinition>
<timeDuration>PT24H</timeDuration>
</timerEventDefinition>
</boundaryEvent>
I can see timer job created in ACT_RU_JOB table. However this job is not triggerred.
Probably you didn't set jobExecutorActivate=true inside your Activiti configuration.
<bean id="processEngineConfiguration" class="org.activiti.spring.SpringProcessEngineConfiguration">
<property name="dataSource" ref="dataSource" />
<property name="transactionManager" ref="transactionManager" />
<property name="databaseSchemaUpdate" value="true" />
<property name="jobExecutorActivate" value="true" />
<property name="history" value="activity"/>
</bean>
Hope it helps.
From activiti 6.0.0 Version
need to use springConfiguration.setAsyncExecutorActivate(true);
<bean id="processEngineConfiguration" class="org.activiti.spring.SpringProcessEngineConfiguration">
<property name="dataSource" ref="dataSource" />
<property name="transactionManager" ref="transactionManager" />
<property name="databaseSchemaUpdate" value="true" />
<property name="asyncExecutorActivate" value="true" />
<property name="history" value="activity"/>
</bean>
Related
Trying hands on with Spring Batch to read data which is created only yesterday. Below is the bean I am trying to use, using JdbcPagingItemReader & SqlPagingQueryProviderFactoryBean. However, the query isn't getting executed.
Appreciate your help!
<bean id="customersPagingItemReader"
class="org.springframework.batch.item.database.JdbcPagingItemReader"
scope="step">
<property name="dataSource" ref="dataSource" />
<property name="queryProvider">
<bean
class="org.springframework.batch.item.database.support.SqlPagingQueryProviderFactoryBean">
<property name="dataSource" ref="dataSource" />
<property name="selectClause" value="SELECT CUST_ID, CREATED " />
<property name="fromClause" value=" from CUSTOMERS" />
<property name="whereClause" value=" where CREATED >= trunc(SYSDATE-1) and CREATED < trunc(SYSDATE)" />
</bean>
</property>
<property name="pageSize" value="5" />
<property name="fetchSize" value="5" />
<property name="rowMapper">
<bean class="com.yahoo.affiliationapi.api.CustomerRowMapper" />
</property>
</bean>
I was able to figure this out. When I looked at the Job Step Exit Message says - 'sortKey must be specified'
I just added the below property to the above code & it started working fine.
<property name="sortKey" value="CUST_ID" />
you have to set sort key for queryProvider.
you can refer this example:
#Bean
public SqlPagingQueryProviderFactoryBean queryProvider() {
SqlPagingQueryProviderFactoryBean provider = new SqlPagingQueryProviderFactoryBean();
provider.setSelectClause("select id, name, credit");
provider.setFromClause("from customer");
provider.setWhereClause("where status=:status");
provider.setSortKey("id");
return provider;
}
I use activiti in my project. when i run project it crate all activiti tables in my (mysql) database. I want use embed H2 of activiti database. Now my question is how integrate activiti with spring that when i process a task all information save in embed database?
add this in you applicationContext.xml file
<!-- Activiti Configuration -->
<bean id="processEngine" class="org.activiti.spring.ProcessEngineFactoryBean">
<property name="processEngineConfiguration" ref="processEngineConfiguration" />
</bean>
<bean id="processEngineConfiguration" class="org.activiti.spring.SpringProcessEngineConfiguration">
<property name="dataSource" ref="dataSourceActiviti" />
<property name="transactionManager" ref="ActivitiTransactionManager" />
<property name="databaseSchemaUpdate" value="true" />
<property name="jobExecutorActivate" value="true" />
<!-- <property name="deploymentResources" value="classpath*:diagrams/*.bpmn20.xml"
/> -->
<!-- <property name="deploymentResources" value="classpath*:/diagrams/*.bpmn"
/> -->
</bean>
<bean id="dataSourceActiviti"
class="org.springframework.jdbc.datasource.SimpleDriverDataSource">
<property name="driverClassName" value="org.h2.Driver" />
<property name="url" value="jdbc:h2:mem:activiti;DB_CLOSE_DELAY=1000" />
<property name="username" value="sa" />
<property name="password" value="" />
</bean>
<bean id="ActivitiTransactionManager"
class="org.springframework.jdbc.datasource.DataSourceTransactionManager">
<property name="dataSource" ref="dataSourceActiviti" />
</bean>
<bean id="repositoryService" factory-bean="processEngine"
factory-method="getRepositoryService" />
<bean id="runtimeService" factory-bean="processEngine"
factory-method="getRuntimeService" />
<bean id="taskService" factory-bean="processEngine"
factory-method="getTaskService" />
<bean id="historyService" factory-bean="processEngine"
factory-method="getHistoryService" />
<bean id="managementService" factory-bean="processEngine"
factory-method="getManagementService" />
<bean id="formService" factory-bean="processEngine"
factory-method="getFormService" />
<bean id="identityService" factory-bean="processEngine"
factory-method="getIdentityService" />
Study Activiti's documentation which is quite good (link).
I'm sharing a link of example in which activiti is used in spring mvc project.
For your case, you can refer to the activiti http://www.activiti.org/userguide/#databaseConfiguration part
I am having an issue creating xa datasources in spring 4.0.
I have setup my datasources in weblogic using an xa driver.
I then added added jndi-lookups for the data sources in spring:
<jee:jndi-lookup id="dataSourceOne" jndi-name="/jdbc/XAONE" resource-ref="true" />
<jee:jndi-lookup id="dataSourceTwo" jndi-name="/jdbc/XATWO" resource-ref="true" />
I have then created the configuration for the entity managers:
<bean id="emfone" class="org.springframework.orm.jpa.LocalContainerEntityManagerFactoryBean">
<property name="dataSource" ref="dataSourceOne" />
<property name="jpaVendorAdapter" ref="jpaVendorAdapter" />
<property name="packagesToScan" value="..." />
</bean>
<bean id="emftwo"
class="org.springframework.orm.jpa.LocalContainerEntityManagerFactoryBean">
<property name="dataSource" ref="dataSourceTwo" />
<property name="jpaVendorAdapter" ref="jpaVendorAdapter" />
<property name="packagesToScan" value="..." />
</bean>
<bean id="jpaVendorAdapter"
class="org.springframework.orm.jpa.vendor.HibernateJpaVendorAdapter">
<property name="database" value="ORACLE" />
<property name="showSql" value="true" />
<property name="generateDdl" value="false" />
<property name="databasePlatform" value="org.hibernate.dialect.Oracle10gDialect" />
</bean>
After this I have my transaction manager configured:
<tx:annotation-driven />
<tx:jta-transaction-manager />
<bean id="transactionManager" class="org.springframework.orm.jpa.JpaTransactionManager">
<property name="entityManagerFactory" ref="emfone" />
<qualifier value="tmOne"/>
</bean>
<bean id="docTransactionManager" class="org.springframework.orm.jpa.JpaTransactionManager">
<property name="entityManagerFactory" ref="emftwo" />
<qualifier value="tmTwo"/>
</bean>
I have a service class method annotated with #Transactional that calls a DAO. The DAO uses both entity managers for persisting data.
When the DAO tries to persist using the emftwo a no transaction in progress error is thrown. Does anybody know where I am going wrong?
Thanks,
I have a Batch Job Configured to read messages from JMS Destination and write to a XML file using Chuck Tasklet. The JMS reader is custom implemented which inturn invokes JMSTemplate's receive method. I am using webMethods Broker as JMS Broker. During Batch run, we observed that the Consumer session created while reading the messages from Broker Destination are not being destroyed up on completion of the batch. They are only destroyed after I shutdown the JVM. I have provided more details below,
JMS Spring XML Configuration :
<bean id="JMS.SourceQueue.JndiTemplate" class="org.springframework.jndi.JndiTemplate">
<property name="environment">
<map>
<entry key="java.naming.provider.url" value="wmjmsnaming://Broker #1#X.X.X.X:6849" />
<entry key="java.naming.factory.initial" value="com.webmethods.jms.naming.WmJmsNamingCtxFactory" />
<entry key="com.webmethods.jms.naming.clientgroup" value="IS-JMS" />
</map>
</property>
</bean>
<bean id="JMS.SourceQueue.JmsConnectionFactory" class="org.springframework.jndi.JndiObjectFactoryBean">
<property name="jndiTemplate" ref="JMS.SourceQueue.JndiTemplate" />
<property name="jndiName" value="SmartBatchConnectionFactory" />
<property name="lookupOnStartup" value="true" />
<property name="cache" value="false" />
<property name="proxyInterface" value="javax.jms.ConnectionFactory" />
</bean>
<bean id="JMS.SourceQueue.ConnectionFactory"
class="org.springframework.jms.connection.CachingConnectionFactory">
<constructor-arg ref="JMS.SourceQueue.JmsConnectionFactory" />
</bean>
<bean id="JMS.SourceQueue.DefaultDestination" class="org.springframework.jndi.JndiObjectFactoryBean">
<property name="jndiTemplate" ref="JMS.SourceQueue.JndiTemplate" />
<property name="jndiName" value="SourceQueue" />
</bean>
<bean id="JMS.SourceQueue.MessageTemplate" class="org.springframework.jms.core.JmsTemplate">
<property name="connectionFactory" ref="JMS.SourceQueue.ConnectionFactory" />
<property name="receiveTimeout" value="10000" />
<property name="sessionTransacted" value="true" />
<property name="defaultDestination" ref="JMS.SourceQueue.DefaultDestination" />
</bean>
Any help on pointing out the actual issue would be great.
Call destroy() on the JMS.SourceQueue.ConnectionFactory at the end of the last step (or otherwise when the job is completed).
Using the caching connection factory is recommended to avoid creating connections/consumers for each message, but it needs to be told when to physically release the resources.
We have an ActiveMQ / Camel configuration that has previously been using exclusively message queues, with concurrent consumers.
However, we're now introducing message topics, and finding that - because of the concurrent consumers - messages received in the topic are consumed mulltiple times.
What's the correct configuration for this scenario?
ie., we want multiple concurrent consumers for messages received on a queue, but only a single consumer defined for messages received on a topic.
Here's the current configuration:
<amq:connectionFactory id="amqConnectionFactory"
useAsyncSend="true" brokerURL="${${ptl.Servername}.jms.cluster.uri}"
userName="${jms.username}" password="${jms.password}" sendTimeout="1000"
optimizeAcknowledge="true" disableTimeStampsByDefault="true">
</amq:connectionFactory>
<bean id="cachingConnectionFactory"
class="org.springframework.jms.connection.CachingConnectionFactory">
<property name="targetConnectionFactory" ref="amqConnectionFactory"></property>
<property name="cacheConsumers" value="true"></property>
<property name="cacheProducers" value="true"></property>
<property name="reconnectOnException" value="true"></property>
<property name="sessionCacheSize" value="${jms.sessioncachesize}"></property>
</bean>
<bean id="jmsConfig" class="org.apache.camel.component.jms.JmsConfiguration">
<property name="connectionFactory" ref="cachingConnectionFactory" />
<property name="transacted" value="false" />
<property name="concurrentConsumers" value="${jms.concurrentConsumer}" />
<property name="maxConcurrentConsumers" value="${jms.max.concurrentConsumer}" />
<property name="preserveMessageQos" value="true" />
<property name="timeToLive" value="${jms.timeToLive}" />
</bean>
<bean id="activemq" class="org.apache.activemq.camel.component.ActiveMQComponent">
<property name="configuration" ref="jmsConfig" />
</bean>
you can explicitly set concurrentConsumers/maxConcurrentConsumers to "1" for any topic consumers.
from("activemq:topic:myTopic?concurrentConsumers=1&maxConcurrentConsumers=1")...
alternatively, set the JmsConfiguration concurrent/maxConcurrentConsumers properties to "1" and then explicitly enable concurrent consumption for queues as needed.
from("activemq:queue:myQueue?maxConcurrentConsumers=5")...
also, you can use Virtual Topics to perform concurrent consumption of Topic messages without getting duplicates (highly recommended over traditional Topics)
The solution I ended up using was to create a separate jmsConfig/activeMQ config block.
The total configration looks as follows:
<!-- This is appropriate for consuming Queues, but not topics. For topics, use
jmsTopicConfig / activemqTopics -->
<bean id="jmsConfig" class="org.apache.camel.component.jms.JmsConfiguration">
<property name="connectionFactory" ref="cachingConnectionFactory" />
<property name="transacted" value="false" />
<property name="concurrentConsumers" value="${jms.concurrentConsumer}" />
<property name="maxConcurrentConsumers" value="${jms.max.concurrentConsumer}" />
<property name="preserveMessageQos" value="true" />
<property name="timeToLive" value="${jms.timeToLive}" />
</bean>
<bean id="activemq" class="org.apache.activemq.camel.component.ActiveMQComponent">
<property name="configuration" ref="jmsConfig" />
</bean>
<!-- This config limits to a single concurrent consumer. This config is appropriate for
consuming Topics, not Queues. -->
<bean id="jmsTopicConfig" class="org.apache.camel.component.jms.JmsConfiguration">
<property name="connectionFactory" ref="cachingConnectionFactory" />
<property name="transacted" value="false" />
<property name="concurrentConsumers" value="1" />
<property name="maxConcurrentConsumers" value="1" />
<property name="preserveMessageQos" value="true" />
<property name="timeToLive" value="${jms.timeToLive}" />
</bean>
<bean id="activemqTopics" class="org.apache.activemq.camel.component.ActiveMQComponent">
<property name="configuration" ref="jmsTopicConfig" />
</bean>
Then, in the camel pipeline, consuming the topic off the activemqTopics bean, as follows:
<camel:route id="myTopicResponder">
<camel:from uri="activemqTopics:topic:stockQuotes?concurrentConsumers=1" />
<camel:to uri="bean:stockQuoteResponder?method=saveStockQuote"/>
</camel:route>