javascript
Spring boot mongodb
mongodb語法
?
spring boot mongodb
引入
pom依賴
<dependencies><dependency><groupId>org.springframework.boot</groupId><artifactId>spring-boot-starter-data-mongodb</artifactId></dependency></dependencies>application配置
spring: mongodb:uri: mongodb://name:password@localhost:27017/test?
訪問數據
MongoRepository
public interface PersonMongoDBRepository extends MongoRepository<Person,String> {Person findByName(String name);@Query("{'age':?0}")List<Person> withQueryFindByAge(Integer age);}@Service class AA { @Autowired PersonMongoDBRepository personMongoDBRepository ; }MongoRepository提供了通過id 操作文檔的能力。
MongoTemplate
@Autowiredpublic MongoTemplate mongoTemplate;MongoTemplate提供了自定義查詢的能力。
<T> List<T> find(Query query, Class<T> entityClass); <T> List<T> find(Query query, Class<T> entityClass, String collectionName);Query
1、org.springframework.data.mongodb.core.query
構造函數
Query (Criteria criteria)
接受的參數是org.springframework.data.mongodb.core.query.Criteria
Criteria是標準查詢的接口,可以引用靜態的Criteria.where的把多個條件組合在一起,就可以輕松地將多個方法標準和查詢連接起來,方便我們操作查詢語句
2、BasicQuery
子類 org.springframework.data.mongodb.core.query.BasicQuery 提供了更底層的查詢能力,即JSON格式的封裝。
BasicQuery(DBObject queryObject) BasicQuery(DBObject queryObject, DBObject fieldsObject) BasicQuery(java.lang.String query) BasicQuery(java.lang.String query, java.lang.String fields)?
3、Document
通過org.bson.Document直接操作BSON定義查詢,需要自己進行類型轉換。
//自定義查詢 ,JSON格式。Document filter = builderFilter(request.getFilter());if (filterExtension != null) {filter = filterExtension.apply(filter);}//獲取CollectionString collectionName = mongoTemplate.getCollectionName(AppData.class);MongoCollection collection = mongoTemplate.getCollection(collectionName);long count = collection.countDocuments(filter);FindIterable<Document> found = collection.find(filter);//設置排序Document sort = buildSort(request.getSort());found.sort(sort);//設置 projectionDocument projection = buildProjection(request);if (projection != null) {found.projection(projection);}if (request.getFrom() > 0) {found.skip(request.getFrom());}if (request.getSize() > 0) {found.limit(request.getSize());}List<AppData> list = new ArrayList<>();//進行類型轉換。使用MongoConverterfound.forEach((Block<? super Document>) e -> {AppData appData = mongoConverter.read(AppData.class, e);list.add(appData);});PagedResult<AppData> result = new PagedResult<>(count, list);Update
update可以更新數據,修改某個屬性,可以是簡單類型,也可以是自定義類型
//更新版本int newVersion = appData.getVersion() + 1;Update update = Update.update(AppData.PATH_VERSION, newVersion);//更新檢查狀態update.set(PATH_QUALITY,appData.getSMD().getQuality());mongoTemplate.updateMulti(query,update,AppData.class);?
實體
/*** 應用數據日志*/ @Data @Document(collection = "AppDataLog") public class AppDataLog {@Idprivate ObjectId id;/*** 資源Id*/@Field("ResourceId")private String resourceId;/*** 版本*/@Field("Version")private int version;/*** 服務名稱*/@Field("Service")private String service ="";/*** 是否已檢查*/@Field("Checked")private boolean checked;/*** 檢查時間*/@Field("CheckedTime")private Date checkedTime = null;/*** 檢查結果*/@Field("CheckedStatus")private int checkedStatus = 0;public QualityStatus getCheckedStatus(){return QualityStatus.valueOf(this.checkedStatus);}public void setCheckedStatus(QualityStatus status){this.checkedStatus = status.getValue();};}?
注解
spring-data-mongodb中的實體映射是通過MongoMappingConverter這個類實現的。它可以通過注釋把java類轉換為mongodb的文檔。
它有以下幾種注釋:
- @Id
?文檔的唯一標識,在mongodb中為ObjectId,它是唯一的,通過時間戳+機器標識+進程ID+自增計數器(確保同一秒內產生的Id不會沖突)構成。
- @Document
把一個java類聲明為mongodb的文檔,可以通過collection參數指定這個類對應的文檔。
@DBRef 聲明類似于關系數據庫的關聯關系。ps:暫不支持級聯的保存功能,當你在本實例中修改了DERef對象里面的值時,單獨保存本實例并不能保存DERef引用的對象,它要另外保存,如下面例子的Person和Account。
- @Field
代表一個字段,可以不加,不加的話默認以參數名為列名。參數名為 定義的 Java類字段的名稱,不是get**,set**等的標準屬性名。
例如:private int version //屬性對應的mongodb名稱為version,而不是Version。
- @Indexed?
聲明該字段需要索引,建索引可以大大的提高查詢效率。
- @CompoundIndex
復合索引的聲明,建復合索引可以有效地提高多字段的查詢效率。
- @GeoSpatialIndexed?
聲明該字段為地理信息的索引。
- @Transient??
映射忽略的字段,該字段不會保存到mongodb。
- @PersistenceConstructor?
聲明構造函數,作用是把從數據庫取出的數據實例化為對象。該構造函數傳入的值為從DBObject中取出的數據。
問題解決
去掉_class字段
方法:為MongoTypeMapper指定一個空的TypeMapper。
@BeanMappingMongoConverter mappingMongoConverter(MongoDbFactory factory, MongoMappingContext context,MongoCustomConversions conversions) {DbRefResolver dbRefResolver = new DefaultDbRefResolver(factory);MappingMongoConverter mappingConverter = new MappingMongoConverter(dbRefResolver, context);mappingConverter.setCustomConversions(conversions);mappingConverter.setTypeMapper(new DefaultMongoTypeMapper(null) );return mappingConverter;}枚舉Enum與int 的轉換
mongodb默認不支持int與Enum的轉換,spring提供的converts包含了,但是mongodb在判斷時沒有使用。
自定義converter(不可用)
@Beanpublic MongoCustomConversions customConversions() {List<Converter<?,?>> converters = new ArrayList<Converter<?,?>>();converters.add( new IntegerToEnumConvert ());converters.add( new EnumToIntegerConvert());return new MongoCustomConversions(converters);}問題:
1、IntegerToEnum 會覆蓋mongodb中的Int to Int,導致異常。
2、EnumToInt ,不會被使用,內部會找到自帶的EnumToIntFactory,自定義的只會作為觸發,讓代碼去找EnumToIntFactory,如果不加入,代碼不會去找?EnumToIntFactory 。
枚舉只作為訪問方法結果和參數類型:
public enum QualityStatus {//待檢查Pending(0,"待檢查"),//合法Available(1,"合法"),//異常Abnormal(2,"異常");private int value ;private String description;private QualityStatus (int value,String description){this.value = value;this.description = description;}public int getValue(){return value;}public String getDescription(){return description;}public static QualityStatus valueOf(int value){switch (value){case 0:return Pending;case 1:return Available;case 2:return Abnormal;default:throw new IllegalArgumentException(Integer.toString(value));}}}GridFSBucket 不存在
@Configuration public class MongodbConfig {@Autowiredprivate MongoDbFactory mongoDbFactory;@Beanpublic GridFSBucket getGridFSBucket(){MongoDatabase db = mongoDbFactory.getDb();return GridFSBuckets.create(db);} }去掉其他數據庫
springboot啟動報錯:Failed to configure a DataSource: 'url' attribute is not specified and no embedded
如果有其他數據庫,但是不使用,可以排除掉。
@EnableAutoConfiguration(exclude = DataSourceAutoConfiguration.class) public class AssetsBizAppliction { }Projection
1、Projection cannot have a mix of inclusion and exclusion.
只有_id可以混合 包含與過濾
CodecConfigurationException
org.bson.codecs.configuration.CodecConfigurationException: Can't find a codec for class XXX;
??????? @Autowired
?????? MongoConverter mongoConverter;
?
????? //進行類型轉換。使用MongoConverter
??????? found.forEach((Block<? super Document>) e -> {
??????????? AppData appData = mongoConverter.read(AppData.class, e);
??????????? list.add(appData);
??????? });
總結
以上是生活随笔為你收集整理的Spring boot mongodb的全部內容,希望文章能夠幫你解決所遇到的問題。
- 上一篇: Spring @Conditional
- 下一篇: Spring @Import源码解析