MongoDB: сложный запрос с массивом ввода - PullRequest
0 голосов
/ 12 ноября 2018

Я застрял в поиске решения для следующего запроса.

1) пользователь может выбрать много категорий и подкатегорий.

2) пользователь может видеть всех других пользователей, каквыбрал те же категории и подкатегории в пределах определенного радиуса.

Вот Schema пользователя

const userSchema = new Schema(
  {
    image: { type: String, default: 'NA' },
    firstName: { type: String, default: 'first name' },
    lastName: { type: String, default: 'last name' },
    email: { type: String, lowercase: true, unique: true, trim: true },
    password: { type: String, min: 6 },
    gender: { type: String, emun: ['male','female','other'] },
    about: { type: String, default: 'about you' },
    address: {
      zipCode: { type: Number, default: 000000 },
      place: { type: String, default: 'place' },
      street: { type: String, default: 'street' },
      country: { type: String, default: 'Country' },
      location: {
        type: { type: String, default:'Point'},
        coordinates: { type:[Number], index:'2dsphere', default:[0,0] }
      }
    },
    interests: [
      {
        _id : false,
        category: {
          id: { type: Schema.Types.ObjectId, ref: 'Category' },
          name: { type: String }
        },
        subCategory: [
          {
            _id : false,
            id: { type: Schema.Types.ObjectId, ref: 'Subcategory' },
            name: { type: String }
          }
        ]
      }
    ]
  }
);

В моем контроллере вот что я пробовал

homeData: async (req, res, next) => {
    const limit = Number(req.params.limit);
    const { latitude, longitude, minDistance, maxDistance } = getUserCurrentLocation(req);

    const usersWithSameInterests = await User.aggregate([
     {
       "$geoNear": {
          "near": {
            "type": "Point",
            "coordinates": [longitude, latitude]
          },
          "distanceField": "distance",
          "minDistance": minDistance,
          "maxDistance": maxDistance,
          "spherical": true,
          "query": { "location.type": "Point" }
        }
      },
      {
        "$match": { "interests": { "$elemMatch": {name: 'Sports'} }} // hard coded for testing
      },
      { "$sort": { "distance": 1 } },
      { "$limit" : limit },
      {
        "$project": {
          "_id": 1,
          "image": 1,
          "firstName":1,
          "lastName":1,
          "distance": 1,
          "createdAt": 1
        }
      }
    ]);

    return respondSuccess(res, null, {
      newNotification: false,
      usersWithSameInterests: usersWithSameInterests
    });
  },

Ответ, который я получаю:

{
  "success": true,
  "message": "query was successfull",
  "data": {
      "newNotification": false,
      "usersWithSameInterests": []
  }
}

Примеры категорий и подкатегорий Категория: Спорт Подкатегории: Крикет, Футбол, Хоккей, Теннис

Категория: Изучение языков Подкатегории: английский, немецкий,Испанский, хинди

с нетерпением жду столь необходимой помощи.

спасибо.

1 Ответ

0 голосов
/ 12 ноября 2018

Похоже, у вас есть несколько несовпадающих столбцов.

В конвейере $geonear строка "query": { "location.type": "Point" } должна быть: 'query': {'address.location.type': 'Point'}.

И на $matchконвейер, линия { "interests": { "$elemMatch": {name: 'Sports'} } должна быть 'interests': { '$elemMatch:' {'category.name': 'Sports'} }

Редактировать :

Чтобы сопоставить несколько интересов в поле категории и подкатегории, вы можете использовать $inоператор на конвейере $match.Например:

{
  'interests.category.name': { $in: ['Sports'] },
  'interests.subCategory.name': {$in: ['Soccer']}
}

Вернется любой, у кого в названии категории есть Спорт и Футбол в названии подкатегории.

Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...