admin管理员组文章数量:1401401
I’m encountering some issues when querying nested MongoDB documents using spring-boot-starter-data-mongodb.
After checking, I can confirm that the valid documents are present in MongoDB. Here's an example:
[
{
"_id": {"$oid": "67e0261f4b8ed21de1e2afb5"},
"_class": "com.ucapital.adv.documents.BannerDoc",
"balance": 52.94,
"costs": {
"costPerClick": 1.31,
"costPerImpression": 62.48
},
"createdAt": {"$date": "2025-03-23T15:17:51.078Z"},
"description": "Neque distinctio velit vel sed sed molestias accusamus.",
"enabled": true,
"imageUrl": ".jpg",
"link": "www.lesa-heaney",
"metrics": {
"clicks": 6,
"impressions": 173
},
"priority": 3,
"title": "aspernatur accusamus et",
"updatedAt": {"$date": "2025-03-23T15:17:51.078Z"},
"validFrom": {"$date": "2025-02-02T15:17:51.023Z"},
"validTo": {"$date": "2025-06-11T15:17:51.023Z"}
}
]
First approach with Criteria:
public static Criteria isNotExpired() {
Date currentDate = new Date();
return where("validFrom").lte(currentDate)
.andOperator(where("validTo").gte(currentDate));
}
public static Criteria isEnabled() {
return where("enabled").is(true);
}
public static Criteria hasBudget() {
return new Criteria().orOperator(
where("balance").gte("$costs.costPerClick"),
where("balance").gte("$costs.costPerImpression")
);
}
List<Criteria> criteriaList = List.of(isEnabled(), isNotExpired(), hasBudget());
Query query = Query.query(new Criteria().andOperator(criteriaList.toArray(new Criteria[criteriaList.size()])));
System.out.println(query.getQueryObject()); // Log the query
long total = mongoTemplate.count(query, BannerDoc.class);
The number of documents retrieved is 0. The issue is with the hasBudget Criteria because when I remove it, the objects are retrieved correctly.
Fallback approach using aggregations:
Aggregation aggregation = Aggregation.newAggregation(
Aggregation.match(Criteria.where("enabled").is(true)),
Aggregation.project()
.andExpression("balance >= costs.costPerClick && balance >= costs.costPerImpression")
.as("hasBudget"),
Aggregation.match(Criteria.where("hasBudget").is(true))
);
List<BannerDoc> banners = mongoTemplate.aggregate(aggregation, "banners", BannerDoc.class).getMappedResults();
System.out.println(banners);
In this case, the elements are retrieved, but all the attributes of the object are null.
Does anyone know what’s wrong with my hasBudget Criteria, or can anyone help me resolve the aggregation fallback approach?
Thanks!
I’m encountering some issues when querying nested MongoDB documents using spring-boot-starter-data-mongodb.
After checking, I can confirm that the valid documents are present in MongoDB. Here's an example:
[
{
"_id": {"$oid": "67e0261f4b8ed21de1e2afb5"},
"_class": "com.ucapital.adv.documents.BannerDoc",
"balance": 52.94,
"costs": {
"costPerClick": 1.31,
"costPerImpression": 62.48
},
"createdAt": {"$date": "2025-03-23T15:17:51.078Z"},
"description": "Neque distinctio velit vel sed sed molestias accusamus.",
"enabled": true,
"imageUrl": "http://lorempixel/1024/768/city/image.jpg",
"link": "www.lesa-heaney.",
"metrics": {
"clicks": 6,
"impressions": 173
},
"priority": 3,
"title": "aspernatur accusamus et",
"updatedAt": {"$date": "2025-03-23T15:17:51.078Z"},
"validFrom": {"$date": "2025-02-02T15:17:51.023Z"},
"validTo": {"$date": "2025-06-11T15:17:51.023Z"}
}
]
First approach with Criteria:
public static Criteria isNotExpired() {
Date currentDate = new Date();
return where("validFrom").lte(currentDate)
.andOperator(where("validTo").gte(currentDate));
}
public static Criteria isEnabled() {
return where("enabled").is(true);
}
public static Criteria hasBudget() {
return new Criteria().orOperator(
where("balance").gte("$costs.costPerClick"),
where("balance").gte("$costs.costPerImpression")
);
}
List<Criteria> criteriaList = List.of(isEnabled(), isNotExpired(), hasBudget());
Query query = Query.query(new Criteria().andOperator(criteriaList.toArray(new Criteria[criteriaList.size()])));
System.out.println(query.getQueryObject()); // Log the query
long total = mongoTemplate.count(query, BannerDoc.class);
The number of documents retrieved is 0. The issue is with the hasBudget Criteria because when I remove it, the objects are retrieved correctly.
Fallback approach using aggregations:
Aggregation aggregation = Aggregation.newAggregation(
Aggregation.match(Criteria.where("enabled").is(true)),
Aggregation.project()
.andExpression("balance >= costs.costPerClick && balance >= costs.costPerImpression")
.as("hasBudget"),
Aggregation.match(Criteria.where("hasBudget").is(true))
);
List<BannerDoc> banners = mongoTemplate.aggregate(aggregation, "banners", BannerDoc.class).getMappedResults();
System.out.println(banners);
In this case, the elements are retrieved, but all the attributes of the object are null.
Does anyone know what’s wrong with my hasBudget Criteria, or can anyone help me resolve the aggregation fallback approach?
Thanks!
Share Improve this question asked Mar 23 at 15:38 user3187960user3187960 3452 silver badges17 bronze badges 1- 1 You need $expr to compare fields from the same document – user20042973 Commented Mar 23 at 17:03
1 Answer
Reset to default 0If anyone is interested, I resolved the issue this way:
public static Criteria hasBudget() {
MongoExpression expr1 = ComparisonOperators.Gte
.valueOf("$balance")
.greaterThanEqualToValue(ConvertOperators.ToDouble.toDouble("$costs.costPerClick"));
MongoExpression expr2 = ComparisonOperators.Gte
.valueOf("$balance")
.greaterThanEqualToValue(ConvertOperators.ToDouble.toDouble("$costs.costPerImpression"));
return Criteria.where("$or").is(List.of(
Criteria.expr(expr1),
Criteria.expr(expr2)
));
}
本文标签: Issues with MongoDB Querying Nested Documents Using springbootstarterdatamongodbStack Overflow
版权声明:本文标题:Issues with MongoDB Querying Nested Documents Using spring-boot-starter-data-mongodb - Stack Overflow 内容由网友自发贡献,该文观点仅代表作者本人, 转载请联系作者并注明出处:http://www.betaflare.com/web/1744280948a2598648.html, 本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如发现本站有涉嫌抄袭侵权/违法违规的内容,一经查实,本站将立刻删除。
发表评论