Igor P.
Igor P.

Reputation: 1477

Node.js: POST request sent twice by system

I send JSON POST data via a form in a MEAN environment to my server. On the server side, I process the data inside of a waterfall function, using the async library, including various operations such as: [...] - create a database entry for a new author - create a database entry for a new book - associate the new book to an author (reference to book ID) [...]

This is the method called by my route, which handles the associated POST-request:

exports.createAuthor = function(req, res) {

    console.log(req.url+' !!!POST REQUEST INCOMING!!! '+req.body);

    async.waterfall([

        function(callback){
            //create Author db entry
        },

        function(parameter, callback){
            //add author to additional directory (db action)
        },

        function(parameter, callback){
            //create book db entry
        },

        function(parameter, callback){
            //associate book to author (db action)
        }

    ], function (err, result) {
        console.log('DONE!!!');
        res.send('200');
    }); 
}

This is the client-side AngularJS controller code:

searchApp = angular.module("searchApp",[]);
searchApp.controller('authorCreator', function ($scope,$http) {

    $scope.tags = [];

    $scope.sendAuthor = function(){  

    alert('I was called!');    
    $http({
        method: 'POST',
        url: '/newauthor/',
        data: { 'authorname' : $scope.authorName,
                'authordescription' : $scope.authorDescr, 
                'bookname' : $scope.bookName, 
                'tags' : $scope.tags }
        })
        .success(function(data){
            //no actions yet
        })
        .error(function(){
            //no actions yet
        });
    };
});

This is the AngularJS form:

<div ng-controller="authorCreator">
    <form>
        <p>Author name: <input ng-model="authorName"></p>
        <p>Author description: <input ng-model="authorDescr"></p>
        <p>Book name: <input ng-model="bookName"></p>
        <p>Tags:<input ng-model="tags"></p>
        <p><button ng-click="sendAuthor()">Send</button></p>
    </form>
</div>

I noticed that, if the waterfall-process is "stuck" somewhere, meaning the client does not get an answer to it's request whatsoever, the POST request seems to be sent a second time automatically (as soon as the browser is giving a timeout according to firebug). According to firebug, a second POST request does not seem to be sent by the browser, so the call must be initiated from somewhere else. I found out by checking the database (multiple documents with identical values, except the ObjectID of course) and monitoring the node.js console window where I output incoming POST data. Again: as soon as the entire waterfall-process completes, hence the client browser does not abort the post request after a while, and res.send('200') executes, the error does not occur (= no multiple db entries). Can anyone please tell me, who does initiate this second POST request and how may I deactivate it? Cheers

Igor

Upvotes: 2

Views: 3057

Answers (3)

aaron
aaron

Reputation: 66

i "fixed" this by adding

 .get('/favicon.ico:1', (req, res) =>{
//do nothing because i dont care
  })

Upvotes: 0

Igor P.
Igor P.

Reputation: 1477

After spending some time on that issue I found out, that this error seems to be based on missing answers to the client (be it via res.json, res.sendfile, ...). Therefore the client seems to re-send the request after some time, thus executing server-side code a second time. Responding to the client in reasonable time solves this issue. Sorry for the confusion.

Upvotes: 1

Benjamin RD
Benjamin RD

Reputation: 12034

Try adding this:

exports.createAuthor = function(req, res) {
if(req.method == 'POST' && req.url = 'REQUESTEDURL'){
    console.log('POST REQUEST INCOMING!!! '+req.body);
    async.waterfall([
      //TODO...
    ]);
}

Maybe the problem is that the favicon or some other resource is doing a request to

Upvotes: 2

Related Questions