热门标签 | HotTags
当前位置:  开发笔记 > 编程语言 > 正文

MongoRepository的findById方法查不出_id值的解决方案.md

搭一个新项目,从mongo数据库中查询数据,我直接使用的spring-data-mongodb模块。直接创建Repository接口,继承MongoRepos

搭一个新项目,从mongo数据库中查询数据,我直接使用的spring-data-mongodb模块。直接创建Repository接口,继承MongoRepository

public interface ResourceRepository extends MongoRepository {
}

使用MongoRepository的findById方法,查询"_id"为某个值,程序中查询不出来,但是数据库中有值。并且使用db.getCollection(‘resource’).find({"_id":})验证过。
然后查询的时候debug了下,走到了MongoTemplate的findById方法中,它将_id替换为了id:

public T findById(Object id, Class entityClass, String collectionName) {Assert.notNull(id, "Id must not be null!");Assert.notNull(entityClass, "EntityClass must not be null!");Assert.notNull(collectionName, "CollectionName must not be null!");MongoPersistentEntity persistentEntity = mappingContext.getPersistentEntity(entityClass);String idKey = ID_FIELD;//_idif (persistentEntity != null) {if (persistentEntity.getIdProperty() != null) {idKey = persistentEntity.getIdProperty().getName();//赋值为id}}return doFindOne(collectionName, new Document(idKey, id), new Document(), entityClass);}

idKey = persistentEntity.getIdProperty().getName();这句代码把“_id”的key换为了“id”,这样如果mongo集合中只有“_id”字段,就查询不出来了。

解决方案

继承MongoTemplate类,重写它的findById方法,我Debug后MongoTemplate执行的是public MongoTemplate(MongoDbFactory mongoDbFactory, @Nullable MongoConverter mongoConverter) 的构造方法:在这里插入图片描述
我们也创建类似的构造方法:

@Component
public class PMongoTemplate extends MongoTemplate{private static final String ID_FIELD = "_id";@Autowiredpublic PMongoTemplate(MongoDbFactory mongoDbFactory, @Nullable MongoConverter mongoConverter) {super(mongoDbFactory,mongoConverter);}@Overridepublic T findById(Object id, Class entityClass, String collectionName) {Assert.notNull(id, "Id must not be null!");Assert.notNull(entityClass, "EntityClass must not be null!");Assert.notNull(collectionName, "CollectionName must not be null!");String idKey = ID_FIELD;return doFindOne(collectionName, new Document(idKey, id), new Document(), entityClass);}
}

启动之后报如下错误,没有创建Bean ‘mongoTemplate’:

因为我们自定了一个MongoTemplate类型的Bean,所以Spring在初始化的时候,不不再创建同一类型的了。所以我们之前创建的ResourceRepository等接口都无法使用了,这些接口继承MongoRepository,启动后创建对应的SimpleMongoRepository,SimpleMongoRepository间接依赖了mongoTemplate。

这样走不通,那我们就用MongoTemplate自带的方法:

protected T doFindOne(String collectionName, Document query, Document fields, Class entityClass) {MongoPersistentEntity entity = mappingContext.getPersistentEntity(entityClass);Document mappedQuery = queryMapper.getMappedObject(query, entity);Document mappedFields = queryMapper.getMappedObject(fields, entity);if (LOGGER.isDebugEnabled()) {LOGGER.debug("findOne using query: {} fields: {} for class: {} in collection: {}", serializeToJsonSafely(query),mappedFields, entityClass, collectionName);}return executeFindOneInternal(new FindOneCallback(mappedQuery, mappedFields),new ReadDocumentCallback(this.mongoConverter, entityClass, collectionName), collectionName);}@Nullable@Overridepublic T findOne(Query query, Class entityClass, String collectionName) {Assert.notNull(query, "Query must not be null!");Assert.notNull(entityClass, "EntityClass must not be null!");Assert.notNull(collectionName, "CollectionName must not be null!");if (ObjectUtils.isEmpty(query.getSortObject()) && !query.getCollation().isPresent()) {return doFindOne(collectionName, query.getQueryObject(), query.getFieldsObject(), entityClass);} else {query.limit(1);List results = find(query, entityClass, collectionName);return results.isEmpty() ? null : results.get(0);}}

doFindOne是protected修饰的我们无法直接调用,findOne可以调用,我们只需要创建Query对象,将条件传递进去即可,下面是简单的实现:

@Component
public class MongoQLService {@AutowiredMongoTemplate mongoTemplate;public T findById(Object id,Class entityClass,String collectionName) {Query query = new Query();query.addCriteria( new Criteria("_id").is(id));return mongoTemplate.findOne(query, entityClass, collectionName);}
}

关于Query的构建,参考Spring Data MongoDB 基本文档查询


推荐阅读
  • Iamtryingtomakeaclassthatwillreadatextfileofnamesintoanarray,thenreturnthatarra ... [详细]
  • Spring特性实现接口多类的动态调用详解
    本文详细介绍了如何使用Spring特性实现接口多类的动态调用。通过对Spring IoC容器的基础类BeanFactory和ApplicationContext的介绍,以及getBeansOfType方法的应用,解决了在实际工作中遇到的接口及多个实现类的问题。同时,文章还提到了SPI使用的不便之处,并介绍了借助ApplicationContext实现需求的方法。阅读本文,你将了解到Spring特性的实现原理和实际应用方式。 ... [详细]
  • 本文讨论了一个关于cuowu类的问题,作者在使用cuowu类时遇到了错误提示和使用AdjustmentListener的问题。文章提供了16个解决方案,并给出了两个可能导致错误的原因。 ... [详细]
  • 标题: ... [详细]
  • 前景:当UI一个查询条件为多项选择,或录入多个条件的时候,比如查询所有名称里面包含以下动态条件,需要模糊查询里面每一项时比如是这样一个数组条件:newstring[]{兴业银行, ... [详细]
  • 微软头条实习生分享深度学习自学指南
    本文介绍了一位微软头条实习生自学深度学习的经验分享,包括学习资源推荐、重要基础知识的学习要点等。作者强调了学好Python和数学基础的重要性,并提供了一些建议。 ... [详细]
  • 在Android开发中,使用Picasso库可以实现对网络图片的等比例缩放。本文介绍了使用Picasso库进行图片缩放的方法,并提供了具体的代码实现。通过获取图片的宽高,计算目标宽度和高度,并创建新图实现等比例缩放。 ... [详细]
  • 向QTextEdit拖放文件的方法及实现步骤
    本文介绍了在使用QTextEdit时如何实现拖放文件的功能,包括相关的方法和实现步骤。通过重写dragEnterEvent和dropEvent函数,并结合QMimeData和QUrl等类,可以轻松实现向QTextEdit拖放文件的功能。详细的代码实现和说明可以参考本文提供的示例代码。 ... [详细]
  • android listview OnItemClickListener失效原因
    最近在做listview时发现OnItemClickListener失效的问题,经过查找发现是因为button的原因。不仅listitem中存在button会影响OnItemClickListener事件的失效,还会导致单击后listview每个item的背景改变,使得item中的所有有关焦点的事件都失效。本文给出了一个范例来说明这种情况,并提供了解决方法。 ... [详细]
  • Python正则表达式学习记录及常用方法
    本文记录了学习Python正则表达式的过程,介绍了re模块的常用方法re.search,并解释了rawstring的作用。正则表达式是一种方便检查字符串匹配模式的工具,通过本文的学习可以掌握Python中使用正则表达式的基本方法。 ... [详细]
  • 在重复造轮子的情况下用ProxyServlet反向代理来减少工作量
    像不少公司内部不同团队都会自己研发自己工具产品,当各个产品逐渐成熟,到达了一定的发展瓶颈,同时每个产品都有着自己的入口,用户 ... [详细]
  • 本文介绍了一个在线急等问题解决方法,即如何统计数据库中某个字段下的所有数据,并将结果显示在文本框里。作者提到了自己是一个菜鸟,希望能够得到帮助。作者使用的是ACCESS数据库,并且给出了一个例子,希望得到的结果是560。作者还提到自己已经尝试了使用"select sum(字段2) from 表名"的语句,得到的结果是650,但不知道如何得到560。希望能够得到解决方案。 ... [详细]
  • 本文详细介绍了Spring的JdbcTemplate的使用方法,包括执行存储过程、存储函数的call()方法,执行任何SQL语句的execute()方法,单个更新和批量更新的update()和batchUpdate()方法,以及单查和列表查询的query()和queryForXXX()方法。提供了经过测试的API供使用。 ... [详细]
  • springmvc学习笔记(十):控制器业务方法中通过注解实现封装Javabean接收表单提交的数据
    本文介绍了在springmvc学习笔记系列的第十篇中,控制器的业务方法中如何通过注解实现封装Javabean来接收表单提交的数据。同时还讨论了当有多个注册表单且字段完全相同时,如何将其交给同一个控制器处理。 ... [详细]
  • FeatureRequestIsyourfeaturerequestrelatedtoaproblem?Please ... [详细]
author-avatar
浪漫族屋nr
这个家伙很懒,什么也没留下!
PHP1.CN | 中国最专业的PHP中文社区 | DevBox开发工具箱 | json解析格式化 |PHP资讯 | PHP教程 | 数据库技术 | 服务器技术 | 前端开发技术 | PHP框架 | 开发工具 | 在线工具
Copyright © 1998 - 2020 PHP1.CN. All Rights Reserved | 京公网安备 11010802041100号 | 京ICP备19059560号-4 | PHP1.CN 第一PHP社区 版权所有