2013-09-30 3 views
5

В моем сценарии, мне нужно получить словарь, чтобы преобразовать кодированные значения в именах:Условные обещания

$.ajax({ 
    // retrieve dictionary 
}) 
.done(function(dictionary){ 
    // convert encoded values into names 
}) 
.done(function(){ 
    // run my application 
}); 

Однако, иногда словарь уже загружен другим приложением, и в этом случае я не нужен АЯКС вызов:

if (dictionary) { 
    // convert encoded values into names 
    // run my application 
} 
else { 
$.ajax({ 
    // retrieve dictionary 
}) 
.done(function(dictionary){ 
    // convert encoded values into names 
}) 
.done(function(){ 
    // run my application 
}); 
} 

Это, если/другое заявление является довольно тяжелым, есть способ, чтобы сделать его короче:

// load dictionary if needed 
// then run my application 

Примечание: я использовал знак $ для моего псевдокода, но я не обязательно привязан к jQuery.

+1

В моих приложениях я делаю это довольно много. Дело в том, что если данные будут получены асинхронно, тогда вы ДОЛЖНЫ получить доступ к ним с помощью асинхронных методов независимо от того, было ли это уже получено или нет - причина при каждом использовании, вы не знаете, являются ли данные сразу же доступен или необходимо его получить. –

+0

@ Beetroot-Beetroot вы могли бы объяснить, как вы получаете доступ к уже полученным данным с помощью асинхронных методов? Может быть, ответьте с кодом или псевдокодом? – Christophe

+0

См. Ответы, уже опубликованные. Это то, что ребята пытаются объяснить. –

ответ

0

Может создать фиктивное обещание с $ .when?

var promise; 
if (dictionary) promise = $.when(dictionary); 
else { 
    promise = $.ajax({ 

    }) 
    .done(function(dictionary){ 
     // convert encoded values into names 
    }); 
} 

promise 
    .done(function(){ 
     // run my application 
    }); 
2

Вы должны позвонить $.ajax() ровно один раз и сохранить возвращенное обещание в переменной (global-ish) dictionary.

Затем, каждый раз, когда вы хотите использовать результат, просто напишите dictionary.then(...).
Если запрос AJAX уже завершен, обратный вызов будет запущен немедленно.

+1

Ну, это не так, как это работает. Как я уже сказал в вопросе, даже когда мой код начинается, словарь может уже присутствовать (загружается другим скриптом, который не под моим контролем), и в этом случае мне даже не нужен первый вызов ajax. Например, словарь может храниться в localStorage. – Christophe

+0

@Christophe: Затем установите глобальное значение в заранее разрешенное обещание и вызовите '.then()' в любом случае. – SLaks

+0

ОК, вот что я пытаюсь понять, как написать условное обещание. – Christophe

3

Это образец, который я обычно использую:

var done = function() { 
    //continue loading application 
} 

if(!dictionary) { 
    $.ajax({ 

    }) 
     .done(done); 
} else { 
    done.apply(this); 
} 

Очень похожая картина, которая всегда делает использование отложенного объекта, может быть следующие:

var 
    dictionaryDeferred = new $.Deferred(), 
    dictionaryPromise = dictionaryDeferred.promise(); 

if(!dictionary) { 
    $.ajax({ 

    }) 
     .done(function() { 
      //do something with the response 
      dictionaryDeferred.resolve(); 
     }); 
} else { 
    dictionaryDeferred.resolve(); 
} 

dictionaryPromise.then(function() { 
    //continue loading application 
}); 
+0

Спасибо. Мне нравится второй образец лучше, так как он упрощает цепочку. Одна из проблем может заключаться в том, что разрешенное значение словаря Promise несовместимо между двумя ветвями (но не проблема в моем случае, поскольку словарь является глобальной переменной). – Christophe

+0

Вам не нужно использовать 'DictionaryPromise' в обоих местах, где может потребоваться словарь, вы можете просто использовать его в этом месте, где приложение загружается, если хотите, потому что вы по-прежнему проверяете' if (! Dictionary) 'уже существует здесь или нет. – Adam

+0

Зачем использовать 'new' с $ .Deferred(), когда использование 'new' является необязательным? –

Смежные вопросы