doron
doron

Reputation: 1538

Polymer 1.0 computed variable with ajax request

I'm trying to compute a polymer variable based on an ajax call with another variable as property.

For instance, I want to pass a variable like this:

<my-custom-element user-email="[email protected]"></my-custom-element>

And on the <my-custom-element> template to compute another boolean variable called exists and populate it with an ajax request to my server's user list.

When I try a regular ajax call I get nothing...

 Polymer({
  is: "my-custom-element",

  properties: {
    userEmail: {
      type: String,

    },
    exists: {
      type: Boolean,
      computed: '_getExistsFromEmail(userEmail)'
    }
  },
  _getExistsFromEmail: function(userEmail) {
    var xhr = new XMLHttpRequest();

    xhr.open('POST',
        encodeURI('http://api.test.im/land_emails'));
    xhr.setRequestHeader('Content-Type', 'application/x-www-form-urlencoded');
    var that = this;
    xhr.onload = function () {
      var responseJson = JSON.parse(xhr.responseText);

      if (xhr.status === 200 || xhr.status === 201) {
        if (responseJson.status) { // If user exists

          return true;

        }
        else { // User does not exists
          return false;
        }

      }

    };

    var params = "email=" + userEmail;
    xhr.send(encodeURI(params));
  }})

This doesn't work and the variable is not defined. How can I make it possible? Is it?

Upvotes: 0

Views: 315

Answers (1)

Maria
Maria

Reputation: 5604

The problem here is caused by the fact that the ajax callback is asynchronous. What you define in this function xhr.onload = function () { will be triggered when the ajax call has finished. Returning true or false in here does not have the effect of assigning the return value to exists. Rather, the return value of _getExistsFromEmail is assigned to exists, which is not defined. And because of the asynchronicity it also not possible to define it like that. However, you can achieve what you want as follows (assuming your ajax code works as expected).

Polymer({
    is: "my-custom-element",

    properties: {
        userEmail: {
          type: String
        },
        exists: {
          type: Boolean,
        }
    },

    observers: ['_getExistsFromEmail(userEmail)'],

    _getExistsFromEmail: function(userEmail) {
        var xhr = new XMLHttpRequest();

        xhr.open('POST',
            encodeURI('http://api.test.im/land_emails'));
        xhr.setRequestHeader('Content-Type', 'application/x-www-form-urlencoded');
        var that = this;
        xhr.onload = function () {
          var responseJson = JSON.parse(xhr.responseText);

          if (xhr.status === 200 || xhr.status === 201) {
            if (responseJson.status) { // If user exists

              this.exists = true;

            }
            else { // User does not exists
               this.exists = false;
            }

          }

        }.bind(this);

        var params = "email=" + userEmail;
        xhr.send(encodeURI(params));

    }
});

Whenever userEmail changes, _getExistsFromEmail is called. In there, exists is updated, whenever the ajax response is received.

Upvotes: 2

Related Questions