alexwck
alexwck

Reputation: 21

Error from nodejs server thrown not being passed back to AJAX

I have the following AJAX that will send the entered data to the node server and the controller will check whether such data exist in the database or not. If I do enter the data correctly, then everything is working fine.

However, I tried enter anything that the database does not have and it immediately throw an error, causing the server to stop. The error said that I did not handle the event, so I tried with res.json(err) in the controller instead of throw new Error, hoping that the error will be passed back to AJAX under the error key, but it is still not working. The error still gets thrown and the node server terminate itself.

I would like the server to continue and alert to the user that the data that was entered is not in the database but I have no idea why my approach is not correct. I was thinking of using this SO thread if I'm able to get the error message back first from server side. jQuery Ajax error handling, show custom exception messages

To solve the server from stopping, I used the code in app.js that was referred from this link

How do I prevent node.js from crashing? try-catch doesn't work

I'm not sure whether should I use the accepted answer for my case.

function createProduct(inputval){
    let inputAction = window.location.pathname;
    $.ajax({
        type: "POST",
        url:  inputAction,
        data: {order: inputval.split('-')[0].trim(), lot: inputval.split('-')[1].substring(0,5)},
        success: function(data) {
            $('#product').val('');
            //Another function to add HTML 
            display(data);
        },
        error: function(jqXHR, textStatus, errorThrown) {
            console.log("XHR" + jqXHR)
            console.log("Status" + textStatus)
            console.log(errorThrown)
        }
     });
}

Controller File

exports.createProduct = function (req, res) {

    db.Product.findOne({ "order": req.body.order, "lot": req.body.lot }).exec(function (err, product) {
        if (!product || err){
              throw new Error("The product entered returns null");
        }
        res.json(product);
  });
};

Main File: app.js

process.on('uncaughtException', function (err) {
    console.error(err);
    console.log("Node NOT Exiting...");
});

Upvotes: 0

Views: 68

Answers (2)

alexwck
alexwck

Reputation: 21

I finally figure it out thanks to feedback from other community, so I thought I would just share it here. It's so simple and silly me for neglecting such statement.

First, the code in app.js can just be removed.

Second, based on the answer given by @Milad Aghamohammadi. Instead of just:

res.status(500).end();

Use:

return res.status(500).json({err: "Server error"});

This way, the error is able to be handled by the AJAX error function and the node server will not be terminated from the event loop.

Upvotes: 0

Milad Aghamohammadi
Milad Aghamohammadi

Reputation: 1986

You should use correct status code for your response. I suggest change your controller like below snippet

exports.createProduct = function (req, res) {

    db.Product.findOne({ "order": req.body.order, "lot": req.body.lot }).exec(function (err, product) {
        if (err){
            res.status(500).end();//means internal server error
        } else if (!product) {
            res.status(404).end();//means product not found
        } else {
            res.json(product);
        }
    });
};

Upvotes: 1

Related Questions