2016-04-24 5 views
5

Diciamo che ho una funzione sincrona come path.join(). Voglio racchiuderlo in un Promise perché voglio che le excetions siano gestite nel blocco catch(). Se mi avvolgo come di seguito, non posso fare eccezione nel blocco .catch().catch(). Quindi devo usare if per controllare il valore di ritorno, se si tratta di un errore o meno e quindi chiamare risolvere, rifiutare le funzioni. ci sono altre soluzioni?Qual è il modo migliore per racchiudere le funzioni sincrone in una promessa

var joinPaths = function(path1,path2) { 
    return new promise(function (resolve, reject) { 
    resolve(path.join(path1, path2)); 
    }); 
}; 
+2

Perché vuoi racchiudere una funzione sincrona in una promessa? –

+1

Il test delle unità è un caso comune quando è necessario sostituire una chiamata asincrona con un valore codificato –

+1

Il modo migliore per includere una funzione sincrona in una promessa non è farlo. – Bergi

risposta

6

Non è chiaro il motivo per cui si dovrebbe avvolgere un funzionamento sincrono in una promessa che rende solo più difficile da usare e operazioni sincrone può già essere utilizzato all'interno di catene promessa più che bene.

Gli unici due punti in cui ho ritenuto utile promettere qualcosa di sincrono sono l'avvio di una catena di promettenti in cui le operazioni successive saranno asincrone o in fase di ramificazione e un risultato del ramo è promessa asincrona e il l'altro è sincrono. Quindi, in questo caso, si desidera solo restituire una promessa in entrambi i casi in modo che il chiamante abbia un'interfaccia asincrona coerente indipendentemente dal ramo.

Oltre a ciò, in genere non si dovrebbero rendere asincroni le cose sincrone perché complicano inutilmente l'uso di esse.

Il modo più semplice che conosco per farne una promessa sarebbe questo:

Promise.resolve(path.join(path1, path2)).then(function(path) { 
    // use the result here 
}); 

Per i vostri commenti, all'interno di un gestore .then(), le eccezioni sono già catturati dall'infrastruttura promessa e trasformato in una promessa respinto . Quindi, se avessi questo:

someAsyncOp().then(function(value) { 
    // some other stuff 
    // something that causes an exception 
    throw new Error("timeout"); 
}).catch(function(err){ 
    console.log(err); // will show timeout 
}); 

Quindi, quell'eccezione è già mappata in un rifiuto di promessa per te. Naturalmente, se si desidera gestire l'eccezione all'interno del gestore .then() (non trasformare la promessa in un rifiuto), è possibile utilizzare semplicemente un try/catch tradizionale attorno all'operazione sincrona per rilevare un'eccezione locale (non diversa da qualsiasi altra codice sincrono). Ma se vuoi che la promessa venga rifiutata se c'è un'eccezione nel gestore .then(), allora tutto è fatto automaticamente (una caratteristica molto bella delle promesse).

+0

Se sto usando 'path.join' nella catena di promesse e voglio gestire le eccezioni nel blocco' .catch() 'di' promise', come posso farlo con fuori avvolgendolo in una promessa? – CoderS

+2

@Srinesh - Come sempre, se metti il ​​tuo codice effettivo e il problema reale nella tua domanda, possiamo aiutarti molto meglio. Non seguo esattamente quello che stai cercando di fare. Un handler '.then()' in una catena di promesse è già avvolto in un try/catch e qualsiasi eccezione lanciata in un gestore '.then()' rifiuterà automaticamente la catena delle promesse. Non devi fare nulla per ottenere quella funzionalità all'interno di un gestore '.then()'. Puoi anche usare try/catch te stesso per catturare un'eccezione sincrona e gestirla localmente. – jfriend00

+1

Uno dei motivi per cui si consiglia di racchiudere una funzione sincrona in una promessa è se si sta tentando di attenersi a un contratto, ad esempio 'if (needsUpdating) {return object.asyncUpdate(); } else {return object}; 'Se un percorso restituisce una Promessa, allora dovrebbe essere l'altro percorso, anche se non esegue alcun codice asincrono. –

Problemi correlati