#132 DynamicSpecification不再对输入参数做自动类型转换,因为数字的话Hibernate会自动转,日期的格式很难自动转。另对昨天的修改增加了测试用例
This commit is contained in:
+4
-4
@@ -45,7 +45,7 @@ public class AccountSoapServiceImpl implements AccountSoapService {
|
||||
private Validator validator;
|
||||
|
||||
/**
|
||||
* @see AccountSoapService#getTeamDetail()
|
||||
* @see AccountSoapService#getTeamDetail(Long)
|
||||
*/
|
||||
@Override
|
||||
public GetTeamDetailResult getTeamDetail(Long id) {
|
||||
@@ -70,7 +70,7 @@ public class AccountSoapServiceImpl implements AccountSoapService {
|
||||
}
|
||||
|
||||
/**
|
||||
* @see AccountSoapService#getUser()
|
||||
* @see AccountSoapService#getUser(Long)
|
||||
*/
|
||||
@Override
|
||||
public GetUserResult getUser(Long id) {
|
||||
@@ -96,7 +96,7 @@ public class AccountSoapServiceImpl implements AccountSoapService {
|
||||
}
|
||||
|
||||
/**
|
||||
* @see AccountSoapService#searchUser()
|
||||
* @see AccountSoapService#searchUser(String, String)
|
||||
*/
|
||||
@Override
|
||||
public SearchUserResult searchUser(String loginName, String name) {
|
||||
@@ -113,7 +113,7 @@ public class AccountSoapServiceImpl implements AccountSoapService {
|
||||
}
|
||||
|
||||
/**
|
||||
* @see AccountSoapService#createUser()
|
||||
* @see AccountSoapService#createUser(UserDTO)
|
||||
*/
|
||||
@Override
|
||||
public IdResult createUser(UserDTO user) {
|
||||
|
||||
@@ -80,8 +80,7 @@
|
||||
<!-- production环境 -->
|
||||
<beans profile="production">
|
||||
<context:property-placeholder ignore-resource-not-found="true"
|
||||
location="classpath*:/application.properties,
|
||||
classpath*:/application.local.properties" />
|
||||
location="classpath*:/application.properties" />
|
||||
|
||||
<!-- 数据源配置,使用应用内的DBCP数据库连接池 -->
|
||||
<bean id="dataSource" class="org.apache.commons.dbcp.BasicDataSource" destroy-method="close">
|
||||
@@ -129,7 +128,8 @@
|
||||
<!-- unit test环境 -->
|
||||
<beans profile="test">
|
||||
<context:property-placeholder ignore-resource-not-found="true"
|
||||
location="classpath*:/application.properties" />
|
||||
location="classpath*:/application.properties,
|
||||
classpath*:/application.test.properties" />
|
||||
|
||||
<!-- 嵌入式内存中数据库 -->
|
||||
<jdbc:embedded-database id="dataSource" type="H2">
|
||||
|
||||
@@ -28,7 +28,7 @@
|
||||
</div>
|
||||
</div>
|
||||
|
||||
<table class="table table-striped table-bordered table-condensed">
|
||||
<table id="contentTable" class="table table-striped table-bordered table-condensed">
|
||||
<thead>
|
||||
<tr>
|
||||
<th>登录名</th>
|
||||
|
||||
+3
@@ -5,6 +5,7 @@ import static org.junit.Assert.*;
|
||||
import org.junit.Test;
|
||||
import org.junit.experimental.categories.Category;
|
||||
import org.openqa.selenium.By;
|
||||
import org.openqa.selenium.WebElement;
|
||||
import org.springside.examples.showcase.functional.BaseSeleniumTestCase;
|
||||
import org.springside.modules.test.category.Smoke;
|
||||
|
||||
@@ -22,6 +23,8 @@ public class UserManagerFT extends BaseSeleniumTestCase {
|
||||
s.click(By.linkText("帐号管理"));
|
||||
loginAsAdminIfNecessary();
|
||||
assertEquals("Showcase示例:综合演示用例", s.getTitle());
|
||||
WebElement table = s.findElement(By.id("contentTable"));
|
||||
assertEquals("管理员 ", s.getTable(table, 0, 1));
|
||||
}
|
||||
|
||||
@Test
|
||||
|
||||
+2
@@ -28,10 +28,12 @@ public class UserJaxRsFT extends BaseFunctionalTestCase {
|
||||
public void getUser() {
|
||||
UserDTO user = restTemplate.getForObject(resoureUrl + "/{id}.json", UserDTO.class, 1L);
|
||||
assertEquals("admin", user.getLoginName());
|
||||
assertEquals("管理员", user.getName());
|
||||
assertEquals(new Long(1), user.getTeamId());
|
||||
|
||||
user = restTemplate.getForObject(resoureUrl + "/{id}.xml", UserDTO.class, 1L);
|
||||
assertEquals("admin", user.getLoginName());
|
||||
assertEquals("管理员", user.getName());
|
||||
assertEquals(new Long(1), user.getTeamId());
|
||||
}
|
||||
}
|
||||
|
||||
+2
-1
@@ -89,6 +89,7 @@ public class UserRestFT extends BaseFunctionalTestCase {
|
||||
HttpEntity<UserDTO> response = jdkTemplate.exchange(resoureUrl + "/{id}.xml", HttpMethod.GET, requestEntity,
|
||||
UserDTO.class, 1L);
|
||||
assertEquals("admin", response.getBody().getLoginName());
|
||||
assertEquals("管理员", response.getBody().getName());
|
||||
assertEquals(new Long(1), response.getBody().getTeamId());
|
||||
}
|
||||
|
||||
@@ -101,6 +102,7 @@ public class UserRestFT extends BaseFunctionalTestCase {
|
||||
public void getUserAsJson() {
|
||||
UserDTO user = httpClientRestTemplate.getForObject(resoureUrl + "/{id}.json", UserDTO.class, 1L);
|
||||
assertEquals("admin", user.getLoginName());
|
||||
assertEquals("管理员", user.getName());
|
||||
assertEquals(new Long(1), user.getTeamId());
|
||||
}
|
||||
|
||||
@@ -143,6 +145,5 @@ public class UserRestFT extends BaseFunctionalTestCase {
|
||||
Servlets.encodeHttpBasic(user, password));
|
||||
return execution.execute(request, body);
|
||||
}
|
||||
|
||||
}
|
||||
}
|
||||
|
||||
+14
-4
@@ -24,16 +24,17 @@ public class DynamicSpecificationTest extends SpringTransactionalTestCase {
|
||||
|
||||
@Test
|
||||
public void fineUserByFilter() {
|
||||
|
||||
// EQ
|
||||
SearchFilter filter = new SearchFilter("name", Operator.EQ, "Admin");
|
||||
SearchFilter filter = new SearchFilter("name", Operator.EQ, "管理员");
|
||||
List<User> users = userDao
|
||||
.findAll(DynamicSpecifications.bySearchFilter(Lists.newArrayList(filter), User.class));
|
||||
assertEquals(1, users.size());
|
||||
|
||||
// LIKE
|
||||
filter = new SearchFilter("loginName", Operator.LIKE, "min");
|
||||
users = userDao.findAll(DynamicSpecifications.bySearchFilter(Lists.newArrayList(filter), User.class));
|
||||
assertEquals(1, users.size());
|
||||
|
||||
// GT
|
||||
filter = new SearchFilter("id", Operator.GT, "1");
|
||||
users = userDao.findAll(DynamicSpecifications.bySearchFilter(Lists.newArrayList(filter), User.class));
|
||||
@@ -42,6 +43,7 @@ public class DynamicSpecificationTest extends SpringTransactionalTestCase {
|
||||
filter = new SearchFilter("id", Operator.GT, "6");
|
||||
users = userDao.findAll(DynamicSpecifications.bySearchFilter(Lists.newArrayList(filter), User.class));
|
||||
assertEquals(0, users.size());
|
||||
|
||||
// GTE
|
||||
filter = new SearchFilter("id", Operator.GTE, "1");
|
||||
users = userDao.findAll(DynamicSpecifications.bySearchFilter(Lists.newArrayList(filter), User.class));
|
||||
@@ -59,6 +61,7 @@ public class DynamicSpecificationTest extends SpringTransactionalTestCase {
|
||||
filter = new SearchFilter("id", Operator.LT, "1");
|
||||
users = userDao.findAll(DynamicSpecifications.bySearchFilter(Lists.newArrayList(filter), User.class));
|
||||
assertEquals(0, users.size());
|
||||
|
||||
// LTE
|
||||
filter = new SearchFilter("id", Operator.LTE, "6");
|
||||
users = userDao.findAll(DynamicSpecifications.bySearchFilter(Lists.newArrayList(filter), User.class));
|
||||
@@ -76,16 +79,23 @@ public class DynamicSpecificationTest extends SpringTransactionalTestCase {
|
||||
assertEquals(6, users.size());
|
||||
|
||||
// AND 2 Conditions
|
||||
SearchFilter filter1 = new SearchFilter("name", Operator.EQ, "Admin");
|
||||
SearchFilter filter1 = new SearchFilter("name", Operator.EQ, "管理员");
|
||||
SearchFilter filter2 = new SearchFilter("loginName", Operator.LIKE, "min");
|
||||
users = userDao.findAll(DynamicSpecifications.bySearchFilter(Lists.newArrayList(filter1, filter2), User.class));
|
||||
assertEquals(1, users.size());
|
||||
|
||||
filter1 = new SearchFilter("name", Operator.EQ, "Admin");
|
||||
filter1 = new SearchFilter("name", Operator.EQ, "管理员");
|
||||
filter2 = new SearchFilter("loginName", Operator.LIKE, "user");
|
||||
users = userDao.findAll(DynamicSpecifications.bySearchFilter(Lists.newArrayList(filter1, filter2), User.class));
|
||||
assertEquals(0, users.size());
|
||||
|
||||
// 2 conditions on same field
|
||||
filter1 = new SearchFilter("id", Operator.GTE, "1");
|
||||
filter2 = new SearchFilter("id", Operator.LTE, "6");
|
||||
|
||||
users = userDao.findAll(DynamicSpecifications.bySearchFilter(Lists.newArrayList(filter1, filter2), User.class));
|
||||
assertEquals(6, users.size());
|
||||
|
||||
// Nest Attribute
|
||||
filter = new SearchFilter("team.id", Operator.EQ, "1");
|
||||
users = userDao.findAll(DynamicSpecifications.bySearchFilter(Lists.newArrayList(filter), User.class));
|
||||
|
||||
@@ -5,6 +5,6 @@ selenium.driver=firefox
|
||||
|
||||
#(optional)override jdbc url for functional test
|
||||
jdbc.driver=org.h2.Driver
|
||||
jdbc.url=jdbc:h2:file:~/.h2/showcase-test;AUTO_SERVER=TRUE
|
||||
jdbc.url=jdbc:h2:file:~/.h2/showcase4-test;AUTO_SERVER=TRUE
|
||||
jdbc.username=sa
|
||||
jdbc.password=
|
||||
@@ -1,4 +1,4 @@
|
||||
insert into ss_user (id, login_name, name, email, password, salt, status, team_id) values(1,'admin','Admin','admin@springside.org.cn','691b14d79bf0fa2215f155235df5e670b64394cc','7efbd59d9741d34f','enabled',1);
|
||||
insert into ss_user (id, login_name, name, email, password, salt, status, team_id) values(1,'admin','管理员','admin@springside.org.cn','691b14d79bf0fa2215f155235df5e670b64394cc','7efbd59d9741d34f','enabled',1);
|
||||
insert into ss_user (id, login_name, name, email, password, salt, status, team_id) values(2,'user','Calvin','user@springside.org.cn','2488aa0c31c624687bd9928e0a5d29e7d1ed520b','6d65d24122c30500','enabled',1);
|
||||
insert into ss_user (id, login_name, name, email, password, salt, status, team_id) values(3,'user2','Jack','jack@springside.org.cn','2488aa0c31c624687bd9928e0a5d29e7d1ed520b','6d65d24122c30500','enabled',1);
|
||||
insert into ss_user (id, login_name, name, email, password, salt, status, team_id) values(4,'user3','Kate','kate@springside.org.cn','2488aa0c31c624687bd9928e0a5d29e7d1ed520b','6d65d24122c30500','enabled',1);
|
||||
|
||||
-11
@@ -10,16 +10,12 @@ import javax.persistence.criteria.Predicate;
|
||||
import javax.persistence.criteria.Root;
|
||||
|
||||
import org.apache.commons.lang3.StringUtils;
|
||||
import org.springframework.core.convert.ConversionService;
|
||||
import org.springframework.core.convert.support.DefaultConversionService;
|
||||
import org.springframework.data.jpa.domain.Specification;
|
||||
import org.springside.modules.utils.Collections3;
|
||||
|
||||
import com.google.common.collect.Lists;
|
||||
|
||||
public class DynamicSpecifications {
|
||||
private static final ConversionService conversionService = new DefaultConversionService();
|
||||
|
||||
public static <T> Specification<T> bySearchFilter(final Collection<SearchFilter> filters, final Class<T> clazz) {
|
||||
return new Specification<T>() {
|
||||
@Override
|
||||
@@ -35,13 +31,6 @@ public class DynamicSpecifications {
|
||||
expression = expression.get(names[i]);
|
||||
}
|
||||
|
||||
// convert value from string to target type
|
||||
Class attributeClass = expression.getJavaType();
|
||||
if (!attributeClass.equals(String.class) && filter.value instanceof String
|
||||
&& conversionService.canConvert(String.class, attributeClass)) {
|
||||
filter.value = conversionService.convert(filter.value, attributeClass);
|
||||
}
|
||||
|
||||
// logic operator
|
||||
switch (filter.operator) {
|
||||
case EQ:
|
||||
|
||||
@@ -23,21 +23,31 @@ public class SearchFilter {
|
||||
this.operator = operator;
|
||||
}
|
||||
|
||||
/**
|
||||
* searchParams中key的格式为OPERATOR_FIELDNAME
|
||||
*/
|
||||
public static Map<String, SearchFilter> parse(Map<String, Object> searchParams) {
|
||||
Map<String, SearchFilter> filters = Maps.newHashMap();
|
||||
|
||||
for (Entry<String, Object> entry : searchParams.entrySet()) {
|
||||
// 过滤掉空值
|
||||
String key = entry.getKey();
|
||||
Object value = entry.getValue();
|
||||
if (StringUtils.isBlank((String) value)) {
|
||||
continue;
|
||||
}
|
||||
String[] names = StringUtils.split(entry.getKey(), "_");
|
||||
|
||||
// 拆分operator与filedAttribute
|
||||
String[] names = StringUtils.split(key, "_");
|
||||
if (names.length != 2) {
|
||||
throw new IllegalArgumentException(entry.getKey() + " is not a valid search filter name");
|
||||
throw new IllegalArgumentException(key + " is not a valid search filter name");
|
||||
}
|
||||
SearchFilter filter = new SearchFilter(names[1], Operator.valueOf(names[0]), value);
|
||||
filters.put(entry.getKey(), filter);
|
||||
String filedName = names[1];
|
||||
Operator operator = Operator.valueOf(names[0]);
|
||||
|
||||
// 创建searchFilter
|
||||
SearchFilter filter = new SearchFilter(filedName, operator, value);
|
||||
filters.put(key, filter);
|
||||
}
|
||||
|
||||
return filters;
|
||||
|
||||
@@ -20,12 +20,12 @@ public class SearchFilterTest {
|
||||
|
||||
Map<String, SearchFilter> filters = SearchFilter.parse(params);
|
||||
|
||||
SearchFilter nameFilter = filters.get("name");
|
||||
SearchFilter nameFilter = filters.get("EQ_name");
|
||||
assertEquals(Operator.EQ, nameFilter.operator);
|
||||
assertEquals("name", nameFilter.fieldName);
|
||||
assertEquals("foo", nameFilter.value);
|
||||
|
||||
SearchFilter ageFilter = filters.get("age");
|
||||
SearchFilter ageFilter = filters.get("LT_age");
|
||||
assertEquals(Operator.LT, ageFilter.operator);
|
||||
assertEquals("age", ageFilter.fieldName);
|
||||
assertEquals("1", ageFilter.value);
|
||||
|
||||
@@ -22,7 +22,7 @@
|
||||
<activemq.version>5.7.0</activemq.version>
|
||||
<quartz.version>2.1.6</quartz.version>
|
||||
<ehcache.version>2.6.2</ehcache.version>
|
||||
<spymemcached.version>2.8.7</spymemcached.version>
|
||||
<spymemcached.version>2.8.9</spymemcached.version>
|
||||
<hibernate-validator.version>4.3.1.Final</hibernate-validator.version>
|
||||
<jolokia.version>1.0.6</jolokia.version>
|
||||
<jackson.version>2.1.2</jackson.version>
|
||||
@@ -904,7 +904,7 @@
|
||||
<plugin>
|
||||
<groupId>org.codehaus.mojo</groupId>
|
||||
<artifactId>versions-maven-plugin</artifactId>
|
||||
<version>1.3.1</version>
|
||||
<version>2.0</version>
|
||||
</plugin>
|
||||
|
||||
<!-- ant插件 -->
|
||||
|
||||
Reference in New Issue
Block a user