Last active
January 26, 2022 11:03
Mixing Promises And async / await For Caching Purposes In JavaScript
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
figure.mouseenter( handleFigureMouseenter ); | |
// ... | |
function handleFigureMouseenter() { | |
figure.off( "mouseenter", handleFigureMouseenter ); | |
// Just preload a single image in each direction (Prev and Next). | |
preCachePrevPhoto( +prevPhoto.data( "rel" ), 1 ); | |
preCacheNextPhoto( +nextPhoto.data( "rel" ), 1 ); | |
} |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
async function preCacheNextPhoto( photoID, wiggleRoom = 3 ) { | |
// All recursive algorithms needs a base-case that will cause the recursion | |
// to halt. When we run out of wiggle room, stop recursing. | |
if ( wiggleRoom <= 0 ) { | |
return; | |
} | |
if ( ! cache[ photoID ] ) { | |
// CAUTION: The ApiClient returns PROMISES. Our cache is going to be | |
// filled with Promises, not with raw photo data. | |
cache[ photoID ] = apiClient.makeRequest({ | |
url: "/index.cfm", | |
params: { | |
event: "api.sitePhotos.photo", | |
index: photoID | |
} | |
}); | |
} | |
try { | |
// BLOCK AND WAIT for Promise RESOLUTION (ie, the raw photo data). | |
var response = await cache[ photoID ]; | |
// Warm up the browser cache for this image binary. | |
new Image().src = response.src; | |
// Recursively cache the next photo. Note that we are NOT AWAITING this | |
// recursive call since we are not consuming the response. We also | |
// don't want any failures within the recursion to clear the cache for | |
// the current ID. | |
preCacheNextPhoto( response.nextPhotoID, --wiggleRoom ); | |
} catch ( error ) { | |
// If something goes wrong, let's assume that the cached Promise is | |
// problematic (a rejection) and delete it. This way, the next request | |
// will attempt to fetch and re-cache it. | |
delete( cache[ photoID ] ); | |
console.warn( "Could not pre-cache next photo." ); | |
console.error( error ); | |
} | |
} |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
async function showNextPhoto( photoID ) { | |
if ( ! cache[ photoID ] ) { | |
cache[ photoID ] = apiClient.makeRequest({ | |
url: "/index.cfm", | |
params: { | |
event: "api.sitePhotos.photo", | |
index: photoID | |
} | |
}); | |
} | |
try { | |
var response = await cache[ photoID ]; | |
renderPhotoResponse( response ); | |
// While the user is looking at the photo that we just rendered, let's | |
// pre-cache more photos in the background. This way, by the time the | |
// user goes to hit the NEXT PHOTO button, we'll (hopefully) have | |
// already loaded that data and can render it immediately. Note that we | |
// are NOT AWAITING this response since we don't care when it completes. | |
preCacheNextPhoto( response.nextPhotoID ); | |
} catch ( error ) { | |
/// If something goes wrong, let's assume that the cached Promise is | |
// problematic (a rejection) and delete it. This way, the next request | |
// will attempt to fetch and re-cache it. | |
delete( cache[ photoID ] ); | |
console.warn( "Could not show next photo information." ); | |
console.error( error ); | |
} | |
} |
Yes, good catch! I had just hand-written the code into the article (since it was heavily truncated).
@stefanjudis consider it fixed.
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment
@bennadel Hey Ben, I'm just reading your article including these snippets and I think you might have a typo here:
handeFigureMouseenter
->handleFigureMouseenter
?Thanks for the article!