Jakarta EE 9 migration
Upgrades many dependency declarations; removes old EJB 2.x support and outdated Servlet-based integrations (Commons FileUpload, FreeMarker JSP support, Tiles). Closes gh-22093 Closes gh-25354 Closes gh-26185 Closes gh-27423 See gh-27424
This commit is contained in:
@@ -1,85 +0,0 @@
|
||||
/*
|
||||
* Copyright 2002-2019 the original author or authors.
|
||||
*
|
||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
||||
* you may not use this file except in compliance with the License.
|
||||
* You may obtain a copy of the License at
|
||||
*
|
||||
* https://www.apache.org/licenses/LICENSE-2.0
|
||||
*
|
||||
* Unless required by applicable law or agreed to in writing, software
|
||||
* distributed under the License is distributed on an "AS IS" BASIS,
|
||||
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
* See the License for the specific language governing permissions and
|
||||
* limitations under the License.
|
||||
*/
|
||||
|
||||
package org.springframework.cache.ehcache;
|
||||
|
||||
import net.sf.ehcache.CacheManager;
|
||||
import net.sf.ehcache.config.CacheConfiguration;
|
||||
import net.sf.ehcache.config.Configuration;
|
||||
import org.junit.jupiter.api.AfterEach;
|
||||
import org.junit.jupiter.api.BeforeEach;
|
||||
|
||||
import org.springframework.cache.transaction.AbstractTransactionSupportingCacheManagerTests;
|
||||
|
||||
/**
|
||||
* @author Stephane Nicoll
|
||||
*/
|
||||
public class EhCacheCacheManagerTests extends AbstractTransactionSupportingCacheManagerTests<EhCacheCacheManager> {
|
||||
|
||||
private CacheManager nativeCacheManager;
|
||||
|
||||
private EhCacheCacheManager cacheManager;
|
||||
|
||||
private EhCacheCacheManager transactionalCacheManager;
|
||||
|
||||
|
||||
@BeforeEach
|
||||
public void setup() {
|
||||
nativeCacheManager = new CacheManager(new Configuration().name("EhCacheCacheManagerTests")
|
||||
.defaultCache(new CacheConfiguration("default", 100)));
|
||||
addNativeCache(CACHE_NAME);
|
||||
|
||||
cacheManager = new EhCacheCacheManager(nativeCacheManager);
|
||||
cacheManager.setTransactionAware(false);
|
||||
cacheManager.afterPropertiesSet();
|
||||
|
||||
transactionalCacheManager = new EhCacheCacheManager(nativeCacheManager);
|
||||
transactionalCacheManager.setTransactionAware(true);
|
||||
transactionalCacheManager.afterPropertiesSet();
|
||||
}
|
||||
|
||||
@AfterEach
|
||||
public void shutdown() {
|
||||
nativeCacheManager.shutdown();
|
||||
}
|
||||
|
||||
|
||||
@Override
|
||||
protected EhCacheCacheManager getCacheManager(boolean transactionAware) {
|
||||
if (transactionAware) {
|
||||
return transactionalCacheManager;
|
||||
}
|
||||
else {
|
||||
return cacheManager;
|
||||
}
|
||||
}
|
||||
|
||||
@Override
|
||||
protected Class<? extends org.springframework.cache.Cache> getCacheType() {
|
||||
return EhCacheCache.class;
|
||||
}
|
||||
|
||||
@Override
|
||||
protected void addNativeCache(String cacheName) {
|
||||
nativeCacheManager.addCache(cacheName);
|
||||
}
|
||||
|
||||
@Override
|
||||
protected void removeNativeCache(String cacheName) {
|
||||
nativeCacheManager.removeCache(cacheName);
|
||||
}
|
||||
|
||||
}
|
||||
@@ -1,91 +0,0 @@
|
||||
/*
|
||||
* Copyright 2002-2019 the original author or authors.
|
||||
*
|
||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
||||
* you may not use this file except in compliance with the License.
|
||||
* You may obtain a copy of the License at
|
||||
*
|
||||
* https://www.apache.org/licenses/LICENSE-2.0
|
||||
*
|
||||
* Unless required by applicable law or agreed to in writing, software
|
||||
* distributed under the License is distributed on an "AS IS" BASIS,
|
||||
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
* See the License for the specific language governing permissions and
|
||||
* limitations under the License.
|
||||
*/
|
||||
|
||||
package org.springframework.cache.ehcache;
|
||||
|
||||
import net.sf.ehcache.CacheManager;
|
||||
import net.sf.ehcache.Ehcache;
|
||||
import net.sf.ehcache.Element;
|
||||
import net.sf.ehcache.config.CacheConfiguration;
|
||||
import net.sf.ehcache.config.Configuration;
|
||||
import org.junit.jupiter.api.AfterEach;
|
||||
import org.junit.jupiter.api.BeforeEach;
|
||||
import org.junit.jupiter.api.Test;
|
||||
|
||||
import org.springframework.context.testfixture.cache.AbstractCacheTests;
|
||||
import org.springframework.core.testfixture.EnabledForTestGroups;
|
||||
|
||||
import static org.assertj.core.api.Assertions.assertThat;
|
||||
import static org.springframework.core.testfixture.TestGroup.LONG_RUNNING;
|
||||
|
||||
/**
|
||||
* @author Costin Leau
|
||||
* @author Stephane Nicoll
|
||||
* @author Juergen Hoeller
|
||||
*/
|
||||
public class EhCacheCacheTests extends AbstractCacheTests<EhCacheCache> {
|
||||
|
||||
private CacheManager cacheManager;
|
||||
|
||||
private Ehcache nativeCache;
|
||||
|
||||
private EhCacheCache cache;
|
||||
|
||||
|
||||
@BeforeEach
|
||||
public void setup() {
|
||||
cacheManager = new CacheManager(new Configuration().name("EhCacheCacheTests")
|
||||
.defaultCache(new CacheConfiguration("default", 100)));
|
||||
nativeCache = new net.sf.ehcache.Cache(new CacheConfiguration(CACHE_NAME, 100));
|
||||
cacheManager.addCache(nativeCache);
|
||||
|
||||
cache = new EhCacheCache(nativeCache);
|
||||
}
|
||||
|
||||
@AfterEach
|
||||
public void shutdown() {
|
||||
cacheManager.shutdown();
|
||||
}
|
||||
|
||||
|
||||
@Override
|
||||
protected EhCacheCache getCache() {
|
||||
return cache;
|
||||
}
|
||||
|
||||
@Override
|
||||
protected Ehcache getNativeCache() {
|
||||
return nativeCache;
|
||||
}
|
||||
|
||||
|
||||
@Test
|
||||
@EnabledForTestGroups(LONG_RUNNING)
|
||||
public void testExpiredElements() throws Exception {
|
||||
String key = "brancusi";
|
||||
String value = "constantin";
|
||||
Element brancusi = new Element(key, value);
|
||||
// ttl = 10s
|
||||
brancusi.setTimeToLive(3);
|
||||
nativeCache.put(brancusi);
|
||||
|
||||
assertThat(cache.get(key).get()).isEqualTo(value);
|
||||
// wait for the entry to expire
|
||||
Thread.sleep(5 * 1000);
|
||||
assertThat(cache.get(key)).isNull();
|
||||
}
|
||||
|
||||
}
|
||||
@@ -1,287 +0,0 @@
|
||||
/*
|
||||
* Copyright 2002-2019 the original author or authors.
|
||||
*
|
||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
||||
* you may not use this file except in compliance with the License.
|
||||
* You may obtain a copy of the License at
|
||||
*
|
||||
* https://www.apache.org/licenses/LICENSE-2.0
|
||||
*
|
||||
* Unless required by applicable law or agreed to in writing, software
|
||||
* distributed under the License is distributed on an "AS IS" BASIS,
|
||||
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
* See the License for the specific language governing permissions and
|
||||
* limitations under the License.
|
||||
*/
|
||||
|
||||
package org.springframework.cache.ehcache;
|
||||
|
||||
import net.sf.ehcache.Cache;
|
||||
import net.sf.ehcache.CacheException;
|
||||
import net.sf.ehcache.CacheManager;
|
||||
import net.sf.ehcache.Ehcache;
|
||||
import net.sf.ehcache.config.CacheConfiguration;
|
||||
import net.sf.ehcache.constructs.blocking.BlockingCache;
|
||||
import net.sf.ehcache.constructs.blocking.SelfPopulatingCache;
|
||||
import net.sf.ehcache.constructs.blocking.UpdatingCacheEntryFactory;
|
||||
import net.sf.ehcache.constructs.blocking.UpdatingSelfPopulatingCache;
|
||||
import org.junit.jupiter.api.Test;
|
||||
|
||||
import org.springframework.core.io.ClassPathResource;
|
||||
|
||||
import static org.assertj.core.api.Assertions.assertThat;
|
||||
import static org.assertj.core.api.Assertions.assertThatExceptionOfType;
|
||||
|
||||
/**
|
||||
* @author Juergen Hoeller
|
||||
* @author Dmitriy Kopylenko
|
||||
* @since 27.09.2004
|
||||
*/
|
||||
public class EhCacheSupportTests {
|
||||
|
||||
@Test
|
||||
public void testBlankCacheManager() {
|
||||
EhCacheManagerFactoryBean cacheManagerFb = new EhCacheManagerFactoryBean();
|
||||
cacheManagerFb.setCacheManagerName("myCacheManager");
|
||||
assertThat(cacheManagerFb.getObjectType()).isEqualTo(CacheManager.class);
|
||||
assertThat(cacheManagerFb.isSingleton()).as("Singleton property").isTrue();
|
||||
cacheManagerFb.afterPropertiesSet();
|
||||
try {
|
||||
CacheManager cm = cacheManagerFb.getObject();
|
||||
assertThat(cm.getCacheNames().length == 0).as("Loaded CacheManager with no caches").isTrue();
|
||||
Cache myCache1 = cm.getCache("myCache1");
|
||||
assertThat(myCache1 == null).as("No myCache1 defined").isTrue();
|
||||
}
|
||||
finally {
|
||||
cacheManagerFb.destroy();
|
||||
}
|
||||
}
|
||||
|
||||
@Test
|
||||
public void testCacheManagerConflict() {
|
||||
EhCacheManagerFactoryBean cacheManagerFb = new EhCacheManagerFactoryBean();
|
||||
try {
|
||||
cacheManagerFb.setCacheManagerName("myCacheManager");
|
||||
assertThat(cacheManagerFb.getObjectType()).isEqualTo(CacheManager.class);
|
||||
assertThat(cacheManagerFb.isSingleton()).as("Singleton property").isTrue();
|
||||
cacheManagerFb.afterPropertiesSet();
|
||||
CacheManager cm = cacheManagerFb.getObject();
|
||||
assertThat(cm.getCacheNames().length == 0).as("Loaded CacheManager with no caches").isTrue();
|
||||
Cache myCache1 = cm.getCache("myCache1");
|
||||
assertThat(myCache1 == null).as("No myCache1 defined").isTrue();
|
||||
|
||||
EhCacheManagerFactoryBean cacheManagerFb2 = new EhCacheManagerFactoryBean();
|
||||
cacheManagerFb2.setCacheManagerName("myCacheManager");
|
||||
assertThatExceptionOfType(CacheException.class).as("because of naming conflict").isThrownBy(
|
||||
cacheManagerFb2::afterPropertiesSet);
|
||||
}
|
||||
finally {
|
||||
cacheManagerFb.destroy();
|
||||
}
|
||||
}
|
||||
|
||||
@Test
|
||||
public void testAcceptExistingCacheManager() {
|
||||
EhCacheManagerFactoryBean cacheManagerFb = new EhCacheManagerFactoryBean();
|
||||
cacheManagerFb.setCacheManagerName("myCacheManager");
|
||||
assertThat(cacheManagerFb.getObjectType()).isEqualTo(CacheManager.class);
|
||||
assertThat(cacheManagerFb.isSingleton()).as("Singleton property").isTrue();
|
||||
cacheManagerFb.afterPropertiesSet();
|
||||
try {
|
||||
CacheManager cm = cacheManagerFb.getObject();
|
||||
assertThat(cm.getCacheNames().length == 0).as("Loaded CacheManager with no caches").isTrue();
|
||||
Cache myCache1 = cm.getCache("myCache1");
|
||||
assertThat(myCache1 == null).as("No myCache1 defined").isTrue();
|
||||
|
||||
EhCacheManagerFactoryBean cacheManagerFb2 = new EhCacheManagerFactoryBean();
|
||||
cacheManagerFb2.setCacheManagerName("myCacheManager");
|
||||
cacheManagerFb2.setAcceptExisting(true);
|
||||
cacheManagerFb2.afterPropertiesSet();
|
||||
CacheManager cm2 = cacheManagerFb2.getObject();
|
||||
assertThat(cm2).isSameAs(cm);
|
||||
cacheManagerFb2.destroy();
|
||||
}
|
||||
finally {
|
||||
cacheManagerFb.destroy();
|
||||
}
|
||||
}
|
||||
|
||||
public void testCacheManagerFromConfigFile() {
|
||||
EhCacheManagerFactoryBean cacheManagerFb = new EhCacheManagerFactoryBean();
|
||||
cacheManagerFb.setConfigLocation(new ClassPathResource("testEhcache.xml", getClass()));
|
||||
cacheManagerFb.setCacheManagerName("myCacheManager");
|
||||
cacheManagerFb.afterPropertiesSet();
|
||||
try {
|
||||
CacheManager cm = cacheManagerFb.getObject();
|
||||
assertThat(cm.getCacheNames().length == 1).as("Correct number of caches loaded").isTrue();
|
||||
Cache myCache1 = cm.getCache("myCache1");
|
||||
assertThat(myCache1.getCacheConfiguration().isEternal()).as("myCache1 is not eternal").isFalse();
|
||||
assertThat(myCache1.getCacheConfiguration().getMaxEntriesLocalHeap() == 300).as("myCache1.maxElements == 300").isTrue();
|
||||
}
|
||||
finally {
|
||||
cacheManagerFb.destroy();
|
||||
}
|
||||
}
|
||||
|
||||
@Test
|
||||
public void testEhCacheFactoryBeanWithDefaultCacheManager() {
|
||||
doTestEhCacheFactoryBean(false);
|
||||
}
|
||||
|
||||
@Test
|
||||
public void testEhCacheFactoryBeanWithExplicitCacheManager() {
|
||||
doTestEhCacheFactoryBean(true);
|
||||
}
|
||||
|
||||
private void doTestEhCacheFactoryBean(boolean useCacheManagerFb) {
|
||||
Cache cache;
|
||||
EhCacheManagerFactoryBean cacheManagerFb = null;
|
||||
boolean cacheManagerFbInitialized = false;
|
||||
try {
|
||||
EhCacheFactoryBean cacheFb = new EhCacheFactoryBean();
|
||||
Class<? extends Ehcache> objectType = cacheFb.getObjectType();
|
||||
assertThat(Ehcache.class.isAssignableFrom(objectType)).isTrue();
|
||||
assertThat(cacheFb.isSingleton()).as("Singleton property").isTrue();
|
||||
if (useCacheManagerFb) {
|
||||
cacheManagerFb = new EhCacheManagerFactoryBean();
|
||||
cacheManagerFb.setConfigLocation(new ClassPathResource("testEhcache.xml", getClass()));
|
||||
cacheManagerFb.setCacheManagerName("cache");
|
||||
cacheManagerFb.afterPropertiesSet();
|
||||
cacheManagerFbInitialized = true;
|
||||
cacheFb.setCacheManager(cacheManagerFb.getObject());
|
||||
}
|
||||
|
||||
cacheFb.setCacheName("myCache1");
|
||||
cacheFb.afterPropertiesSet();
|
||||
cache = (Cache) cacheFb.getObject();
|
||||
Class<? extends Ehcache> objectType2 = cacheFb.getObjectType();
|
||||
assertThat(objectType2).isSameAs(objectType);
|
||||
CacheConfiguration config = cache.getCacheConfiguration();
|
||||
assertThat(cache.getName()).isEqualTo("myCache1");
|
||||
if (useCacheManagerFb){
|
||||
assertThat(config.getMaxEntriesLocalHeap()).as("myCache1.maxElements").isEqualTo(300);
|
||||
}
|
||||
else {
|
||||
assertThat(config.getMaxEntriesLocalHeap()).as("myCache1.maxElements").isEqualTo(10000);
|
||||
}
|
||||
|
||||
// Cache region is not defined. Should create one with default properties.
|
||||
cacheFb = new EhCacheFactoryBean();
|
||||
if (useCacheManagerFb) {
|
||||
cacheFb.setCacheManager(cacheManagerFb.getObject());
|
||||
}
|
||||
cacheFb.setCacheName("undefinedCache");
|
||||
cacheFb.afterPropertiesSet();
|
||||
cache = (Cache) cacheFb.getObject();
|
||||
config = cache.getCacheConfiguration();
|
||||
assertThat(cache.getName()).isEqualTo("undefinedCache");
|
||||
assertThat(config.getMaxEntriesLocalHeap() == 10000).as("default maxElements is correct").isTrue();
|
||||
assertThat(config.isEternal()).as("default eternal is correct").isFalse();
|
||||
assertThat(config.getTimeToLiveSeconds() == 120).as("default timeToLive is correct").isTrue();
|
||||
assertThat(config.getTimeToIdleSeconds() == 120).as("default timeToIdle is correct").isTrue();
|
||||
assertThat(config.getDiskExpiryThreadIntervalSeconds() == 120).as("default diskExpiryThreadIntervalSeconds is correct").isTrue();
|
||||
|
||||
// overriding the default properties
|
||||
cacheFb = new EhCacheFactoryBean();
|
||||
if (useCacheManagerFb) {
|
||||
cacheFb.setCacheManager(cacheManagerFb.getObject());
|
||||
}
|
||||
cacheFb.setBeanName("undefinedCache2");
|
||||
cacheFb.setMaxEntriesLocalHeap(5);
|
||||
cacheFb.setTimeToLive(8);
|
||||
cacheFb.setTimeToIdle(7);
|
||||
cacheFb.setDiskExpiryThreadIntervalSeconds(10);
|
||||
cacheFb.afterPropertiesSet();
|
||||
cache = (Cache) cacheFb.getObject();
|
||||
config = cache.getCacheConfiguration();
|
||||
|
||||
assertThat(cache.getName()).isEqualTo("undefinedCache2");
|
||||
assertThat(config.getMaxEntriesLocalHeap() == 5).as("overridden maxElements is correct").isTrue();
|
||||
assertThat(config.getTimeToLiveSeconds() == 8).as("default timeToLive is correct").isTrue();
|
||||
assertThat(config.getTimeToIdleSeconds() == 7).as("default timeToIdle is correct").isTrue();
|
||||
assertThat(config.getDiskExpiryThreadIntervalSeconds() == 10).as("overridden diskExpiryThreadIntervalSeconds is correct").isTrue();
|
||||
}
|
||||
finally {
|
||||
if (cacheManagerFbInitialized) {
|
||||
cacheManagerFb.destroy();
|
||||
}
|
||||
else {
|
||||
CacheManager.getInstance().shutdown();
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
@Test
|
||||
public void testEhCacheFactoryBeanWithBlockingCache() {
|
||||
EhCacheManagerFactoryBean cacheManagerFb = new EhCacheManagerFactoryBean();
|
||||
cacheManagerFb.afterPropertiesSet();
|
||||
try {
|
||||
CacheManager cm = cacheManagerFb.getObject();
|
||||
EhCacheFactoryBean cacheFb = new EhCacheFactoryBean();
|
||||
cacheFb.setCacheManager(cm);
|
||||
cacheFb.setCacheName("myCache1");
|
||||
cacheFb.setBlocking(true);
|
||||
assertThat(BlockingCache.class).isEqualTo(cacheFb.getObjectType());
|
||||
cacheFb.afterPropertiesSet();
|
||||
Ehcache myCache1 = cm.getEhcache("myCache1");
|
||||
boolean condition = myCache1 instanceof BlockingCache;
|
||||
assertThat(condition).isTrue();
|
||||
}
|
||||
finally {
|
||||
cacheManagerFb.destroy();
|
||||
}
|
||||
}
|
||||
|
||||
@Test
|
||||
public void testEhCacheFactoryBeanWithSelfPopulatingCache() {
|
||||
EhCacheManagerFactoryBean cacheManagerFb = new EhCacheManagerFactoryBean();
|
||||
cacheManagerFb.afterPropertiesSet();
|
||||
try {
|
||||
CacheManager cm = cacheManagerFb.getObject();
|
||||
EhCacheFactoryBean cacheFb = new EhCacheFactoryBean();
|
||||
cacheFb.setCacheManager(cm);
|
||||
cacheFb.setCacheName("myCache1");
|
||||
cacheFb.setCacheEntryFactory(key -> key);
|
||||
assertThat(SelfPopulatingCache.class).isEqualTo(cacheFb.getObjectType());
|
||||
cacheFb.afterPropertiesSet();
|
||||
Ehcache myCache1 = cm.getEhcache("myCache1");
|
||||
boolean condition = myCache1 instanceof SelfPopulatingCache;
|
||||
assertThat(condition).isTrue();
|
||||
assertThat(myCache1.get("myKey1").getObjectValue()).isEqualTo("myKey1");
|
||||
}
|
||||
finally {
|
||||
cacheManagerFb.destroy();
|
||||
}
|
||||
}
|
||||
|
||||
@Test
|
||||
public void testEhCacheFactoryBeanWithUpdatingSelfPopulatingCache() {
|
||||
EhCacheManagerFactoryBean cacheManagerFb = new EhCacheManagerFactoryBean();
|
||||
cacheManagerFb.afterPropertiesSet();
|
||||
try {
|
||||
CacheManager cm = cacheManagerFb.getObject();
|
||||
EhCacheFactoryBean cacheFb = new EhCacheFactoryBean();
|
||||
cacheFb.setCacheManager(cm);
|
||||
cacheFb.setCacheName("myCache1");
|
||||
cacheFb.setCacheEntryFactory(new UpdatingCacheEntryFactory() {
|
||||
@Override
|
||||
public Object createEntry(Object key) {
|
||||
return key;
|
||||
}
|
||||
@Override
|
||||
public void updateEntryValue(Object key, Object value) {
|
||||
}
|
||||
});
|
||||
assertThat(UpdatingSelfPopulatingCache.class).isEqualTo(cacheFb.getObjectType());
|
||||
cacheFb.afterPropertiesSet();
|
||||
Ehcache myCache1 = cm.getEhcache("myCache1");
|
||||
boolean condition = myCache1 instanceof UpdatingSelfPopulatingCache;
|
||||
assertThat(condition).isTrue();
|
||||
assertThat(myCache1.get("myKey1").getObjectValue()).isEqualTo("myKey1");
|
||||
}
|
||||
finally {
|
||||
cacheManagerFb.destroy();
|
||||
}
|
||||
}
|
||||
|
||||
}
|
||||
@@ -1,35 +0,0 @@
|
||||
/*
|
||||
* Copyright 2002-2017 the original author or authors.
|
||||
*
|
||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
||||
* you may not use this file except in compliance with the License.
|
||||
* You may obtain a copy of the License at
|
||||
*
|
||||
* https://www.apache.org/licenses/LICENSE-2.0
|
||||
*
|
||||
* Unless required by applicable law or agreed to in writing, software
|
||||
* distributed under the License is distributed on an "AS IS" BASIS,
|
||||
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
* See the License for the specific language governing permissions and
|
||||
* limitations under the License.
|
||||
*/
|
||||
|
||||
package org.springframework.cache.jcache;
|
||||
|
||||
import javax.cache.Caching;
|
||||
import javax.cache.spi.CachingProvider;
|
||||
|
||||
/**
|
||||
* Just here to be run against EHCache 3, whereas the original JCacheEhCacheAnnotationTests
|
||||
* runs against EhCache 2.x with the EhCache-JCache add-on.
|
||||
*
|
||||
* @author Juergen Hoeller
|
||||
*/
|
||||
public class JCacheEhCache3AnnotationTests extends JCacheEhCacheAnnotationTests {
|
||||
|
||||
@Override
|
||||
protected CachingProvider getCachingProvider() {
|
||||
return Caching.getCachingProvider("org.ehcache.jsr107.EhcacheCachingProvider");
|
||||
}
|
||||
|
||||
}
|
||||
@@ -1,35 +0,0 @@
|
||||
/*
|
||||
* Copyright 2002-2017 the original author or authors.
|
||||
*
|
||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
||||
* you may not use this file except in compliance with the License.
|
||||
* You may obtain a copy of the License at
|
||||
*
|
||||
* https://www.apache.org/licenses/LICENSE-2.0
|
||||
*
|
||||
* Unless required by applicable law or agreed to in writing, software
|
||||
* distributed under the License is distributed on an "AS IS" BASIS,
|
||||
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
* See the License for the specific language governing permissions and
|
||||
* limitations under the License.
|
||||
*/
|
||||
|
||||
package org.springframework.cache.jcache;
|
||||
|
||||
import javax.cache.Caching;
|
||||
import javax.cache.spi.CachingProvider;
|
||||
|
||||
/**
|
||||
* Just here to be run against EHCache 3, whereas the original JCacheEhCacheAnnotationTests
|
||||
* runs against EhCache 2.x with the EhCache-JCache add-on.
|
||||
*
|
||||
* @author Stephane Nicoll
|
||||
*/
|
||||
public class JCacheEhCache3ApiTests extends JCacheEhCacheApiTests {
|
||||
|
||||
@Override
|
||||
protected CachingProvider getCachingProvider() {
|
||||
return Caching.getCachingProvider("org.ehcache.jsr107.EhcacheCachingProvider");
|
||||
}
|
||||
|
||||
}
|
||||
@@ -64,7 +64,7 @@ public class JCacheEhCacheAnnotationTests extends AbstractCacheAnnotationTests {
|
||||
}
|
||||
|
||||
protected CachingProvider getCachingProvider() {
|
||||
return Caching.getCachingProvider("org.ehcache.jcache.JCacheCachingProvider");
|
||||
return Caching.getCachingProvider("org.ehcache.jsr107.EhcacheCachingProvider");
|
||||
}
|
||||
|
||||
@AfterEach
|
||||
|
||||
@@ -54,7 +54,7 @@ public class JCacheEhCacheApiTests extends AbstractValueAdaptingCacheTests<JCach
|
||||
}
|
||||
|
||||
protected CachingProvider getCachingProvider() {
|
||||
return Caching.getCachingProvider("org.ehcache.jcache.JCacheCachingProvider");
|
||||
return Caching.getCachingProvider("org.ehcache.jsr107.EhcacheCachingProvider");
|
||||
}
|
||||
|
||||
@AfterEach
|
||||
|
||||
@@ -24,18 +24,17 @@ import java.util.GregorianCalendar;
|
||||
import java.util.List;
|
||||
import java.util.Properties;
|
||||
|
||||
import javax.activation.FileTypeMap;
|
||||
import javax.mail.Address;
|
||||
import javax.mail.Message;
|
||||
import javax.mail.MessagingException;
|
||||
import javax.mail.NoSuchProviderException;
|
||||
import javax.mail.Session;
|
||||
import javax.mail.Transport;
|
||||
import javax.mail.URLName;
|
||||
import javax.mail.internet.AddressException;
|
||||
import javax.mail.internet.InternetAddress;
|
||||
import javax.mail.internet.MimeMessage;
|
||||
|
||||
import jakarta.activation.FileTypeMap;
|
||||
import jakarta.mail.Address;
|
||||
import jakarta.mail.Message;
|
||||
import jakarta.mail.MessagingException;
|
||||
import jakarta.mail.NoSuchProviderException;
|
||||
import jakarta.mail.Session;
|
||||
import jakarta.mail.Transport;
|
||||
import jakarta.mail.URLName;
|
||||
import jakarta.mail.internet.AddressException;
|
||||
import jakarta.mail.internet.InternetAddress;
|
||||
import jakarta.mail.internet.MimeMessage;
|
||||
import org.junit.jupiter.api.Test;
|
||||
|
||||
import org.springframework.mail.MailParseException;
|
||||
|
||||
@@ -1,155 +0,0 @@
|
||||
/*
|
||||
* Copyright 2002-2019 the original author or authors.
|
||||
*
|
||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
||||
* you may not use this file except in compliance with the License.
|
||||
* You may obtain a copy of the License at
|
||||
*
|
||||
* https://www.apache.org/licenses/LICENSE-2.0
|
||||
*
|
||||
* Unless required by applicable law or agreed to in writing, software
|
||||
* distributed under the License is distributed on an "AS IS" BASIS,
|
||||
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
* See the License for the specific language governing permissions and
|
||||
* limitations under the License.
|
||||
*/
|
||||
|
||||
package org.springframework.validation.beanvalidation2;
|
||||
|
||||
import javax.annotation.PostConstruct;
|
||||
import javax.validation.constraints.NotNull;
|
||||
import javax.validation.constraints.Size;
|
||||
|
||||
import org.junit.jupiter.api.Test;
|
||||
|
||||
import org.springframework.beans.factory.BeanCreationException;
|
||||
import org.springframework.beans.factory.support.RootBeanDefinition;
|
||||
import org.springframework.beans.testfixture.beans.TestBean;
|
||||
import org.springframework.context.annotation.CommonAnnotationBeanPostProcessor;
|
||||
import org.springframework.context.support.GenericApplicationContext;
|
||||
import org.springframework.validation.beanvalidation.BeanValidationPostProcessor;
|
||||
|
||||
import static org.assertj.core.api.Assertions.assertThat;
|
||||
import static org.assertj.core.api.Assertions.assertThatExceptionOfType;
|
||||
|
||||
/**
|
||||
* @author Juergen Hoeller
|
||||
*/
|
||||
public class BeanValidationPostProcessorTests {
|
||||
|
||||
@Test
|
||||
public void testNotNullConstraint() {
|
||||
GenericApplicationContext ac = new GenericApplicationContext();
|
||||
ac.registerBeanDefinition("bvpp", new RootBeanDefinition(BeanValidationPostProcessor.class));
|
||||
ac.registerBeanDefinition("capp", new RootBeanDefinition(CommonAnnotationBeanPostProcessor.class));
|
||||
ac.registerBeanDefinition("bean", new RootBeanDefinition(NotNullConstrainedBean.class));
|
||||
assertThatExceptionOfType(BeanCreationException.class)
|
||||
.isThrownBy(ac::refresh)
|
||||
.havingRootCause()
|
||||
.withMessageContainingAll("testBean", "invalid");
|
||||
ac.close();
|
||||
}
|
||||
|
||||
@Test
|
||||
public void testNotNullConstraintSatisfied() {
|
||||
GenericApplicationContext ac = new GenericApplicationContext();
|
||||
ac.registerBeanDefinition("bvpp", new RootBeanDefinition(BeanValidationPostProcessor.class));
|
||||
ac.registerBeanDefinition("capp", new RootBeanDefinition(CommonAnnotationBeanPostProcessor.class));
|
||||
RootBeanDefinition bd = new RootBeanDefinition(NotNullConstrainedBean.class);
|
||||
bd.getPropertyValues().add("testBean", new TestBean());
|
||||
ac.registerBeanDefinition("bean", bd);
|
||||
ac.refresh();
|
||||
ac.close();
|
||||
}
|
||||
|
||||
@Test
|
||||
public void testNotNullConstraintAfterInitialization() {
|
||||
GenericApplicationContext ac = new GenericApplicationContext();
|
||||
RootBeanDefinition bvpp = new RootBeanDefinition(BeanValidationPostProcessor.class);
|
||||
bvpp.getPropertyValues().add("afterInitialization", true);
|
||||
ac.registerBeanDefinition("bvpp", bvpp);
|
||||
ac.registerBeanDefinition("capp", new RootBeanDefinition(CommonAnnotationBeanPostProcessor.class));
|
||||
ac.registerBeanDefinition("bean", new RootBeanDefinition(AfterInitConstraintBean.class));
|
||||
ac.refresh();
|
||||
ac.close();
|
||||
}
|
||||
|
||||
@Test
|
||||
public void testSizeConstraint() {
|
||||
GenericApplicationContext ac = new GenericApplicationContext();
|
||||
ac.registerBeanDefinition("bvpp", new RootBeanDefinition(BeanValidationPostProcessor.class));
|
||||
RootBeanDefinition bd = new RootBeanDefinition(NotNullConstrainedBean.class);
|
||||
bd.getPropertyValues().add("testBean", new TestBean());
|
||||
bd.getPropertyValues().add("stringValue", "s");
|
||||
ac.registerBeanDefinition("bean", bd);
|
||||
assertThatExceptionOfType(BeanCreationException.class)
|
||||
.isThrownBy(ac::refresh)
|
||||
.havingRootCause()
|
||||
.withMessageContainingAll("stringValue", "invalid");
|
||||
ac.close();
|
||||
}
|
||||
|
||||
@Test
|
||||
public void testSizeConstraintSatisfied() {
|
||||
GenericApplicationContext ac = new GenericApplicationContext();
|
||||
ac.registerBeanDefinition("bvpp", new RootBeanDefinition(BeanValidationPostProcessor.class));
|
||||
RootBeanDefinition bd = new RootBeanDefinition(NotNullConstrainedBean.class);
|
||||
bd.getPropertyValues().add("testBean", new TestBean());
|
||||
bd.getPropertyValues().add("stringValue", "ss");
|
||||
ac.registerBeanDefinition("bean", bd);
|
||||
ac.refresh();
|
||||
ac.close();
|
||||
}
|
||||
|
||||
|
||||
public static class NotNullConstrainedBean {
|
||||
|
||||
@NotNull
|
||||
private TestBean testBean;
|
||||
|
||||
@Size(min = 2)
|
||||
private String stringValue;
|
||||
|
||||
public TestBean getTestBean() {
|
||||
return testBean;
|
||||
}
|
||||
|
||||
public void setTestBean(TestBean testBean) {
|
||||
this.testBean = testBean;
|
||||
}
|
||||
|
||||
public String getStringValue() {
|
||||
return stringValue;
|
||||
}
|
||||
|
||||
public void setStringValue(String stringValue) {
|
||||
this.stringValue = stringValue;
|
||||
}
|
||||
|
||||
@PostConstruct
|
||||
public void init() {
|
||||
assertThat(this.testBean).as("Shouldn't be here after constraint checking").isNotNull();
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
public static class AfterInitConstraintBean {
|
||||
|
||||
@NotNull
|
||||
private TestBean testBean;
|
||||
|
||||
public TestBean getTestBean() {
|
||||
return testBean;
|
||||
}
|
||||
|
||||
public void setTestBean(TestBean testBean) {
|
||||
this.testBean = testBean;
|
||||
}
|
||||
|
||||
@PostConstruct
|
||||
public void init() {
|
||||
this.testBean = new TestBean();
|
||||
}
|
||||
}
|
||||
|
||||
}
|
||||
@@ -1,218 +0,0 @@
|
||||
/*
|
||||
* Copyright 2002-2019 the original author or authors.
|
||||
*
|
||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
||||
* you may not use this file except in compliance with the License.
|
||||
* You may obtain a copy of the License at
|
||||
*
|
||||
* https://www.apache.org/licenses/LICENSE-2.0
|
||||
*
|
||||
* Unless required by applicable law or agreed to in writing, software
|
||||
* distributed under the License is distributed on an "AS IS" BASIS,
|
||||
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
* See the License for the specific language governing permissions and
|
||||
* limitations under the License.
|
||||
*/
|
||||
|
||||
package org.springframework.validation.beanvalidation2;
|
||||
|
||||
import java.lang.annotation.Retention;
|
||||
import java.lang.annotation.RetentionPolicy;
|
||||
|
||||
import javax.validation.ValidationException;
|
||||
import javax.validation.Validator;
|
||||
import javax.validation.constraints.Max;
|
||||
import javax.validation.constraints.NotNull;
|
||||
import javax.validation.groups.Default;
|
||||
|
||||
import org.junit.jupiter.api.Test;
|
||||
|
||||
import org.springframework.aop.framework.ProxyFactory;
|
||||
import org.springframework.beans.MutablePropertyValues;
|
||||
import org.springframework.beans.factory.FactoryBean;
|
||||
import org.springframework.context.annotation.AnnotationConfigApplicationContext;
|
||||
import org.springframework.context.annotation.Bean;
|
||||
import org.springframework.context.annotation.Configuration;
|
||||
import org.springframework.context.annotation.Lazy;
|
||||
import org.springframework.context.support.StaticApplicationContext;
|
||||
import org.springframework.scheduling.annotation.Async;
|
||||
import org.springframework.scheduling.annotation.AsyncAnnotationAdvisor;
|
||||
import org.springframework.scheduling.annotation.AsyncAnnotationBeanPostProcessor;
|
||||
import org.springframework.validation.annotation.Validated;
|
||||
import org.springframework.validation.beanvalidation.CustomValidatorBean;
|
||||
import org.springframework.validation.beanvalidation.MethodValidationInterceptor;
|
||||
import org.springframework.validation.beanvalidation.MethodValidationPostProcessor;
|
||||
|
||||
import static org.assertj.core.api.Assertions.assertThat;
|
||||
import static org.assertj.core.api.Assertions.assertThatExceptionOfType;
|
||||
|
||||
/**
|
||||
* @author Juergen Hoeller
|
||||
*/
|
||||
public class MethodValidationTests {
|
||||
|
||||
@Test
|
||||
@SuppressWarnings("unchecked")
|
||||
public void testMethodValidationInterceptor() {
|
||||
MyValidBean bean = new MyValidBean();
|
||||
ProxyFactory proxyFactory = new ProxyFactory(bean);
|
||||
proxyFactory.addAdvice(new MethodValidationInterceptor());
|
||||
proxyFactory.addAdvisor(new AsyncAnnotationAdvisor());
|
||||
doTestProxyValidation((MyValidInterface<String>) proxyFactory.getProxy());
|
||||
}
|
||||
|
||||
@Test
|
||||
@SuppressWarnings("unchecked")
|
||||
public void testMethodValidationPostProcessor() {
|
||||
StaticApplicationContext ac = new StaticApplicationContext();
|
||||
ac.registerSingleton("mvpp", MethodValidationPostProcessor.class);
|
||||
MutablePropertyValues pvs = new MutablePropertyValues();
|
||||
pvs.add("beforeExistingAdvisors", false);
|
||||
ac.registerSingleton("aapp", AsyncAnnotationBeanPostProcessor.class, pvs);
|
||||
ac.registerSingleton("bean", MyValidBean.class);
|
||||
ac.refresh();
|
||||
doTestProxyValidation(ac.getBean("bean", MyValidInterface.class));
|
||||
ac.close();
|
||||
}
|
||||
|
||||
private void doTestProxyValidation(MyValidInterface<String> proxy) {
|
||||
assertThat(proxy.myValidMethod("value", 5)).isNotNull();
|
||||
assertThatExceptionOfType(ValidationException.class).isThrownBy(() ->
|
||||
proxy.myValidMethod("value", 15));
|
||||
assertThatExceptionOfType(ValidationException.class).isThrownBy(() ->
|
||||
proxy.myValidMethod(null, 5));
|
||||
assertThatExceptionOfType(ValidationException.class).isThrownBy(() ->
|
||||
proxy.myValidMethod("value", 0));
|
||||
proxy.myValidAsyncMethod("value", 5);
|
||||
assertThatExceptionOfType(ValidationException.class).isThrownBy(() ->
|
||||
proxy.myValidAsyncMethod("value", 15));
|
||||
assertThatExceptionOfType(ValidationException.class).isThrownBy(() ->
|
||||
proxy.myValidAsyncMethod(null, 5));
|
||||
assertThat(proxy.myGenericMethod("myValue")).isEqualTo("myValue");
|
||||
assertThatExceptionOfType(ValidationException.class).isThrownBy(() ->
|
||||
proxy.myGenericMethod(null));
|
||||
}
|
||||
|
||||
@Test
|
||||
public void testLazyValidatorForMethodValidation() {
|
||||
@SuppressWarnings("resource")
|
||||
AnnotationConfigApplicationContext ctx = new AnnotationConfigApplicationContext(
|
||||
LazyMethodValidationConfig.class, CustomValidatorBean.class,
|
||||
MyValidBean.class, MyValidFactoryBean.class);
|
||||
ctx.getBeansOfType(MyValidInterface.class).values().forEach(bean -> bean.myValidMethod("value", 5));
|
||||
}
|
||||
|
||||
@Test
|
||||
public void testLazyValidatorForMethodValidationWithProxyTargetClass() {
|
||||
@SuppressWarnings("resource")
|
||||
AnnotationConfigApplicationContext ctx = new AnnotationConfigApplicationContext(
|
||||
LazyMethodValidationConfigWithProxyTargetClass.class, CustomValidatorBean.class,
|
||||
MyValidBean.class, MyValidFactoryBean.class);
|
||||
ctx.getBeansOfType(MyValidInterface.class).values().forEach(bean -> bean.myValidMethod("value", 5));
|
||||
}
|
||||
|
||||
|
||||
@MyStereotype
|
||||
public static class MyValidBean implements MyValidInterface<String> {
|
||||
|
||||
@Override
|
||||
public Object myValidMethod(String arg1, int arg2) {
|
||||
return (arg2 == 0 ? null : "value");
|
||||
}
|
||||
|
||||
@Override
|
||||
public void myValidAsyncMethod(String arg1, int arg2) {
|
||||
}
|
||||
|
||||
@Override
|
||||
public String myGenericMethod(String value) {
|
||||
return value;
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
@MyStereotype
|
||||
public static class MyValidFactoryBean implements FactoryBean<String>, MyValidInterface<String> {
|
||||
|
||||
@Override
|
||||
public String getObject() {
|
||||
return null;
|
||||
}
|
||||
|
||||
@Override
|
||||
public Class<?> getObjectType() {
|
||||
return String.class;
|
||||
}
|
||||
|
||||
@Override
|
||||
public Object myValidMethod(String arg1, int arg2) {
|
||||
return (arg2 == 0 ? null : "value");
|
||||
}
|
||||
|
||||
@Override
|
||||
public void myValidAsyncMethod(String arg1, int arg2) {
|
||||
}
|
||||
|
||||
@Override
|
||||
public String myGenericMethod(String value) {
|
||||
return value;
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
public interface MyValidInterface<T> {
|
||||
|
||||
@NotNull Object myValidMethod(@NotNull(groups = MyGroup.class) String arg1, @Max(10) int arg2);
|
||||
|
||||
@MyValid
|
||||
@Async void myValidAsyncMethod(@NotNull(groups = OtherGroup.class) String arg1, @Max(10) int arg2);
|
||||
|
||||
T myGenericMethod(@NotNull T value);
|
||||
}
|
||||
|
||||
|
||||
public interface MyGroup {
|
||||
}
|
||||
|
||||
|
||||
public interface OtherGroup {
|
||||
}
|
||||
|
||||
|
||||
@Validated({MyGroup.class, Default.class})
|
||||
@Retention(RetentionPolicy.RUNTIME)
|
||||
public @interface MyStereotype {
|
||||
}
|
||||
|
||||
|
||||
@Validated({OtherGroup.class, Default.class})
|
||||
@Retention(RetentionPolicy.RUNTIME)
|
||||
public @interface MyValid {
|
||||
}
|
||||
|
||||
|
||||
@Configuration
|
||||
public static class LazyMethodValidationConfig {
|
||||
|
||||
@Bean
|
||||
public static MethodValidationPostProcessor methodValidationPostProcessor(@Lazy Validator validator) {
|
||||
MethodValidationPostProcessor postProcessor = new MethodValidationPostProcessor();
|
||||
postProcessor.setValidator(validator);
|
||||
return postProcessor;
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
@Configuration
|
||||
public static class LazyMethodValidationConfigWithProxyTargetClass {
|
||||
|
||||
@Bean
|
||||
public static MethodValidationPostProcessor methodValidationPostProcessor(@Lazy Validator validator) {
|
||||
MethodValidationPostProcessor postProcessor = new MethodValidationPostProcessor();
|
||||
postProcessor.setValidator(validator);
|
||||
postProcessor.setProxyTargetClass(true);
|
||||
return postProcessor;
|
||||
}
|
||||
}
|
||||
|
||||
}
|
||||
@@ -1,563 +0,0 @@
|
||||
/*
|
||||
* Copyright 2002-2020 the original author or authors.
|
||||
*
|
||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
||||
* you may not use this file except in compliance with the License.
|
||||
* You may obtain a copy of the License at
|
||||
*
|
||||
* https://www.apache.org/licenses/LICENSE-2.0
|
||||
*
|
||||
* Unless required by applicable law or agreed to in writing, software
|
||||
* distributed under the License is distributed on an "AS IS" BASIS,
|
||||
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
* See the License for the specific language governing permissions and
|
||||
* limitations under the License.
|
||||
*/
|
||||
|
||||
package org.springframework.validation.beanvalidation2;
|
||||
|
||||
import java.lang.annotation.Documented;
|
||||
import java.lang.annotation.ElementType;
|
||||
import java.lang.annotation.Inherited;
|
||||
import java.lang.annotation.Repeatable;
|
||||
import java.lang.annotation.Retention;
|
||||
import java.lang.annotation.RetentionPolicy;
|
||||
import java.lang.annotation.Target;
|
||||
import java.lang.reflect.Field;
|
||||
import java.util.ArrayList;
|
||||
import java.util.Arrays;
|
||||
import java.util.HashMap;
|
||||
import java.util.LinkedHashSet;
|
||||
import java.util.List;
|
||||
import java.util.Locale;
|
||||
import java.util.Map;
|
||||
import java.util.Set;
|
||||
|
||||
import javax.validation.Constraint;
|
||||
import javax.validation.ConstraintValidator;
|
||||
import javax.validation.ConstraintValidatorContext;
|
||||
import javax.validation.ConstraintViolation;
|
||||
import javax.validation.Payload;
|
||||
import javax.validation.Valid;
|
||||
import javax.validation.Validation;
|
||||
import javax.validation.Validator;
|
||||
import javax.validation.constraints.NotNull;
|
||||
import javax.validation.constraints.Pattern;
|
||||
import javax.validation.constraints.Size;
|
||||
|
||||
import org.junit.jupiter.api.BeforeEach;
|
||||
import org.junit.jupiter.api.Test;
|
||||
|
||||
import org.springframework.beans.BeanWrapper;
|
||||
import org.springframework.beans.BeanWrapperImpl;
|
||||
import org.springframework.context.support.StaticMessageSource;
|
||||
import org.springframework.core.testfixture.io.SerializationTestUtils;
|
||||
import org.springframework.util.ObjectUtils;
|
||||
import org.springframework.validation.BeanPropertyBindingResult;
|
||||
import org.springframework.validation.FieldError;
|
||||
import org.springframework.validation.beanvalidation.SpringValidatorAdapter;
|
||||
|
||||
import static org.assertj.core.api.Assertions.assertThat;
|
||||
|
||||
/**
|
||||
* @author Kazuki Shimizu
|
||||
* @author Juergen Hoeller
|
||||
*/
|
||||
public class SpringValidatorAdapterTests {
|
||||
|
||||
private final Validator nativeValidator = Validation.buildDefaultValidatorFactory().getValidator();
|
||||
|
||||
private final SpringValidatorAdapter validatorAdapter = new SpringValidatorAdapter(nativeValidator);
|
||||
|
||||
private final StaticMessageSource messageSource = new StaticMessageSource();
|
||||
|
||||
|
||||
@BeforeEach
|
||||
public void setupSpringValidatorAdapter() {
|
||||
messageSource.addMessage("Size", Locale.ENGLISH, "Size of {0} must be between {2} and {1}");
|
||||
messageSource.addMessage("Same", Locale.ENGLISH, "{2} must be same value as {1}");
|
||||
messageSource.addMessage("password", Locale.ENGLISH, "Password");
|
||||
messageSource.addMessage("confirmPassword", Locale.ENGLISH, "Password(Confirm)");
|
||||
}
|
||||
|
||||
|
||||
@Test
|
||||
public void testUnwrap() {
|
||||
Validator nativeValidator = validatorAdapter.unwrap(Validator.class);
|
||||
assertThat(nativeValidator).isSameAs(this.nativeValidator);
|
||||
}
|
||||
|
||||
@Test // SPR-13406
|
||||
public void testNoStringArgumentValue() throws Exception {
|
||||
TestBean testBean = new TestBean();
|
||||
testBean.setPassword("pass");
|
||||
testBean.setConfirmPassword("pass");
|
||||
|
||||
BeanPropertyBindingResult errors = new BeanPropertyBindingResult(testBean, "testBean");
|
||||
validatorAdapter.validate(testBean, errors);
|
||||
|
||||
assertThat(errors.getFieldErrorCount("password")).isEqualTo(1);
|
||||
assertThat(errors.getFieldValue("password")).isEqualTo("pass");
|
||||
FieldError error = errors.getFieldError("password");
|
||||
assertThat(error).isNotNull();
|
||||
assertThat(messageSource.getMessage(error, Locale.ENGLISH)).isEqualTo("Size of Password must be between 8 and 128");
|
||||
assertThat(error.contains(ConstraintViolation.class)).isTrue();
|
||||
assertThat(error.unwrap(ConstraintViolation.class).getPropertyPath().toString()).isEqualTo("password");
|
||||
assertThat(SerializationTestUtils.serializeAndDeserialize(error.toString())).isEqualTo(error.toString());
|
||||
}
|
||||
|
||||
@Test // SPR-13406
|
||||
public void testApplyMessageSourceResolvableToStringArgumentValueWithResolvedLogicalFieldName() throws Exception {
|
||||
TestBean testBean = new TestBean();
|
||||
testBean.setPassword("password");
|
||||
testBean.setConfirmPassword("PASSWORD");
|
||||
|
||||
BeanPropertyBindingResult errors = new BeanPropertyBindingResult(testBean, "testBean");
|
||||
validatorAdapter.validate(testBean, errors);
|
||||
|
||||
assertThat(errors.getFieldErrorCount("password")).isEqualTo(1);
|
||||
assertThat(errors.getFieldValue("password")).isEqualTo("password");
|
||||
FieldError error = errors.getFieldError("password");
|
||||
assertThat(error).isNotNull();
|
||||
assertThat(messageSource.getMessage(error, Locale.ENGLISH)).isEqualTo("Password must be same value as Password(Confirm)");
|
||||
assertThat(error.contains(ConstraintViolation.class)).isTrue();
|
||||
assertThat(error.unwrap(ConstraintViolation.class).getPropertyPath().toString()).isEqualTo("password");
|
||||
assertThat(SerializationTestUtils.serializeAndDeserialize(error.toString())).isEqualTo(error.toString());
|
||||
}
|
||||
|
||||
@Test // SPR-13406
|
||||
public void testApplyMessageSourceResolvableToStringArgumentValueWithUnresolvedLogicalFieldName() {
|
||||
TestBean testBean = new TestBean();
|
||||
testBean.setEmail("test@example.com");
|
||||
testBean.setConfirmEmail("TEST@EXAMPLE.IO");
|
||||
|
||||
BeanPropertyBindingResult errors = new BeanPropertyBindingResult(testBean, "testBean");
|
||||
validatorAdapter.validate(testBean, errors);
|
||||
|
||||
assertThat(errors.getFieldErrorCount("email")).isEqualTo(1);
|
||||
assertThat(errors.getFieldValue("email")).isEqualTo("test@example.com");
|
||||
assertThat(errors.getFieldErrorCount("confirmEmail")).isEqualTo(1);
|
||||
FieldError error1 = errors.getFieldError("email");
|
||||
FieldError error2 = errors.getFieldError("confirmEmail");
|
||||
assertThat(error1).isNotNull();
|
||||
assertThat(error2).isNotNull();
|
||||
assertThat(messageSource.getMessage(error1, Locale.ENGLISH)).isEqualTo("email must be same value as confirmEmail");
|
||||
assertThat(messageSource.getMessage(error2, Locale.ENGLISH)).isEqualTo("Email required");
|
||||
assertThat(error1.contains(ConstraintViolation.class)).isTrue();
|
||||
assertThat(error1.unwrap(ConstraintViolation.class).getPropertyPath().toString()).isEqualTo("email");
|
||||
assertThat(error2.contains(ConstraintViolation.class)).isTrue();
|
||||
assertThat(error2.unwrap(ConstraintViolation.class).getPropertyPath().toString()).isEqualTo("confirmEmail");
|
||||
}
|
||||
|
||||
@Test // SPR-15123
|
||||
public void testApplyMessageSourceResolvableToStringArgumentValueWithAlwaysUseMessageFormat() {
|
||||
messageSource.setAlwaysUseMessageFormat(true);
|
||||
|
||||
TestBean testBean = new TestBean();
|
||||
testBean.setEmail("test@example.com");
|
||||
testBean.setConfirmEmail("TEST@EXAMPLE.IO");
|
||||
|
||||
BeanPropertyBindingResult errors = new BeanPropertyBindingResult(testBean, "testBean");
|
||||
validatorAdapter.validate(testBean, errors);
|
||||
|
||||
assertThat(errors.getFieldErrorCount("email")).isEqualTo(1);
|
||||
assertThat(errors.getFieldValue("email")).isEqualTo("test@example.com");
|
||||
assertThat(errors.getFieldErrorCount("confirmEmail")).isEqualTo(1);
|
||||
FieldError error1 = errors.getFieldError("email");
|
||||
FieldError error2 = errors.getFieldError("confirmEmail");
|
||||
assertThat(error1).isNotNull();
|
||||
assertThat(error2).isNotNull();
|
||||
assertThat(messageSource.getMessage(error1, Locale.ENGLISH)).isEqualTo("email must be same value as confirmEmail");
|
||||
assertThat(messageSource.getMessage(error2, Locale.ENGLISH)).isEqualTo("Email required");
|
||||
assertThat(error1.contains(ConstraintViolation.class)).isTrue();
|
||||
assertThat(error1.unwrap(ConstraintViolation.class).getPropertyPath().toString()).isEqualTo("email");
|
||||
assertThat(error2.contains(ConstraintViolation.class)).isTrue();
|
||||
assertThat(error2.unwrap(ConstraintViolation.class).getPropertyPath().toString()).isEqualTo("confirmEmail");
|
||||
}
|
||||
|
||||
@Test
|
||||
public void testPatternMessage() {
|
||||
TestBean testBean = new TestBean();
|
||||
testBean.setEmail("X");
|
||||
testBean.setConfirmEmail("X");
|
||||
|
||||
BeanPropertyBindingResult errors = new BeanPropertyBindingResult(testBean, "testBean");
|
||||
validatorAdapter.validate(testBean, errors);
|
||||
|
||||
assertThat(errors.getFieldErrorCount("email")).isEqualTo(1);
|
||||
assertThat(errors.getFieldValue("email")).isEqualTo("X");
|
||||
FieldError error = errors.getFieldError("email");
|
||||
assertThat(error).isNotNull();
|
||||
assertThat(messageSource.getMessage(error, Locale.ENGLISH)).contains("[\\w.'-]{1,}@[\\w.'-]{1,}");
|
||||
assertThat(error.contains(ConstraintViolation.class)).isTrue();
|
||||
assertThat(error.unwrap(ConstraintViolation.class).getPropertyPath().toString()).isEqualTo("email");
|
||||
}
|
||||
|
||||
@Test // SPR-16177
|
||||
public void testWithList() {
|
||||
Parent parent = new Parent();
|
||||
parent.setName("Parent whit list");
|
||||
parent.getChildList().addAll(createChildren(parent));
|
||||
|
||||
BeanPropertyBindingResult errors = new BeanPropertyBindingResult(parent, "parent");
|
||||
validatorAdapter.validate(parent, errors);
|
||||
|
||||
assertThat(errors.getErrorCount() > 0).isTrue();
|
||||
}
|
||||
|
||||
@Test // SPR-16177
|
||||
public void testWithSet() {
|
||||
Parent parent = new Parent();
|
||||
parent.setName("Parent with set");
|
||||
parent.getChildSet().addAll(createChildren(parent));
|
||||
|
||||
BeanPropertyBindingResult errors = new BeanPropertyBindingResult(parent, "parent");
|
||||
validatorAdapter.validate(parent, errors);
|
||||
|
||||
assertThat(errors.getErrorCount() > 0).isTrue();
|
||||
}
|
||||
|
||||
private List<Child> createChildren(Parent parent) {
|
||||
Child child1 = new Child();
|
||||
child1.setName("Child1");
|
||||
child1.setAge(null);
|
||||
child1.setParent(parent);
|
||||
|
||||
Child child2 = new Child();
|
||||
child2.setName(null);
|
||||
child2.setAge(17);
|
||||
child2.setParent(parent);
|
||||
|
||||
return Arrays.asList(child1, child2);
|
||||
}
|
||||
|
||||
@Test // SPR-15839
|
||||
public void testListElementConstraint() {
|
||||
BeanWithListElementConstraint bean = new BeanWithListElementConstraint();
|
||||
bean.setProperty(Arrays.asList("no", "element", "can", "be", null));
|
||||
|
||||
BeanPropertyBindingResult errors = new BeanPropertyBindingResult(bean, "bean");
|
||||
validatorAdapter.validate(bean, errors);
|
||||
|
||||
assertThat(errors.getFieldErrorCount("property[4]")).isEqualTo(1);
|
||||
assertThat(errors.getFieldValue("property[4]")).isNull();
|
||||
}
|
||||
|
||||
@Test // SPR-15839
|
||||
public void testMapValueConstraint() {
|
||||
Map<String, String> property = new HashMap<>();
|
||||
property.put("no value can be", null);
|
||||
|
||||
BeanWithMapEntryConstraint bean = new BeanWithMapEntryConstraint();
|
||||
bean.setProperty(property);
|
||||
|
||||
BeanPropertyBindingResult errors = new BeanPropertyBindingResult(bean, "bean");
|
||||
validatorAdapter.validate(bean, errors);
|
||||
|
||||
assertThat(errors.getFieldErrorCount("property[no value can be]")).isEqualTo(1);
|
||||
assertThat(errors.getFieldValue("property[no value can be]")).isNull();
|
||||
}
|
||||
|
||||
@Test // SPR-15839
|
||||
public void testMapEntryConstraint() {
|
||||
Map<String, String> property = new HashMap<>();
|
||||
property.put(null, null);
|
||||
|
||||
BeanWithMapEntryConstraint bean = new BeanWithMapEntryConstraint();
|
||||
bean.setProperty(property);
|
||||
|
||||
BeanPropertyBindingResult errors = new BeanPropertyBindingResult(bean, "bean");
|
||||
validatorAdapter.validate(bean, errors);
|
||||
|
||||
assertThat(errors.hasFieldErrors("property[]")).isTrue();
|
||||
assertThat(errors.getFieldValue("property[]")).isNull();
|
||||
}
|
||||
|
||||
|
||||
@Same(field = "password", comparingField = "confirmPassword")
|
||||
@Same(field = "email", comparingField = "confirmEmail")
|
||||
static class TestBean {
|
||||
|
||||
@Size(min = 8, max = 128)
|
||||
private String password;
|
||||
|
||||
private String confirmPassword;
|
||||
|
||||
@Pattern(regexp = "[\\w.'-]{1,}@[\\w.'-]{1,}")
|
||||
private String email;
|
||||
|
||||
@Pattern(regexp = "[\\p{L} -]*", message = "Email required")
|
||||
private String confirmEmail;
|
||||
|
||||
public String getPassword() {
|
||||
return password;
|
||||
}
|
||||
|
||||
public void setPassword(String password) {
|
||||
this.password = password;
|
||||
}
|
||||
|
||||
public String getConfirmPassword() {
|
||||
return confirmPassword;
|
||||
}
|
||||
|
||||
public void setConfirmPassword(String confirmPassword) {
|
||||
this.confirmPassword = confirmPassword;
|
||||
}
|
||||
|
||||
public String getEmail() {
|
||||
return email;
|
||||
}
|
||||
|
||||
public void setEmail(String email) {
|
||||
this.email = email;
|
||||
}
|
||||
|
||||
public String getConfirmEmail() {
|
||||
return confirmEmail;
|
||||
}
|
||||
|
||||
public void setConfirmEmail(String confirmEmail) {
|
||||
this.confirmEmail = confirmEmail;
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
@Documented
|
||||
@Constraint(validatedBy = {SameValidator.class})
|
||||
@Target({ElementType.TYPE, ElementType.ANNOTATION_TYPE})
|
||||
@Retention(RetentionPolicy.RUNTIME)
|
||||
@Repeatable(SameGroup.class)
|
||||
@interface Same {
|
||||
|
||||
String message() default "{org.springframework.validation.beanvalidation.Same.message}";
|
||||
|
||||
Class<?>[] groups() default {};
|
||||
|
||||
Class<? extends Payload>[] payload() default {};
|
||||
|
||||
String field();
|
||||
|
||||
String comparingField();
|
||||
|
||||
@Target({ElementType.TYPE, ElementType.ANNOTATION_TYPE})
|
||||
@Retention(RetentionPolicy.RUNTIME)
|
||||
@Documented
|
||||
@interface List {
|
||||
Same[] value();
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
@Documented
|
||||
@Inherited
|
||||
@Target({ElementType.TYPE, ElementType.ANNOTATION_TYPE})
|
||||
@Retention(RetentionPolicy.RUNTIME)
|
||||
@interface SameGroup {
|
||||
|
||||
Same[] value();
|
||||
}
|
||||
|
||||
|
||||
public static class SameValidator implements ConstraintValidator<Same, Object> {
|
||||
|
||||
private String field;
|
||||
|
||||
private String comparingField;
|
||||
|
||||
private String message;
|
||||
|
||||
@Override
|
||||
public void initialize(Same constraintAnnotation) {
|
||||
field = constraintAnnotation.field();
|
||||
comparingField = constraintAnnotation.comparingField();
|
||||
message = constraintAnnotation.message();
|
||||
}
|
||||
|
||||
@Override
|
||||
public boolean isValid(Object value, ConstraintValidatorContext context) {
|
||||
BeanWrapper beanWrapper = new BeanWrapperImpl(value);
|
||||
Object fieldValue = beanWrapper.getPropertyValue(field);
|
||||
Object comparingFieldValue = beanWrapper.getPropertyValue(comparingField);
|
||||
boolean matched = ObjectUtils.nullSafeEquals(fieldValue, comparingFieldValue);
|
||||
if (matched) {
|
||||
return true;
|
||||
}
|
||||
else {
|
||||
context.disableDefaultConstraintViolation();
|
||||
context.buildConstraintViolationWithTemplate(message)
|
||||
.addPropertyNode(field)
|
||||
.addConstraintViolation();
|
||||
return false;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
public static class Parent {
|
||||
|
||||
private Integer id;
|
||||
|
||||
@NotNull
|
||||
private String name;
|
||||
|
||||
@Valid
|
||||
private Set<Child> childSet = new LinkedHashSet<>();
|
||||
|
||||
@Valid
|
||||
private List<Child> childList = new ArrayList<>();
|
||||
|
||||
public Integer getId() {
|
||||
return id;
|
||||
}
|
||||
|
||||
public void setId(Integer id) {
|
||||
this.id = id;
|
||||
}
|
||||
|
||||
public String getName() {
|
||||
return name;
|
||||
}
|
||||
|
||||
public void setName(String name) {
|
||||
this.name = name;
|
||||
}
|
||||
|
||||
public Set<Child> getChildSet() {
|
||||
return childSet;
|
||||
}
|
||||
|
||||
public void setChildSet(Set<Child> childSet) {
|
||||
this.childSet = childSet;
|
||||
}
|
||||
|
||||
public List<Child> getChildList() {
|
||||
return childList;
|
||||
}
|
||||
|
||||
public void setChildList(List<Child> childList) {
|
||||
this.childList = childList;
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
@AnythingValid
|
||||
public static class Child {
|
||||
|
||||
private Integer id;
|
||||
|
||||
@NotNull
|
||||
private String name;
|
||||
|
||||
@NotNull
|
||||
private Integer age;
|
||||
|
||||
@NotNull
|
||||
private Parent parent;
|
||||
|
||||
public Integer getId() {
|
||||
return id;
|
||||
}
|
||||
|
||||
public void setId(Integer id) {
|
||||
this.id = id;
|
||||
}
|
||||
|
||||
public String getName() {
|
||||
return name;
|
||||
}
|
||||
|
||||
public void setName(String name) {
|
||||
this.name = name;
|
||||
}
|
||||
|
||||
public Integer getAge() {
|
||||
return age;
|
||||
}
|
||||
|
||||
public void setAge(Integer age) {
|
||||
this.age = age;
|
||||
}
|
||||
|
||||
public Parent getParent() {
|
||||
return parent;
|
||||
}
|
||||
|
||||
public void setParent(Parent parent) {
|
||||
this.parent = parent;
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
@Constraint(validatedBy = AnythingValidator.class)
|
||||
@Retention(RetentionPolicy.RUNTIME)
|
||||
public @interface AnythingValid {
|
||||
|
||||
String message() default "{AnythingValid.message}";
|
||||
|
||||
Class<?>[] groups() default {};
|
||||
|
||||
Class<? extends Payload>[] payload() default {};
|
||||
}
|
||||
|
||||
|
||||
public static class AnythingValidator implements ConstraintValidator<AnythingValid, Object> {
|
||||
|
||||
private static final String ID = "id";
|
||||
|
||||
@Override
|
||||
public void initialize(AnythingValid constraintAnnotation) {
|
||||
}
|
||||
|
||||
@Override
|
||||
public boolean isValid(Object value, ConstraintValidatorContext context) {
|
||||
List<Field> fieldsErrors = new ArrayList<>();
|
||||
Arrays.asList(value.getClass().getDeclaredFields()).forEach(field -> {
|
||||
field.setAccessible(true);
|
||||
try {
|
||||
if (!field.getName().equals(ID) && field.get(value) == null) {
|
||||
fieldsErrors.add(field);
|
||||
context.buildConstraintViolationWithTemplate(context.getDefaultConstraintMessageTemplate())
|
||||
.addPropertyNode(field.getName())
|
||||
.addConstraintViolation();
|
||||
}
|
||||
}
|
||||
catch (IllegalAccessException ex) {
|
||||
throw new IllegalStateException(ex);
|
||||
}
|
||||
});
|
||||
return fieldsErrors.isEmpty();
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
public class BeanWithListElementConstraint {
|
||||
|
||||
@Valid
|
||||
private List<@NotNull String> property;
|
||||
|
||||
public List<String> getProperty() {
|
||||
return property;
|
||||
}
|
||||
|
||||
public void setProperty(List<String> property) {
|
||||
this.property = property;
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
public class BeanWithMapEntryConstraint {
|
||||
|
||||
@Valid
|
||||
private Map<@NotNull String, @NotNull String> property;
|
||||
|
||||
public Map<String, String> getProperty() {
|
||||
return property;
|
||||
}
|
||||
|
||||
public void setProperty(Map<String, String> property) {
|
||||
this.property = property;
|
||||
}
|
||||
}
|
||||
|
||||
}
|
||||
@@ -1,505 +0,0 @@
|
||||
/*
|
||||
* Copyright 2002-2020 the original author or authors.
|
||||
*
|
||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
||||
* you may not use this file except in compliance with the License.
|
||||
* You may obtain a copy of the License at
|
||||
*
|
||||
* https://www.apache.org/licenses/LICENSE-2.0
|
||||
*
|
||||
* Unless required by applicable law or agreed to in writing, software
|
||||
* distributed under the License is distributed on an "AS IS" BASIS,
|
||||
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
* See the License for the specific language governing permissions and
|
||||
* limitations under the License.
|
||||
*/
|
||||
|
||||
package org.springframework.validation.beanvalidation2;
|
||||
|
||||
import java.lang.annotation.ElementType;
|
||||
import java.lang.annotation.Retention;
|
||||
import java.lang.annotation.RetentionPolicy;
|
||||
import java.lang.annotation.Target;
|
||||
import java.util.ArrayList;
|
||||
import java.util.Arrays;
|
||||
import java.util.Iterator;
|
||||
import java.util.LinkedHashSet;
|
||||
import java.util.List;
|
||||
import java.util.Optional;
|
||||
import java.util.Set;
|
||||
|
||||
import javax.validation.Constraint;
|
||||
import javax.validation.ConstraintValidator;
|
||||
import javax.validation.ConstraintValidatorContext;
|
||||
import javax.validation.ConstraintViolation;
|
||||
import javax.validation.Payload;
|
||||
import javax.validation.Valid;
|
||||
import javax.validation.Validator;
|
||||
import javax.validation.ValidatorFactory;
|
||||
import javax.validation.constraints.NotNull;
|
||||
|
||||
import org.hibernate.validator.HibernateValidator;
|
||||
import org.hibernate.validator.HibernateValidatorFactory;
|
||||
import org.junit.jupiter.api.Test;
|
||||
|
||||
import org.springframework.beans.factory.annotation.Autowired;
|
||||
import org.springframework.context.ConfigurableApplicationContext;
|
||||
import org.springframework.context.annotation.AnnotationConfigApplicationContext;
|
||||
import org.springframework.core.convert.support.DefaultConversionService;
|
||||
import org.springframework.core.env.Environment;
|
||||
import org.springframework.validation.BeanPropertyBindingResult;
|
||||
import org.springframework.validation.Errors;
|
||||
import org.springframework.validation.FieldError;
|
||||
import org.springframework.validation.ObjectError;
|
||||
import org.springframework.validation.beanvalidation.LocalValidatorFactoryBean;
|
||||
|
||||
import static org.assertj.core.api.Assertions.assertThat;
|
||||
|
||||
/**
|
||||
* @author Juergen Hoeller
|
||||
*/
|
||||
@SuppressWarnings("resource")
|
||||
public class ValidatorFactoryTests {
|
||||
|
||||
@Test
|
||||
@SuppressWarnings("cast")
|
||||
public void testSimpleValidation() {
|
||||
LocalValidatorFactoryBean validator = new LocalValidatorFactoryBean();
|
||||
validator.afterPropertiesSet();
|
||||
|
||||
ValidPerson person = new ValidPerson();
|
||||
Set<ConstraintViolation<ValidPerson>> result = validator.validate(person);
|
||||
assertThat(result.size()).isEqualTo(2);
|
||||
for (ConstraintViolation<ValidPerson> cv : result) {
|
||||
String path = cv.getPropertyPath().toString();
|
||||
assertThat(path).matches(actual -> "name".equals(actual) || "address.street".equals(actual));
|
||||
assertThat(cv.getConstraintDescriptor().getAnnotation()).isInstanceOf(NotNull.class);
|
||||
}
|
||||
|
||||
Validator nativeValidator = validator.unwrap(Validator.class);
|
||||
assertThat(nativeValidator.getClass().getName().startsWith("org.hibernate")).isTrue();
|
||||
assertThat(validator.unwrap(ValidatorFactory.class) instanceof HibernateValidatorFactory).isTrue();
|
||||
assertThat(validator.unwrap(HibernateValidatorFactory.class) instanceof HibernateValidatorFactory).isTrue();
|
||||
|
||||
validator.destroy();
|
||||
}
|
||||
|
||||
@Test
|
||||
@SuppressWarnings("cast")
|
||||
public void testSimpleValidationWithCustomProvider() {
|
||||
LocalValidatorFactoryBean validator = new LocalValidatorFactoryBean();
|
||||
validator.setProviderClass(HibernateValidator.class);
|
||||
validator.afterPropertiesSet();
|
||||
|
||||
ValidPerson person = new ValidPerson();
|
||||
Set<ConstraintViolation<ValidPerson>> result = validator.validate(person);
|
||||
assertThat(result.size()).isEqualTo(2);
|
||||
for (ConstraintViolation<ValidPerson> cv : result) {
|
||||
String path = cv.getPropertyPath().toString();
|
||||
assertThat(path).matches(actual -> "name".equals(actual) || "address.street".equals(actual));
|
||||
assertThat(cv.getConstraintDescriptor().getAnnotation()).isInstanceOf(NotNull.class);
|
||||
}
|
||||
|
||||
Validator nativeValidator = validator.unwrap(Validator.class);
|
||||
assertThat(nativeValidator.getClass().getName().startsWith("org.hibernate")).isTrue();
|
||||
assertThat(validator.unwrap(ValidatorFactory.class) instanceof HibernateValidatorFactory).isTrue();
|
||||
assertThat(validator.unwrap(HibernateValidatorFactory.class) instanceof HibernateValidatorFactory).isTrue();
|
||||
|
||||
validator.destroy();
|
||||
}
|
||||
|
||||
@Test
|
||||
public void testSimpleValidationWithClassLevel() {
|
||||
LocalValidatorFactoryBean validator = new LocalValidatorFactoryBean();
|
||||
validator.afterPropertiesSet();
|
||||
|
||||
ValidPerson person = new ValidPerson();
|
||||
person.setName("Juergen");
|
||||
person.getAddress().setStreet("Juergen's Street");
|
||||
Set<ConstraintViolation<ValidPerson>> result = validator.validate(person);
|
||||
assertThat(result.size()).isEqualTo(1);
|
||||
Iterator<ConstraintViolation<ValidPerson>> iterator = result.iterator();
|
||||
ConstraintViolation<?> cv = iterator.next();
|
||||
assertThat(cv.getPropertyPath().toString()).isEqualTo("");
|
||||
assertThat(cv.getConstraintDescriptor().getAnnotation() instanceof NameAddressValid).isTrue();
|
||||
}
|
||||
|
||||
@Test
|
||||
public void testSpringValidationFieldType() {
|
||||
LocalValidatorFactoryBean validator = new LocalValidatorFactoryBean();
|
||||
validator.afterPropertiesSet();
|
||||
|
||||
ValidPerson person = new ValidPerson();
|
||||
person.setName("Phil");
|
||||
person.getAddress().setStreet("Phil's Street");
|
||||
BeanPropertyBindingResult errors = new BeanPropertyBindingResult(person, "person");
|
||||
validator.validate(person, errors);
|
||||
assertThat(errors.getErrorCount()).isEqualTo(1);
|
||||
assertThat(errors.getFieldError("address").getRejectedValue()).isInstanceOf(ValidAddress.class);
|
||||
}
|
||||
|
||||
@Test
|
||||
public void testSpringValidation() {
|
||||
LocalValidatorFactoryBean validator = new LocalValidatorFactoryBean();
|
||||
validator.afterPropertiesSet();
|
||||
|
||||
ValidPerson person = new ValidPerson();
|
||||
BeanPropertyBindingResult result = new BeanPropertyBindingResult(person, "person");
|
||||
validator.validate(person, result);
|
||||
assertThat(result.getErrorCount()).isEqualTo(2);
|
||||
FieldError fieldError = result.getFieldError("name");
|
||||
assertThat(fieldError.getField()).isEqualTo("name");
|
||||
List<String> errorCodes = Arrays.asList(fieldError.getCodes());
|
||||
assertThat(errorCodes.size()).isEqualTo(4);
|
||||
assertThat(errorCodes.contains("NotNull.person.name")).isTrue();
|
||||
assertThat(errorCodes.contains("NotNull.name")).isTrue();
|
||||
assertThat(errorCodes.contains("NotNull.java.lang.String")).isTrue();
|
||||
assertThat(errorCodes.contains("NotNull")).isTrue();
|
||||
fieldError = result.getFieldError("address.street");
|
||||
assertThat(fieldError.getField()).isEqualTo("address.street");
|
||||
errorCodes = Arrays.asList(fieldError.getCodes());
|
||||
assertThat(errorCodes.size()).isEqualTo(5);
|
||||
assertThat(errorCodes.contains("NotNull.person.address.street")).isTrue();
|
||||
assertThat(errorCodes.contains("NotNull.address.street")).isTrue();
|
||||
assertThat(errorCodes.contains("NotNull.street")).isTrue();
|
||||
assertThat(errorCodes.contains("NotNull.java.lang.String")).isTrue();
|
||||
assertThat(errorCodes.contains("NotNull")).isTrue();
|
||||
}
|
||||
|
||||
@Test
|
||||
public void testSpringValidationWithClassLevel() {
|
||||
LocalValidatorFactoryBean validator = new LocalValidatorFactoryBean();
|
||||
validator.afterPropertiesSet();
|
||||
|
||||
ValidPerson person = new ValidPerson();
|
||||
person.setName("Juergen");
|
||||
person.getAddress().setStreet("Juergen's Street");
|
||||
BeanPropertyBindingResult result = new BeanPropertyBindingResult(person, "person");
|
||||
validator.validate(person, result);
|
||||
assertThat(result.getErrorCount()).isEqualTo(1);
|
||||
ObjectError globalError = result.getGlobalError();
|
||||
List<String> errorCodes = Arrays.asList(globalError.getCodes());
|
||||
assertThat(errorCodes.size()).isEqualTo(2);
|
||||
assertThat(errorCodes.contains("NameAddressValid.person")).isTrue();
|
||||
assertThat(errorCodes.contains("NameAddressValid")).isTrue();
|
||||
}
|
||||
|
||||
@Test
|
||||
public void testSpringValidationWithAutowiredValidator() {
|
||||
ConfigurableApplicationContext ctx = new AnnotationConfigApplicationContext(
|
||||
LocalValidatorFactoryBean.class);
|
||||
LocalValidatorFactoryBean validator = ctx.getBean(LocalValidatorFactoryBean.class);
|
||||
|
||||
ValidPerson person = new ValidPerson();
|
||||
person.expectsAutowiredValidator = true;
|
||||
person.setName("Juergen");
|
||||
person.getAddress().setStreet("Juergen's Street");
|
||||
BeanPropertyBindingResult result = new BeanPropertyBindingResult(person, "person");
|
||||
validator.validate(person, result);
|
||||
assertThat(result.getErrorCount()).isEqualTo(1);
|
||||
ObjectError globalError = result.getGlobalError();
|
||||
List<String> errorCodes = Arrays.asList(globalError.getCodes());
|
||||
assertThat(errorCodes.size()).isEqualTo(2);
|
||||
assertThat(errorCodes.contains("NameAddressValid.person")).isTrue();
|
||||
assertThat(errorCodes.contains("NameAddressValid")).isTrue();
|
||||
ctx.close();
|
||||
}
|
||||
|
||||
@Test
|
||||
public void testSpringValidationWithErrorInListElement() {
|
||||
LocalValidatorFactoryBean validator = new LocalValidatorFactoryBean();
|
||||
validator.afterPropertiesSet();
|
||||
|
||||
ValidPerson person = new ValidPerson();
|
||||
person.getAddressList().add(new ValidAddress());
|
||||
BeanPropertyBindingResult result = new BeanPropertyBindingResult(person, "person");
|
||||
validator.validate(person, result);
|
||||
assertThat(result.getErrorCount()).isEqualTo(3);
|
||||
FieldError fieldError = result.getFieldError("name");
|
||||
assertThat(fieldError.getField()).isEqualTo("name");
|
||||
fieldError = result.getFieldError("address.street");
|
||||
assertThat(fieldError.getField()).isEqualTo("address.street");
|
||||
fieldError = result.getFieldError("addressList[0].street");
|
||||
assertThat(fieldError.getField()).isEqualTo("addressList[0].street");
|
||||
}
|
||||
|
||||
@Test
|
||||
public void testSpringValidationWithErrorInSetElement() {
|
||||
LocalValidatorFactoryBean validator = new LocalValidatorFactoryBean();
|
||||
validator.afterPropertiesSet();
|
||||
|
||||
ValidPerson person = new ValidPerson();
|
||||
person.getAddressSet().add(new ValidAddress());
|
||||
BeanPropertyBindingResult result = new BeanPropertyBindingResult(person, "person");
|
||||
validator.validate(person, result);
|
||||
assertThat(result.getErrorCount()).isEqualTo(3);
|
||||
FieldError fieldError = result.getFieldError("name");
|
||||
assertThat(fieldError.getField()).isEqualTo("name");
|
||||
fieldError = result.getFieldError("address.street");
|
||||
assertThat(fieldError.getField()).isEqualTo("address.street");
|
||||
fieldError = result.getFieldError("addressSet[].street");
|
||||
assertThat(fieldError.getField()).isEqualTo("addressSet[].street");
|
||||
}
|
||||
|
||||
@Test
|
||||
public void testInnerBeanValidation() {
|
||||
LocalValidatorFactoryBean validator = new LocalValidatorFactoryBean();
|
||||
validator.afterPropertiesSet();
|
||||
|
||||
MainBean mainBean = new MainBean();
|
||||
Errors errors = new BeanPropertyBindingResult(mainBean, "mainBean");
|
||||
validator.validate(mainBean, errors);
|
||||
Object rejected = errors.getFieldValue("inner.value");
|
||||
assertThat(rejected).isNull();
|
||||
}
|
||||
|
||||
@Test
|
||||
public void testValidationWithOptionalField() {
|
||||
LocalValidatorFactoryBean validator = new LocalValidatorFactoryBean();
|
||||
validator.afterPropertiesSet();
|
||||
|
||||
MainBeanWithOptional mainBean = new MainBeanWithOptional();
|
||||
Errors errors = new BeanPropertyBindingResult(mainBean, "mainBean");
|
||||
validator.validate(mainBean, errors);
|
||||
Object rejected = errors.getFieldValue("inner.value");
|
||||
assertThat(rejected).isNull();
|
||||
}
|
||||
|
||||
@Test
|
||||
public void testListValidation() {
|
||||
LocalValidatorFactoryBean validator = new LocalValidatorFactoryBean();
|
||||
validator.afterPropertiesSet();
|
||||
|
||||
ListContainer listContainer = new ListContainer();
|
||||
listContainer.addString("A");
|
||||
listContainer.addString("X");
|
||||
|
||||
BeanPropertyBindingResult errors = new BeanPropertyBindingResult(listContainer, "listContainer");
|
||||
errors.initConversion(new DefaultConversionService());
|
||||
validator.validate(listContainer, errors);
|
||||
|
||||
FieldError fieldError = errors.getFieldError("list[1]");
|
||||
assertThat(fieldError).isNotNull();
|
||||
assertThat(fieldError.getRejectedValue()).isEqualTo("X");
|
||||
assertThat(errors.getFieldValue("list[1]")).isEqualTo("X");
|
||||
}
|
||||
|
||||
|
||||
@NameAddressValid
|
||||
public static class ValidPerson {
|
||||
|
||||
@NotNull
|
||||
private String name;
|
||||
|
||||
@Valid
|
||||
private ValidAddress address = new ValidAddress();
|
||||
|
||||
@Valid
|
||||
private List<ValidAddress> addressList = new ArrayList<>();
|
||||
|
||||
@Valid
|
||||
private Set<ValidAddress> addressSet = new LinkedHashSet<>();
|
||||
|
||||
public boolean expectsAutowiredValidator = false;
|
||||
|
||||
public String getName() {
|
||||
return name;
|
||||
}
|
||||
|
||||
public void setName(String name) {
|
||||
this.name = name;
|
||||
}
|
||||
|
||||
public ValidAddress getAddress() {
|
||||
return address;
|
||||
}
|
||||
|
||||
public void setAddress(ValidAddress address) {
|
||||
this.address = address;
|
||||
}
|
||||
|
||||
public List<ValidAddress> getAddressList() {
|
||||
return addressList;
|
||||
}
|
||||
|
||||
public void setAddressList(List<ValidAddress> addressList) {
|
||||
this.addressList = addressList;
|
||||
}
|
||||
|
||||
public Set<ValidAddress> getAddressSet() {
|
||||
return addressSet;
|
||||
}
|
||||
|
||||
public void setAddressSet(Set<ValidAddress> addressSet) {
|
||||
this.addressSet = addressSet;
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
public static class ValidAddress {
|
||||
|
||||
@NotNull
|
||||
private String street;
|
||||
|
||||
public String getStreet() {
|
||||
return street;
|
||||
}
|
||||
|
||||
public void setStreet(String street) {
|
||||
this.street = street;
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
@Target(ElementType.TYPE)
|
||||
@Retention(RetentionPolicy.RUNTIME)
|
||||
@Constraint(validatedBy = NameAddressValidator.class)
|
||||
public @interface NameAddressValid {
|
||||
|
||||
String message() default "Street must not contain name";
|
||||
|
||||
Class<?>[] groups() default {};
|
||||
|
||||
Class<?>[] payload() default {};
|
||||
}
|
||||
|
||||
|
||||
public static class NameAddressValidator implements ConstraintValidator<NameAddressValid, ValidPerson> {
|
||||
|
||||
@Autowired
|
||||
private Environment environment;
|
||||
|
||||
@Override
|
||||
public void initialize(NameAddressValid constraintAnnotation) {
|
||||
}
|
||||
|
||||
@Override
|
||||
public boolean isValid(ValidPerson value, ConstraintValidatorContext context) {
|
||||
if (value.expectsAutowiredValidator) {
|
||||
assertThat(this.environment).isNotNull();
|
||||
}
|
||||
boolean valid = (value.name == null || !value.address.street.contains(value.name));
|
||||
if (!valid && "Phil".equals(value.name)) {
|
||||
context.buildConstraintViolationWithTemplate(
|
||||
context.getDefaultConstraintMessageTemplate()).addPropertyNode("address").addConstraintViolation().disableDefaultConstraintViolation();
|
||||
}
|
||||
return valid;
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
public static class MainBean {
|
||||
|
||||
@InnerValid
|
||||
private InnerBean inner = new InnerBean();
|
||||
|
||||
public InnerBean getInner() {
|
||||
return inner;
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
public static class MainBeanWithOptional {
|
||||
|
||||
@InnerValid
|
||||
private InnerBean inner = new InnerBean();
|
||||
|
||||
public Optional<InnerBean> getInner() {
|
||||
return Optional.ofNullable(inner);
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
public static class InnerBean {
|
||||
|
||||
private String value;
|
||||
|
||||
public String getValue() {
|
||||
return value;
|
||||
}
|
||||
public void setValue(String value) {
|
||||
this.value = value;
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
@Retention(RetentionPolicy.RUNTIME)
|
||||
@Target(ElementType.FIELD)
|
||||
@Constraint(validatedBy=InnerValidator.class)
|
||||
public static @interface InnerValid {
|
||||
|
||||
String message() default "NOT VALID";
|
||||
|
||||
Class<?>[] groups() default { };
|
||||
|
||||
Class<? extends Payload>[] payload() default {};
|
||||
}
|
||||
|
||||
|
||||
public static class InnerValidator implements ConstraintValidator<InnerValid, InnerBean> {
|
||||
|
||||
@Override
|
||||
public void initialize(InnerValid constraintAnnotation) {
|
||||
}
|
||||
|
||||
@Override
|
||||
public boolean isValid(InnerBean bean, ConstraintValidatorContext context) {
|
||||
context.disableDefaultConstraintViolation();
|
||||
if (bean.getValue() == null) {
|
||||
context.buildConstraintViolationWithTemplate("NULL").addPropertyNode("value").addConstraintViolation();
|
||||
return false;
|
||||
}
|
||||
return true;
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
public static class ListContainer {
|
||||
|
||||
@NotXList
|
||||
private List<String> list = new ArrayList<>();
|
||||
|
||||
public void addString(String value) {
|
||||
list.add(value);
|
||||
}
|
||||
|
||||
public List<String> getList() {
|
||||
return list;
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
@Retention(RetentionPolicy.RUNTIME)
|
||||
@Target(ElementType.FIELD)
|
||||
@Constraint(validatedBy = NotXListValidator.class)
|
||||
public @interface NotXList {
|
||||
|
||||
String message() default "Should not be X";
|
||||
|
||||
Class<?>[] groups() default {};
|
||||
|
||||
Class<? extends Payload>[] payload() default {};
|
||||
}
|
||||
|
||||
|
||||
public static class NotXListValidator implements ConstraintValidator<NotXList, List<String>> {
|
||||
|
||||
@Override
|
||||
public void initialize(NotXList constraintAnnotation) {
|
||||
}
|
||||
|
||||
@Override
|
||||
public boolean isValid(List<String> list, ConstraintValidatorContext context) {
|
||||
context.disableDefaultConstraintViolation();
|
||||
boolean valid = true;
|
||||
for (int i = 0; i < list.size(); i++) {
|
||||
if ("X".equals(list.get(i))) {
|
||||
context.buildConstraintViolationWithTemplate(context.getDefaultConstraintMessageTemplate()).addBeanNode().inIterable().atIndex(i).addConstraintViolation();
|
||||
valid = false;
|
||||
}
|
||||
}
|
||||
return valid;
|
||||
}
|
||||
}
|
||||
|
||||
}
|
||||
Reference in New Issue
Block a user