Skip to content

feat: improve HEIC, HEIF and JPEG XL browser support detection#26122

Open
nicosemp wants to merge 1 commit intoimmich-app:mainfrom
nicosemp:nicosemp/feat-heic-heif-browser-support-detection
Open

feat: improve HEIC, HEIF and JPEG XL browser support detection#26122
nicosemp wants to merge 1 commit intoimmich-app:mainfrom
nicosemp:nicosemp/feat-heic-heif-browser-support-detection

Conversation

@nicosemp
Copy link
Contributor

@nicosemp nicosemp commented Feb 11, 2026

Description

Following up on #25599, this PR improves browser support detection for JXL, and HEIC/HEIF mime types by:

  • Detecting support on any new browser that adds it.
    • Adds support for Chrome stable and Firefox nightly with the jxl flag enabled, as well as Zen Browser (flag enabled by default).
  • Excluding Safari versions <17 that don't support these mime types.

Details

The HEIC image was generated with ImageMagick from a 1x1 white PNG with this command:

./magick input.png -strip output.heic

and then turned into a base64 string:

base64 -w 0 output.heic > heic_b64.txt

Changing the output to .heif instead of .heic yields the same result, so I guess any browser supporting one format would support the other one too? If this is certainly true I can remove the redundant HEIF test, otherwise it's best to keep it.

Unfortunately the resulting string can't be as short as JPEG XL, but it's the shortest I could achieve.
If anyone else wants to improve it later, this slide suggests a theoretical minimum size of """only""" 386 bytes.

How Has This Been Tested?

Unfortunately this change would need tests running on different browsers to be validated:

  • Copy the added code, along with the supportedImageMimeTypes definition and test the added mime types on:
    • Safari -> it should add jxl, heic and heif.
    • Chrome -> it should not add anything.
    • Chrome with the #enable-jxl-image-format flag on -> it should add jxl.
    • Firefox -> it should not add anything.
    • Firefox nightly with the image.jxl.enabled flag turned on in about:config -> it should add jxl.
    • Zen Browser -> it should add jxl.
  • Tested isSecureContext on secure and insecure contexts.
  • Tested ImageDecoder.isTypeSupported on browsers with and without support for jxl, heic and heif mime types.
  • Tested the fallback support detection with base64 images (also tested in the previous PR).

Checklist:

  • I have performed a self-review of my own code
  • I have made corresponding changes to the documentation if applicable
  • I have no unrelated changes in the PR.
  • I have confirmed that any new dependencies are strictly necessary.
  • I have written tests for new code (if applicable)
  • I have followed naming conventions/patterns in the surrounding code
  • All code in src/services/ uses repositories implementations for database calls, filesystem operations, etc.
  • All code in src/repositories/ is pretty basic/simple and does not have any immich specific logic (that belongs in src/services/)

Please describe to which degree, if any, an LLM was used in creating this pull request.

No LLM.

Copy link
Member

@mertalev mertalev left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Just a thought, but maybe we don't need it to process a full valid HEIF. We just need to know if the browser is willing to decode it, right? Maybe a truncated HEIF would give a different kind of error on an HEIF-compatible browser than one that can't decode it?

@meesfrensel
Copy link
Collaborator

Just leaving this here as an fyi and a note for the future: the ImageDecoder.isTypeSupported does exactly what we want here. The one problem: safari doesn't support it. I don't know if/when they plan on implementing the api, but firefox only supports it since late 2024 so there's still hope.

@nicosemp
Copy link
Contributor Author

Long day, I just read the comments now. Thanks for the quick response as always.

@meesfrensel that's a great suggestion, didn't know it existed. The current code already checks for isSafari via the user agent, so we could use that to add jxl, heic and heif mime types. On other browsers - if (!isSafari) - we can use ImageDecoder.isTypeSupported for each mime type.

@mertalev if this sounds good I'll rework my PR.

Also Caniuse.com currently reports Safari 11-16.6 at 0.35% global usage, while version >=17.0 is at 0.77%. Nearly a third of Safari users don't have JPEG XL, HEIC or HEIF support.
The current isSafari implementation only checks for the browser, not its version. Safari < 17.0 still evaluates to true and will try displaying JPEG XL, HEIC and HEIF images even though they are not supported. Should I narrow the definition to take the version into account?

The alternative is to keep the base64 image check only for Safari, but maybe a version check in the userAgent is better.

@mertalev
Copy link
Member

Using ImageDecoder.isTypeSupported seems ideal. Between that and isSafari, it seems like that covers the bases without needing to decode anything. The check could be something like isSafari || (ImageDecoder.isTypeSupported && ImageDecoder.isTypeSupported(type)). There's no point in checking all the formats though - isTypeSupported only has 81.71% coverage and we know everything but HEIF and JXL is supported in that list.

Also Caniuse.com currently reports Safari 11-16.6 at 0.35% global usage, while version >=17.0 is at 0.77%. Nearly a third of Safari users don't have JPEG XL, HEIC or HEIF support.

It's worth noting this is only macOS - the vast majority of iOS devices support it. It's probably good to check it though.

@nicosemp nicosemp force-pushed the nicosemp/feat-heic-heif-browser-support-detection branch from 18b3f2a to a559de7 Compare February 12, 2026 00:37
@nicosemp nicosemp changed the title feat: HEIF and HEIC browser support detection feat: rework HEIC, HEIF and JPEG XL browser support detection Feb 12, 2026
@michelheusschen
Copy link
Collaborator

ImageDecoder is only available in secure contexts and I don't think it's reasonable to expect that everyone runs Immich in a secure context

@meesfrensel
Copy link
Collaborator

Sorry I missed that. The currently proposed implementation won't error or anything since it checks for if (ImageDecoder) but that does mean no heic/jxl image support in non-secure contexts. A combination of approaches would work but that'll get unwieldy...

@mertalev
Copy link
Member

Good point about secure contexts, but I think this is fine for now. The status quo before was that these formats were only added for Safari, so this PR extends that to other browsers in secure contexts.

@nicosemp
Copy link
Contributor Author

Does Immich use telemetry to know what percentage of users access the website in/outside a secure context? I only access it locally, so definitely no https.

Either way I'd rather add back the two base64 tests for non-secure contexts if that's ok with you. It would just use a window.isSecureContext check, so only 1 type of test would run for any browser+context combination, and this would allow maximum support.

@mertalev
Copy link
Member

Sure, I think that's okay.

@nicosemp nicosemp force-pushed the nicosemp/feat-heic-heif-browser-support-detection branch from a559de7 to a28e5f1 Compare February 13, 2026 11:20
@nicosemp nicosemp force-pushed the nicosemp/feat-heic-heif-browser-support-detection branch from a28e5f1 to 3f600c7 Compare February 20, 2026 15:35
@nicosemp nicosemp changed the title feat: rework HEIC, HEIF and JPEG XL browser support detection feat: improve HEIC, HEIF and JPEG XL browser support detection Feb 20, 2026
@nicosemp nicosemp force-pushed the nicosemp/feat-heic-heif-browser-support-detection branch from 3f600c7 to 8b47225 Compare February 23, 2026 10:47
@nicosemp nicosemp force-pushed the nicosemp/feat-heic-heif-browser-support-detection branch from 8b47225 to 0697027 Compare February 23, 2026 12:26
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Projects

None yet

Development

Successfully merging this pull request may close these issues.

6 participants