1

I'm facing some difficulties in my code related to scope. Here is my code:

<script type="text/javascript">
    var totalHoras = {};
    var dadosCategorias = {"teste": "1234"};
    var t; // timeout handler para exibição de feedback para o usuário

    $().ready(function() {
        // obtém dados das categorias
        var obterDadosCategorias = function() {
            $.post(
                "{{ baseRoute }}/cadastro/categoria/listar"
                , {
                    "ajax": "true"
                }
            ).done(function(data) {
                var obj = $.parseJSON(data);
                if (obj.result) {
                    console.log(dadosCategorias); // returns 'object{"teste": "1234"}'
                    dadosCategorias = obj.data;
                    console.log(dadosCategorias); // returns 'string(11) "it works!!!"'
                } else {
                    alert('Erro interno: não foi possível obter os dados das categorias');
                }
            });
        };

        obterDadosCategorias();
        console.log(dadosCategorias); // returns 'object{"teste": "1234"}'

The question is: why the hell is the third call of console.log returning the orginal var value? isn't is suposed to be overwriten?

The console was suposed to be

'object{"teste": "1234"}'
'string(11) "it works!!!"'
'string(11) "it works!!!"'

But it is

'object{"teste": "1234"}'
'string(11) "it works!!!"'
'object{"teste": "1234"}'

I've trie to use the "context" option with window in $.ajax() function, but does not work too :(

AstroCB
  • 12,337
  • 20
  • 57
  • 73
  • 2
    why would the third console.log wait for your POST to finish? it runs immediately after obterDadosCategorias(), which won't have had any time whatsoever to fire off the POST request, get the response, parse the body, AND reassign the content of `obterDadosCategorias` – Mike 'Pomax' Kamermans Sep 28 '14 at 22:40
  • When I read through this, I would expect it to be 'object{etc}', 'object{etc}', 'string(11) it works''). This is neither what it is nor what the poster is expecting – Andrew Shepherd Sep 28 '14 at 22:46
  • You are not understanding what 'asynchronous' means (the A in AJAX). Try putting a unique identifier into your console.log calls (ex., console.log(1, dadosCategorias)) to see in which order they are getting called. – 76484 Sep 29 '14 at 01:06
  • you guys are correct. I will try to make a synchronous request. (and tanks for the tip of identifying the console.log calls) –  Sep 29 '14 at 01:59

1 Answers1

0

Thanks to the comments guys! :D

I've found the answer. The problem wasn't the scope at all. Actually, the calls to console.log() wasn't in the order of the script. The calling order was 312 before, now it is 123 :D I changed the ajax method to $.ajax() instead of $.post() and set the option 'async' to false to achieve this, like so:

<script type="text/javascript">
    var totalHoras = {};
    var dadosCategorias = {"teste": "1234"};
    var t; // timeout handler para exibição de feedback para o usuário

    $().ready(function() {
        // obtém dados das categorias
        var obterDadosCategorias = function() {
            $.ajax(
                "{{ baseRoute }}/cadastro/categoria/listar"
                , {
                    "type": "POST"
                    , "async": false
                    , "data": {
                        "ajax": "true"
                    }
                }
            ).done(function(data) {
                var obj = $.parseJSON(data);
                if (obj.result) {
                    console.log(1, dadosCategorias);
                    dadosCategorias = obj.data;
                    console.log(2, dadosCategorias);
                } else {
                    alert('Erro interno: não foi possível obter os dados das categorias');
                }
            });
        };

        obterDadosCategorias();
        console.log(3, dadosCategorias);
  • setting `async: false` is a very bad design idea... as it look block the browser for the duration of the ajax request – Arun P Johny Sep 29 '14 at 03:44
  • Yes, please don't do it that way. Pass a function to `obterDadosCategorias` and call it in the `done` handler. – 76484 Sep 29 '14 at 03:50
  • why not? obtaining the data returned from this function is mandatory. The application can't even run without that response, so I think I can make it synchronous. –  Sep 29 '14 at 16:04