10

I want to implement method in schema class like below.

import { SchemaFactory, Schema, Prop } from '@nestjs/mongoose';
import { Document } from 'mongoose';
import bcrypt from 'bcrypt';

@Schema()
export class Auth extends Document {
  @Prop({ required: true, unique: true })
  username: string;

  @Prop({ required: true })
  password: string;

  @Prop({
    methods: Function,
  })
  async validatePassword(password: string): Promise<boolean> {
    return bcrypt.compareAsync(password, this.password);
  }
}
export const AuthSchema = SchemaFactory.createForClass(Auth);

this schema return undefined when log the method . How can I write method in class schema with nestjs/mongoose package?

Sajjad Hadafi
  • 347
  • 1
  • 7
  • 18

2 Answers2

29

You can use below approach to achieve this.

@Schema()
export class Auth extends Document {
    ...
    
    validatePassword: Function;
}

export const AuthSchema = SchemaFactory.createForClass(Auth);

AuthSchema.methods.validatePassword = async function (password: string): Promise<boolean> {
    return bcrypt.compareAsync(password, this.password);
};
Suroor Ahmmad
  • 1,110
  • 4
  • 23
  • 33
  • Hi, new to typed mongo in nestjs. Why cant we define these instance methods in the `@Schema` decorator with methods option. I tired this but it doesnt seem to work! Thanks for your solution, it works! Just wondering why its provided in the decorator and if you are aware of how to use it @Suroor Ahmmad – utsavojha95 Mar 15 '23 at 21:09
  • 1
    With the `@Schema()` decorator, you can only specify the schema and not define the method inside it. – Suroor Ahmmad Mar 17 '23 at 10:11
  • Ok thanks, just wondering why we can define an instance/methods object with functions in it in @Schema() decorator in @nestjs/mongoose. But yes it does not work I am wondering what is the use of this option that we can pass to the @Schema decorator. – utsavojha95 Mar 17 '23 at 22:07
0

Use this function instead of SchemaFactory.createForClass(Auth):

export function createSchema(document: any) {
  const schema = SchemaFactory.createForClass(document);

  const instance = Object.create(document.prototype);

  for (const objName of Object.getOwnPropertyNames(document.prototype)) {
    if (
      objName != 'constructor' &&
      typeof document.prototype[objName] == 'function'
    ) {
      schema.methods[objName] = instance[objName];
    }
  }

  return schema;
}
Weiner Nir
  • 1,435
  • 1
  • 15
  • 19