Fix: resolve relative -d/--project-dir path in `pio device monitor`
`device_monitor_cmd`'s `-d/--project-dir` option accepted a relative path
without resolving it to absolute. The command then entered
`with fs.cd(options["project_dir"]):`, changing the working directory into
that relative subdir. Downstream, a platform monitor filter (e.g. the
espressif32 exception decoder) re-enters the same still-relative
`project_dir` via `load_build_metadata()`'s own `fs.cd()`, duplicating the
path segment onto the already-changed cwd and crashing with
FileNotFoundError (platformio/platformio-core#5439).
Add `resolve_path=True` to the click.Path type so the path is resolved to
absolute once, at the point it enters the system, before any fs.cd() chain
runs. This does not change the no-flag default (os.getcwd already returns
absolute) or the already-absolute case (passes through unchanged, modulo
symlink resolution).
Add a regression test mirroring the nested fs.cd() scenario, plus coverage
for the default and already-absolute cases.
This introduces "disable_udev_rules_check" option in Linux environment.
If set to True, udev rules are not checked. This allows to suppress annoying
warnings when 99-platformio-udev.rules is not installed intentionally.
If set to False (default), udev rules are checked as before.
* Avoid infinite loop when cached mirror redirect keeps failing
The registry mirror iterator caches the HEAD redirect for one hour,
but the cache hit path never advanced _visited_mirrors, and the
cached payload did not include X-PIO-Mirror. When a prior run cached
a redirect to a mirror that now fails (for example an SSL error on
the download), subsequent iterations kept hitting the same cache key
and returning the same failing mirror forever, so tool installs
looped until interrupted.
Store X-PIO-Mirror in the cached payload, and on cache hit only
reuse the entry if it names a mirror not already tried; otherwise
fall through to a fresh HEAD with bypass set. Stale cache entries
written before this change lack X-PIO-Mirror and fall through
naturally, so the fix self heals without a manual cache clear.
* Add unit tests for registry mirror iterator cache handling
Cover the cache hit path advancing _visited_mirrors, stale cache
entries without X-PIO-Mirror falling through to a fresh HEAD, and
new HEAD responses persisting X-PIO-Mirror so later runs can tell
whether the cached redirect still names an untried mirror. Each
test fails against the previous iterator implementation.
* Add type annotations to mirror iterator tests
* Use typing.X annotations for 3.6 compatibility
* Satisfy pylint and black on mirror iterator tests