2015-09-10 2 views
5

Je construis une validation de formulaire et d'apprendre des promesses que j'ai décidé de mettre en œuvre des fonctions de validation asynchrone à l'aide modèle de promesse:ABORT ajax dans une promesse

var validateAjax = function(value) { 
    return new Promise(function(resolve, reject) { 
     $.ajax('data.json', {data: {value: value}}).success(function(data, status, xhr) { 
      if (data.valid) { 
       resolve(xhr) 
      } 
      else { 
       reject(data.message) 
      } 
     }).error(function(xhr, textStatus) { 
      reject(textStatus) 
     }) 
    }) 
} 

//... 
var validators = [validateAjax]; 
$('body').delegate('.validate', 'keyup', function() { 
    var value = $('#the-input').val(); 
    var results = validators.map(function(validator) { 
     return validator(input) 
    }); 

    var allResolved = Promise.all(results).then(function() { 
     //... 
    }).catch(function() { 
     //... 
    }) 
}); 

Cela semble fonctionner très bien, l'entrée est validée comme les types d'utilisateurs (le code est simplifié pour ne pas être trop long, par exemple le délai d'expiration après que le code est manquant, etc.).

Maintenant, je me demande comment tuer la requête ajax si la validation de l'événement de keyup précédent est toujours en cours. Est-il en quelque sorte possible de détecter dans quel état la promesse est et éventuellement de rejeter la promesse de l'extérieur?

Répondre

8

L'annulation de la promesse est actuellement en cours de spécification, il n'y a pas de manière intégrée pour le faire encore (il vient cependant). Nous pouvons mettre en œuvre nous-mêmes:

var validateAjax = function(value) { 
    // remove explicit construction: http://stackoverflow.com/questions/23803743 
    var xhr = $.ajax('data.json', {data: {value: value}}); 
    var promise = Promise.resolve(xhr).then(function(data){ 
     if(!data.isValid) throw new Error(data.message); // throw errors 
     return data; 
    }); 
    promise.abort = function(){ 
     xhr.abort(); 
    }); 
    return promise; 
} 

Maintenant, nous pouvons tuer le validateAjax appelle en appelant abort sur la promesse:

var p = validateAjax("..."); // make request 
p.abort(); // abort it; 
+0

Grand, je l'obtiens, merci pour votre réponse. Quoi qu'il en soit en ce qui concerne la suppression de la construction explicite - le xhr doit toujours être renvoyé par la fonction validateAjax, n'est-ce pas? –

+0

votre validateAjax renvoie undefined - manque-t-il une ligne? –

+0

@LukasKral - Je pense que le var 'promet' devrait être retourné, car il a la fonction' .abort' - mais je n'ai pas écrit le code, donc je ne peux que spéculer –