test(l10n): per-catalog attribution and file:line output for the coverage guard - #1679
test(l10n): per-catalog attribution and file:line output for the coverage guard#1679Chessing234 wants to merge 3 commits into
Conversation
The catalog guard named only the file a missing key was written in, so finding it in a 900-line view meant grepping. Collect each literal `String(localized:)` reference with its repo-relative path and line, and print one `path:line key` per line instead of a comma-joined blob.
The guard accepted a key found in either catalog. The share extension bundles only its own, so a key it references that lives solely in the app catalog ships English there just as surely as one that exists nowhere - which is the gap that let the share-extension strings drift. Check `bitchat/` against the app catalog and `bitchatShareExtension/` against the extension catalog, and say in the failure which of the two cases it is.
There was a problem hiding this comment.
💡 Codex Review
Here are some automated review suggestions for this pull request.
Reviewed commit: f835465104
ℹ️ About Codex in GitHub
Your team has set up Codex to review pull requests in this repo. Reviews are triggered when you
- Open a pull request for review
- Mark a draft as ready
- Comment "@codex review".
If Codex has suggestions, it will comment; otherwise it will react with 👍.
Codex can also answer questions or update the PR. Try commenting "@codex address that feedback".
| for (sourceRoot, ownKeys, otherKeys, ownCatalog, otherCatalog) in [ | ||
| ("bitchat", mainKeys, shareKeys, Self.mainCatalogPath, Self.shareExtensionCatalogPath), | ||
| ("bitchatShareExtension", shareKeys, mainKeys, | ||
| Self.shareExtensionCatalogPath, Self.mainCatalogPath) | ||
| ] { |
There was a problem hiding this comment.
Validate shared extension sources against extension catalog
The share extension target also has membership for shared files under bitchat/ (bitchat.xcodeproj/project.pbxproj:70-76 lists bitchat/Services/SharedContentHandoff.swift and bitchat/Services/TransportConfig.swift for the extension), but this loop assigns every bitchat/ reference to the app catalog only. If a user-facing String(localized:) is added to one of those shared helpers for the extension path and its key exists only in bitchat/Localizable.xcstrings, this guard will still pass even though the extension does not bundle that catalog, recreating the per-target blind spot this change is meant to close.
Useful? React with 👍 / 👎.
bitchat/Services/SharedContentHandoff.swift and bitchat/Services/ TransportConfig.swift are compiled into bitchatShareExtension as well (project.pbxproj membership exceptions), so a key they reference has to resolve in both catalogs -- each target bundles only its own. The exception list is read from project.pbxproj rather than hardcoded, so the check follows the set when it changes.
|
good catch on the shared sources — the share extension does compile bitchat/Services/SharedContentHandoff.swift and bitchat/Services/TransportConfig.swift (project.pbxproj membership exceptions), so a key referenced from either has to be in both catalogs. pushed b2641f8: the check now reads that exception list out of project.pbxproj (so it follows the set instead of hardcoding two paths) and additionally requires every key referenced from those files to exist in the extension catalog. probed it by adding String(localized: "Choose an image") — an app-only key — to TransportConfig.swift; the first check stays silent and the new one fails with the file:line. tree as it stands is clean on both. |
the two follow-ups you named on #1613, on current main.
per-catalog attribution. the code-side guard accepted a key found in either catalog. the share extension bundles only its own, so a key it references that lives solely in the app catalog ships english there exactly like one that exists nowhere. now
bitchat/is checked againstbitchat/Localizable.xcstringsandbitchatShareExtension/against the extension catalog, and the failure says which of the two cases it is.file:line. failures named only the file, so finding the key in a 900-line view meant grepping. each reference now carries its repo-relative path and line, one per line.
both are clean on current main (520 app keys, 5 extension keys, no misattributed references).
what i ran locally: no xcode on this machine, so i lifted the test into a stub harness (
#expect/#requirereplaced by plain functions) and ran the four checks against the real catalogs — all pass. then i injected two probe keys intoShareViewController.swiftto see the failure text:and reverted the probes. i could not run the real
Testingsuite here — CI covers that.