如何将MongoDB查询转换为Spring Data查询

huangapple go评论83阅读模式
英文:

How to Convert MongoDB Query to Spring Data Query

问题

以下是已经翻译好的内容:

我正在尝试将以下的Mongo查询转换为适用于Spring Data的查询:

db.product.aggregate([
    {$unwind: '$barcodes'},
    {$project: {
        _id: 0, 
        productId: '$_id',
        productTitle: '$title',
        productVariation: '$variation', 
        barcode: '$barcodes'
    }}
])

这是我目前的尝试。它返回了聚合结果,但带有空值:

UnwindOperation unwindOperation = Aggregation.unwind("barcodes");

ProjectionOperation projectStage = Aggregation.project()
    .and("productId").as("_id")
    .and("productTitle").as("title")
    .and("productVariation").as("variation")
    .and("barcodeTitle").as("barcodes.title")
    .and("barcodeValue").as("barcodes.value")
    .and("barcodeType").as("barcodes.type")
    .and("codeStandard").as("barcodes.codeStandard")
    .and("quantity").as("barcodes.quantity")
    .and("status").as("barcodes.status");

SortOperation sortOperation = Aggregation.sort(Sort.by(Sort.Direction.DESC, "title"));

Aggregation agg = Aggregation.newAggregation(unwindOperation, projectStage, sortOperation);

AggregationResults<BarcodeAggregateList> results = mongoTemplate.aggregate(agg, "product", BarcodeAggregateList.class);

返回的示例:

如何将MongoDB查询转换为Spring Data查询

我正在映射到的类(具有getter和setter):

public class BarcodeAggregateList {
   private String productId;
   private String productTitle;
   private String productVariation;
   private String barcodeTitle;
   private String barcodeValue;
   private String barcodeType;
   private String codeStandard;
   private int quantity;
   private String status;
}

数据来自的Product类:

public class Product implements Serializable {
   // ...(省略其他属性)
   private List<Barcode> barcodes;
   private ProductVariation variation;
   // ...(省略其他属性)
}

Barcode类:

public class Barcode {
    private String type;
    private String title;
    private String value;
    private String status;
    private String codeStandard;
    private int quantity;
}

我感谢对此的任何帮助,以及提供帮助我更好理解如何执行这些类型转换的资源。

对于那些尝试解决类似问题的人,我发现以下资源有些许帮助:

英文:

I'm trying to convert the following Mongo query for use with Spring data.

db.product.aggregate([
{$unwind: &#39;$barcodes&#39;},
{$project: {
	_id: 0, 
	productId: &#39;$_id&#39;,
	productTitle: &#39;$title&#39;,
	productVariation: &#39;$variation&#39;, 
	barcode: &#39;$barcodes&#39;
}}])

This is what I've been trying so far. It returns the aggregation, but with null values:

UnwindOperation unwindOperation = Aggregation.unwind(&quot;barcodes&quot;);

ProjectionOperation projectStage = Aggregation.project().and(&quot;productId&quot;).as(&quot;_id&quot;).and(&quot;productTitle&quot;)
  .as(&quot;title&quot;)
  .and(&quot;productVariation&quot;).as(&quot;variation&quot;)
  .and(&quot;barcodeTitle&quot;).as(&quot;barcodes.title&quot;)
  .and(&quot;barcodeValue&quot;).as(&quot;barcodes.value&quot;)
  .and(&quot;barcodeType&quot;).as(&quot;barcodes.type&quot;)
  .and(&quot;codeStandard&quot;).as(&quot;barcodes.codeStandard&quot;)
  .and(&quot;quantity&quot;).as(&quot;barcodes.quantity&quot;)
  .and(&quot;status&quot;).as(&quot;barcodes.status&quot;);

SortOperation sortOperation = Aggregation.sort(Sort.by(Sort.Direction.DESC, &quot;title&quot;));

Aggregation agg = Aggregation.newAggregation(unwindOperation, projectStage, sortOperation);

AggregationResults&lt;BarcodeAggregateList&gt; results = mongoTemplate.aggregate(agg, &quot;product&quot;, BarcodeAggregateList.class);

What it is returning:

如何将MongoDB查询转换为Spring Data查询

The class I am mapping to (has getters/setters):

public class BarcodeAggregateList {
   private String productId;
   private String productTitle;
   private String productVariation;
   private String barcodeTitle;
   private String barcodeValue;
   private String barcodeType;
   private String codeStandard;
   private int quantity;
   private String status;
}

Product class that the data is coming from:

public class Product implements Serializable {
   private static final long serialVersionUID = -998149317494604215L;
   private String id;
   private String title;
   private String description;
   private String SKU;
   private double cost;
   private double retailPrice;
   private String status;
   private LocalDate launchDate;
   private LocalDate discontinueDate;
   private String discontinueReason;
   private String salesChannel;
   private List&lt;Barcode&gt; barcodes;
   private ProductVariation variation;
   private List&lt;Supplier&gt; supplier;
   private Product parentProduct;
   private boolean updateChildren;
   private Label label;
   private int secondaryStockLevel;
   private int primaryStockLevel;
   private Date createdDate;
   private Date modifiedDate;
   private List&lt;Dimension&gt; dimensions;
   private boolean isDeleted = false;
}

Barcode class

public class Barcode {
    private String type;
    private String title;
    private String value;
    private String status;
    private String codeStandard;
    private int quantity;
}

I appreciate any help with this or resources to help me better understand how to perform these types of conversions.

For anyone trying to solve similar issues, I've found the following resources somewhat helpful:

答案1

得分: 1

BarcodeAggregateList类的字段是null,因为在ProjectionOperationand()as()方法中存在一个小问题。正确的语法是

Aggregation.project().and(SOURCE_FIELD).as(TARGET_FIELD)

您写的是and("productId").as("_id"),这是错误的。

您需要将其写成and("_id").as("productId"),因为源字段是_id

完整代码:

UnwindOperation unwindOperation = Aggregation.unwind("barcodes");

ProjectionOperation projectStage = Aggregation.project()
        .and("_id").as("productId")
        .and("title").as("productTitle")
        .and("variation").as("productVariation")
        .and("barcodes.title").as("barcodeTitle")
        .and("barcodes.value").as("barcodeValue")
        .and("barcodes.type").as("barcodeType")
        .and("barcodes.codeStandard").as("codeStandard")
        .and("barcodes.quantity").as("quantity")
        .and("barcodes.status").as("status");

SortOperation sortOperation = Aggregation.sort(Sort.by(Sort.Direction.DESC, "productTitle"));

Aggregation agg = Aggregation.newAggregation(unwindOperation, projectStage, sortOperation);

AggregationResults<BarcodeAggregateList> results = mongoTemplate.aggregate(agg, "product", BarcodeAggregateList.class);
英文:

BarcodeAggregateList class fields are null because there is a minor issue in ProjectionOperation's and() and as() methods. The correct syntax is

Aggregation.project().and(SOURCE_FIELD).as(TARGET_FIELD)

You have written and(&quot;productId&quot;).as(&quot;_id&quot;) , which is wrong

You need to write this as and(&quot;_id&quot;).as(&quot;productId&quot;) , because source field is _id

complete code:

UnwindOperation unwindOperation = Aggregation.unwind(&quot;barcodes&quot;);

ProjectionOperation projectStage = Aggregation.project()
        .and(&quot;_id&quot;).as(&quot;productId&quot;)
        .and(&quot;title&quot;).as(&quot;productTitle&quot;)
        .and(&quot;variation&quot;).as(&quot;productVariation&quot;)
        .and(&quot;barcodes.title&quot;).as(&quot;barcodeTitle&quot;)
        .and(&quot;barcodes.value&quot;).as(&quot;barcodeValue&quot;)
        .and(&quot;barcodes.type&quot;).as(&quot;barcodeType&quot;)
        .and(&quot;barcodes.codeStandard&quot;).as(&quot;codeStandard&quot;)
        .and(&quot;barcodes.quantity&quot;).as(&quot;quantity&quot;)
        .and(&quot;barcodes.status&quot;).as(&quot;status&quot;);

SortOperation sortOperation = Aggregation.sort(Sort.by(Sort.Direction.DESC, &quot;productTitle&quot;));

Aggregation agg = Aggregation.newAggregation(unwindOperation, projectStage, sortOperation);

AggregationResults&lt;BarcodeAggregateList&gt; results = mongoTemplate.aggregate(agg, &quot;product&quot;, BarcodeAggregateList.class);

huangapple
  • 本文由 发表于 2020年10月22日 01:16:29
  • 转载请务必保留本文链接:https://go.coder-hub.com/64468560.html
匿名

发表评论

匿名网友

:?: :razz: :sad: :evil: :!: :smile: :oops: :grin: :eek: :shock: :???: :cool: :lol: :mad: :twisted: :roll: :wink: :idea: :arrow: :neutral: :cry: :mrgreen:

确定