-1

I was looking at Benjamin Gruenbaum's answer, where he prints result in the body of the HTML. While he does talk extensively, him and other answers about how this works, they do not directly answer the question that is How do I return the response from an asynchronous call?

As I understand it, he (and I) wanted to be able to return the result and assign it to a variable for instance, or console.log() it outside the function foo. Here is the code:

      foo(function (result) {
        document.body.innerHTML = result;
      });

      function foo(callback) {
        httpRequest = new XMLHttpRequest();
        httpRequest.onreadystatechange = function () {
            if (httpRequest.readyState === 4) { // request is done
                if (httpRequest.status === 200) { // successfully
                    callback(httpRequest.responseText); // we're calling our method
                }
            }
        };
        httpRequest.open('GET', "someFile.json");
        httpRequest.send();
      }

What I really want is to read the file "someFile.json" and store the corresponding string in a variable jsonString instead of assigning it to the body of the page, so I can do something with it somewhere else.

Community
  • 1
  • 1
MorganFR
  • 331
  • 3
  • 19
  • 2
    and you can. Just don't "do something with it" before `callback` executes and assigns it. – Igor Nov 08 '16 at 16:41
  • 1
    *"they do not directly answer the question that is How do I return the response from an asynchronous call?"* Well, the direct answer would be: *you can't*, but that's not really useful. Instead we show you how to structure your code instead. – Felix Kling Nov 08 '16 at 16:44
  • @Igor My bad, I copied the wrong part after I tried some things. I just want to assign `result` to a variable, but when I do it ends up undefined. – MorganFR Nov 08 '16 at 16:44
  • @FelixKling So is there no way for me to assign `result` to an existing variable instead of updating `body` without having to resort to server side programming? – MorganFR Nov 08 '16 at 16:48
  • You can do whatever you want *inside the callback*, e.g. `someExistingVariable = result;`. But usually there are better solution depending on your exact use case. – Felix Kling Nov 08 '16 at 16:49
  • @FelixKling I tried creating a variable before the two function, called `var jsonString;`, but when I replace (or add after) `document.body.innerHTML = result;` the line `jsonString = result`, the variable stays undefined. – MorganFR Nov 08 '16 at 16:52
  • *"the variable stays undefined."* You are most likely accessing `jsonString` **before** the callback was executed (see also [Why is my variable unaltered after I modify it inside of a function? - Asynchronous code reference](http://stackoverflow.com/q/23667086/218196)). And that's exactly the reason why this is not a common thing to do: You don't know when to access the variable unless you execute the code that needs to access the variable/response from the callback. Explaining this and providing solutions is the whole point of the question you are linked to! – Felix Kling Nov 08 '16 at 16:54
  • Let us [continue this discussion in chat](http://chat.stackoverflow.com/rooms/127651/discussion-between-morganfr-and-felix-kling). – MorganFR Nov 08 '16 at 17:06

1 Answers1

0

You can do it using a variable if this is what you are after. Just keep in mind that the variable will only get value when onreadystatechange executes and assigns it.

  var someFileContent;

  foo(function () {
    console.log(someFileContent);
  });

  function foo(callback) {
    httpRequest = new XMLHttpRequest();
    httpRequest.onreadystatechange = function () {
        if (httpRequest.readyState === 4) { // request is done
            if (httpRequest.status === 200) { // successfully
                someFileContent = httpRequest.responseText;
                callback(); // we're calling our method
            }
        }
    };
    httpRequest.open('GET', "someFile.json");
    httpRequest.send();
  }
Igor
  • 15,833
  • 1
  • 27
  • 32
  • And why would you want to do this instead of passing the value to the callback? – Felix Kling Nov 08 '16 at 16:52
  • @FelixKling Naturally. On a small chance that this was what the OP was missing. I am planning to delete this since it is so plainly obvious. – Igor Nov 08 '16 at 16:53
  • @Igor I know I can do that, but the issue remains, while I can do whatever I want with the variable `someFileContent`, I cannot get it to be assigned outside the callback, or assign the value to another variable outside of the callback. For instance, I would like to be able to use `console.log(someFileContent)` after both those functions and use it afterwards, like counting the lines or something. But it has to happen outside the callback. – MorganFR Nov 08 '16 at 16:58
  • @MorganFR - the code I showed does that. Do you see the content of you expect in the browser console? – Igor Nov 08 '16 at 16:59
  • @Igor I do see what I want, but not where I want. I do not want to continue the rest of my program within the callback function. I have no interest in printing it, I want to use that data later on via a variable. – MorganFR Nov 08 '16 at 17:03
  • @MorganFR If by "outside the callback" you mean "before the callback", you need to get the "cause and effect" in your code straight. `onreadystatechange`, where `someFileContent` is assigned, is the earliest moment when the content from server becomes available to client-side code. – Igor Nov 08 '16 at 17:03
  • @Igor I mean after the callback. I simply want to read the file, and store it in a variable to be used later. The callback would be a good moment to assign the content to the variable, however, the rest of the code is executed before the callback is done, and therefore nothing happens. – MorganFR Nov 08 '16 at 17:06
  • Let us [continue this discussion in chat](http://chat.stackoverflow.com/rooms/127652/discussion-between-morganfr-and-igor). – MorganFR Nov 08 '16 at 17:10