1

In specific case where we execute asynchronous call inside the if block, how come the else statement block gets executed if doSubmit evaluates to true? Outcome of this is that it always ends up at line after the ERROR_2 comment:

$scope.save = function() {
    if (doSubmit) {
        var dto = {
            'attributes': $scope.fields,
            'requestOrigin': $location.absUrl()
        };
        var req = {
            method: 'POST',
            url: 'endpoint',
            data: dto
        };
        $http(req).success(function(data, status) {
            // SUCCESS
            $scope.completed(data);
        }).error(function(data, status) {
            // ERROR_1
            $scope.validationFailed();
        });

    } else {
        // ERROR_2
        $scope.validationFailed();
    }
}
// Used to provide error messages about input validation
$scope.validationFailed = function(message, id) {
    $scope.alerts.push({ 
        type: 'danger', 
        msg: message || 'error.validation_failed', id: id || 'general'
    });
}

I read about this case somewhere but can't remember the source. Any link or short elaboration would be helpful.

ADDITION 1 $scope.validationFailed

maljukan
  • 2,148
  • 2
  • 25
  • 35
  • http://blog.slaks.net/2015-01-04/async-method-patterns/ – SLaks Aug 30 '15 at 19:58
  • 1
    How do you know that `doSubmit === true` ??? as `if ( doSubmit ) { } else { }` will always execute the first block if true. Oh forgot.. The success and error functions will run after you have exited the current call stack so will not effect that conditional statement. – Blindman67 Aug 30 '15 at 20:05
  • @Blindman67 inspected it of course, consider it hardcoded – maljukan Aug 30 '15 at 20:09
  • Is doSubmit a variable or a function? The obvious answer is that doSubmit does not evaluate to true, even if you think it is doing so. The code inside the if statement cannot affect the if statement itself. – HeadCode Aug 30 '15 at 20:25
  • @HeadCode It is a variable, inspected it so many times...repeated the scenario where it ends up evaluating to true – maljukan Aug 30 '15 at 20:30
  • 1
    @ IOlander OK, two more questions. What happens when you replace 'doSubmit' with 'true'? What happens when you comment out the code inside the if block? – HeadCode Aug 30 '15 at 20:36
  • @Juhana I don't think so. In the case of the if block running, the outcome would not be $scope.outcome === 'ERROR_2', it would be $scope.outcome === undefined. – HeadCode Aug 30 '15 at 20:44
  • @HeadCode Good one, when i hardcode `doSubmit` to `true` it's the same, skips breakpoints on `ERROR_1` and ends on breakpoint at line with `ERROR_2`. However when i comment out the code in if statement and leave only a line with `SUCCESS` it holds there as expected. – maljukan Aug 30 '15 at 20:52
  • So if you add `var doSubmit = true;` just before the code does it work? The only reason that it would act strangely is if you are calling the code with the condition elsewhere? – Blindman67 Aug 30 '15 at 20:53
  • @Blindman67 Do submit is true and no it doesn't, still ends up in else block. Only when i remove async part and leave just SUCCESS line as is - then it stays in the if block. – maljukan Aug 30 '15 at 20:58
  • For me, the strangest part is why does it end up in the else block. There is not a single scenario in my head to explain that. – maljukan Aug 30 '15 at 21:04
  • 1
    All you are left with is to step through the code and see it happen. And just to ease my A.D.D. put a semicolon after you declare `var req = {...};` We need to see all the code around the code snippet you gave to work out what is going on as there is other stuff happening that we can not see. – Blindman67 Aug 30 '15 at 21:07
  • @IOlander Just to be clear, I was suggesting putting the reserved word 'true' inside the parentheses where you currently have doSubmit. That is the only way you can really test whether or not something else is messing with the doSubmit variable. – HeadCode Aug 30 '15 at 21:17
  • @Blinman67 Searched all the occurrences of the `save` function which surround this code, nothing else than `ngClick` event bind on a button. Will try to replicate the scenario with a mock logic and show it using jsfiddle. I did exactly that, `if (true) {` I'll even put that in a comment above the line of code. – maljukan Aug 30 '15 at 21:18
  • @IOlander Ah, OK. Well, this is the most bizarre thing I'm probably going to see all week.... – HeadCode Aug 30 '15 at 21:23
  • @HeadCode Probably most bizarre thing i did ever, stay tuned to find out the stupid cause – maljukan Aug 30 '15 at 21:29
  • @IOlander I have to at least guess one last time. Were you presetting $scope.outcome = 'ERROR_2' somewhere ahead of this code? – HeadCode Aug 30 '15 at 21:30
  • @HeadCode Well i just realized that there are some thing that i've hidden and it was totally unneeded, will update the question now – maljukan Aug 30 '15 at 21:37
  • 1
    Maybe it's the `$http` **error** callback from where `$scope.validationFailed();` is executed? Try adding `alert(1);` in your error callback – Alon Eitan Aug 30 '15 at 22:07
  • @Alon Bingo, can you elaborate in answer why didn't it break on the line of that error? – maljukan Aug 30 '15 at 22:14

1 Answers1

1

My comment as an answer:

Maybe it's the $http error callback from where $scope.validationFailed(); is executed? Try adding alert(1); in your error callback.

This might indicate a server side problem, causing the server return status code different from 200 Both your else statement and the error callback are eventually executing the same function, but it just show that the else statement is NOT the one being executed.

Alon Eitan
  • 11,997
  • 8
  • 49
  • 58
  • 1
    Strange thing for me is that the execution didn't stop on the breakpoint of that specific call of `validationFailed()` function, but the later one in an `else` block. Great idea with that `alert()` – maljukan Aug 30 '15 at 22:32