You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

如何优化关键词查询的类型检查?能否用泛型简化冗余类型?

简化ApiFeatures类的冗余类型:泛型方案可行且更优

你的代码里query的类型确实存在冗余重复的问题,完全可以用泛型来简化,而且泛型方案比当前的硬编码类型更灵活、可复用性更强。

原代码问题

你重复书写了两次Query<(ProductDoc & { _id: Types.ObjectId })[], ProductDoc & { _id: Types.ObjectId }, {}, ProductDoc>,不仅冗余,还限制了类只能处理ProductDoc类型的文档。

泛型优化方案

通过引入泛型参数,我们可以把重复的类型逻辑抽象出来,同时让类支持任意Mongoose文档类型:

步骤1:定义泛型类

import { Query, Types } from 'mongoose';
import { ParsedQs } from 'qs';

// 可选:定义类型别名简化重复的组合类型
type WithObjectId<T> = T & { _id: Types.ObjectId };

export class ApiFeatures<T> {
  query: Query<WithObjectId<T>[], WithObjectId<T>, {}, T>;
  queryStr: ParsedQs;

  constructor(
    query: Query<WithObjectId<T>[], WithObjectId<T>, {}, T>,
    queryStr: ParsedQs
  ) {
    this.query = query;
    this.queryStr = queryStr;
  }

  search() {
    const keyword = this.queryStr.keyword
      ? {
          title: {
            $regex: this.queryStr?.keyword,
            $options: "i",
          },
        }
      : {};

    this.query = this.query.find({ ...keyword });
    return this;
  }
}

步骤2:使用泛型类

当你需要处理ProductDoc时,只需在实例化时传入泛型参数:

// 假设productQuery是针对ProductDoc的Mongoose查询对象
const apiFeatures = new ApiFeatures<ProductDoc>(productQuery, req.query);

泛型方案的优势

  1. 消除冗余:无需重复书写复杂的Query类型参数,只需通过泛型参数T推导即可
  2. 提升复用性:如果以后需要处理其他文档类型(比如UserDoc),直接替换泛型参数即可,无需修改类的内部逻辑
  3. 类型安全:保持了原有的类型检查能力,不会丢失类型约束

总结

当前的硬编码类型方案虽然能工作,但泛型方案明显更优——既简化了代码,又增强了扩展性,完全替代原方案没有问题。

内容的提问来源于stack exchange,提问作者Stackerme

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.08.09 17:35:27