通过Mongoose中的一个关键词搜索名字和电子邮件

时间:2017-03-15 17:58:51

标签: mongodb search text

下面你可以找到我的代码,我尝试用一​​个关键词搜索Mongoose中的字段(名字,姓氏和电子邮件)。不幸的是,它没有像我预期的那样工作。如果输入完整的名字或姓氏,它只返回结果,但我想在所有情况下得到结果:

示例:

用户名和姓=约翰史密斯

  1. case:keyWord = Jo
  2. case:keyWord = John
  3. case:keyWord = John Sm
  4. case:keyWord = John Smith
  5. case:keyWord = john.smith@mail.com
  6. 在firstName,lastName和email上使用文本索引的代码:

    User.findOne({ _id: req.user.id })
          .populate({
            path: 'friends',
            select: 'firstName lastName email avatarPath facebookID',
            match: { $text: { $search: req.query.keyWord } }
          })
          .populate({
            path: 'receivedFriendRequests',
            select: 'firstName lastName email avatarPath facebookID',
            match: { $text: { $search: req.query.keyWord } }
          })
          .exec(function (err, user) {
            if (err) {
              logger.error('Friend 500 ' + err)
              return res.status(500).json({
                code: config.errorCode.status500.code,
                message: config.errorCode.status500.message
              })
            }
            if (!user) {
              logger.error('Friend 404 User does not exist.')
              return res.status(404).json({
                code: config.errorCode.status404.code,
                message: config.errorCode.status404.message
              })
            }else {
              if (!user.friends) {
                logger.error('Friend 404 User friends do not exist.')
                return res.status(404).json({
                  code: config.errorCode.status404.code,
                  message: config.errorCode.status404.message
                })
              }
              return res.json({
                receivedFriendRequests: user.receivedFriendRequests.slice(0, 5),
                data: user.friends
              })
            }
          })
    

    我也尝试过这种方式,但它并不适用于所有5种情况:

    User.findOne({ _id: req.user.id })
          .populate({
            path: 'friends',
            select: 'firstName lastName email avatarPath facebookID',
            match: {
              $or: [
                {
                  firstName: { $regex: req.query.keyWord, $options: 'i'}
                },
                {
                  lastName: { $regex: req.query.keyWord, $options: 'i'}
                },
                {
                  email: { $regex: req.query.keyWord, $options: 'i'}
                }
              ]
            }
          })
          .populate({
            path: 'receivedFriendRequests',
            select: 'firstName lastName email avatarPath facebookID',
            match: {
              $or: [
                {
                  firstName: { $regex: req.query.keyWord, $options: 'i'}
                },
                {
                  lastName: { $regex: req.query.keyWord, $options: 'i'}
                },
                {
                  email: { $regex: req.query.keyWord, $options: 'i'}
                }
              ]
            }
          })
          .exec(function (err, user) {
            if (err) {
              logger.error('Friend 500 ' + err)
              return res.status(500).json({
                code: config.errorCode.status500.code,
                message: config.errorCode.status500.message
              })
            }
            if (!user) {
              logger.error('Friend 404 User does not exist.')
              return res.status(404).json({
                code: config.errorCode.status404.code,
                message: config.errorCode.status404.message
              })
            }else {
              if (!user.friends) {
                logger.error('Friend 404 User friends do not exist.')
                return res.status(404).json({
                  code: config.errorCode.status404.code,
                  message: config.errorCode.status404.message
                })
              }
              return res.json({
                receivedFriendRequests: user.receivedFriendRequests.slice(0, 5),
                data: user.friends
              })
            }
          })
    

    用户架构:

    var UserSchema = new Schema({
      firstName: {
        type: String
      },
      frstNameNormalized: {
        type: String
      },
      lastName: {
        type: String
      },
      lastNameNormalized: {
        type: String
      },
      email: {
        type: String,
        // unique: true,
        // required: true,
        lowercase: true,
      // match: [/^\w+([\.-]?\w+)*@\w+([\.-]?\w+)*(\.\w{2,3})+$/, 'Please enter a valid email address']
      },
      birthDate: {
        type: Date
      },
      facebookID: {
        type: String
      },
      twitterID: {
        type: String
      },
      password: {
        type: String
      },
      nickname: {
        type: String,
        default: ''
      },
      description: {
        type: String,
        default: ''
      },
      avatarPath: {
        type: String,
        default: ''
      },
      friends: [{ type: Schema.Types.ObjectId, ref: 'User' }],
      receivedFriendRequests: [{ type: Schema.Types.ObjectId, ref: 'User' }],
      sentFriendRequests: [{ type: Schema.Types.ObjectId, ref: 'User' }],
      sharedFriendCheckIns: [{ type: Schema.Types.ObjectId, ref: 'User' }],
      resetPasswordToken: String,
      resetPasswordExpires: Date,
      emailConfirmToken: String,
      emailConfirmExpires: Date,
      emailConfirmed: {
        type: Boolean,
        default: false
      }
    })
    ....
    
    UserSchema.index({ firstName: 'text', lastName: 'text', email: 'text'})
    
    var User = module.exports = mongoose.model('User', UserSchema)
    

    我做错了什么或有没有办法实施所有5个案例?

2 个答案:

答案 0 :(得分:2)

如果有人需要,我已经解决了这个问题。由于我是初学者,因此解决方案很简单,可能不是最佳解决方案,但它可以做到应有的目标。

FriendController.route('/').get(passport.authenticate('jwt', { session: false }), function (req, res) {

var parts = (req.query.keyWord).split(' ')
var firstName = ''
var lastName = ''

if (parts.length > 1) {

  firstName = (req.query.keyWord).split(' ').slice(0, -1).join(' ')
  lastName = (req.query.keyWord).split(' ').slice(-1).join(' ')

} else {

  firstName = req.query.keyWord
  lastName = req.query.keyWord

}

User.find({
  $and: [
    {
      $or: [
        {
          firstName: { $regex: firstName, $options: 'i'}
        },
        {
          lastName: { $regex: lastName, $options: 'i'}
        },
        {
          email: req.query.keyWord
        }
      ]
    },
    {
      friends: req.user.id
    }
  ]
})
  .select('firstName lastName email avatarPath facebookID')
  .exec(function (err, friends) {
    if (err) {
      logger.error('Friend 500 ' + err)
      return res.status(500).json({
        code: config.errorCode.status500.code,
        message: config.errorCode.status500.message
      })
    }
    User.find({
      $and: [
        {
          $or: [
            {
              firstName: { $regex: firstName, $options: 'i'}
            },
            {
              lastName: { $regex: lastName, $options: 'i'}
            },
            {
              email: req.query.keyWord
            }
          ]
        },
        {
          sentFriendRequests: req.user.id
        }
      ]
    })
      .select('firstName lastName email avatarPath facebookID')
      .exec(function (err, friendRequests) {
        if (err) {
          logger.error('Friend 500 ' + err)
          return res.status(500).json({
            code: config.errorCode.status500.code,
            message: config.errorCode.status500.message
          })
        }
        return res.json({
          receivedFriendRequests: friendRequests,
          data: friends
        })
      })
  })
})

答案 1 :(得分:0)

只需尝试使用此代码,我已使用$ text

替换了正则表达式
User.findOne({ _id: req.user.id })
              .populate({
                path: 'friends',
                select: 'firstName lastName email avatarPath facebookID',
                match: 
                  { $text: { $search: req.query.keyWord } }
              })
              .populate({
                path: 'receivedFriendRequests',
                select: 'firstName lastName email avatarPath facebookID',
                match: {
                   $text: { $search: req.query.keyWord } 
                }
              })
              .exec(function (err, user) {
                if (err) {
                  logger.error('Friend 500 ' + err)
                  return res.status(500).json({
                    code: config.errorCode.status500.code,
                    message: config.errorCode.status500.message
                  })
                }
                if (!user) {
                  logger.error('Friend 404 User does not exist.')
                  return res.status(404).json({
                    code: config.errorCode.status404.code,
                    message: config.errorCode.status404.message
                  })
                }else {
                  if (!user.friends) {
                    logger.error('Friend 404 User friends do not exist.')
                    return res.status(404).json({
                      code: config.errorCode.status404.code,
                      message: config.errorCode.status404.message
                    })
                  }
                  return res.json({
                    receivedFriendRequests: user.receivedFriendRequests.slice(0, 5),
                    data: user.friends
                  })
                }
              })