Skip to content

Instantly share code, notes, and snippets.

@XoseLluis
Created January 26, 2020 18:45
Show Gist options
  • Star 0 You must be signed in to star a gist
  • Fork 0 You must be signed in to fork a gist
  • Save XoseLluis/fdb379421cb6648dbd1331370f82eb34 to your computer and use it in GitHub Desktop.
Save XoseLluis/fdb379421cb6648dbd1331370f82eb34 to your computer and use it in GitHub Desktop.
Proxying sync and async methods
let calculator = {
simpleCalculation(n){
return 25 * n;
},
complexCalculation(n){
return new Promise(res => {
setTimeout(() => res(44 * n), 3000)
});
},
//mainly the same as the above
async complexCalculation2(n){
let res = await new Promise(res => {
setTimeout(() => res(44 * n), 3000)
});
return res;
}
}
let proxiedCalculator = new Proxy(calculator, {
get: function(target, property, receiver){
let it = target[property];
if (typeof it !== "function"){
return it;
}
return function(){
console.log("before invoking");
//we're not trapping additional calls done from this method, so we invoke the original method via "target" rather than via "this"
let result = target[property](...arguments);
//same as the above:
//let result = it.call(target, ...arguments);
if (result instanceof Promise){
return result.then(res => {
console.log("after completion of async function");
return res;
});
}
else{
console.log("after completion of sync function");
return result;
}
};
}
});
//THE BELOW APPROACH IS WRONG, it won't work properly for synchronous methods
let wronglyProxiedCalculator = new Proxy(calculator, {
get: function(target, property, receiver){
let it = target[property];
if (typeof it !== "function"){
return it;
}
//I can not do it like this, cause with the async I would be returning a Promise in both cases, so for the invoker of a sync function he gets a promise of X rathern than X, so that's not what he's expecting
return async function(){
//I'm not trapping additional calls done from this object
console.log("before invoking");
let result = target[property](...arguments);
//it.call(target, ...arguments);
if (result instanceof Promise){
let resolvedResult = await result;
console.log("after completion of async function");
return resolvedResult;
}
else{
console.log("after completion of sync function");
return result;
}
};
}
});
(async () => {
let result = proxiedCalculator.simpleCalculation(2);
console.log(result);
result = await proxiedCalculator.complexCalculation(2);
console.log(result);
console.log("- doing it the wrong way now:");
result = wronglyProxiedCalculator.simpleCalculation(2);
console.log(result);
//it prints: Promise { 50 }
//rather than 50
result = await wronglyProxiedCalculator.complexCalculation(2);
console.log(result);
})();
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment