简体   繁体   English

使用Spring的Infinispan,从缓存投射失败

[英]Infinispan with Spring, casting from cache failing

I have Spring 1.4 app which is deployed to WildFly 10, and it is using Infinispan 8.1 built in with WildFly. 我有Spring 1.4应用程序,该应用程序已部署到WildFly 10,它使用的是WildFly内置的Infinispan 8.1。

I have managed to deploy the app properly, and this is the configuration for the Infinispan: 1) CacheManager 我已经设法正确部署了应用程序,这是Infinispan的配置:1)CacheManager

@Bean
public CacheManager cacheManager() throws Exception {
    JndiTemplate jndiTemplate = new JndiTemplate();
    EmbeddedCacheManager embededCacheManager = (EmbeddedCacheManager) jndiTemplate.lookup("java:jboss/infinispan/container/CONTAINER");
    SpringEmbeddedCacheManager cacheManager = new SpringEmbeddedCacheManager(embededCacheManager);
}

2) pom.xml 2)pom.xml

<dependency>
    <groupId>org.infinispan</groupId>
    <artifactId>infinispan-spring</artifactId>
    <version>8.1.0.Final</version>
    <exclusions>
        <exclusion>
            <groupId>org.springframework.boot</groupId>
            <artifactId>spring-boot-starter-logging</artifactId>
        </exclusion>
        <exclusion>
            <groupId>javax.servlet</groupId>
            <artifactId>servlet-api</artifactId>
        </exclusion>
        <exclusion>
            <groupId>org.apache.logging.log4j</groupId>
            <artifactId>log4j-core</artifactId>
        </exclusion>
        <exclusion>
            <groupId>org.apache.logging.log4j</groupId>
            <artifactId>log4j-jcl</artifactId>
        </exclusion>
        <exclusion>
            <groupId>org.apache.logging.log4j</groupId>
            <artifactId>log4j-slf4j-impl</artifactId>
        </exclusion>
    </exclusions>
</dependency>

<plugin>
    <groupId>org.apache.maven.plugins</groupId>
    <artifactId>maven-war-plugin</artifactId>
    <configuration>
        <archive>
            <manifestEntries>
                <Dependencies>org.infinispan, org.infinispan.commons, org.jboss.as.clustering.infinispan export</Dependencies>
            </manifestEntries>
        </archive>
    </configuration>
</plugin>

When I deploy the app for the first time everything works fine. 当我第一次部署应用程序时,一切正常。 However, after the cache has been started, and when the application is redeployed I get the following error when using cache: 但是,在启动缓存后以及重新部署应用程序后,使用缓存时出现以下错误:

java.lang.ClassCastException: com.dplesa.Class cannot be cast to com.dplesa.Class

I tried this with different classes and no mater what I do, the error is the same. 我尝试使用不同的类进行此操作,但没有做任何事情,错误是相同的。 However, I don't get this error from caches where simple Strings are cached. 但是,我没有从缓存简单字符串的缓存中得到此错误。 What could cause this problem? 是什么导致此问题?

This may sound scary but in this case, the behavior is correct. 这听起来可能很可怕,但是在这种情况下,行为是正确的。

A class is always binded to a particular classloader. 类始终绑定到特定的类加载器。 Wildfly uses modular classloaders and each deployment uses different classloader instance. Wildfly使用模块化的类加载器,每个部署使用不同的类加载器实例。 Now imagine that you put some instances of your class using classloader 'A', do redeployment (classloader 'A' is being disposed and new deployment is loaded using classloader 'B') and try to read data from cache using classloader 'B'. 现在,假设您使用类加载器“ A”放置了类的某些实例,进行了重新部署(正在处理类加载器“ A”,并使用类加载器“ B”加载了新部署),并尝试使用类加载器“ B”从缓存中读取数据。 Those classloaders don't match and this results with your exception - Class com.dplesa.Class cannot be cast to com.dplesa.Class . 这些类加载器不匹配,并且出现例外情况com.dplesa.Class无法转换为com.dplesa.Class

There are several ways to fix this: 有几种方法可以解决此问题:

  1. Embed Infinispan with your application (using infinispan-embedded artifact for example). 将Infinispan与您的应用程序infinispan-embedded (例如,使用infinispan-embedded工件)。 With this trick, Infinispan will be loaded with the same classloader as your domain classes. 使用此技巧,Infinispan将使用与您的域类相同的类加载器进行加载。

  2. Put your domain classes in Wildfly modules. 将您的域类放在Wildfly模块中。

  3. Deploy Infinispan cluster separately and connect to it using HotRod Client (using infinispan-remote artifact for example). 分别部署Infinispan集群,并使用HotRod Client(例如,使用infinispan-remote工件)连接到该集群。

Solution #1 is the simplest but you need to pay attention what's happening to your cluster during redeployments (make sure your nodes join/leave the cluster properly, that your data replicates as you desire etc). 解决方案#1最简单,但是您需要注意重新部署期间集群所发生的事情(确保节点正确加入/离开集群,并根据需要复制数据等)。

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM