Let's say I have multiple classes that have a similar method. In this case, a bunch of services that have a saveModel method:
public async saveModel(newModel: IModel): Promise<IModel> {
return await newModel.save();
}
The generic method I made looks like this:
public async saveModel<P extends Document>(newModel: P): Promise<P> {
return await newModel.save();
}
All of my services (the ones that use that method) extend a class that contains that generic method, so now on any of those services, I can call answerService.saveModel(newAnswer)
and it'll save the answer. Everything was dandy until I realized that I can put an object of type IQuestion in there as well. And an object of type IDinosaur if I wanted, as long as it extends the Mongoose Document interface.
Is there any way for me to enforce certain interfaces to be used in each service? How would I make sure that the answerService only saves objects with type IAnswer? Does the answerService need to implement an interface that has that saveModel signature like this:
interface IAnswerService {
saveModel(newModel: IAnswer): Promise<IAnswer>;
}
This is a skeleton of what the entire thing looks like:
EntityService.ts
import { Document } from 'mongoose';
export class EntityService implements IEntityService {
public async saveModel<P extends Document>(newModel: P): Promise<P> {
try {
const savedModel = await newModel.save();
return savedModel;
} catch (err) {
console.log(err);
return null;
}
}
}
answer.service.ts
import { Answer, IAnswer } from '@models/answer.model';
import { EntityService } from '@classes/EntityService';
class AnswerService extends EntityService {
private static instance: AnswerService;
private constructor() {
super();
}
static getInstance(): AnswerService {
if (!AnswerService.instance) {
AnswerService.instance = new AnswerService();
}
return AnswerService.instance;
}
}
const answerService = AnswerService.getInstance();
export default answerService;
answer.model.ts
import mongoose, { Schema, Document, Model } from 'mongoose';
export interface IAnswer extends Document {
answerText: string;
posterID: string;
}
const AnswerSchema: Schema = new Schema({
answerText: {type: String, required: true},
posterID: {type: String, required: true}
}, {
minimize: false
});
export const Answer: Model<IAnswer> = mongoose.model<IAnswer>('Answer', AnswerSchema);
All other interfaces inherit from the same things that IAnswer does (Model, Schema, Document).
And usage of the AnswerService looks generally like this:
import answerService from 'answer.service';
import { Answer } from 'answer.model';
const answer = new Answer({
answerText: 'Stuff',
posterID: '123456789'
})
answerService.saveModel(answer);
Aucun commentaire:
Enregistrer un commentaire