簡體   English   中英

使用 $text 索引查找 MongoDB 無法正常工作

[英]MongoDB find with $text index doesn't work properly

我正在嘗試使用他的用戶名實現對用戶的搜索,用戶名字段是唯一的。 結果是其用戶名包含字符串的所有用戶。 在查詢過程中,'q'參數被正確傳遞給find()函數,但是當'q'參數在響應中只包含用戶名的一部分時,返回一個空數組。 但是,當給出整個用戶名時,答案是正確的。

我的 users.controller 功能:

async findAllUsers(req, res) {
    const sort_by = {};
        sort_by[req.query.sort_by || 'createdAt'] = req.query.order_by || 'desc';
        const offset = parseInt(req.query.offset) || 0;
        const per_page = parseInt(req.query.per_page) || 2;
        const usersPromise =
        User.find(req.filters)
            .skip(offset)
            .limit(per_page)
            .sort(sort_by);
        const countPromise = User.countDocuments(req.filters);
        const [users, count] = await Promise.all([usersPromise, countPromise]);
        return res.status(200).send({ data: users, count });
  }

我的過濾功能:

export default function getFilters(req, res, next){
  const availableFilters = Object.keys(Users.schema.paths);
  const filters = qs.parse(req.query);

  const schemaFilters = _.pickBy(filters, (value, key) => availableFilters.indexOf(key) > -1);
  let searchFilter = {};
  if(filters.q){
    searchFilter = {
      $text: {
        $search: filters.q
      }
    }
  }

  req.filters = { ...searchFilter, ...schemaFilters };
  next(); 
}

我的用戶模型如下所示:

const User = new mongoose.Schema({
  username: {
    type: String,
    required: true,
    unique: true,
    lowercase: true,
    minlength: 6,
  },
  password:{
    type: String,
    required: true,
    minlength: 8
  },
  email:{
    type: String,
    unique: true,
    required: true
  },
  age: {
    type: Number,
  },
  description: String, 
  permissions: {
    type: Number,
    required: true,
    enum: [1, 2, 3],
  }
}, { timestamps: true });

User.index({ username: 'text' });

export default mongoose.model('User', User);

我的路線是這樣的:

  api.get("/users", getFilters, catchAsync(usersController.findAllUsers));

數據庫中的用戶示例:

{
    "_id" : ObjectId("5fba87e118f11129905aea93"),
    "username" : "Brody_Muller",
    "password" : "$2b$10$Smb9HP5dIINvO0.6K48PkOTXpXn9Tu.H.218XRIHOMOUthrWNCk7C",
    "email" : "Mariane.Crist@gmail.com",
    "age" : 44,
    "description" : "Voluptas deserunt occaecati ut perferendis qui temporibus.",
    "permissions" : 3,
    "createdAt" : "2020-11-22T15:46:37.777Z",
    "updatedAt" : "2020-11-22T15:46:37.777Z"
}

我還嘗試在 describtion 字段中創建索引,但在這里搜索部分字符串和搜索整個字符串都不成功。 我究竟做錯了什么?

搜索不是這樣工作的。 它可能比這更復雜,但似乎只做了簡單的推斷

“blue”,它不會匹配藍莓; 然而,“blueberry”將匹配藍莓。

您仍然可以在username上創建標准索引,然后使用正則表達式,如下所示:

 db.test1.find({username:/Brody/})

這將匹配查詢。 您也可以使用不敏感的搜索來改進事物,並使其成為單詞/^Brody/i的開頭。


從評論中擴展。 MongoDB 關於“停用詞”

文本索引刪除特定語言的停用詞(例如,英語、the、an、a 和等)並使用簡單的語言特定后綴詞干。

對此的解決方案是:

db.coll.createIndex({description:"text"},{language:"none"})

如果您將語言值指定為“none”,則文本索引使用簡單的標記化,沒有停用詞列表和詞干。

暫無
暫無

聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.

 
粵ICP備18138465號  © 2020-2024 STACKOOM.COM