$ поиск в массиве объектов с таблицей

#node.js #mongodb #aggregation-framework #lookup

#node.js #mongodb #структура агрегации #поиск

Вопрос:

У меня есть объект данных, который содержит массив. И у меня есть таблица поставщиков.

  1. если идентификатор массива должен быть равен идентификатору таблицы поставщика Id == id
  2. если идентификатор повторяется, считайте повторное количество как membersCounts else membersCounts = 0
  3. Добавьте объект membersCounts с данными

объект данных

 const data = {
  Milk: [
    {
      Id: 1,
      name: 'a'
    },
    {
      Id: 2,
      name: 'b'
    },
    {
      Id: 3,
      name: 'c'
    },
    {
      Id: 4,
      name: 'd'
    },
    {
      Id: 52,
      name: 'e'
    }
  ],
  Grocery: [
    {
      Id: 8,
      name: '2a'
    },
    {
      Id: 22,
      name: '2b'
    },
    {
      Id: 32,
      name: '2c'
    },
    {
      Id: 42,
      name: '2d'
    }
  ]
}
 

таблица поставщиков

 const providers = [
  {
    id: 1,
    status: 'active'
  },
  {
    id: 1,
    status: 'active'
  },
  {
    id: 1,
    status: 'active'
  },
  {
    id: 1,
    status: 'active'
  },
  {
    id: 4,
    status: 'active'
  },
  {
    id: 2,
    status: 'active'
  },
  {
    id: 3,
    status: 'active'
  },
  {
    id: 3,
    status: 'active'
  },
  {
    id: 52,
    status: 'active'
  },
  {
    id: 1,
    status: 'active'
  }
]

 

здесь код javascript

этот код работает хорошо, но я хочу выполнить это с помощью запросов mongodb. Так что производительность хорошая. Это можно сделать с помощью запроса mongodb. Мне нужно скрыть код javascript в запросе mongodb.

 getMembersWithVendors(data, providers) {
    for (var key in data) {
      var arr = data[key]
      arr.forEach((element) => {
        element.memberCounts = 0
        element.new = true
        providers.map((el) => {
          if (element._id == el.vendorId) {
            (element.memberCounts = element.memberCounts   1),
              (element.new = false)
          }
        })
      })
    }
    return data
  }
 

вывод

 { Milk:
   [ { Id: 1, name: 'a', memberCounts: 5 },   
     { Id: 2, name: 'b', memberCounts: 1 },   
     { Id: 3, name: 'c', memberCounts: 2 },   
     { Id: 4, name: 'd', memberCounts: 1 },   
     { Id: 52, name: 'e', memberCounts: 1 } ],
  Grocery:
   [ { Id: 8, name: '2a', memberCounts: 0 },  
     { Id: 22, name: '2b', memberCounts: 0 },
     { Id: 32, name: '2c', memberCounts: 0 },
     { Id: 42, name: '2d', memberCounts: 0 } ] }
 

Спасибо!!

Комментарии:

1. сообщение о том, как данные хранятся в БД

2. Большой файл json

3. опубликовать модель и немного данных в json

Ответ №1:

этот код работает хорошо, но я хочу выполнить это с помощью запросов mongodb. Так что производительность хорошая

Это не очень хорошая идея выполнять все операции в запросе, это может вызвать проблемы с производительностью, потому что ваши входные данные такие большие, но вы можете улучшить некоторые вещи,

  • $group по запросу id и получению count это вернет уникальные идентификаторы и их общее количество
 let providers = await db.providers.aggregate([
  {
    $group: {
      _id: "$id",
      count: { $sum: 1 }
    }
  }
]);
 
  • цикл итерации массива объекта
  • поиск у поставщиков на основе идентификатора
  • получить количество из отфильтрованного документа
 for (let key in data) {
    data[key].forEach(e => {
        let p = providers.find(p => p._id === e.Id);
        e.memberCounts = p ? p.count : 0;
    })
}

console.log(data);
 

Игровая площадка Repl

Комментарии:

1. Grocey и Milk — это динамические поля.

2. хорошо, я постараюсь, если это возможно, обновить вас в ближайшее время.

3. данные — это не таблица, это мой вводимый объект

4. о, это странно, вам не нужно выполнять все операции в запросе, вы можете выполнить половину части на стороне nodejs, позвольте мне проверить

5. 1. данные — это объект 2. поставщики — это извлеченные записи из таблицы поставщиков.