Exercise - Ajax with promises

by Ryan Morris

JavaScript

/******************************************************************************/
/*
 * All data coming in and going out will be converted to/from JSON.
 *
 * Promises should be resolved with response data from the server,
 * decoded from JSON.
 *
 * Hints:
 *
 * Set content type before sending a request:
 *
 *   req.setRequestHeader("Content-Type", "application/json;charset=UTF-8");
 *
 * Send a data object as JSON:
 *
 *    req.send(JSON.stringify(data));
 *
 * Parse an incoming JSON string:
 *
 *   var data = JSON.parse(req.responseText || "null");
 *
 * Only resolve the promise if the (load) `status' code is >= 200 and
 * < 300.  Otherwise reject the promise.  Also reject the promise on
 * XHR failure (error).
 *
 */
Ajax = (function(){

  /**
   * raw
   * Likely abstraction for the raw ajax request
   *
   * @return {Promise}
   */
  var raw = function(url, method, data) {

    var ajaxPromise = new Promise(function(resolve, reject) {

      var req = new XMLHttpRequest();

      req.addEventListener("load", function(e) {

        if (req.status >= 200 && req.status < 300) {
          resolve(JSON.parse(req.responseText || "null"));
        }

        reject(req.status);

      });

      req.addEventListener("error", function() {
        reject("Something went wrong with the request");
      });

      req.open(method, url);
      req.setRequestHeader("Content-Type", "application/json;charset=UTF-8");
      req.send(data && JSON.stringify(data));

    });

    return ajaxPromise;

  };

  // HTTP GET (Fetch resource).
  var get = function(url) {

    return raw(url, 'GET');

  };

  // HTTP POST (Create new resource).
  var post = function(url, data) {

    return raw(url, 'POST', data);

  };

  // HTTP PATCH (Update existing resource).
  var patch = function(url, data) {

    return raw(url, 'PATCH', data);

  };

  // HTTP DELETE (Delete existing resource).
  var destroy = function(url) {

    return raw(url, 'DELETE');

  };

  // Public interface...