SpringBoot 通用 MongoDao 封装

本贴最后更新于 2061 天前,其中的信息可能已经天翻地覆

MongoDao

package com.yoyo.framework.mongo; import com.mongodb.client.result.DeleteResult; import com.mongodb.client.result.UpdateResult; import com.yoyo.framework.api.RTPaging; import com.yoyo.framework.json.JSONUtils; import com.yoyo.framework.reflect.ReflectUtil; import org.bson.Document; import org.springframework.beans.factory.annotation.Autowired; import org.springframework.data.annotation.Id; import org.springframework.data.domain.Sort; 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 org.springframework.stereotype.Repository; import org.springframework.util.Assert; import java.lang.reflect.ParameterizedType; import java.util.List; import java.util.Objects; import java.util.Optional; /*** @Author:MrHuang @Date: 2019/9/4 16:19 @DESC: TODO @VERSION: 1.0 ***/ @Repository public class MongoDao<K,V> { @Autowired private MongoTemplate mongoTemplate; /** * 新增 * @param v * @return */ public V insert(V v) { return mongoTemplate.insert(v); } /** * 查询 * @param id * @return */ public V findById(K id) { Class<V> vClass = (Class<V>)((ParameterizedType)getClass().getGenericSuperclass()).getActualTypeArguments()[1]; return mongoTemplate.findById(id, vClass); } /** * 根据ID批量查询 * @param ids * @return */ public List<V> findByIds(List<K> ids) { Class<V> vClass = (Class<V>)((ParameterizedType)getClass().getGenericSuperclass()).getActualTypeArguments()[1]; String idFieldName = ReflectUtil.getFieldName(vClass, Id.class); Assert.notNull(idFieldName, "@Id not find"); return mongoTemplate.find(Query.query(Criteria.where(idFieldName).in(ids)), vClass); } /** * 强制更新 * @param v * @return */ public UpdateResult updateById(V v) { Update update = Update.fromDocument(Document.parse(JSONUtils.object2Json(v))); ReflectUtil.FieldNameValue id = ReflectUtil.getFieldNameValue(v, Id.class); Assert.notNull(id, "@Id not find"); return mongoTemplate.updateFirst(Query.query(Criteria.where(id.getFieldName()).is(id.getFieldValue())), update, v.getClass()); } /** * 乐观锁更新 * @param v * @return */ public UpdateResult updateByIdWithVersion(V v) { ReflectUtil.FieldNameValue id = ReflectUtil.getFieldNameValue(v, Id.class); Assert.notNull(id, "@Id not find"); ReflectUtil.FieldNameValue version = ReflectUtil.getFieldNameValue(v, MongoVersion.class); Assert.notNull(version, "@MongoVersion not find"); Object fieldValue = Optional.ofNullable(version.getFieldValue()).orElse("0"); Criteria criteria = Criteria.where(id.getFieldName()).is(id.getFieldValue()).and(version.getFieldName()).is(fieldValue); // 版本号+1 ReflectUtil.setFieldValue(v, version.getFieldName(), (Integer.parseInt(fieldValue.toString()) + 1) + ""); Update update = Update.fromDocument(Document.parse(JSONUtils.object2Json(v))); update.set("_class", v.getClass().getName()); return mongoTemplate.updateFirst(Query.query(criteria), update, v.getClass()); } /** * 物理删除 * @param id * @return */ public DeleteResult deleteById(K id) { Class<V> vClass = (Class<V>)((ParameterizedType)getClass().getGenericSuperclass()).getActualTypeArguments()[1]; String idFieldName = ReflectUtil.getFieldName(vClass, Id.class); Assert.notNull(idFieldName, "@Id not find"); return mongoTemplate.remove(Query.query(Criteria.where(idFieldName).is(id)), vClass); } /** * 根据查询条件查找列表 * @param criteria * @return */ public List<V> find(Criteria criteria) { Class<V> vClass = (Class<V>)((ParameterizedType)getClass().getGenericSuperclass()).getActualTypeArguments()[1]; return mongoTemplate.find(Query.query(criteria), vClass); } /** * 根据查询条件查找列表 * @param criteria * @return */ public List<V> find(Criteria criteria, Sort sort, Long skip, Integer limit) { Class<V> vClass = (Class<V>)((ParameterizedType)getClass().getGenericSuperclass()).getActualTypeArguments()[1]; Query query = Query.query(criteria); if (Objects.nonNull(sort)) { query.with(sort); } if (Objects.nonNull(skip)) { query.skip(skip); } if (Objects.nonNull(limit)) { query.limit(limit); } return mongoTemplate.find(query, vClass); } /** * 根据查询条件查找条数 * @param criteria * @return */ public long count(Criteria criteria) { Class<V> vClass = (Class<V>)((ParameterizedType)getClass().getGenericSuperclass()).getActualTypeArguments()[1]; return mongoTemplate.count(Query.query(criteria), vClass); } /** * 根据查询条件分页查询 * @param criteria 查询条件 * @param sort 排序条件 * @param pageNow 查找的页数 * @param pageSize 每页显示大小 */ public RTPaging<V> paging(Criteria criteria, Sort sort, long pageNow, int pageSize) { long totalRecord = this.count(criteria); long totalPage = RTPaging.getTotalPage(totalRecord, pageSize); long skip = RTPaging.getSkip(pageNow, pageSize); List<V> recond = this.find(criteria, sort, skip, pageSize); return new RTPaging<V>().setPageNow(pageNow).setPageSize(pageSize) .setTotalRecord(totalRecord).setTotalPage(totalPage) .setRecord(recond); } /** * 更新第一条匹配到的 * @param criteria * @param update * @return */ public UpdateResult updateFirst(Criteria criteria, Update update) { Class<V> vClass = (Class<V>)((ParameterizedType)getClass().getGenericSuperclass()).getActualTypeArguments()[1]; return mongoTemplate.updateFirst(Query.query(criteria), update, vClass); } /** * 更新所有匹配到的 * @param criteria * @param update * @return */ public UpdateResult updateMulti(Criteria criteria, Update update) { Class<V> vClass = (Class<V>)((ParameterizedType)getClass().getGenericSuperclass()).getActualTypeArguments()[1]; return mongoTemplate.updateMulti(Query.query(criteria), update, vClass); } }

ReflectUtil

package com.yoyo.framework.reflect; import lombok.Data; import lombok.experimental.Accessors; import lombok.extern.slf4j.Slf4j; import org.apache.commons.lang3.reflect.FieldUtils; import org.springframework.util.Assert; import org.springframework.util.CollectionUtils; import java.io.Serializable; import java.lang.annotation.Annotation; import java.lang.reflect.Field; import java.util.List; import java.util.Objects; import java.util.Optional; /*** @Author:MrHuang @Date: 2019/9/4 16:42 @DESC: TODO @VERSION: 1.0 ***/ @Slf4j public class ReflectUtil { /** * 根据注解获取Field * @param clazz * @param annotationCls * @return */ public static Field getField(Class<?> clazz, Class<? extends Annotation> annotationCls) { List<Field> list = FieldUtils.getFieldsListWithAnnotation(clazz, annotationCls); if (!CollectionUtils.isEmpty(list)) { return list.get(0); } return null; } /** * 根据注解获取FieldValue * @param object * @param annotationCls * @return */ public static Object getFieldValue(Object object, Class<? extends Annotation> annotationCls) { return Optional.ofNullable(getFieldNameValue(object, annotationCls)).map(FieldNameValue::getFieldValue).orElse(null); } /** * 根据注解获取FieldName * @param object * @param annotationCls * @return */ public static String getFieldName(Object object, Class<? extends Annotation> annotationCls) { return Optional.ofNullable(getFieldNameValue(object, annotationCls)).map(FieldNameValue::getFieldName).orElse(null); } public static String getFieldName(Class objectClass, Class<? extends Annotation> annotationCls) { Field field = ReflectUtil.getField(objectClass, annotationCls); return Objects.nonNull(field) ? field.getName() : null; } /** * 根据注解获取FieldNameValue * @param object * @param annotationCls * @return */ public static FieldNameValue getFieldNameValue(Object object, Class<? extends Annotation> annotationCls) { if (Objects.isNull(object) || Objects.isNull(annotationCls)) { return null; } Field field = ReflectUtil.getField(object.getClass(), annotationCls); if (Objects.nonNull(field)) { field.setAccessible(true); try { return new FieldNameValue().setFieldName(field.getName()).setFieldValue(field.get(object)); } catch (IllegalAccessException e) { log.error("ReflectUtil getFieldNameValue error", e); } } return null; } /** * 根据注解获取FieldNameValue * @param object * @param fieldName * @param newFieldValue * @return */ public static void setFieldValue(Object object, String fieldName, Object newFieldValue) { Field field = FieldUtils.getField(object.getClass(), fieldName, true); try { field.set(object, newFieldValue); } catch (IllegalAccessException e) { log.error("ReflectUtil setFieldValue error", e); } } @Data @Accessors(chain = true) public static class FieldNameValue implements Serializable { private String fieldName; private Object fieldValue; } }

RoleDTO

package com.yoyo.authority.role.pojo.dto; import com.yoyo.framework.mongo.MongoVersion; import lombok.Data; import lombok.experimental.Accessors; import org.springframework.data.annotation.Id; import org.springframework.data.mongodb.core.mapping.Document; import org.springframework.data.mongodb.core.mapping.Field; import java.io.Serializable; import java.time.LocalDateTime; import java.util.List; /*** @Author:MrHuang @Date: 2019/9/4 10:48 @DESC: TODO @VERSION: 1.0 ***/ @Data @Accessors(chain = true) @Document(collection = "t_role") public class RoleDTO implements Serializable { @Id private String rid; @Field private String name; @Field private String remark; @Field private Integer roleStatus; @Field private List<String> bindMenuId; @Field private String createTime; @Field private String updateTime; @MongoVersion private String version; }

MongoVersion

package com.yoyo.framework.mongo; import java.lang.annotation.ElementType; import java.lang.annotation.Retention; import java.lang.annotation.RetentionPolicy; import java.lang.annotation.Target; /*** @Author:MrHuang @Date: 2019/9/5 15:02 @DESC: TODO 乐观锁版本 @VERSION: 1.0 ***/ @Target({ElementType.FIELD}) @Retention(RetentionPolicy.RUNTIME) public @interface MongoVersion { }

RoleDao

package com.yoyo.authority.role.dao; import com.yoyo.authority.role.pojo.dto.RoleDTO; import com.yoyo.framework.mongo.MongoDao; import org.springframework.stereotype.Repository; /*** @Author:MrHuang @Date: 2019/9/5 16:54 @DESC: TODO @VERSION: 1.0 ***/ @Repository public class RoleDao extends MongoDao<String, RoleDTO> { }
  • Spring

    Spring 是一个开源框架,是于 2003 年兴起的一个轻量级的 Java 开发框架,由 Rod Johnson 在其著作《Expert One-On-One J2EE Development and Design》中阐述的部分理念和原型衍生而来。它是为了解决企业应用开发的复杂性而创建的。框架的主要优势之一就是其分层架构,分层架构允许使用者选择使用哪一个组件,同时为 JavaEE 应用程序开发提供集成的框架。

    949 引用 • 1460 回帖
  • MongoDB

    MongoDB(来自于英文单词“Humongous”,中文含义为“庞大”)是一个基于分布式文件存储的数据库,由 C++ 语言编写。旨在为应用提供可扩展的高性能数据存储解决方案。MongoDB 是一个介于关系数据库和非关系数据库之间的产品,是非关系数据库当中功能最丰富,最像关系数据库的。它支持的数据结构非常松散,是类似 JSON 的 BSON 格式,因此可以存储比较复杂的数据类型。

    91 引用 • 59 回帖

相关帖子

欢迎来到这里!

我们正在构建一个小众社区,大家在这里相互信任,以平等 • 自由 • 奔放的价值观进行分享交流。最终,希望大家能够找到与自己志同道合的伙伴,共同成长。

注册 关于
请输入回帖内容 ...
  • wenbao

    这个还不错哦

  • 其他回帖
  • cloudlang via macOS

    的确很不错。

    RTPaging 这个类少了