Search code examples
ajaxreactjsreactjs-fluxflux

Ajax request from Fluxxor not dispatching success action


I am trying to use jquery.ajax from a Flux action using Fluxxor. I am working off of the Async example at http://fluxxor.com/guides/async-data.html.

The call is successful (I'm getting a response), but I can't figure out why it's not dispatching LOAD_BUZZ_SUCCESS.

I am replacing this block of code:

 var BuzzwordClient = {
      load: function(success, failure) {
        setTimeout(function() {
          success(_.range(10).map(Faker.Company.catchPhrase));
        }, 1000);
      }
    //...
    };

with

var BuzzwordClient = {
  load: function(success, failure) {
      jquery.ajax({
          url: "test.json",
          dataType: 'json',
          cache: false,
          success: function(data) {
            console.log("success");
            console.log(data);

          }.bind(this),
          error: function(xhr, status, err) {
              console.log("error");
          }.bind(this)
      });
  }
//...
};

The call is here from the actions var:

BuzzwordClient.load(function(words) {
      this.dispatch(constants.LOAD_BUZZ_SUCCESS, {words: words});
    }.bind(this), function(error) {
      this.dispatch(constants.LOAD_BUZZ_FAIL, {error: error});
    }.bind(this));
  }

Do I need to wrap the ajax call with something else? What is the client's load function supposed to return?


Solution

  • When you call

    BuzzwordClient.load(function(words) {
      this.dispatch(constants.LOAD_BUZZ_SUCCESS, {words: words});
    }.bind(this), function(error) {
      this.dispatch(constants.LOAD_BUZZ_FAIL, {error: error});
    }.bind(this));
    

    The two functions passed to load are available in the parameters success and failure in the load method:

    var BuzzwordClient = {
      load: function(success, failure) {
    

    But these functions are never called. Notice how the original example calls the passed success function, passing in the words:

    success(_.range(10).map(Faker.Company.catchPhrase));
    

    You need to do the same in your Ajax callbacks:

    var BuzzwordClient = {
      load: function(success, failure) {
          jquery.ajax({
              url: "test.json",
              dataType: 'json',
              cache: false,
              success: function(data) {
                success(data); // or something similar
              },
              error: function(xhr, status, err) {
                failure(err); // or something similar
              }
          });
      }
    //...
    };
    

    Here is a simple example: http://jsfiddle.net/BinaryMuse/6p98L2h8/

    What is the client's load function supposed to return?

    In general, asynchronous functions don't return anything. The value you care about is not available until some later time (which is what makes it asynchronous), so you need to use the callbacks for execution flow.

    You could also use something like promises to abstract away part of this, but in JavaScript you'll still fall back to callbacks at some point.