If you have ever rendered a list of images from untrusted data, you know the pattern. Most URLs are fine, a few are dead, and the broken-image icon ruins the layout. You can wrap everything in try/catch, or you can ask the browser directly: can you load this?
That is what checkUrl does. It returns a Promise that resolves when the image loads and rejects when it does not. No fetch, no CORS handling, and no manual HEAD requests.
The idea
A Promise that resolves or rejects based on whether the image loads:
// success
const promise = new Promise<void>((resolve, reject) => { resolve() })
// failure
const promise = new Promise<void>((resolve, reject) => { reject() })
Using the built-in Image object
Inside the callback, create an Image, wire up onload and onerror, and then set src to start the request.
const img = new Image();
img.onload = () => resolve();
img.onerror = () => reject();
img.src = url;
That is the entire mechanism. The browser does the work, and the Promise is a thin wrapper around two events.
Using it with a fallback
The most common use case is swapping to a fallback when the original URL is broken.
const fallbackImage = 'https://example.com/fallback.png';
let url: string = anonymousOBJECT.image;
const checkImage = async () => {
try {
await checkUrl(url);
// valid, keep the original
} catch {
// invalid, swap in the fallback
url = fallbackImage;
}
};
checkImage();
<img :src="url" />
No custom error handling in the template, no flicker of a broken image, and a resolved URL by the time it hits the DOM.
Originally published on LinkedIn.

