Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

mongoose static method returns a bluebird promise

I am creating a mongoose static method 'load' so that my main controller function can use it (for chainning and error handling).

UserSchema.load('54ae92dd8b8eef540eb3a66d')
.then(....)
.catch(....);

The thing is the id is something wrong so I need to catch this error. and I am thinking it is better to do this in the model layer.

When I do the following the controller can catch this error.

UserSchema.statics.load = function(id) {

    if (!mongoose.Types.ObjectId.isValid(id)) {
        return Promise.resolve().then(function() {
            throw new Error('not a mongoose id');
        }); ------------( * )
    }

    return Promise.cast(this.findOne({
        _id: id
    }).exec());
};

But if I only do the following the error is not successfully thrown into the controller .catch function.

AchievementSchema.statics.load = function(id) {
    if (!mongoose.Types.ObjectId.isValid(id)) {
        throw new Error('not a mongoose id');
    }
    return Promise.cast(this.findOne({
        _id: id
    }).exec());
};

so my question is am I doing this correctly? If so is there easier ways to write the (*) statement? What I am doing seems ugly.. Thanks.

like image 425
Shih-Min Lee Avatar asked Dec 14 '25 07:12

Shih-Min Lee


1 Answers

Yes, there is a shorthand called Promise.reject.

Your code in:

if (!mongoose.Types.ObjectId.isValid(id)) {
    return Promise.resolve().then(function() {
        throw new Error('not a mongoose id');
    }); ------------( * )
}

Can be written as:

return Promise.reject(new Error("Not a mongoose id");

You can do even better though, Promise.method exists to ensure anything that might return a promise will return a promise:

UserSchema.statics.load = Promise.method(function(id) {

    if (!mongoose.Types.ObjectId.isValid(id)) {
        throw new Error('not a mongoose id: ' + id);
    }
    return this.findOne({ _id: id }).exec());
});

This will both case the findOne result to a Bluebird trusted promise and convert the throw to a rejection for you. You might want to consider throwing a subclass of Promise.OperationalError rather than Error though.

As an unrelated tip Promise.cast was deprecated in favor of Promise.resolve over a year ago.

like image 128
Benjamin Gruenbaum Avatar answered Dec 16 '25 22:12

Benjamin Gruenbaum



Donate For Us

If you love us? You can donate to us via Paypal or buy me a coffee so we can maintain and grow! Thank you!