What's the differences between this Infinispan cache factories for Hibernate second level cache? - caching

I'm trying to figure out the difference between this factories, used in hibernate.cache.region.factory_class property.
Example:
<property name="hibernate.cache.region.factory_class" value="org.hibernate.cache.infinispan.JndiInfinispanRegionFactory" />
<property name="hibernate.cache.infinispan.cachemanager" value="java:jboss/infinispan/container/hibernate" />
There are 4 possible options.
The 2 options that I know something about is:
org.hibernate.cache.infinispan.InfinispanRegionFactory: for standalone aplications (not in a cluster, I think).
org.hibernate.cache.infinispan.JndiInfinispanRegionFactory: this is bounded to a JNDI in the property hibernate.cache.infinispan.cachemanager.
And I don't have any idea about these 2:
org.jboss.as.jpa.hibernate5.infinispan.SharedInfinispanRegionFactory: ?
org.jboss.as.jpa.hibernate5.infinispan.InfinispanRegionFactory: ?
We have a cluster configured on Wildfly 10.1.0 using domain mode. We want to share the entity cache among the nodes and we are having some doubts about how to do that.

If you're using Wildfly, you don't have to worry about setting the region factory class because Wildfly uses Infinispan as second-level cache provider by default. It's all explained here.
All you have to do is enable hibernate.cache.use_second_level_cache and you're good to go. See examples in the docu.

I agree with Galder, +1!
Regarding the purpose of [org.jboss.as.jpa.hibernate5.infinispan.SharedInfinispanRegionFactory][1] + [org.jboss.as.jpa.hibernate5.infinispan.InfinispanRegionFactory][2], these classes extend the Hibernate ORM [hibernate-infinispan][3] implementation classes, the purpose being to start the internal WildFly Infinispan cache services used for the JPA second level caching. They also deal with configuration as well. The below links may become outdated over time, as I think we [3] code might move to the Infinispan project (eventually).
A little more of the related code is at [HibernateSecondLevelCache.java][4], which backs up what Galder said. You can see that the WildFly JPA container automatically is setting the region factory class for you (if caching is enabled via [HibernatePersistenceProviderAdaptor.java][5].
I'm not sure if the code links are helpful to you, I thought they might be. :)
As a stackoverflow newbie, I am not allowed to post with more than 2 links, which is why [3] - [5] are invalid links.
Scott
[1] https://github.com/wildfly/wildfly/blob/master/jpa/hibernate5/src/main/java/org/jboss/as/jpa/hibernate5/infinispan/SharedInfinispanRegionFactory.java
[2] https://github.com/wildfly/wildfly/blob/master/jpa/hibernate5/src/main/java/org/jboss/as/jpa/hibernate5/infinispan/InfinispanRegionFactory.java
[3] github.com/hibernate/hibernate-orm/tree/master/hibernate-infinispan
[4] github.com/wildfly/wildfly/blob/master/jpa/hibernate5/src/main/java/org/jboss/as/jpa/hibernate5/HibernateSecondLevelCache.java
[5] github.com/wildfly/wildfly/blob/master/jpa/hibernate5/src/main/java/org/jboss/as/jpa/hibernate5/HibernatePersistenceProviderAdaptor.java#L91

The configuration envolves Infinispan, Hibernate and JGroups.
Using domain-mode on Wildfly10 you'll need this configuration on your application EAR:
<property name="hibernate.cache.use_second_level_cache" value="true"/>
Your server group need to use a profile that has the ha resources(high availability) such as full-ha or ha profiles. These profiles have the Infinispan and JGroups default configuration.
Then, you need to have the private 'Network Interfaces' on ALL Hosts' configuration that share the cache. JGroups uses the private Edit the domain/configuration/host.xml or use the wildfly console admin to add this configuration (200.0.0.171 needs to be replaced by the server's IP):
<interfaces>
...
<interface name="private">
<inet-address value="${jboss.bind.address.private:200.0.0.171}"/>
</interface>
<!-- .... -->
</interfaces>
For example, supposing you have a HostController HC1(with server-1 and server-2) and HC2(with server-3 and server-4)
Starting all the servers and Host Controllers, you'll see on your server.log:
INFO [org.infinispan.remoting.transport.jgroups.JGroupsTransport] (MSC service thread 1-4) ISPN000078: Starting JGroups channel hibernate
....
....
Received new cluster view for channel hibernate: [HC1:server-1, HC2-server-2, HC2-server-3, HC2-server-4]

Related

Binding datasource to application when using springBootApplication in Liberty?

When deploying "regular" web apps to Liberty, I was used to binding the global datasource configured in Liberty's server.xml to the individual application by using a child element within the element, like this:
<application context-root="helloApp" location="..." name="helloApp" type="war">
<application-bnd>
<data-source id="db2appDs" name="jdbc/datasource" binding-name="jdbc/theDB"/>
</application-bnd>
...
</application>
<dataSource id="db2ds" jndiName="jdbc/theDB" type="javax.sql.DataSource">
...
</dataSource>
When configuring my first Spring Boot application to deploy to Liberty, I am trying to use the new <springBootApplication> element for it - but I don't seem to be able to add a binding for the datasource I want to use the same way, as this element doesn't seem to support such a child. (It seems to want only <classloader> as a child).
I've seen people suggest I use an #Resource annotation that includes both application-local JDNI name and global JNDI name for the datasorce - but that defeats the purpose, since I don't want to know what the global name is until deploy time.
Is there another way to do this, like we used to before? Or are applications deployed through <springBootApplication> expected to know the global JNDI name of the datasource(s) they want?
Application-defined datasources are not supported for <springBootApplication/>’s. While your application may certainly access a Liberty datasource using its global JNDI name, you should configure the spring.datasource.jndi-name property within your Spring Boot application as described in section 29.1.3 of the Spring Boot features reference. For your example try spring.datasource.jndi-name=jdbc/theDB.

Connecting ActiveMQ Web-Console to an existing broker (instead of starting a new one)

Having deployed the activemq-web-console war into a Tomcat embedded application how can one make it connect to an existing broker rather than create a new one?
The war comes with a set of predefined configurations, in particular, the WEB-INF/activemq.xml contains a configuration for the BrokerService
<broker brokerName="web-console" useJmx="true" xmlns="http://activemq.apache.org/schema/core">
<persistenceAdapter><kahaDB directory="target/kahadb"/></persistenceAdapter>
<transportConnectors>
<transportConnector uri="tcp://localhost:12345"/>
</transportConnectors>
</broker>
used from webconsole-embedded.xml in the following manner:
<bean id="brokerService" class="org.apache.activemq.xbean.BrokerFactoryBean">
<property name="config" value="/WEB-INF/activemq.xml"/>
</bean>
This configuration creates a new instance of BrokerService and tries to start the broker.
It is reported that the web console can be used to monitor an existing broker service rather than creating a new one. For this one should set the following properties somewhere:
webconsole.type=properties
webconsole.jms.url=tcp://localhost:61616
webconsole.jmx.url=service:jmx:rmi:///jndi/rmi://localhost:1099/karaf-trun
The questions is, where does one have to set these properties within the Tomcat embedded app and which XML changes in the above have to be performed for them to be used. I cannot find any sensible explanation how to configure it, and a BrokerService instance seems to be required by the remaining spring config.
Any ideas?
Please do not suggest to use hawtio instead!
I had the same problem today. You can start the webconsole in "properties" mode which gives you the oppertunity to connect over jmx.
I added following java arguments to our Jboss 6.1 and it worked immediatley. I didn't change any of the xmls (works out of the box)...
Example:
-Dwebconsole.type=properties -Dwebconsole.jms.url=tcp://<hostname>:61616 -Dwebconsole.jmx.url=service:jmx:rmi:///jndi/rmi://<hostname>:1090/jmxrmi -Dwebconsole.jmx.user=admin -Dwebconsole.jmx.password=123456
Also discussed here: https://svn.apache.org/repos/infra/websites/production/activemq/content/5.7.0/web-console.html

How can I enable versioning?

I'd like to enable versioning for a replicated cache in a locally-running Infinispan server (8.2.4 final, two Infinispan servers form a cluster).
This is documented in the user guide.
Quote:
10.2.5. Configuration
By default versioning will be disabled.
and the user guide contains the following snippet:
<versioning scheme="SIMPLE|NONE" />
I am using locally-running Infinispan servers, the configuration is in clustered.xml.
A fragment thereof:
<subsystem xmlns="urn:infinispan:server:core:8.2" default-cache-container="clustered">
<cache-container name="clustered" default-cache="default" statistics="true">
[...]
<replicated-cache name="demoCache" mode="ASYNC" >
<versioning scheme="SIMPLE"/>
</replicated-cache>
So when I add the versioning element, starting fails with
Caused by: javax.xml.stream.XMLStreamException: ParseError at [row,col]:[186,6]
Message: WFLYCTL0198: Unexpected element '{urn:infinispan:server:core:8.2}versioning' encountered
The XML element versioning indeed exists in urn:infinispan:config:8.2, but not in urn:infinispan:server:core:8.2 (which is used in clustered.xml).
urn:infinispan:config:8.2 is defined in infinispan-server-8.2.4.Final/docs/schema/infinispan-config-8.2.xsd.
urn:infinispan:server:core:8.2 is defined in infinispan-server-8.2.4.Final/docs/schema/jboss-infinispan-core_8_2.xsd
How can I enable (cluster aware) versioning when running Infinispan as a separate server?
Versioning does not make sense when using Infinispan remotely since versioning is purely used to detect write skew situations with repeteable read transactions, and that functionality is not really available to users in server mode.

How to set up Eclipselink cache coordination with Wildfly

I have set up a persistancce caching with Eclipselink on Wildfly 8. It works, but I also want to do cache coordination. I have the following setup for Eclipselink cache coordination in my persistance.xml:
<property name="eclipselink.cache.coordination.protocol" value="jms" />
<property name="eclipselink.cache.coordination.jms.topic" value="jms/MemberTopic" />
<property name="eclipselink.cache.coordination.jms.factory" value="jms/MemberConnectionFactory" />
However, when my entity is merged, no messages are sent by Eclipselink. I have logging set to "ALL", but nothing appears in the console.
I tried adding coordinationType=CacheCoordinationType.SEND_NEW_OBJECTS_WITH_CHANGES to entity's #Cache annotation, but it doesn't change anything. Also tried using an MDB as suggested for WebSphere (http://www.eclipse.org/eclipselink/documentation/2.4/concepts/cache011.htm#CDECEHFH).
The JMS topic and connectionfactory exist and Wildfly startup / application deployment shows no errors. For server clustering I run Wildfly in domain mode.
The problem ironically was in my Wildfly configuration instead - I didn't have my messaging cluster set up. I used the default messaging cluster settings from full-ha profile and set Eclipselink's cache coordination host accordingly:
<property name="eclipselink.cache.coordination.jms.host" value="231.7.7.7:9876" />

how to get XADatasource using JNDI look up for Atomikos Transaction Management

I am configuring Atomikios TM API with my Spring Application to achieve global transaction. As Atomikios require XADatasource to work, so I have done JNDI look up to get the same. But, unfortunately I am getting following errors while doing the look up.
Object of type [class com.ibm.ws.rsadapter.jdbc.WSJdbcDataSource] available at JNDI location [jdbc/cuds] is not assignable to [javax.sql.XADataSource]
<jee:jndi-lookup id="dataSourceCu" jndi-name="jdbc/cuds" cache="true" resource-ref="true" lookup-on-startup="true" expected-type="javax.sql.XADataSource" />
<jee:jndi-lookup id="dataSourceGodb" jndi-name="jdbc/pushpullds" cache="true" resource-ref="true" lookup-on-startup="true" expected-type="javax.sql.XADataSource" />
I am using Spring 3.0/ hibernate with WebSphere 7.0.Where I am doing wrong. Please help me. Thanks.
The data source configured under jdbc/cuds is not an XADataSource but a normal one. You need to change the data source configuration in WebSphere (I have no idea how to do this).
However since you're on WebSphere which has it's own transaction manager there really is no need for configuring Atomikios. You can either use
<tx:jta-transaction-manager>
or org.springframework.transaction.jta.JtaTransactionManager / org.springframework.transaction.jta.WebSphereUowTransactionManager but the data source still needs to be XA.
XADataSource defines a contract between a JDBC provider and the application server and can only be used in that context. The DataSource object that you get when looking up the data source via JNDI in your application will never implement the XADataSource interface, even if the underlying data source is configured to support XA.
If you want to use your own transaction manager, then you would also have to manage the data sources yourself. Note that personally I wouldn't do that and strongly advice to use WebSphere's transaction manager instead. The reason is that distributed transactions involve lots of subtleties (e.g. recovery and in-doubt transactions) and it is unlikely that setting up a transaction manager inside an application would achieve the same level of robustness as WebSphere's transaction manager.

Resources