docs(skills): web selectors are exact, native ones are substrings

This commit is contained in:
pj committed 2026-08-16 01:08:19 +05:30
1 parent 906759dc15
commit 7c085c8c9d
1 file changed
+14 -6
+14 -6
View File
@@ -86,12 +86,20 @@ function of that string can separate them.
**Match whole keys, not endings or substrings.** `endsWith` attribution judges an **Match whole keys, not endings or substrings.** `endsWith` attribution judges an
older account named `Emergency Fund` when the user typed `Fund`. older account named `Emergency Fund` when the user typed `Fund`.
Selector matching has the same trap and it is easy to miss which keys carry it. Selector matching has the same trap on Android and iOS, and it is easy to miss
`id`, `text`, `desc` and `descPrefix` resolve by their own rules, so `{id: "Sub"}` which keys carry it. `id`, `desc` and `descPrefix` resolve by rules of their own
correctly matches nothing. Every other key, `testTag` included, falls through to a (exact or `:id/`-suffixed, exact or comma-prefixed, starts-with), so
substring compare, so `{testTag: "Sub"}` matches `AddAccountSubmit`. That is not a `{id: "Sub"}` correctly matches nothing. Every other key, `text` and `testTag`
match, it is a coincidence, and a property built on it judges whichever element included, falls through to a substring compare, so `{testTag: "Sub"}` matches
happens to contain the fragment. `AddAccountSubmit`. That is not a match, it is a coincidence, and a property
built on it judges whichever element happens to contain the fragment.
The web path does not share the rule, which is its own trap. `web-runtime.ts`
compiles an object selector to CSS, and every key becomes an exact attribute
match (`descPrefix` alone becomes a `^=` prefix). So the loose selector that
resolved on Android resolves to nothing on web, and every property over it goes
vacuously true rather than red. Reviewing a cross-platform spec means checking
that each selector is exact enough for native and literal enough for web.
**Drop the carrier when the screen changes.** A value carried across a route **Drop the carrier when the screen changes.** A value carried across a route
change is a value read from a screen that is no longer there. change is a value read from a screen that is no longer there.