Сортировка массива поддокументов в MongoDB (без использования агрегации) - PullRequest
0 голосов
/ 14 января 2020

Я пытаюсь отсортировать в пн go, используя поле, принадлежащее массиву объекта. Проблема в том, что я не могу использовать агрегацию, и схема не может быть изменена из-за внешних ограничений.

это пример моих документов

[{
  "name": "product 1",
  "tags": [{
    "tag": "category",
    "value": "shoes"
  },{
    "tag": "gender",
    "value": "man"
  }]
},
{
  "name": "product 2",
  "tags": [{
    "tag": "category",
    "value": "bags"
  },{
    "tag": "season",
    "value": "fall-winter"
  }]
},
{
  "name": "product 3",
  "tags": [{
    "tag": "category",
    "value": "clothing"
  },{
    "tag": "gender",
    "value": "woman"
  }]
}]

давайте предположим, что я хочу отсортировать их по возрастанию, используя категория тега, поэтому у меня должны быть документы, отсортированные таким образом: «продукт 2», «продукт 3», «продукт 1»

Есть ли способ сделать это без агрегации и без изменения схемы?

Ответы [ 2 ]

1 голос
/ 15 января 2020

... я не могу использовать агрегацию ...

Следующий код выполнит сортировку, если поддокумент "category" является first элемент массива tags.

db.product_cats.find().toArray().sort( (a, b) => {
    return a.tags[0].value > b.tags[0].value;
});

Если поддокумент "category" появляется в любом индексе массива, следующее будет выполнять сортировку.

db.product_cats.find().toArray().sort( (a, b) => {
    let ixa = a.tags.findIndex(e => e.tag == "category");
    let ixb = b.tags.findIndex(e => e.tag == "category"); 
    return a.tags[ixa].value > b.tags[ixb].value;
});

Если вложенный документ "category" отсутствует для некоторых документов, тогда будет выполнена сортировка:

db.product_cats.find().toArray().sort( (a, b) => {

    let ixa = a.tags.findIndex(e => e.tag == "category");
    let ixb = b.tags.findIndex(e => e.tag == "category");

    if ( ixa == -1 ) { a.tags = [ ]; a.tags[ ixa] = { value: "" } };
    if ( ixb == -1 ) { b.tags = [ ]; b.tags[ ixa] = { value: "" } };

    return a.tags[ixa].value > b.tags[ixb].value;
});
0 голосов
/ 14 января 2020

Ваши критерии сортировки должны быть следующими:

db.sorter.find().sort({"tags.value": 1})

Результат

{ "_id" : ObjectId("5e1dd93f4a030a105864baaa"), "name" : "product 2", "tags" : [ { "tag" : "category", "value" : "bags" }, { "tag" : "season", "value" : "fall-winter" } ] }
{ "_id" : ObjectId("5e1dd93f4a030a105864baab"), "name" : "product 3", "tags" : [ { "tag" : "category", "value" : "clothing" }, { "tag" : "gender", "value" : "woman" } ] }
{ "_id" : ObjectId("5e1dd93f4a030a105864baa9"), "name" : "product 1", "tags" : [ { "tag" : "category", "value" : "shoes" }, { "tag" : "gender", "value" : "man" } ] }
Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...