像 mongoose 一样简单加入 SQL
simple join SQL like with mongoose
我有文档和参数,我正在尝试对 select 与参数匹配的文档构建查询。
document {
_id : ...,
status : ...,
type : ...,
...
}
parameter {
_id : ...,
parameter : ...,
status : ...,
type : ...,
}
我确实认为 SQL 它杀了我。
我该怎么做:
select document.* from document,parameter
where document.type = parameter.type and document.status = parameter.status
and parameter.parameter="example"
我可能不认为这是正确的方法 ex :我不在两个对象之间使用任何引用 link,我可能但它会是 N 到 N link 并且我不觉得容易维护,因为参数或文档会更新。
我想出了这个有问题的东西,但我仍然愿意接受建议。
parameter.find({parameter :"example"}, function(err, parameters){
var parameters_status;
var parameters_type;
if (err) {
// do error handling
return;
}
parameters_status= parameters.map(function (parameters) { return parameters.status; });
parameters_type= parameters.map(function (parameters) { return parameters.type; });
document.find({type: {$in: parameters_type},status : {$in: parameters_status} }, function (err, documents) {
if (err) {
// do error handling
return;
}
console.log(documents);
// do something with the documents
});
});
请尝试以下查询:
db.document.aggregate([
{
$lookup:
{
from: "parameter",
let: { type: "$type", status: "$status" },
pipeline: [
{ $match:
{ $expr:
{ $and:
[
{ $eq: [ "$parameter", "example" ] },
{ $eq: [ "$type", "$$type" ] },
{ $eq: [ "$status", "$$status" ] }
]
}
}
}
],
as: "documentParameterJoined"
}
}
])
文档收集数据:
/* 1 */
{
"_id" : ObjectId("5e160929627ef782360f69aa"),
"status" : "mystatus",
"type" : "whattype"
}
/* 2 */
{
"_id" : ObjectId("5e160931627ef782360f6abb"),
"status" : "mystatus1",
"type" : "whattype1"
}
参数采集数据:
/* 1 */
{
"_id" : ObjectId("5e16095f627ef782360f6e1d"),
"parameter" : "example",
"status" : "mystatus",
"type" : "whattype"
}
/* 2 */
{
"_id" : ObjectId("5e16097e627ef782360f70b5"),
"parameter" : "example",
"status" : "mystatus1",
"type" : "whattype1"
}
/* 3 */
{
"_id" : ObjectId("5e160985627ef782360f7152"),
"parameter" : "example1",
"status" : "mystatus",
"type" : "whatType"
}
/* 4 */
{
"_id" : ObjectId("5e160a39627ef782360f8027"),
"parameter" : "example",
"status" : "mystatus1",
"type" : "whatType"
}
/* 5 */
{
"_id" : ObjectId("5e160a42627ef782360f80ec"),
"parameter" : "example",
"status" : "mystatus",
"type" : "whatType1"
}
结果:
// You don't see docs 3 to 5 as they don't match any filter criteria.
/* 1 */
{
"_id" : ObjectId("5e160929627ef782360f69aa"),
"status" : "mystatus",
"type" : "whattype",
"documentParameterJoined" : [
{
"_id" : ObjectId("5e16095f627ef782360f6e1d"),
"parameter" : "example",
"status" : "mystatus",
"type" : "whattype"
}
]
}
/* 2 */
{
"_id" : ObjectId("5e160931627ef782360f6abb"),
"status" : "mystatus1",
"type" : "whattype1",
"documentParameterJoined" : [
{
"_id" : ObjectId("5e16097e627ef782360f70b5"),
"parameter" : "example",
"status" : "mystatus1",
"type" : "whattype1"
}
]
}
您不需要进行两次数据库调用,您可以使用 $lookup
(mongoDB 固有的)和表达式来实现所需的。您也可以使用 mongoose populate
尝试类似的方法(这是 mongoDB $lookup
的一种包装)
参考: $lookup , mongoose-populate
我有文档和参数,我正在尝试对 select 与参数匹配的文档构建查询。
document {
_id : ...,
status : ...,
type : ...,
...
}
parameter {
_id : ...,
parameter : ...,
status : ...,
type : ...,
}
我确实认为 SQL 它杀了我。 我该怎么做:
select document.* from document,parameter
where document.type = parameter.type and document.status = parameter.status
and parameter.parameter="example"
我可能不认为这是正确的方法 ex :我不在两个对象之间使用任何引用 link,我可能但它会是 N 到 N link 并且我不觉得容易维护,因为参数或文档会更新。
我想出了这个有问题的东西,但我仍然愿意接受建议。
parameter.find({parameter :"example"}, function(err, parameters){
var parameters_status;
var parameters_type;
if (err) {
// do error handling
return;
}
parameters_status= parameters.map(function (parameters) { return parameters.status; });
parameters_type= parameters.map(function (parameters) { return parameters.type; });
document.find({type: {$in: parameters_type},status : {$in: parameters_status} }, function (err, documents) {
if (err) {
// do error handling
return;
}
console.log(documents);
// do something with the documents
});
});
请尝试以下查询:
db.document.aggregate([
{
$lookup:
{
from: "parameter",
let: { type: "$type", status: "$status" },
pipeline: [
{ $match:
{ $expr:
{ $and:
[
{ $eq: [ "$parameter", "example" ] },
{ $eq: [ "$type", "$$type" ] },
{ $eq: [ "$status", "$$status" ] }
]
}
}
}
],
as: "documentParameterJoined"
}
}
])
文档收集数据:
/* 1 */
{
"_id" : ObjectId("5e160929627ef782360f69aa"),
"status" : "mystatus",
"type" : "whattype"
}
/* 2 */
{
"_id" : ObjectId("5e160931627ef782360f6abb"),
"status" : "mystatus1",
"type" : "whattype1"
}
参数采集数据:
/* 1 */
{
"_id" : ObjectId("5e16095f627ef782360f6e1d"),
"parameter" : "example",
"status" : "mystatus",
"type" : "whattype"
}
/* 2 */
{
"_id" : ObjectId("5e16097e627ef782360f70b5"),
"parameter" : "example",
"status" : "mystatus1",
"type" : "whattype1"
}
/* 3 */
{
"_id" : ObjectId("5e160985627ef782360f7152"),
"parameter" : "example1",
"status" : "mystatus",
"type" : "whatType"
}
/* 4 */
{
"_id" : ObjectId("5e160a39627ef782360f8027"),
"parameter" : "example",
"status" : "mystatus1",
"type" : "whatType"
}
/* 5 */
{
"_id" : ObjectId("5e160a42627ef782360f80ec"),
"parameter" : "example",
"status" : "mystatus",
"type" : "whatType1"
}
结果:
// You don't see docs 3 to 5 as they don't match any filter criteria.
/* 1 */
{
"_id" : ObjectId("5e160929627ef782360f69aa"),
"status" : "mystatus",
"type" : "whattype",
"documentParameterJoined" : [
{
"_id" : ObjectId("5e16095f627ef782360f6e1d"),
"parameter" : "example",
"status" : "mystatus",
"type" : "whattype"
}
]
}
/* 2 */
{
"_id" : ObjectId("5e160931627ef782360f6abb"),
"status" : "mystatus1",
"type" : "whattype1",
"documentParameterJoined" : [
{
"_id" : ObjectId("5e16097e627ef782360f70b5"),
"parameter" : "example",
"status" : "mystatus1",
"type" : "whattype1"
}
]
}
您不需要进行两次数据库调用,您可以使用 $lookup
(mongoDB 固有的)和表达式来实现所需的。您也可以使用 mongoose populate
尝试类似的方法(这是 mongoDB $lookup
的一种包装)
参考: $lookup , mongoose-populate