我正在尝试模拟以下MongoDB shellcode:
db.collection.find( { $and: [ { $or: [ { document: { field: "X" } }, { field: "X" } ] }, { _id: ObjectId("X") } ] } );
这是我尝试过的(使用新的MongoDB-C-Driver ):
bson_init(&query);
bson_append_document_begin(&query, "$and", 4, &and);
bson_append_oid(&and, "_id", 3, oid);
bson_append_document_begin(&and, "$or", 3, &or);
bson_append_utf8(&query, "field", 5, "X", 1);
bson_append_document_end(&and, &or);
bson_append_document_begin(&and, "$or", 3, &or);
bson_append_utf8(&query, "document.field", 14, "X", 1);
bson_append_document_end(&and, &or);
bson_append_document_end(&query, &and);
collection = mongoc_client_get_collection (client, "db", "collection");
cursor = mongoc_collection_find(collection, MONGOC_QUERY_NONE, 0, 1, 0, &query, NULL, NULL);
if(mongoc_cursor_next(cursor, &doc)){
printf("> Field found\r\n");
}
提前谢谢。
最好的问候。
答案 0 :(得分:2)
用于创建嵌套文档的libbson命令式API有点棘手,不幸的是,您偶然发现了一个容易陷入的陷阱。使用bson_append_document_begin或bson_append_array_begin打开子文档后,在执行相应的_end()调用之前,不得写入该子文档。在这种情况下,您在"或"中有append_utf8()调用。写入"查询"。
的文件为了更容易理解bson组合,请考虑使用BCON api,它提供了更具说明性的语法,并且开销最小:
BCON_APPEND(&other_query,
"$and", "{",
"_id", BCON_OID(&oid),
"$or", "{",
"field", "X",
"}",
"$or", "{",
"document.field", "X",
"}",
"}");
使用bcon api也可能会给你一个提示,说明你并没有完全复制你的想法。
要生成你在shell中看到的bson:
BCON_APPEND(&correct_query,
"$and",
"[",
"{", "$or", "[",
"{", "document", "{", "field", "X", "}", "}",
"{", "field", "X", "}",
"]", "}",
"{", "_id", BCON_OID(&oid), "}",
"]"
);
您还可以使用bson_as_json()函数将bson文档字符串化为json,这样可以更容易地查看您构建的对象
iterative: { "$and" : { "_id" : { "$oid" : "53ff00f4342d8c1c712b4841" }, "$or" : { "field" : "X" }, "$or" : { "document.field" : "X" } } }
bcon: { "$and" : { "_id" : { "$oid" : "53ff00f4342d8c1c712b4841" }, "$or" : { "field" : "X" }, "$or" : { "document.field" : "X" } } }
correct: { "$and" : [ { "$or" : [ { "document" : { "field" : "X" } }, { "field" : "X" } ] }, { "_id" : { "$oid" : "53ff00f4342d8c1c712b4841" } } ] }