Spring Data 与MongoDB 集成一:入门篇(开发环境搭建和简单CRUD)

来源:互联网 发布:php中级开发工程师 编辑:程序博客网 时间:2024/05/22 10:29

一、简介

                      SpringData 项目提供与MongoDB文档数据库的集成。

二、SpringData 与MongoDB 配置及对应Jar包

1、安装mongodb 数据库,请查考:待补充
2、下载spring-data 关联两个子项目:spring-data-commons和spring-data-mongodb
我下载的jar 文件是:
spring-data-commons-1.7.2.RELEASE.jar
spring-data-mongodb-1.4.2.RELEASE.jar
3、下载mongodb的驱动包.
我下载的jar 文件是:
mongo-java-driver-3.0.4.jar
4、测试mongodb 数据库是否能够连接:两种方式(java代码方式和mongodb 工具方式(Robomongo 0.9.0-RC10))
      
java代码连接方式:
package com.spring.main;import java.util.Set;import org.junit.Test;import org.junit.runner.RunWith;import org.springframework.test.context.ContextConfiguration;import org.springframework.test.context.junit4.SpringJUnit4ClassRunner;import com.mongodb.DB;import com.mongodb.Mongo;@RunWith(SpringJUnit4ClassRunner.class)  //使用junit4进行测试    @ContextConfiguration(locations={"classpath*:mongodb.xml"})  public class MongodbConnection {@Testpublic void connection(){try{                 // 连接到 mongodb 服务               Mongo mongo = new Mongo("192.168.1.88", 27017);                //根据mongodb数据库的名称获取mongodb对象 ,               DB db = mongo.getDB( "database" );               Set<String> collectionNames = db.getCollectionNames();                   // 打印出test中的集合                  for (String name : collectionNames) {                        System.out.println("collectionName==="+name);                  }                             }catch(Exception e){               e.printStackTrace();            }  }}

测试结果:


mongodb.xml 配置文件:

<?xml version="1.0" encoding="UTF-8"?><beans xmlns="http://www.springframework.org/schema/beans"xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xmlns:context="http://www.springframework.org/schema/context"xmlns:mongo="http://www.springframework.org/schema/data/mongo"xsi:schemaLocation="http://www.springframework.org/schema/context http://www.springframework.org/schema/context/spring-context-3.1.xsdhttp://www.springframework.org/schema/data/mongo http://www.springframework.org/schema/data/mongo/spring-mongo-1.1.xsdhttp://www.springframework.org/schema/beans http://www.springframework.org/schema/beans/spring-beans-3.1.xsd"><!-- Default bean name is 'mongo' --><mongo:mongo host="192.168.1.88" port="27017" /><mongo:db-factory dbname="database" mongo-ref="mongo" /><bean id="mongoTemplate" class="org.springframework.data.mongodb.core.MongoTemplate"><constructor-arg name="mongoDbFactory" ref="mongoDbFactory" /></bean><bean id="businessDao" class="com.spring.operation.BusinessDao"></bean><bean id="businessPositionDao" class="com.spring.operation.BusinessPositionDao"></bean><bean id="mongoDaoImpl" class="com.spring.operation.MongoDaoImpl"></bean></beans>

Robomongo 0.9.0-RC10连接特定mongodb 数据库



三、SpringData 实现Mongodb CRUD简单封装:

1、实现一个基础接口,是比较通用的BaseMongoDao.java类
package com.spring.mongodb;import java.util.List;import org.springframework.data.mongodb.core.query.Query;  import org.springframework.data.mongodb.core.query.Update;  import com.mongodb.WriteResult;    public interface BaseMongoDao<T> {      /**      * 插入      */      public T save(T entity);        /**      * 根据ID查询      */      public T findById(String id);        /**      * 通过ID获取记录,并且指定了集合名(表的意思)      */      public T findById(String id, String collectionName);        /**      * 获得所有该类型记录      */      public List<T> findAll();        /**      * 获得所有该类型记录,并且指定了集合名(表的意思)      */      public List<T> findAll(String collectionName);        /**      * 根据条件查询      */      public List<T> find(Query query);        /**      * 根据条件查询一个      */      public T findOne(Query query);        /**      * 分页查询      */      public Page<T> findPage(Page<T> page, Query query);        /**      * 根据条件 获得总数      */      public long count(Query query);        /**      * 根据条件 更新      */      public WriteResult update(Query query, Update update);        /**      * 更新符合条件并sort之后的第一个文档 并返回更新后的文档      */      public T updateOne(Query query, Update update);        /**      * 根据传入实体ID更新      */      public WriteResult update(T entity);        /**      * 根据条件 删除      *       * @param query      */      public void remove(Query query);  }  

2、编写基础通用类BaseMongoDaoImpl ,继承BaseMongoDao

package com.spring.mongodb;import java.lang.reflect.Field;  import java.util.List;  import javax.annotation.Resource;    import org.springframework.data.mongodb.core.MongoTemplate;  import org.springframework.data.mongodb.core.query.Criteria;  import org.springframework.data.mongodb.core.query.Query;  import org.springframework.data.mongodb.core.query.Update;    import com.mongodb.WriteResult;  public class BaseMongoDaoImpl<T> implements BaseMongoDao<T> {/**      * spring mongodb 集成操作类       */      @Resource      protected MongoTemplate mongoTemplate;        /**      * 注入mongodbTemplate      *       * @param mongoTemplate      */      protected void setMongoTemplate(MongoTemplate mongoTemplate) {          this.mongoTemplate = mongoTemplate;      }      public T save(T entity) {          mongoTemplate.insert(entity);          return entity;      }        public T findById(String id) {          return mongoTemplate.findById(id, this.getEntityClass());      }        public T findById(String id, String collectionName) {          return mongoTemplate.findById(id, this.getEntityClass(), collectionName);      }        public List<T> findAll() {          return mongoTemplate.findAll(this.getEntityClass());      }        public List<T> findAll(String collectionName) {          return mongoTemplate.findAll(this.getEntityClass(), collectionName);      }        public List<T> find(Query query) {          return mongoTemplate.find(query, this.getEntityClass());      }        public T findOne(Query query) {          return mongoTemplate.findOne(query, this.getEntityClass());      }        public Page<T> findPage(Page<T> page, Query query) {          //如果没有条件 则所有全部          query=query==null?new Query(Criteria.where("_id").exists(true)):query;          long count = this.count(query);          // 总数          page.setTotalCount((int) count);          int currentPage = page.getCurrentPage();          int pageSize = page.getPageSize();          query.skip((currentPage - 1) * pageSize).limit(pageSize);          List<T> rows = this.find(query);          page.build(rows);          return page;      }        public long count(Query query) {          return mongoTemplate.count(query, this.getEntityClass());      }        public WriteResult update(Query query, Update update) {          if (update==null) {              return null;          }          return mongoTemplate.updateMulti(query, update, this.getEntityClass());      }        public T updateOne(Query query, Update update) {          if (update==null) {              return null;          }          return mongoTemplate.findAndModify(query, update, this.getEntityClass());      }          public WriteResult update(T entity) {          Field[] fields = this.getEntityClass().getDeclaredFields();          if (fields == null || fields.length <= 0) {              return null;          }          Field idField = null;          // 查找ID的field          for (Field field : fields) {              if (field.getName() != null                      && "id".equals(field.getName().toLowerCase())) {                  idField = field;                  break;              }          }          if (idField == null) {              return null;          }          idField.setAccessible(true);          String id=null;          try {              id = (String) idField.get(entity);          } catch (IllegalArgumentException e) {              e.printStackTrace();          } catch (IllegalAccessException e) {              e.printStackTrace();          }          if (id == null || "".equals(id.trim()))              return null;          // 根据ID更新          Query query = new Query(Criteria.where("_id").is(id));          // 更新          // Update update = new Update();          // for (Field field : fields) {          // // 不为空 不是主键 不是序列化号          // if (field != null          // && field != idField          // && !"serialversionuid"          // .equals(field.getName().toLowerCase())) {          // field.setAccessible(true);          // Object obj = field.get(entity);          // if (obj == null)          // continue;          // update.set(field.getName(), obj);          // }          // }          Update update = ReflectionUtils.getUpdateObj(entity);          if (update == null) {              return null;          }          return mongoTemplate.updateFirst(query, update, getEntityClass());      }        public void remove(Query query) {          mongoTemplate.remove(query, this.getEntityClass());      }      /**      * 获得泛型类      */      private Class<T> getEntityClass() {                return ReflectionUtils.getSuperClassGenricType(getClass());      }    }  

3、编写需要存储的实例类Business.java
package com.spring.entity;import java.io.Serializable;public class Business implements Serializable {/** *  */private static final long serialVersionUID = 1L;//维度private double lat;//经度private double lng;//商家编号private int openid;//默认构造函数public Business() {super();}//set和get public double getLat() {return lat;}public void setLat(double lat) {this.lat = lat;}public double getLng() {return lng;}public void setLng(double lng) {this.lng = lng;}public int getOpenid() {return openid;}public void setOpenid(int openid) {this.openid = openid;}}

4、编写BuinessDao 类文件,继承BaseMongoDaoImpl<T>,实现对Buiness的CRUD操作。
package com.spring.operation;import com.spring.entity.Business;import com.spring.mongodb.BaseMongoDaoImpl;public class BusinessDao extends BaseMongoDaoImpl<Business> {}


5、实例测试
package com.spring.main;import java.util.List;import org.junit.Test;import org.junit.runner.RunWith;import org.springframework.beans.factory.annotation.Autowired;import org.springframework.data.mongodb.core.query.Criteria;import org.springframework.data.mongodb.core.query.Query;import org.springframework.data.mongodb.core.query.Update;import org.springframework.test.context.ContextConfiguration;import org.springframework.test.context.junit4.SpringJUnit4ClassRunner;import com.spring.entity.Business;import com.spring.mongodb.Page;import com.spring.operation.BusinessDao;@RunWith(SpringJUnit4ClassRunner.class)  //使用junit4进行测试    @ContextConfiguration(locations={"classpath*:mongodb.xml"})   public class MongodbMain {@Autowired private BusinessDao businessDao;     //测试数据插入 @Test   public void test1(){   Business business =new Business(); business.setLat(22.588402); business.setLng(113.867822);  business.setOpenid(5);  businessDao.save(business); System.out.println("数据插入成功"); } //测试数据获取(id)@Testpublic void test2(){Business business = businessDao.findById("582174af6e6407195c0cd10a");System.out.println("商家编号:"+business.getOpenid());System.out.println("经度:"+business.getLat());System.out.println("维度:"+business.getLng());}//测试数据获取(id,collectionName)@Testpublic void test3(){Business business = businessDao.findById("582175986e64071f888bee69","business");System.out.println("商家编号:"+business.getOpenid());System.out.println("经度:"+business.getLat());System.out.println("维度:"+business.getLng());}//测试数据获取(all)@Testpublic void test4(){List<Business> list = businessDao.findAll();if(list !=null && list.size()>0){for(Business business : list){System.out.println("商家编号:"+business.getOpenid());System.out.println("经度:"+business.getLat());System.out.println("维度:"+business.getLng());}}}//测试数据获取(collectionName)@Testpublic void test5(){List<Business> list = businessDao.findAll("business");if(list !=null && list.size()>0){for(Business business : list){System.out.println("商家编号:"+business.getOpenid());System.out.println("经度:"+business.getLat());System.out.println("维度:"+business.getLng());}}}//测试数据获取(query);   注意请求参数属性与实体对象属性一一对应。@Testpublic void test6(){Query query = new Query(Criteria.where("lng").is(114.038804).and("lat").is(22.669214).and("openid").is(2));List<Business> list = businessDao.find(query);if(list !=null && list.size()>0){for(Business business : list){System.out.println("商家编号:"+business.getOpenid());System.out.println("经度:"+business.getLat());System.out.println("维度:"+business.getLng());}}}//测试数据获取(query);   注意请求参数属性与实体对象属性一一对应。@Testpublic void test7(){Query query = new Query(Criteria.where("lng").is(114.038804).and("lat").is(22.669214).and("openid").is(2));Business business = businessDao.findOne(query);if(business !=null){System.out.println("商家编号:"+business.getOpenid());System.out.println("经度:"+business.getLat());System.out.println("维度:"+business.getLng());}}//测试数据获取(page);@Testpublic void test8(){Query query = new Query();Page<Business> page = new Page<Business>();//page.setPageSize(2); //设置分页记录数//page.setCurrentPage(3);//设置当前页面Page<Business> pages = businessDao.findPage(page, query);List<Business> list = pages.getRows();if(list !=null && list.size()>0){for(Business business :list){System.out.println("商家编号:"+business.getOpenid());System.out.println("经度:"+business.getLat());System.out.println("维度:"+business.getLng());}}}//测试数据获取(total)@Testpublic void test9(){Query query = new Query();long num = businessDao.count(query);System.out.println("记录总数:"+num);}//测试数据修改(update)  注意:修改返回的实体对象是之前存储的数据信息@Testpublic void test10(){Query query = new Query(Criteria.where("openid").is(2));Update  update =new Update();update.set("lng", 110.649865);Business business = businessDao.updateOne(query, update);if(business !=null){System.out.println("商家编号:"+business.getOpenid());System.out.println("经度:"+business.getLat());System.out.println("维度:"+business.getLng());}}}

6、相关工具类封装(Page.java[java分页工具类])和(ReflectionUtils(反射工具类))
package com.spring.mongodb;import java.io.Serializable;  import java.util.List;      public class Page<T> implements Serializable {      private static final long serialVersionUID = 5760097915453738435L;      public static final int DEFAULT_PAGE_SIZE = 10;      /**      * 每页显示个数      */      private int pageSize;      /**      * 当前页数      */      private int currentPage;      /**      * 总页数      */      private int totalPage;      /**      * 总记录数      */      private int totalCount;      /**      * 结果列表      */      private List<T> rows;            public Page(){           this.currentPage = 1;           this.pageSize = DEFAULT_PAGE_SIZE;      }      public Page(int currentPage,int pageSize){          this.currentPage=currentPage<=0?1:currentPage;          this.pageSize=pageSize<=0?1:pageSize;      }      public int getPageSize() {          return pageSize;      }      public void setPageSize(int pageSize) {          this.pageSize = pageSize;      }      public int getCurrentPage() {          return currentPage;      }      public void setCurrentPage(int currentPage) {          this.currentPage = currentPage;      }      public int getTotalPage() {          return totalPage;      }      public void setTotalPage(int totalPage) {          this.totalPage = totalPage;      }      public int getTotalCount() {          return totalCount;      }      public void setTotalCount(int totalCount) {          this.totalCount = totalCount;      }        /**      * 设置结果 及总页数      * @param list      */       public void build(List<T> rows) {                this.setRows(rows);                int count =  this.getTotalCount();                int divisor = count / this.getPageSize();                int remainder = count % this.getPageSize();                this.setTotalPage(remainder == 0 ? divisor == 0 ? 1 : divisor : divisor + 1);            }      public List<T> getRows() {          return rows;      }      public void setRows(List<T> rows) {          this.rows = rows;      }    }  


package com.spring.mongodb;import java.lang.reflect.Field;import java.lang.reflect.InvocationTargetException;import java.lang.reflect.Method;import java.lang.reflect.ParameterizedType;import java.lang.reflect.Type;import java.util.HashMap;import java.util.Map;import org.slf4j.Logger;import org.slf4j.LoggerFactory;import org.springframework.data.domain.Sort;import org.springframework.data.domain.Sort.Direction;import org.springframework.data.mongodb.core.query.Criteria;import org.springframework.data.mongodb.core.query.Query;import org.springframework.data.mongodb.core.query.Update;import org.springframework.util.Assert;import org.springframework.util.StringUtils;public class ReflectionUtils {private static Logger logger = LoggerFactory.getLogger(ReflectionUtils.class);/** * 调用Getter方法. */public static Object invokeGetterMethod(Object obj, String propertyName) {String getterMethodName = "get" + StringUtils.capitalize(propertyName);return invokeMethod(obj, getterMethodName, new Class[] {},new Object[] {});}/** * 调用Setter方法.使用value的Class来查找Setter方法. */public static void invokeSetterMethod(Object obj, String propertyName,Object value) {invokeSetterMethod(obj, propertyName, value, null);}/** * 调用Setter方法. *  * @param propertyType *            用于查找Setter方法,为空时使用value的Class替代. */public static void invokeSetterMethod(Object obj, String propertyName,Object value, Class<?> propertyType) {Class<?> type = propertyType != null ? propertyType : value.getClass();String setterMethodName = "set" + StringUtils.capitalize(propertyName);invokeMethod(obj, setterMethodName, new Class[] { type },new Object[] { value });}/** * 直接读取对象属性值, 无视private/protected修饰符, 不经过getter函数. */public static Object getFieldValue(final Object obj, final String fieldName) {Field field = getAccessibleField(obj, fieldName);if (field == null) {throw new IllegalArgumentException("Could not find field ["+ fieldName + "] on target [" + obj + "]");}Object result = null;try {result = field.get(obj);} catch (IllegalAccessException e) {logger.error("不可能抛出的异常{}", e.getMessage());}return result;}/** * 直接设置对象属性值, 无视private/protected修饰符, 不经过setter函数. */public static void setFieldValue(final Object obj, final String fieldName,final Object value) {Field field = getAccessibleField(obj, fieldName);if (field == null) {throw new IllegalArgumentException("Could not find field ["+ fieldName + "] on target [" + obj + "]");}try {field.set(obj, value);} catch (IllegalAccessException e) {logger.error("不可能抛出的异常:{}", e.getMessage());}}/** * 循环向上转型, 获取对象的DeclaredField, 并强制设置为可访问. *  * 如向上转型到Object仍无法找到, 返回null. */public static Field getAccessibleField(final Object obj,final String fieldName) {Assert.notNull(obj, "object不能为空");Assert.hasText(fieldName, "fieldName");for (Class<?> superClass = obj.getClass(); superClass != Object.class; superClass = superClass.getSuperclass()) {try {Field field = superClass.getDeclaredField(fieldName);field.setAccessible(true);return field;} catch (NoSuchFieldException e) {// NOSONAR// Field不在当前类定义,继续向上转型}}return null;}/** * 直接调用对象方法, 无视private/protected修饰符. 用于一次性调用的情况. */public static Object invokeMethod(final Object obj,final String methodName, final Class<?>[] parameterTypes,final Object[] args) {Method method = getAccessibleMethod(obj, methodName, parameterTypes);if (method == null) {throw new IllegalArgumentException("Could not find method ["+ methodName + "] on target [" + obj + "]");}try {return method.invoke(obj, args);} catch (Exception e) {throw convertReflectionExceptionToUnchecked(e);}}/** * 循环向上转型, 获取对象的DeclaredMethod,并强制设置为可访问. 如向上转型到Object仍无法找到, 返回null. *  * 用于方法需要被多次调用的情况. 先使用本函数先取得Method,然后调用Method.invoke(Object obj, Object... * args) */public static Method getAccessibleMethod(final Object obj,final String methodName, final Class<?>... parameterTypes) {Assert.notNull(obj, "object不能为空");for (Class<?> superClass = obj.getClass(); superClass != Object.class; superClass = superClass.getSuperclass()) {try {Method method = superClass.getDeclaredMethod(methodName,parameterTypes);method.setAccessible(true);return method;} catch (NoSuchMethodException e) {// NOSONAR// Method不在当前类定义,继续向上转型}}return null;}/** * 通过反射, 获得Class定义中声明的父类的泛型参数的类型. 如无法找到, 返回Object.class. eg. public UserDao * extends HibernateDao<User> *  * @param clazz *            The class to introspect * @return the first generic declaration, or Object.class if cannot be *         determined */@SuppressWarnings({ "unchecked", "rawtypes" })public static <T> Class<T> getSuperClassGenricType(final Class clazz) {return getSuperClassGenricType(clazz, 0);}/** * 通过反射, 获得Class定义中声明的父类的泛型参数的类型. 如无法找到, 返回Object.class. *  * 如public UserDao extends HibernateDao<User,Long> *  * @param clazz *            clazz The class to introspect * @param index *            the Index of the generic ddeclaration,start from 0. * @return the index generic declaration, or Object.class if cannot be *         determined */@SuppressWarnings("rawtypes")public static Class getSuperClassGenricType(final Class clazz,final int index) {Type genType = clazz.getGenericSuperclass();if (!(genType instanceof ParameterizedType)) {logger.warn(clazz.getSimpleName()+ "'s superclass not ParameterizedType");return Object.class;}Type[] params = ((ParameterizedType) genType).getActualTypeArguments();if (index >= params.length || index < 0) {logger.warn("Index: " + index + ", Size of "+ clazz.getSimpleName() + "'s Parameterized Type: "+ params.length);return Object.class;}if (!(params[index] instanceof Class)) {logger.warn(clazz.getSimpleName()+ " not set the actual class on superclass generic parameter");return Object.class;}return (Class) params[index];}/** * 将反射时的checked exception转换为unchecked exception. */public static RuntimeException convertReflectionExceptionToUnchecked(Exception e) {if (e instanceof IllegalAccessException|| e instanceof IllegalArgumentException|| e instanceof NoSuchMethodException) {return new IllegalArgumentException("Reflection Exception.", e);} else if (e instanceof InvocationTargetException) {return new RuntimeException("Reflection Exception.",((InvocationTargetException) e).getTargetException());} else if (e instanceof RuntimeException) {return (RuntimeException) e;}return new RuntimeException("Unexpected Checked Exception.", e);}/** * 根据对象获得mongodb Update语句 除id字段以外,所有被赋值的字段都会成为修改项 */public static Update getUpdateObj(final Object obj) {if (obj == null)return null;Field[] fields = obj.getClass().getDeclaredFields();Update update = null;boolean isFirst = true;for (Field field : fields) {field.setAccessible(true);try {Object value = field.get(obj);if (value != null) {if ("id".equals(field.getName().toLowerCase())|| "serialversionuid".equals(field.getName().toLowerCase()))continue;if (isFirst) {update = Update.update(field.getName(), value);isFirst = false;} else {update = update.set(field.getName(), value);}}} catch (IllegalArgumentException e) {e.printStackTrace();} catch (IllegalAccessException e) {e.printStackTrace();}}return update;}/** * 根据对象获得mongodb Query语句 *  * 1.时间范围查询:在时间字段前增加begin或end,为这两个字段分别赋值 例:private Date createDate; 开始时间 * private Date beginCreateDate; 结束时间 private Date endCreateDate; * 分析后结果:where createDate >= beginCreateDate and createDate < * beginCreateDate *  * 2.排序 定义并赋值VO中 orderBy 字段,以英文“,”分割多个排序,以空格分隔排序方向 asc可不写 例:private String * orderBy; orderBy="createDate desc,sendDate asc,id" 分析结构:order by * createDate desc,sendDate asc,id asc *  * 3.固定值搜索 定义并赋值VO中的任意字段,搜索时会把以赋值的字段当作为搜索条件 */public static Query getQueryObj(final Object obj) {if (obj == null)return null;Field[] fields = obj.getClass().getDeclaredFields();// Sort sort=new Sort(new Order(Direction.DESC,"createDate"));Query query = new Query();// 存放日期范围或者确定日期Map<String, Criteria> dateMap = new HashMap<String, Criteria>();String sortStr = null;for (Field field : fields) {field.setAccessible(true);try {Object value = field.get(obj);if (value != null) {if ("serialversionuid".equals(field.getName().toLowerCase())) {continue;}if ("orderby".equals(field.getName().toLowerCase())) {sortStr = String.valueOf(value);continue;}if (field.getType().getSimpleName().equals("Date")) {if (field.getName().toLowerCase().startsWith("begin")) {String beginName = field.getName().substring(5);if (beginName.isEmpty()) {dateMap.put("begin", Criteria.where("begin").is(value));} else {//beginName = StringUtil//.toLowerCaseFirstOne(beginName);Criteria criteria = dateMap.get(beginName) == null ? Criteria.where(beginName).gte(value) : dateMap.get(beginName).gte(value);dateMap.put(beginName, criteria);}continue;}if (field.getName().toLowerCase().startsWith("end")) {String endName = field.getName().substring(3);if (endName.isEmpty()) {dateMap.put("end",Criteria.where("end").is(value));} else {//endName = StringUtil//.toLowerCaseFirstOne(endName);Criteria criteria = dateMap.get(endName) == null ? Criteria.where(endName).lt(value) : dateMap.get(endName).lt(value);dateMap.put(endName, criteria);}continue;}dateMap.put(field.getName(),Criteria.where(field.getName()).is(value));continue;}query.addCriteria(Criteria.where(field.getName()).is(value));}} catch (Exception e) {e.printStackTrace();}}// 日期类型查询条件for (String key : dateMap.keySet()) {if (dateMap.get(key) != null) {query.addCriteria(dateMap.get(key));}}// 排序if (sortStr != null && !sortStr.trim().isEmpty()) {Sort sort = null;String[] strs = sortStr.split(",");for (String str : strs) {str = str.trim();if (str.isEmpty()) {continue;}int i = str.indexOf(" ");if (i < 0) {if (sort == null) {sort = new Sort(Direction.ASC, str);} else {sort = sort.and(new Sort(Direction.ASC, str));}} else {String name = str.substring(0, i);String dire = str.substring(i + 1).trim();Sort sn = null;if ("desc".equals(dire.toLowerCase())) {sn = new Sort(Direction.DESC, name);} else {sn = new Sort(Direction.ASC, name);}if (sort == null) {sort = sn;} else {sort = sort.and(sn);}}}if (sort != null) {query.with(sort);}}return query;}}

项目源码:待补充。


0 1
原创粉丝点击