Skip to content

Conversation

@xmo-odoo
Copy link
Contributor

Currently _cache is only populated on load, this is an issue with code which do a lot of locale parsing / instantiation but for one reason or an other rarely end up needing to actually load the locale data (e.g. date formatting with non-locale-dependent patterns) because every cache miss is an os.path.exists.

This change takes advantage of semantics differences between exists and load: exists just needs the entry to exist in the cache, while load needs the entry to be truthy. Thus exists can cache its lookup by setting an empty dict (or even None but that seems a bit too dodgy).

Alternatively we could remove the os.path.exists "slow path" and call normalize_locale every time, as locale_identifiers gets cached on first call, the initial call would be a lot more expensive but then no further exists would need to touch the filesystem.

For a third alternative, exists could be decorated with functools.cache, in order to have its own cache completely independent of load. load could also be migrated to functools.cache as, as far as I can tell, the localedata._cache is never invalidated anyway, with the drawback that a locale's data might be resolved multiple times if concurrent calls are tight enough (functools.cache synchronises the cache but not the resolution of the value).

Currently `_cache` is only populated on `load`, this is an issue with code which do a lot of locale parsing / instantiation but for one reason or an other rarely end up needing to actually load the locale data (e.g. date formatting with non-locale-dependent patterns) because every cache miss is an `os.path.exists`.

This change takes advantage of semantics differences between `exists` and `load`: `exists` just needs the entry to exist in the cache, while `load` needs the entry to be truthy. Thus `exists` can cache its lookup by setting an empty dict (or even `None` but that seems a bit too dodgy).

Alternatively we could remove the `os.path.exists` "slow path" and call `normalize_locale` every time, as `locale_identifiers` gets cached on first call, the initial call would be a lot more expensive but then no further `exists` would need to touch the filesystem.

For a third alternative, `exists` could be decorated with `functools.cache`, in order to have its own cache completely independent of `load`. `load` could also be migrated to `functools.cache` as, as far as I can tell, the `localedata._cache` is never invalidated anyway, with the drawback that a locale's data might be resolved multiple times if concurrent calls are tight enough (`functools.cache` synchronises the cache but not the resolution of the value).
@codecov
Copy link

codecov bot commented Feb 12, 2026

Codecov Report

✅ All modified and coverable lines are covered by tests.
✅ Project coverage is 92.05%. Comparing base (56c63ca) to head (32e6561).

Additional details and impacted files
@@           Coverage Diff           @@
##           master    #1254   +/-   ##
=======================================
  Coverage   92.04%   92.05%           
=======================================
  Files          27       27           
  Lines        4715     4718    +3     
=======================================
+ Hits         4340     4343    +3     
  Misses        375      375           
Flag Coverage Δ
macos-14-3.10 91.09% <100.00%> (+<0.01%) ⬆️
macos-14-3.11 91.03% <100.00%> (+<0.01%) ⬆️
macos-14-3.12 91.24% <100.00%> (+<0.01%) ⬆️
macos-14-3.13 91.24% <100.00%> (+<0.01%) ⬆️
macos-14-3.14 91.22% <100.00%> (+<0.01%) ⬆️
macos-14-3.8 90.96% <100.00%> (+<0.01%) ⬆️
macos-14-3.9 91.02% <100.00%> (+<0.01%) ⬆️
macos-14-pypy3.10 91.09% <100.00%> (+<0.01%) ⬆️
ubuntu-24.04-3.10 91.11% <100.00%> (+<0.01%) ⬆️
ubuntu-24.04-3.11 91.05% <100.00%> (+<0.01%) ⬆️
ubuntu-24.04-3.12 91.26% <100.00%> (+<0.01%) ⬆️
ubuntu-24.04-3.13 91.26% <100.00%> (+<0.01%) ⬆️
ubuntu-24.04-3.14 91.24% <100.00%> (+<0.01%) ⬆️
ubuntu-24.04-3.8 90.98% <100.00%> (+<0.01%) ⬆️
ubuntu-24.04-3.9 91.04% <100.00%> (+<0.01%) ⬆️
ubuntu-24.04-pypy3.10 91.11% <100.00%> (+<0.01%) ⬆️
windows-2022-3.10 91.10% <100.00%> (+<0.01%) ⬆️
windows-2022-3.11 91.04% <100.00%> (+<0.01%) ⬆️
windows-2022-3.12 91.25% <100.00%> (+<0.01%) ⬆️
windows-2022-3.13 91.25% <100.00%> (+<0.01%) ⬆️
windows-2022-3.14 91.23% <100.00%> (+<0.01%) ⬆️
windows-2022-3.8 91.08% <100.00%> (+<0.01%) ⬆️
windows-2022-3.9 91.04% <100.00%> (+<0.01%) ⬆️
windows-2022-pypy3.10 91.10% <100.00%> (+<0.01%) ⬆️

Flags with carried forward coverage won't be shown. Click here to find out more.

☔ View full report in Codecov by Sentry.
📢 Have feedback on the report? Share it here.

🚀 New features to boost your workflow:
  • ❄️ Test Analytics: Detect flaky tests, report on failures, and find test suite problems.
  • 📦 JS Bundle Analysis: Save yourself from yourself by tracking and limiting bundle sizes in JS merges.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

1 participant