<!doctype html>
<!--
Copyright (c) 2015 The Polymer Project Authors. All rights reserved.
This code may only be used under the BSD style license found at http://polymer.github.io/LICENSE.txt
The complete set of authors may be found at http://polymer.github.io/AUTHORS.txt
The complete set of contributors may be found at http://polymer.github.io/CONTRIBUTORS.txt
Code distributed by Google as part of the polymer project is also
subject to an additional IP rights grant found at http://polymer.github.io/PATENTS.txt
-->
<html>
<head>
  <title>iron-ajax</title>

  <script src="../../webcomponentsjs/webcomponents.js"></script>
  <script src="../../web-component-tester/browser.js"></script>

  <link rel="import" href="../../polymer/polymer.html">
  <link rel="import" href="../../promise-polyfill/promise-polyfill.html">
  <link rel="import" href="../iron-ajax.html">
</head>
<body>
  <test-fixture id="TrivialGet">
    <template>
      <iron-ajax url="/responds_to_get_with_json"></iron-ajax>
    </template>
  </test-fixture>
  <test-fixture id="ParamsGet">
    <template>
      <iron-ajax url="/responds_to_get_with_json"
                 params='{"a": "a"}'></iron-ajax>
    </template>
  </test-fixture>
  <test-fixture id="AutoGet">
    <template>
      <iron-ajax auto url="/responds_to_get_with_json"></iron-ajax>
    </template>
  </test-fixture>
  <test-fixture id="GetEcho">
    <template>
      <iron-ajax handle-as="json" url="/echoes_request_url"></iron-ajax>
    </template>
  </test-fixture>
  <test-fixture id="TrivialPost">
    <template>
      <iron-ajax method="POST"
                 url="/responds_to_post_with_json"></iron-ajax>
    </template>
  </test-fixture>
  <test-fixture id="DebouncedGet">
    <template>
      <iron-ajax auto
                 url="/responds_to_debounced_get_with_json"
                 debounce-duration="150"></iron-ajax>
    </template>
  </test-fixture>
  <test-fixture id='BlankUrl'>
    <template>
      <iron-ajax auto handle-as='text'></iron-ajax>
    </template>
  </test-fixture>
  <!-- note(rictic):
       This makes us dependent on a third-party server, but we need to be able
       to check what headers the browser actually sends on the wire.
       If necessary we can spin up our own httpbin server, as the code is open
       source.
    -->
  <test-fixture id="RealPost">
    <template>
      <iron-ajax method="POST" url="http://httpbin.org/post"></iron-ajax>
    </template>
  </test-fixture>
  <test-fixture id="Delay">
    <template>
      <iron-ajax url="http://httpbin.org/delay/1"></iron-ajax>
    </template>
  </test-fixture>
  <script>
    'use strict';
    suite('<iron-ajax>', function () {
      var responseHeaders = {
        json: { 'Content-Type': 'application/json' },
        plain: { 'Content-Type': 'text/plain' }
      };
      var ajax;
      var request;
      var server;

      function timePasses(ms) {
        return new Promise(function(resolve) {
          window.setTimeout(function() {
            resolve();
          }, ms);
        });
      }

      setup(function() {
        server = sinon.fakeServer.create();
        server.respondWith(
          'GET',
          /\/responds_to_get_with_json.*/,
          [
            200,
            responseHeaders.json,
            '{"success":true}'
          ]
        );

        server.respondWith(
          'POST',
          '/responds_to_post_with_json',
          [
            200,
            responseHeaders.json,
            '{"post_success":true}'
          ]
        );

        server.respondWith(
          'GET',
          '/responds_to_get_with_text',
          [
            200,
            responseHeaders.plain,
            'Hello World'
          ]
        );

        server.respondWith(
          'GET',
          '/responds_to_debounced_get_with_json',
          [
            200,
            responseHeaders.json,
            '{"success": "true"}'
          ]
        );

        server.respondWith(
          'GET',
          '/responds_to_get_with_502_error_json',
          [
            502,
            responseHeaders.json,
            '{"message": "an error has occurred"}'
          ]
        );

        ajax = fixture('TrivialGet');
      });

      teardown(function() {
        server.restore();
      });

      // Echo requests are responded to individually and on demand, unlike the
      // others in this file which are responded to with server.respond(),
      // which responds to all open requests.
      // We don't use server.respondWith here because there's no way to use it
      // and only respond to a subset of requests.
      // This way we can test for delayed and out of order responses and
      // distinquish them by their responses.
      function respondToEchoRequest(request) {
        request.respond(200, responseHeaders.json, JSON.stringify({
          url: request.url
        }));
      }

      suite('when making simple GET requests for JSON', function() {
        test('has sane defaults that love you', function() {
          request = ajax.generateRequest();

          server.respond();

          expect(request.response).to.be.ok;
          expect(request.response).to.be.an('object');
          expect(request.response.success).to.be.equal(true);
        });

        test('will be asynchronous by default', function() {
          expect(ajax.toRequestOptions().async).to.be.eql(true);
        });
      });

      suite('when setting custom headers', function() {
        test('are present in the request headers', function() {
          ajax.headers['custom-header'] = 'valid';
          var options = ajax.toRequestOptions();

          expect(options.headers).to.be.ok;
          expect(options.headers['custom-header']).to.be.an('string');
          expect(options.headers.hasOwnProperty('custom-header')).to.be.equal(
              true);
        });

        test('non-objects in headers are not applied', function() {
          ajax.headers = 'invalid';
          var options = ajax.toRequestOptions();

          expect(Object.keys(options.headers).length).to.be.equal(0);
        });
      });

      suite('when url isn\'t set yet', function() {
        test('we don\'t fire any automatic requests', function() {
          expect(server.requests.length).to.be.equal(0);
          ajax = fixture('BlankUrl');

          return timePasses(1).then(function() {
            // We don't make any requests.
            expect(server.requests.length).to.be.equal(0);

            // Explicitly asking for the request to fire works.
            ajax.generateRequest();
            expect(server.requests.length).to.be.equal(1);
            server.requests = [];

            // Explicitly setting url to '' works too.
            ajax = fixture('BlankUrl');
            ajax.url = '';
            return timePasses(1);
          }).then(function() {
            expect(server.requests.length).to.be.equal(1);
          });
        });
      });

      suite('when properties are changed', function() {
        test('generates simple-request elements that reflect the change', function() {
          request = ajax.generateRequest();

          expect(request.xhr.method).to.be.equal('GET');

          ajax.method = 'POST';
          ajax.url = '/responds_to_post_with_json';

          request = ajax.generateRequest();

          expect(request.xhr.method).to.be.equal('POST');
        });
      });

      suite('when generating a request', function() {
        test('yields an iron-request instance', function() {
          var IronRequest = document.createElement('iron-request').constructor;

          expect(ajax.generateRequest()).to.be.instanceOf(IronRequest);
        });

        test('correctly adds params to a URL that already has some', function() {
          ajax.url += '?a=b';
          ajax.params = {'c': 'd'};
          expect(ajax.requestUrl).to.be.equal('/responds_to_get_with_json?a=b&c=d')
        })

        test('encodes params properly', function() {
          ajax.params = {'a b,c': 'd e f'};

          expect(ajax.queryString).to.be.equal('a%20b%2Cc=d%20e%20f');
        });

        test('encodes array params properly', function() {
          ajax.params = {'a b': ['c','d e', 'f']};

          expect(ajax.queryString).to.be.equal('a%20b=c&a%20b=d%20e&a%20b=f');
        });

        test('reflects the loading state in the `loading` property', function() {
          var request = ajax.generateRequest();

          expect(ajax.loading).to.be.equal(true);

          server.respond();

          return request.completes.then(function() {
            return timePasses(1);
          }).then(function() {
            expect(ajax.loading).to.be.equal(false);
          });
        });
      });

      suite('when there are multiple requests', function() {
        var requests;
        var echoAjax;
        var promiseAllComplete;

        setup(function() {
          echoAjax = fixture('GetEcho');
          requests = [];

          for (var i = 0; i < 3; ++i) {
            echoAjax.params = {'order': i + 1};
            requests.push(echoAjax.generateRequest());
          }
          var allPromises = requests.map(function(r){return r.completes});
          promiseAllComplete = Promise.all(allPromises);
        });

        test('holds all requests in the `activeRequests` Array', function() {
          expect(requests).to.deep.eql(echoAjax.activeRequests);
        });

        test('empties `activeRequests` when requests are completed', function() {
          expect(echoAjax.activeRequests.length).to.be.equal(3);
          for (var i = 0; i < 3; i++) {
            respondToEchoRequest(server.requests[i]);
          }
          return promiseAllComplete.then(function() {
            return timePasses(1);
          }).then(function() {
            expect(echoAjax.activeRequests.length).to.be.equal(0);
          });
        });

        test('avoids race conditions with last response', function() {
          expect(echoAjax.lastResponse).to.be.equal(undefined);

          // Resolving the oldest request doesn't update lastResponse.
          respondToEchoRequest(server.requests[0]);
          return requests[0].completes.then(function() {
            expect(echoAjax.lastResponse).to.be.equal(undefined);

            // Resolving the most recent request does!
            respondToEchoRequest(server.requests[2]);
            return requests[2].completes;
          }).then(function() {
            expect(echoAjax.lastResponse).to.be.deep.eql(
                {url: '/echoes_request_url?order=3'});


            // Resolving an out of order stale request after does nothing!
            respondToEchoRequest(server.requests[1]);
            return requests[1].completes;
          }).then(function() {
            expect(echoAjax.lastResponse).to.be.deep.eql(
                {url: '/echoes_request_url?order=3'});
          });
        });

        test('`loading` is true while the last one is loading', function() {
          expect(echoAjax.loading).to.be.equal(true);

          respondToEchoRequest(server.requests[0]);
          return requests[0].completes.then(function() {
            // We're still loading because requests[2] is the most recently
            // made request.
            expect(echoAjax.loading).to.be.equal(true);

            respondToEchoRequest(server.requests[2]);
            return requests[2].completes;
          }).then(function() {
            // Now we're done loading.
            expect(echoAjax.loading).to.be.eql(false);

            // Resolving an out of order stale request after should have
            // no effect.
            respondToEchoRequest(server.requests[1]);
            return requests[1].completes;
          }).then(function() {
            expect(echoAjax.loading).to.be.eql(false);
          });
        });
      });

      suite('when params are changed', function() {
        test('generates a request that reflects the change', function() {
          ajax = fixture('ParamsGet');
          request = ajax.generateRequest();

          expect(request.xhr.url).to.be.equal('/responds_to_get_with_json?a=a');

          ajax.params = {b: 'b'};
          request = ajax.generateRequest();

          expect(request.xhr.url).to.be.equal('/responds_to_get_with_json?b=b');
        });
      });

      suite('when `auto` is enabled', function() {
        setup(function() {
          ajax = fixture('AutoGet');
        });

        test('automatically generates new requests', function() {
          return new Promise(function(resolve) {
            ajax.addEventListener('request', function() {
              resolve();
            });
          });
        });

        test('does not send requests if url is not a string', function() {
          return new Promise(function(resolve, reject) {
            ajax.addEventListener('request', function() {
              reject('A request was generated but url is null!');
            });

            ajax.url = null;
            ajax.handleAs = 'text';

            Polymer.Base.async(function() {
              resolve();
            }, 1);
          });
        });

        test('deduplicates multiple changes to a single request', function() {
          return new Promise(function(resolve, reject) {
            ajax.addEventListener('request', function() {
              server.respond();
            });

            ajax.addEventListener('response', function() {
              try {
                expect(ajax.activeRequests.length).to.be.eql(1);
                resolve()
              } catch (e) {
                reject(e);
              }
            });

            ajax.handleas = 'text';
            ajax.params = { foo: 'bar' };
            ajax.headers = { 'X-Foo': 'Bar' };
          });
        });

        test('automatically generates new request when a sub-property of params is changed', function(done) {
          ajax.addEventListener('request', function() {
            server.respond();
          });

          ajax.params = { foo: 'bar' };
          ajax.addEventListener('response', function() {
            ajax.addEventListener('request', function() {
              done();
            });

            ajax.set('params.foo', 'xyz');
          });
        });
      });

      suite('the last response', function() {
        setup(function() {
          request = ajax.generateRequest();
          server.respond();
        });

        test('is accessible as a readonly property', function() {
          return request.completes.then(function (request) {
            expect(ajax.lastResponse).to.be.equal(request.response);
          });
        });


        test('updates with each new response', function() {
          return request.completes.then(function(request) {

            expect(request.response).to.be.an('object');
            expect(ajax.lastResponse).to.be.equal(request.response);

            ajax.handleAs = 'text';
            request = ajax.generateRequest();
            server.respond();

            return request.completes;
          }).then(function(request) {
            expect(request.response).to.be.a('string');
            expect(ajax.lastResponse).to.be.equal(request.response);
          });
        });
      });

      suite('when making POST requests', function() {
        setup(function() {
          ajax = fixture('TrivialPost');
        });

        test('POSTs the value of the `body` attribute', function() {
          var requestBody = JSON.stringify({foo: 'bar'});

          ajax.body = requestBody;
          ajax.generateRequest();

          expect(server.requests[0]).to.be.ok;
          expect(server.requests[0].requestBody).to.be.equal(requestBody);
        });

        test('if `contentType` is set to form encode, the body is encoded',function() {
          ajax.body = {foo: 'bar\nbip', 'biz bo': 'baz blar'};
          ajax.contentType = 'application/x-www-form-urlencoded';
          ajax.generateRequest();

          expect(server.requests[0]).to.be.ok;
          expect(server.requests[0].requestBody).to.be.equal(
              'foo=bar%0D%0Abip&biz+bo=baz+blar');
        });

        test('if `contentType` is json, the body is json encoded', function() {
          var requestObj = {foo: 'bar', baz: [1,2,3]}
          ajax.body = requestObj;
          ajax.contentType = 'application/json';
          ajax.generateRequest();

          expect(server.requests[0]).to.be.ok;
          expect(server.requests[0].requestBody).to.be.equal(
              JSON.stringify(requestObj));
        });

        suite('the examples in the documentation work', function() {
          test('json content, body attribute is an object', function() {
            ajax.setAttribute('body', '{"foo": "bar baz", "x": 1}');
            ajax.contentType = 'application/json';
            ajax.generateRequest();

            expect(server.requests[0]).to.be.ok;
            expect(server.requests[0].requestBody).to.be.equal(
                '{"foo":"bar baz","x":1}');
          });

          test('form content, body attribute is an object', function() {
            ajax.setAttribute('body', '{"foo": "bar baz", "x": 1}');
            ajax.contentType = 'application/x-www-form-urlencoded';
            ajax.generateRequest();

            expect(server.requests[0]).to.be.ok;
            expect(server.requests[0].requestBody).to.be.equal(
                'foo=bar+baz&x=1');
          });
        });

        suite('and `contentType` is explicitly set to form encode', function() {
          test('we encode a custom object', function() {
            function Foo(bar) { this.bar = bar };
            var requestObj = new Foo('baz');
            ajax.body = requestObj;
            ajax.contentType = 'application/x-www-form-urlencoded';
            ajax.generateRequest();

            expect(server.requests[0]).to.be.ok;
            expect(server.requests[0].requestBody).to.be.equal('bar=baz');
          });
        })

        suite('and `contentType` isn\'t set', function() {
          test('we don\'t try to encode an ArrayBuffer', function() {
            var requestObj = new ArrayBuffer()
            ajax.body = requestObj;
            ajax.generateRequest();

            expect(server.requests[0]).to.be.ok;
            // We give the browser the ArrayBuffer directly, without trying
            // to encode it.
            expect(server.requests[0].requestBody).to.be.equal(requestObj);
          });
        })
      });

      suite('when debouncing requests', function() {
        setup(function() {
          ajax = fixture('DebouncedGet');
        });

        test('only requests a single resource', function() {
          ajax._requestOptionsChanged();
          expect(server.requests[0]).to.be.equal(undefined);
          ajax._requestOptionsChanged();
          return timePasses(200).then(function() {
            expect(server.requests[0]).to.be.ok;
          });
        });
      });

      suite('when a response handler is bound', function() {
        var responseHandler;

        setup(function() {
          responseHandler = sinon.spy();
          ajax.addEventListener('response', responseHandler);
        });

        test('calls the handler after every response', function() {
          ajax.generateRequest();
          ajax.generateRequest();

          server.respond();

          return ajax.lastRequest.completes.then(function() {
            expect(responseHandler.callCount).to.be.equal(2);
          });
        });
      });

      suite('when the response type is `json`', function() {
        setup(function() {
          server.restore();
        });

        test('finds the JSON on any platform', function() {
          ajax.url = '../bower.json';
          request = ajax.generateRequest();
          return request.completes.then(function() {
            expect(ajax.lastResponse).to.be.instanceOf(Object);
          });
        });
      });

      suite('when handleAs parameter is `text`', function() {

        test('response type is string', function () {
          ajax.url = '/responds_to_get_with_json';
          ajax.handleAs = 'text';

          request = ajax.generateRequest();
          var promise = request.completes.then(function () {
            expect(typeof(ajax.lastResponse)).to.be.equal('string');
          });

          expect(server.requests.length).to.be.equal(1);
          expect(server.requests[0].requestHeaders['accept']).to.be.equal(
            'text/plain');
          server.respond();

          return promise;
        });

      });

      suite('when a request fails', function() {
        test('we give an error with useful details', function() {
          ajax.url = '/responds_to_get_with_502_error_json';
          ajax.handleAs = 'json';
          var eventFired = false;
          ajax.addEventListener('error', function(event) {
            expect(event.detail.request).to.be.okay;
            expect(event.detail.error).to.be.okay;
            eventFired = true;
          });
          var request = ajax.generateRequest();
          var promise = request.completes.then(function() {
            throw new Error('Expected the request to fail!');
          }, function(error) {
            expect(error).to.be.instanceof(Error);
            expect(request.succeeded).to.be.eq(false);
            return timePasses(100);
          }).then(function() {
            expect(eventFired).to.be.eq(true);
            expect(ajax.lastError).to.not.be.eq(null);
          });

          server.respond();

          return promise;
        });

        test('we give a useful error even when the domain doesn\'t resolve', function() {
          ajax.url = 'http://nonexistant.example.com/';
          server.restore();
          var eventFired = false;
          ajax.addEventListener('error', function(event) {
            expect(event.detail.request).to.be.okay;
            expect(event.detail.error).to.be.okay;
            eventFired = true;
          });
          var request = ajax.generateRequest();
          var promise = request.completes.then(function() {
            throw new Error('Expected the request to fail!');
          }, function(error) {
            expect(request.succeeded).to.be.eq(false);
            expect(error).to.not.be.eq(null);
            return timePasses(100);
          }).then(function() {
            expect(eventFired).to.be.eq(true);
            expect(ajax.lastError).to.not.be.eq(null);
          });

          server.respond();

          return promise;
        });
      });

      suite('when handleAs parameter is `json`', function() {

        test('response type is string', function () {
          ajax.url = '/responds_to_get_with_json';
          ajax.handleAs = 'json';

          request = ajax.generateRequest();
          var promise = request.completes.then(function () {
            expect(typeof(ajax.lastResponse)).to.be.equal('object');
          });

          expect(server.requests.length).to.be.equal(1);
          expect(server.requests[0].requestHeaders['accept']).to.be.equal(
            'application/json');

          server.respond();

          return promise;
        });

      });

      suite('when making a POST over the wire', function() {
        test('FormData is handled correctly', function() {
          server.restore();
          var requestBody = new FormData();
          requestBody.append('a', 'foo');
          requestBody.append('b', 'bar');

          var ajax = fixture('RealPost');
          ajax.body = requestBody;
          return ajax.generateRequest().completes.then(function() {
            expect(ajax.lastResponse.headers['Content-Type']).to.match(
                /^multipart\/form-data; boundary=.*$/);

            expect(ajax.lastResponse.form.a).to.be.equal('foo');
            expect(ajax.lastResponse.form.b).to.be.equal('bar');
          });
        });

        test('json is handled correctly', function() {
          server.restore();
          var ajax = fixture('RealPost');
          ajax.body = JSON.stringify({a: 'foo', b: 'bar'});
          ajax.contentType = 'application/json';
          return ajax.generateRequest().completes.then(function() {
            expect(ajax.lastResponse.headers['Content-Type']).to.match(
                /^application\/json(;.*)?$/);
            expect(ajax.lastResponse.json.a).to.be.equal('foo');
            expect(ajax.lastResponse.json.b).to.be.equal('bar');
          });
        });

        test('urlencoded data is handled correctly', function() {
          server.restore();
          var ajax = fixture('RealPost');
          ajax.body = 'a=foo&b=bar';
          return ajax.generateRequest().completes.then(function() {
            expect(ajax.lastResponse.headers['Content-Type']).to.match(
                /^application\/x-www-form-urlencoded(;.*)?$/);

            expect(ajax.lastResponse.form.a).to.be.equal('foo');
            expect(ajax.lastResponse.form.b).to.be.equal('bar');
          });
        });

        test('xml is handled correctly', function() {
          server.restore();
          var ajax = fixture('RealPost');

          var xmlDoc = document.implementation.createDocument(
              null, "foo", null);
          var node = xmlDoc.createElement("bar");
          node.setAttribute("name" , "baz");
          xmlDoc.documentElement.appendChild(node);
          ajax.body = xmlDoc;
          return ajax.generateRequest().completes.then(function() {
            expect(ajax.lastResponse.headers['Content-Type']).to.match(
                /^application\/xml(;.*)?$/);
            expect(ajax.lastResponse.data).to.match(
                /<foo\s*><bar\s+name="baz"\s*\/><\/foo\s*>/);
          });
        });
      });

      suite('when setting timeout', function() {
        setup(function() {
          server.restore();
        });

        test('it is present in the request xhr object', function () {
          ajax.url = '/responds_to_get_with_json';
          ajax.timeout = 5000; // 5 Seconds

          request = ajax.generateRequest();
          expect(request.xhr.timeout).to.be.equal(5000); // 5 Seconds
        });

        test('it fails once that timeout is reached', function () {
          var ajax = fixture('Delay');
          ajax.timeout = 1; // 1 Millisecond

          request = ajax.generateRequest();
          return request.completes.then(function () {
            throw new Error('Expected the request to throw an error.');
          }, function() {
            expect(request.succeeded).to.be.equal(false);
            expect(request.xhr.status).to.be.equal(0);
            expect(request.timedOut).to.be.equal(true);
            return timePasses(1);
          }).then(function() {
            expect(ajax.loading).to.be.equal(false);
            expect(ajax.lastResponse).to.be.equal(null);
            expect(ajax.lastError).to.not.be.equal(null);
          });
        });
      });

    });
  </script>

</body>
</html>
