【问题标题】:Auto Increment Sequence in NestJs/MongooseNestJs/Mongoose 中的自动增量序列
【发布时间】:2023-03-20 07:22:01
【问题描述】:

我正在将一个 NodeJs 项目迁移到 NestJs,该项目使用 MongoDB 作为后端数据库,使用 Mongoose 作为 ODM。我使用 mongoose-sequence 插件来处理自动增量序列,但是我遇到了需要 NestJs 下的库的麻烦。

mongoose-sequence 文档解释了如何使用 CommonJS 语法导入库,如下所示:

const mongoose = require('mongoose')
const AutoIncrementFactory = require('mongoose-sequence');

const connection = await mongoose.createConnection('mongodb://...');

const AutoIncrement = AutoIncrementFactory(connection);

使用 ES6 导入语法会是这样的:

import * as mongoose from 'mongoose';
import * as AutoIncrementFactory from 'mongoose-sequence';

const connection = ...;

const AutoIncrement = AutoIncrementFactory(connection);

但是由于 NestJs 使用依赖注入,访问原生连接并不是那么直接。根据documentation to integrate MongoDB using Mongoose 访问本机Mongoose Connection 对象可以使用@InjectConnection() 装饰器完成,如下所示:

@Injectable()
export class CatsService {
  constructor(@InjectConnection() private connection: Connection) {}
}

但由于 TypeScript decorators 只能附加到类声明、方法、访问器、属性或参数,我看不到如何注入连接,需要插件并在我的 Schema 类上初始化它。

【问题讨论】:

    标签: node.js mongodb mongoose nestjs mongoose-sequence


    【解决方案1】:

    可以使用MongooseModuleforFeatureAsync() 方法以及工厂提供程序(即useFactory)为给定架构注册插件。

    按照official documentation中的示例:

    @Module({
      imports: [
        MongooseModule.forFeatureAsync([
          {
            name: Cat.name,
            useFactory: () => {
              const schema = CatsSchema;
              schema.plugin(require('mongoose-autopopulate'));
              return schema;
            },
          },
        ]),
      ],
    })
    export class AppModule {}
    

    但是,对于mongoose-sequence 插件,必须将本机 Mongoose 连接对象传递给插件初始化。这可以通过使用getConnectionToken 方法将连接注入工厂提供程序来实现:

    import {getConnectionToken, MongooseModule} from '@nestjs/mongoose';
    import * as AutoIncrementFactory from 'mongoose-sequence';
    
    @Module({
      imports: [
        MongooseModule.forFeatureAsync([
          {
            name: Cat.name,
            useFactory: async (connection: Connection) => {
              const schema = CatsSchema;
              const AutoIncrement = AutoIncrementFactory(connection);
              schema.plugin(AutoIncrement, {inc_field: 'id'});
              return schema;
            },
            inject: [getConnectionToken('YOUR_CONNECTION_NAME')],
          },
        ]),
      ],
    })
    export class AppModule {}
    

    【讨论】:

    • 感谢您的回答。我正在尝试使用它,但我从 AutoIncrementFactory(connection) 收到打字错误。 “Connection 类型的参数不可分配给 'Schema' 类型的参数。您是否也遇到过这种情况?
    • 嗨@Todd,不,我没有遇到这个问题,在我看来,您正在将连接分配给不是连接的东西,但如果没有更多上下文,很难说。
    • 感谢安德烈斯。我的模块看起来就像你上面的一样。也许我们安装的底层库不同。
    • 好的,我通过在主 AppModule 而不是 OrderModule 上执行此 forFeatureAsync 导入来修复。终于成功了。
    • @AndresFelipe 知道这个错误吗? Cannot read property 'modelNames' of undefined
    猜你喜欢
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2014-07-06
    • 1970-01-01
    • 1970-01-01
    • 2016-10-16
    • 2021-05-01
    相关资源
    最近更新 更多