Meteor: Utilizzo di librerie sincrone - wrapAsync e bindEnvironment
###Che cosa Meteor.wrapAsync e Meteor.bindEnvironment?
Nella Parte 1, abbiamo visto come Meteor ha astratto il codice asincrono utilizzando Fibers e ha fornito un modo semplice per scrivere JS in stile sincrono. Nella parte 2 abbiamo capito come lavorare con le librerie asincrone pure
Utilizzando Fibers possiamo modificare una funzione asincrona, per scrivere codice sincrono come il codice. Ma cosa succede quando non possiamo modificare la funzione come nel caso di librerie di terze parti?
A ShareThis, la nostra applicazione Meteor utilizza Amazon S3 come livello di memorizzazione dei dati e cache. Dalla documentazione di Amazon S3, la firma del metodo JavaScript da aggiungere ad un secchio S3 sembra
“`
getObject(params = {}, callback) ⇒ AWS.Request
//This is how the function would look in Meteor server code
S3.putObject({
Secchio: "sharethis-salone",
Chiave : chiave,
Corpo : dati
}, function(err, result){
se(risultato){
console.log ("Fatto");
//optionally pass in callback
}
});
“`
Il codice di cui sopra non funzionerà come previsto, in quanto il richiamo a S3.putObject non è legato alla Fibra corrente
In questo caso d'uso, usiamo Meteor.wrapAsync e per avvolgere la funzione asincrona nella Fibra corrente
###Che cosa fa Meteor.wrapAsync?
Meteor.wrapAsync prende il metodo che gli si dà come primo parametro e lo esegue nella fibra corrente.
Inoltre vi allega un callback (assume lo stile tradizionale del nodo di usare un callback, cioè il metodo prende un callback come parametro finale con due argomenti (errore e risultato) di cui uno o l'altro sarà nullo a seconda del risultato della chiamata
Il richiamo è legato a Meteor.bindEnvironment e blocca la Fibra corrente fino a quando il richiamo non viene attivato. Non appena la callback spara, restituisce il risultato o lancia l'errore.
"Javascript
funzione synchronousFunc(){
ritorno Meteor.wrapAsync(asyncFunction)
}
“`
**Come si accede all'oggetto errore utilizzando le funzioni wrapped sincrone restituite da Meteor.wrapAsync?
Un metodo è l'utilizzo di blocchi try/catch, perché in caso di errore, sarà lanciato dalla funzione sync invece di essere passato come primo argomento della funzione async callback.
”`
provare{
var result=synchronousFunc(params);
console.log ("Successo :",risultato);
}
catch(error){
console.log ("Errore:",errore);
}
// which is equivalent to –
asyncFunction(params,function(error,result){
se(errore)
console.log ("errore",errore);
altro
console.log ("risultato :",risultato);
});
“`
Questo è ottimo per convertire il codice asincrono in codice sincrono, poiché è possibile utilizzare il risultato del metodo sulla riga successiva invece di utilizzare un callback e/o nidificare funzioni più profonde. Si occupa anche di legare il callback alla fibra corrente (usando Meteor.bindEnvironment) per voi.
Un'ultima nota, se si vuole che il richiamo alla funzione di libreria asincrona faccia qualcosa di più (solo perché) si deve usare esplicitamente Meteor.bindEnvironment oppure si ottiene un errore che afferma che il codice Meteor deve sempre girare all'interno di una Fibra.
”`
var func = function(cb){
S3.putObject(params, Meteor.bindEnvironment(function(err, data) {
se (err){
lanciare un nuovo Meteor.Error ("Storage on S3 Failed");
} else{
console.log ("Dati memorizzati con successo su S3");
cb(nullo, dati);
}
}));
};
return (Meteor.wrapAsync(func))();
“`
Pochi Gotchas di cui bisogna essere consapevoli quando si utilizza Meteor.wrapAsync
Si intende lavorare con funzioni di async puro che si aspettano un richiamo con errore e risultato come argomenti. Inoltre, funzionano solo sul lato server (poiché non è possibile utilizzare Fibre sul lato client)
I metodi lato server come Meteor.HTTP.call sono già confezionati in questo modo. Se lo si chiama senza un callback, il metodo si blocca fino a quando la risposta non viene ricevuta. Altrimenti, tornerà immediatamente ed eseguirà il callback una volta ricevuta la risposta di rete.