An Appium capability you set for a community-garden plot app is ignored with no error — what explains it?
answer
- silence is the clue
- a legal name nobody reads
- the server log says unrecognised
- --strict-caps makes it fail instead
basics
~20 sA key that carries the appium: namespace but that the chosen driver does not know is still a legal extension capability, so the server accepts it and nothing ever reads it. Only an unprefixed non-standard key fails the session outright.
solid answer
~40 sThe prefix rule has two failure modes and they are not symmetric. Drop the namespace from a non-standard key and the session dies immediately with an invalid argument error. Keep the namespace but get the rest of the name wrong — a typo, a capability that belongs to a different driver, a setting renamed since the article you copied — and you have written a syntactically valid extension capability that the driver simply never reads. The session starts, the run looks healthy, and the behaviour you configured never happens. Diagnose it by reading the server log for the capability not being recognised, and by comparing each name against the driver's own constraints. Make it loud by starting the server with `--strict-caps`, which fails a session that carries capabilities the selected driver does not recognise.
go deeper
Be ready to say that a capability can be spelled legally and still do nothing, and that the server log is where you look first when a setting seems to have had no effect.
Explain the asymmetry: a missing namespace fails the session, while a namespaced name the driver does not know is accepted and never read. Name --strict-caps as the switch that removes the silence.
Show the diagnosis path on a real run — log, driver constraints, platform, then a direct assertion of the effect — and connect the silent no-op to symptoms that look like flakiness rather than configuration.
Own the policy: strict capability checking on shared servers and pipelines, generated or schema-validated capability sets, and capability changes reviewed as behaviour changes rather than as configuration noise.
## The two failure modes are not symmetric The `appium:` namespace is a syntax rule, and syntax rules can only catch syntax mistakes. That produces two very different outcomes from what feels like the same class of error. | Mistake | Namespace | Outcome | |---|---|---| | Bare non-standard name, e.g. `appPackage` | missing | invalid argument error, no session created | | Namespaced name the driver does not know, e.g. a typo after `appium:` | present | session starts, capability never read | The first is loud, immediate and self-describing: the error names the key. The second is silent by design. The server has no way to distinguish a capability meant for a driver it is not running from a capability that is simply misspelled — both are well-formed extension capabilities, and the protocol says a remote end may receive vendor keys it does not act on. So it accepts the set and starts the session. ## Why this is expensive on a real suite A suite for a community-garden plot app sets a capability to raise the idle timeout so a long harvest-log scenario is not reaped mid-run. Someone renames it slightly while merging two capability sets. The namespace is intact, so nothing fails. The session starts, the driver applies its own default instead, and the run now fails intermittently on the slowest scenarios — a symptom that looks exactly like flakiness and nothing like a configuration defect. The same shape appears in worse forms: - A reset-behaviour capability that is ignored, so state leaks between cases and one case passes only when another ran first. - A per-session port capability that is ignored, so parallel workers collide and failures move around the suite. - An Android-only key sent to an Apple run, or an Apple-only key sent to an Android run, where it is accepted and does nothing on the platform that has no such capability. - A capability that used to exist under an older name, copied from an article, now inert. In every case the run is green enough to be believed and wrong enough to waste a day. ## Diagnosing it 1. Read the server log for the session. Appium records that a capability was not recognised, which is the cheapest signal available and the one most teams never look at. 2. Compare each key against the constraints of the driver you actually selected, not against a general list — the drivers declare different capabilities, and a name valid for one is inert on another. 3. Check the platform. A capability that only the Android drivers declare is silently inert on an Apple run, and the reverse is equally true. 4. Confirm the behaviour directly rather than assuming: if the capability was supposed to change a timeout or a reset, assert the effect once in a smoke case instead of trusting that the key was applied. 5. Rule out the duplicate-definition case: if the set uses `appium:options`, a nested key overrides a same-named top-level one, so the value you are reading may not be the value in force. ## Making the failure loud The permissive default is a choice, and Appium lets you reverse it. Starting the server with `--strict-caps` makes a session fail when it carries capabilities the selected driver does not recognise, which converts every silent no-op into an immediate, named error at session creation — the same class of failure a missing prefix already produces. That is the right default for a shared server or a pipeline, where nobody is watching the log, and where a silently unapplied capability turns into a flaky suite that costs far more than a failed session would. On a developer machine, where a capability set is being explored, the permissive default is often more comfortable. ## What to build so it does not recur - Generate capability sets from typed helpers or a validated schema rather than hand-editing JSON, so a name is checked before it is sent. - Keep one spelling convention per suite — flat prefixed keys or one `appium:options` block — so a reviewer can see a missing or duplicated key. - Review capability changes as code changes, since a capability edit is a behaviour change with no test covering it by default. - Assert the effect of the capabilities that matter, at least once, so an inert key is caught by a failing assertion rather than by intermittent timeouts weeks later. The rule to carry away: the `appium:` namespace guarantees that a key is *legal*, never that it is *read*. Legality is enforced by the protocol; being read is enforced only by the driver, by `--strict-caps`, or by your own review.
- Why can the server not just reject an unknown namespaced capability by default?Because a well-formed extension capability may legitimately be meant for something other than the driver in play, and the protocol allows a remote end to receive vendor keys it does not act on. Rejecting them by default would break legitimate sets, so the strictness is opt-in through `--strict-caps`.
- How would you catch this before a run rather than during one?Stop hand-writing capability JSON. Build sets from typed helpers or validate them against a schema so a name is checked at build time, keep one spelling convention per suite, and run shared servers with `--strict-caps` so an unrecognised key fails the session instead of silently doing nothing.
- A capability works on the Android target and does nothing on the Apple one. Is that the same bug?It is the same mechanism. The Android drivers and the XCUITest driver declare different capabilities, so a key one platform knows is, on the other, a legal extension capability nobody reads. Split the shared set into a common part and per-platform parts rather than sending every key everywhere.
saying these in an interview costs you the question
- Believes any accepted capability was necessarily applied
- Expects the server to reject unknown namespaced keys by default
- Treats a silently inert capability as suite flakiness
- Assumes one capability set works unchanged on both platforms
- Never reads the server log for unrecognised capability messages