From 3831e6e017137ae49f071227f8b002f9024b867f Mon Sep 17 00:00:00 2001 From: Loren Eteval Date: Sat, 19 Sep 2026 11:41:29 +0800 Subject: [PATCH] Refine repository guidance Signed-off-by: Loren Eteval --- .github/AGENTS.md | 14 ++++++++------ AGENTS.md | 11 +++++++---- Furious/AGENTS.md | 8 +++++--- Furious/Actions/AGENTS.md | 11 ++++++----- Furious/Application/AGENTS.md | 10 ++++++---- Furious/Backends/AGENTS.md | 8 +++++--- Furious/Backends/ExternalCore/AGENTS.md | 11 ++++++----- Furious/Backends/Hysteria1/AGENTS.md | 11 ++++++----- Furious/Backends/Hysteria2/AGENTS.md | 10 ++++++---- Furious/Backends/Xray/AGENTS.md | 8 +++++--- Furious/Controllers/AGENTS.md | 10 ++++++---- Furious/Core/AGENTS.md | 8 ++++++-- Furious/Data/AGENTS.md | 9 +++++---- Furious/Extensions/AGENTS.md | 15 ++++++++------- Furious/Externals/AGENTS.md | 9 +++++---- Furious/Frozenlib/AGENTS.md | 8 +++++--- Furious/Interface/AGENTS.md | 9 +++++---- Furious/Models/AGENTS.md | 10 ++++++---- Furious/Plugins/AGENTS.md | 10 ++++++---- Furious/Qt/AGENTS.md | 11 +++++++---- Furious/Repository/AGENTS.md | 10 +++++++--- Furious/Service/AGENTS.md | 13 ++++++++----- Furious/Utility/AGENTS.md | 7 ++++--- Furious/Widget/AGENTS.md | 13 ++++++++----- Furious/Window/AGENTS.md | 12 +++++++----- Icons/AGENTS.md | 3 ++- tests/AGENTS.md | 6 ++++-- 27 files changed, 159 insertions(+), 106 deletions(-) diff --git a/.github/AGENTS.md b/.github/AGENTS.md index 1d0ffbb1..6e7621c2 100644 --- a/.github/AGENTS.md +++ b/.github/AGENTS.md @@ -14,9 +14,10 @@ exceptions; it does not define the source test suite or imply that every package - Treat each matrix row as a supported product target with explicit runner OS/architecture, Python, Qt/PySide source, native-binding toolchain, compatibility floor, `Deploy.py` output, and upload pattern. Artifact names and architecture checks must agree; never infer target architecture from the host label alone. -- Current target-specific assertions are intentional: Linux proves an Essentials-only/no-WebEngine application and its - Flatpak sandbox dependencies; macOS verifies its WebEngine frameworks, helpers, resources, relocation, and signing; - Windows verifies native imports and every packaged PE machine type, with a separate Windows 7 compatibility toolchain. +- Current target-specific checks are intentional: Linux checks the Essentials-only/no-WebEngine build and its + Flatpak native dependency closure; macOS checks WebEngine frameworks, helpers, resources, relocation, and signing; + Windows checks native imports and packaged PE machine types, with a separate Windows 7 compatibility toolchain. + These assertions establish artifact properties, not complete application behavior on those platforms. Change an exception only with evidence from the affected target. Binary jobs filter shared requirements before installing target-specific Qt/native bindings; copying the ordinary package dependency list into those jobs can reintroduce Addons on Linux or replace a compatibility build. Review the effective installed set, not just the @@ -42,10 +43,11 @@ exceptions; it does not define the source test suite or imply that every package source/native import checks, Nuitka/installer output, packaged architecture/dependency checks, artifact upload, and tag gates. When a target cannot run locally, add a narrow CI assertion that fails before publication with a useful reason. - `workflows/source-tests.yml` runs isolated source unittest discovery on Windows, Linux, and macOS and is a - required dependency of PyPI publication through `deploy-pypi.yml`. It can also run manually. Daily binary + required dependency of PyPI publication through `workflows/deploy-pypi.yml`. It can also run manually. Daily binary builds retain their separate artifact scope. Source tests do not establish packaged behavior or Python/Qt floors beyond their matrix. Do not call an artifact build a regression-test pass; use `tests/README.md` for - source verification. Check actual `needs` and tag gates rather than assuming a downstream publish job runs on every build. Follow each publication - dependency back to its required artifact checks; upload success alone does not establish release eligibility. + source verification. Follow actual `needs` and tag gates back to required checks; upload success alone does not + establish release eligibility. A diagnostic Nuitka build that changes compiler/runtime flags is separate evidence + from the ordinary release configuration; record and exercise the latter before claiming a packaged defect resolved. - Revalidate version/architecture claims against the current matrix instead of duplicating all pins here. When build topology intentionally changes, update this scope and follow every consumer through upload and publication. diff --git a/AGENTS.md b/AGENTS.md index 070e9b02..fc615598 100644 --- a/AGENTS.md +++ b/AGENTS.md @@ -28,7 +28,9 @@ scopes in place. - Inheritance follows directory ancestry. Name the nearest governing guide when clarifying a scope; a sibling guide identifies a contract to consult, not another parent. Verification and self-evolution here apply to every descendant - scope without repeating the same maintenance checklist in each file. + scope without repeating the same maintenance checklist in each file. Ignored comparison checkouts retain their own + scopes and toolchains; their manifests and local guides govern their code, not Furious's Python/Qt recipes. + Git diff alone cannot verify ignored guides: compare their paths and contents with the initial inventory too. ## Operating model @@ -124,6 +126,7 @@ - After significant architectural work, re-read the applicable hierarchy as a fresh agent: can it identify the owner, invariant, failure boundary, and relevant tests without relying on conversation history? Challenge rules likely to become stale, circular references, and wording that freezes incidental structure. -- Distinguish observed behavior from design requirements and name tests/consumers that can challenge a local rule. - A known limitation is not a desired invariant. During guidance-only work, report code defects separately instead - of changing production code to satisfy the prose. +- Distinguish requirements, observed implementation, and verified gaps. State the evidence boundary: a test name is an + investigation anchor, not proof that every failure path is covered. Keep run-specific counts, versions, and diagnostic + experiments in the work report; put only durable constraints in guidance. During guidance-only work, report defects + separately instead of changing production code to satisfy the prose. diff --git a/Furious/AGENTS.md b/Furious/AGENTS.md index 6c7eb734..6635fe8a 100644 --- a/Furious/AGENTS.md +++ b/Furious/AGENTS.md @@ -1,7 +1,8 @@ # Furious package guidance Inherit repository-wide rules from the root `AGENTS.md`. This file preserves the package-level boundary between -domain, persistence, orchestration, platform integration, and presentation; nested guides specialize it in place. +domain, persistence, orchestration, platform integration, and presentation; nested guides specialize it in +place. ## Responsibility boundaries @@ -53,8 +54,9 @@ domain, persistence, orchestration, platform integration, and presentation; nest record. Choose the explicit profile, metadata, or connection representation required by each boundary; generic mapping conversion is not a profile backup. - Import, clipboard, share-link, file, and QR paths reuse the owning plugin codecs and validation. QR is a presentation - transport, not a second protocol parser; construct a complete neutral result before repository mutation and never log - the secret-bearing payload. + transport, not a second protocol parser. Decoding a transport envelope, validating a protocol, and committing a + profile are separate boundaries: a recognized envelope is not permission to clear a group or import an unsupported + protocol. Construct a complete valid result for each commit unit and never log the secret-bearing payload. ## Local guides diff --git a/Furious/Actions/AGENTS.md b/Furious/Actions/AGENTS.md index e56c0db3..2900bf2c 100644 --- a/Furious/Actions/AGENTS.md +++ b/Furious/Actions/AGENTS.md @@ -1,7 +1,7 @@ # Action guidance -Inherit the root and `Furious/AGENTS.md`; this scope adds rules for translating user gestures into owned commands and -presentation without becoming a workflow authority. +Inherit `Furious/AGENTS.md` and its root ancestor; this scope adds rules for translating user gestures into +owned commands and presentation without becoming a workflow authority. ## Command boundary @@ -29,9 +29,10 @@ presentation without becoming a workflow authority. transient windows. Each screen-capture action owns a separate native capture handle, including separate tray/page instances; type-deduplicated cleanup must not leave one open. QR export generation belongs to its result window, not a parallel action-owned exporter. -- Small profile imports use the direct bulk path; large imports yield between bounded batches. Preserve captured - input and one operation context until completion/cancellation, reject deferred calls after teardown, and retain - already committed batches when cancellation stops later work. A parser call itself is not preempted by a batch. +- Small profile imports use the direct bulk path; large imports yield between bounded batches. One operation owns + captured input and its continuation through completion/cancellation; teardown rejects deferred calls. A parser call + itself is not preempted by a batch. Keep preparation and insertion distinct so a failed batch cannot publish a + partially validated result. - Batch limits bound work between event-loop yields; the minimum progress interval throttles status refreshes at those boundaries. It is not an independent paint timer. Keep terminal feedback accurate and choose scale policies from measured responsiveness rather than freezing a batch count into the command contract. diff --git a/Furious/Application/AGENTS.md b/Furious/Application/AGENTS.md index bae1c8da..117e3058 100644 --- a/Furious/Application/AGENTS.md +++ b/Furious/Application/AGENTS.md @@ -1,7 +1,7 @@ # Application composition guidance -Inherit the root and package guides. This scope owns process-lifetime Qt composition and the boundary between the outer -child-process supervisor and the inner application event loop. +Inherit `Furious/AGENTS.md` and its root ancestor. This scope owns process-lifetime Qt composition and the +boundary between the outer child-process supervisor and the inner application event loop. - `Furious.__main__` and `AppMainProcess` own the outer process/crash boundary; `DesktopApplication` owns the inner Qt composition. Keep those responsibilities separate and preserve semantic exit codes and original failure context. @@ -26,8 +26,10 @@ child-process supervisor and the inner application event loop. observations. - Native session callbacks cross to the GUI thread before touching Qt-owned state. Tray, dock, System Proxy daemon, Flatpak/AppImage, and no-tray behavior are explicit platform capabilities. -- The application owns the top-level window/tray wrappers; `MainWindow` owns the persistent page tree. Do not let dynamic - menus, sockets, theme snapshots, workers, or partial startup owners outlive their registered cleanup stage. +- The application owns the top-level window/tray wrappers; `MainWindow` owns the persistent page tree. Cleanup order + follows dependencies: consumers stop while the plugins, repositories, and Qt objects they need are still valid. + A registered cleanup callback establishes responsibility, not proof that its menus, sockets, snapshots, or workers + were released. Verify partial composition as well as a fully constructed application. - Verify each acquisition failure, reverse/repeated cleanup, singleton races/commands, queued session shutdown, tray-present/absent close policy, restored connection, and exact child/thread-pool ownership with host effects mocked. Start with `tests/test_architecture_refactors.py`, `tests/test_application_process.py`, and diff --git a/Furious/Backends/AGENTS.md b/Furious/Backends/AGENTS.md index 0298cd31..a969d20a 100644 --- a/Furious/Backends/AGENTS.md +++ b/Furious/Backends/AGENTS.md @@ -1,7 +1,8 @@ # Backend guidance -Inherit the root and package guides. Consult Plugins/Models/Service for the contracts consumed by this scope. This -scope adds rules shared by all bundled proxy backends without making the richest backend the generic default. +Inherit `Furious/AGENTS.md` and its root ancestor. Consult Plugins/Models/Service for the contracts consumed by +this scope. This scope adds rules shared by all bundled proxy backends without making the richest backend the +generic default. ## Common backend contract @@ -19,7 +20,8 @@ scope adds rules shared by all bundled proxy backends without making the richest - Configuration/runtime modules stay importable without constructing Qt editors. Plugin registration remains explicit enough for compiled discovery. An editor factory returns a fresh projection, not a repository commit: the caller owns the editable snapshot, acceptance validation, identity resolution, and eventual write-back. Runtime factories - likewise transfer fresh execution resources to the workflow owner. + likewise transfer fresh execution resources to the workflow owner. Editor acceptance and runtime readiness are + different validations; neither may silently rewrite stored data to make a later stage succeed. ## TUN and runtime policy diff --git a/Furious/Backends/ExternalCore/AGENTS.md b/Furious/Backends/ExternalCore/AGENTS.md index 660cbfb3..5ae5d68a 100644 --- a/Furious/Backends/ExternalCore/AGENTS.md +++ b/Furious/Backends/ExternalCore/AGENTS.md @@ -1,7 +1,7 @@ # External Core guidance -Inherit the root, package, and common backend guides; consult Plugins for capability contracts. This file preserves -the intentionally different direct-subprocess scope for user-selected executables. +Inherit `Furious/Backends/AGENTS.md` and its ancestors; consult Plugins for capability contracts. This file +preserves the intentionally different direct-subprocess scope for user-selected executables. ## Structured executable boundary @@ -36,6 +36,7 @@ the intentionally different direct-subprocess scope for user-selected executable `tests/test_external_core.py` and `tests/test_backend_editor_contract.py`. Exercise a child that remains alive after escalation and readers/watchers that outlast their joins. A failed final reap is a cleanup failure to report; clearing the runtime's process/thread references must not be used as evidence that those resources exited. - Direct-child exit also does not prove that descendants closed inherited pipes. Current stop/join paths can clear - references after unsuccessful waits; treat that as a cleanup-contract gap, not a guarantee of reaping. A repair must - retain observable outstanding resources and coordinate failure semantics with the consuming runtime lease. + Retain an independent reference in failure tests so an empty runtime field cannot make the test pass. Direct-child + exit also does not prove that descendants closed inherited pipes. `Process.py` currently clears references after + unsuccessful waits; this is a cleanup-contract gap. A repair must retain observable outstanding resources and + coordinate failure semantics with `Furious/Service/RuntimeLease.py`, without broad process-name cleanup. diff --git a/Furious/Backends/Hysteria1/AGENTS.md b/Furious/Backends/Hysteria1/AGENTS.md index 02fa256c..0cbc4c96 100644 --- a/Furious/Backends/Hysteria1/AGENTS.md +++ b/Furious/Backends/Hysteria1/AGENTS.md @@ -1,7 +1,7 @@ # Hysteria 1 guidance -Inherit the root, package, and common backend guides; consult Plugins for capability contracts. This scope exists to -preserve Hysteria 1's legacy flat schema and lifecycle without importing assumptions from Hysteria 2. +Inherit `Furious/Backends/AGENTS.md` and its ancestors; consult Plugins for capability contracts. This scope +exists to preserve Hysteria 1's legacy flat schema and lifecycle without importing assumptions from Hysteria 2. - Hysteria 1 is the legacy flat client schema and `hysteria://` share-link backend. Do not import Hysteria 2 nested documents, obfuscation, statistics, realm, or native-TUN semantics merely because the upstream names are related. @@ -17,9 +17,10 @@ preserve Hysteria 1's legacy flat schema and lifecycle without importing assumpt launch data before the child starts; a missing/unreadable file is logged and falls back to empty input. Preserve that observable fallback unless deliberately changing the contract, and include this synchronous file work in preparation responsiveness review. A prepared runtime advertises its local HTTP readiness endpoint separately - from child liveness. The built-in factory has no statistics provider; shared UI handles that absence. Download - preparation replaces the HTTP listener and removes SOCKS on a copy; do not route test traffic through a stored - listener or apply host System Proxy/TUN merely because the ordinary profile enables it. + from child liveness. +- Capability absence is deliberate: this factory supplies neither native TUN nor a statistics provider. Shared UI + must not infer either from Hysteria 2 support. Download preparation replaces the HTTP listener and removes SOCKS + on a copy; test traffic must use its owned endpoint without applying ordinary connection host effects. - Verify legacy/current URI and mapping compatibility, unknown/tolerated values, stored-copy isolation, MMDB/ACL absence or malformed paths, asynchronous readiness and rollback, core-exit translation, application-TUN policy, and repeated editor/runtime cleanup. Use `tests/test_hysteria1_protocol.py`, diff --git a/Furious/Backends/Hysteria2/AGENTS.md b/Furious/Backends/Hysteria2/AGENTS.md index 49558a57..116cab2c 100644 --- a/Furious/Backends/Hysteria2/AGENTS.md +++ b/Furious/Backends/Hysteria2/AGENTS.md @@ -1,7 +1,7 @@ # Hysteria 2 guidance -Inherit the root, package, and common backend guides; consult Plugins for capability contracts. This scope owns -Hysteria 2's nested upstream document, native-TUN capability, statistics, and editor projection. +Inherit `Furious/Backends/AGENTS.md` and its ancestors; consult Plugins for capability contracts. This scope +owns Hysteria 2's nested upstream document, native-TUN capability, statistics, and editor projection. ## Native document and editor projection @@ -19,8 +19,10 @@ Hysteria 2's nested upstream document, native-TUN capability, statistics, and ed including malformed data for the core to reject; only absence permits application tun2socks. Linux native TUN requires the backend’s privilege and server-route-exclusion guarantees. The application's Linux privilege-helper path does not grant an embedded native-TUN core the same privileges. Test these availability decisions separately. - Probe/download copies always remove native TUN. Managed preparation currently resolves server addresses - synchronously; do not describe the whole native-TUN stage as event-driven merely because readiness is asynchronous. + Failure to establish required managed server-route exclusions is terminal: use `TUNPreparationError` so registry + dispatch cannot interpret it as permission to fall back to another TUN path. Probe/download copies always remove + native TUN. Managed preparation currently resolves server addresses synchronously; asynchronous readiness does not + make that preparation interruptible. - The statistics provider is a process-lifetime capability; the runtime captures a configured server-API target and sampling owns its monitor/query lifetime. API URL, client ID, and authorization secret are distinct from client connection credentials. Keep requests bounded, validate counters, and never log the secret or infer statistics diff --git a/Furious/Backends/Xray/AGENTS.md b/Furious/Backends/Xray/AGENTS.md index 3a02e1ce..1dd41113 100644 --- a/Furious/Backends/Xray/AGENTS.md +++ b/Furious/Backends/Xray/AGENTS.md @@ -1,7 +1,7 @@ # Xray guidance -Inherit the root, package, and common backend guides; consult Plugins for capability contracts. This scope owns Xray's -full JSON preservation, routing/assets/statistics, and protocol/transport/TLS projections. +Inherit `Furious/Backends/AGENTS.md` and its ancestors; consult Plugins for capability contracts. This scope +owns Xray's full JSON preservation, routing/assets/statistics, and protocol/transport/TLS projections. ## Full-document preservation @@ -40,7 +40,9 @@ full JSON preservation, routing/assets/statistics, and protocol/transport/TLS pr so owner destruction also ends pending confirmation callbacks. - Statistics preparation is optional and may leave a valid runtime without a statistics target. Preserve that distinction from connection failure; later sampling uses the target captured for this runtime, not newly edited - settings or an assumption based solely on the backend name. + settings or an assumption based solely on the backend name. `configureXrayStats()` merges the required API service + and counter policy into the runtime copy, preserving unrelated valid API/policy fields. Do not replace a user's + entire API or policy branch merely to enable counters; test both the merged launch and unchanged stored document. - Verify full-document and URI preservation, aliases and unknown values, runtime-copy isolation for routing/log/TUN/tests, multiple TUN inbounds, asset integrity/failure, statistics and process cleanup, compiled-safe UI callbacks, and repeated editor/window destruction. Use `tests/test_xray_asset_download.py`, diff --git a/Furious/Controllers/AGENTS.md b/Furious/Controllers/AGENTS.md index 96fc1c6d..ac94a58c 100644 --- a/Furious/Controllers/AGENTS.md +++ b/Furious/Controllers/AGENTS.md @@ -1,7 +1,8 @@ # Controller guidance -Inherit the root and package guides. This scope preserves controllers as process-lifetime authorities for shared -transitions. Services own execution resources; existing prompts are presentation compatibility paths. +Inherit `Furious/AGENTS.md` and its root ancestor. This scope preserves controllers as process-lifetime +authorities for shared transitions. Services own execution resources; existing prompts are presentation +compatibility paths. ## Shared state authorities @@ -17,8 +18,9 @@ transitions. Services own execution resources; existing prompts are presentation failure. Worker/native callbacks cross to the controller’s Qt thread before transition. - The active live profile is not the prepared document used by an already-started runtime. Resolve identity and generation before changing state or host effects, and preserve typed runtime failures; cancellation and supersession - are not generic connection errors. Progress completion ends the presentation interval; it is not a success result. - Consumers use connection state and structured error/notification signals to distinguish failure from Connected. + are not generic connection errors. Runtime commit, host-effect success, and visible connection state are distinct + observations. Progress completion only ends the presentation interval; consumers and tests use connection state, + structured errors/notifications, and host results to establish the outcome. - `RoutingController` owns available capability options plus selected/persisted routing. Distinguish a newly selected repository profile from the active-profile reference and the independent runtime document; changes use controlled reconnect, not mutation of the running document. Capability refresh prefers the active profile and diff --git a/Furious/Core/AGENTS.md b/Furious/Core/AGENTS.md index b8a4d643..7ed73883 100644 --- a/Furious/Core/AGENTS.md +++ b/Furious/Core/AGENTS.md @@ -1,7 +1,8 @@ # Embedded runtime guidance -Inherit the root and package guides. Consult Interface for runtime contracts and Service for connection ownership. -This scope owns reusable embedded execution machinery and application tun2socks; connection policy remains outside it. +Inherit `Furious/AGENTS.md` and its root ancestor. Consult Interface for runtime contracts and Service for +connection ownership. This scope owns reusable embedded execution machinery and application tun2socks; +connection policy remains outside it. - `Core` supplies shared multiprocessing runtime machinery, bounded output transport, and application tun2socks. External Core owns its separate direct `subprocess.Popen`; neither layer owns controller, repository, UI, or protocol policy. @@ -17,6 +18,9 @@ This scope owns reusable embedded execution machinery and application tun2socks; resources. Stop must bound waits, escalate only the owned child, and remain safe after partial start or repetition. A join timeout or failed handle close is not a successful reap. Verify actual child liveness before describing a terminal execution state as complete resource release; include failed escalation in ownership tests. + `MultiprocessingRuntime._closeProcess()` currently discards its process reference even when handle close fails. + This is a cleanup-contract gap, not a permissible ownership transfer: a fix must preserve observability of the + outstanding child/handle and agree with the service lease's cleanup-failure semantics. - Process-backed runtimes own exit monitoring and interpretation: publish one typed terminal event per execution, preserving the raw exit and whether stop was requested. `isRunning()` is a passive liveness query and must not consume or dispatch lifecycle events. diff --git a/Furious/Data/AGENTS.md b/Furious/Data/AGENTS.md index c5fd0e0c..57c86449 100644 --- a/Furious/Data/AGENTS.md +++ b/Furious/Data/AGENTS.md @@ -1,7 +1,7 @@ # Bundled runtime data guidance -Inherit the root and package guides. This scope exists for shipped runtime assets and their provenance; it is not an -application-data or settings directory. +Inherit `Furious/AGENTS.md` and its root ancestor. This scope exists for shipped runtime assets and their +provenance; it is not an application-data or settings directory. ## Boundary and provenance @@ -34,5 +34,6 @@ application-data or settings directory. - Verify the real consuming backend/widget, source and packaged path resolution, package-data/Nuitka inclusion, integrity and failure behavior, and license presence. Tests use fixtures or mocked downloads, never live asset refreshes. `tests/test_endpoint_info.py` and `tests/test_public_api.py` cover map/resource consumers; release - artifacts require their own inclusion checks. Revalidate provenance/network claims when an asset provider or - loader changes. + artifacts require their own inclusion checks. Check actual artifact contents, including nested Markdown exclusions, + rather than only the presence of package-data patterns. Successful inclusion does not prove runtime write access or + optional WebEngine availability. Revalidate provenance/network claims when an asset provider or loader changes. diff --git a/Furious/Extensions/AGENTS.md b/Furious/Extensions/AGENTS.md index f2c05d70..5ecf8865 100644 --- a/Furious/Extensions/AGENTS.md +++ b/Furious/Extensions/AGENTS.md @@ -1,7 +1,8 @@ # Bundled extension guidance -Inherit the root and package guides; consult Plugins for capability and registration contracts. This scope covers -host-shipped non-runtime plugins and must not gain private authority merely because the code is bundled. +Inherit `Furious/AGENTS.md` and its root ancestor; consult Plugins for capability and registration contracts. +This scope covers host-shipped non-runtime plugins and must not gain private authority merely because the code +is bundled. - `Extensions` contains host-shipped plugins that are not proxy runtimes. They register through the same public API and lifecycle as entry-point plugins. New extension contracts must be usable without private @@ -13,11 +14,11 @@ host-shipped non-runtime plugins and must not gain private authority merely beca - Automatic detection probes decoders by priority; explicit selection does not authorize format substitution. Return `None` for a mismatch. Recognizing a share-link envelope does not validate its URI schemes or protocols; the importer owns that decision. Preserve useful names/upstream IDs and never log a complete payload or link. Current - standard formats are linear plain/Base64 share-link envelopes; introduce explicit size/depth/work limits before - adding richer recursive or nested formats. Standard decoders opt into worker execution; that declaration covers - all shared parser state and caches, not merely absence of widgets in the immediate method. Worker preparation also - requires the selected protocol handlers to opt in; a safe envelope decoder cannot authorize an unsafe downstream - parser. Preserve the GUI compatibility fallback for unclassified capabilities. + standard formats are plain/Base64 share-link envelopes; linear parsing is not an input-size bound. Introduce + explicit size/depth/work limits before adding richer recursive or nested formats. +- Worker safety is a property of the whole preparation path. Standard decoders opt in, but the selected protocol + handlers must also opt in after their shared state, caches, and Qt use are audited. Preserve the GUI compatibility + fallback for unclassified capabilities; a safe envelope decoder cannot authorize an unsafe downstream parser. - Decoder output is descriptive, not a repository transaction. Supplied names and upstream IDs are input to profile construction, not permission to overwrite local identity or grant remote ownership. It cannot mutate a group, cancel tests, reconnect, or publish UI state; those decisions remain at the import/manager commit boundaries. diff --git a/Furious/Externals/AGENTS.md b/Furious/Externals/AGENTS.md index 8363e797..12bdc2b2 100644 --- a/Furious/Externals/AGENTS.md +++ b/Furious/Externals/AGENTS.md @@ -1,7 +1,7 @@ # Translation catalog guidance -Inherit the root and package guides. This scope preserves the split between extracted catalog structure and -human-reviewed translations. +Inherit `Furious/AGENTS.md` and its root ancestor. This scope preserves the split between extracted catalog +structure and human-reviewed translations. ## Source and generation contract @@ -20,8 +20,9 @@ human-reviewed translations. meaning. Curated, verified translations need `isReviewed` set to the string `'True'`, as the generator compares that literal; a Python Boolean is not equivalent. Review applies to the entry, so inspect its other language values too. Do not clear approved review flags or hand-maintain the generated `source` module list. Runtime lookup reverse-maps - translated text to a source key, so collisions can change retranslation behavior even when extraction succeeds. - Exercise colliding translations at lookup time rather than treating the diagnostic as cosmetic. + translated text to a source key through a shared reverse index across languages. Equal translations for different + source keys can therefore affect later retranslation, including after a language switch. Exercise lookup and + retranslation under explicit locales rather than treating collision diagnostics as cosmetic. ## Extractable source text diff --git a/Furious/Frozenlib/AGENTS.md b/Furious/Frozenlib/AGENTS.md index d8ceb035..a5effa6f 100644 --- a/Furious/Frozenlib/AGENTS.md +++ b/Furious/Frozenlib/AGENTS.md @@ -1,7 +1,7 @@ # Platform and compatibility guidance -Inherit the root and package guides. This scope contains compatibility and host-integration boundaries, not a license -for unrelated application orchestration to accumulate in a broad helper namespace. +Inherit `Furious/AGENTS.md` and its root ancestor. This scope contains compatibility and host-integration +boundaries, not a license for unrelated application orchestration to accumulate in a broad helper namespace. - `Frozenlib` is the low-level settings, platform, compatibility, and broad export surface. Keep imports cheap, cross-platform, and free of application/UI construction; preserve curated wildcard exports until consumers and @@ -10,7 +10,9 @@ for unrelated application orchestration to accumulate in a broad helper namespac isolated tests, or teardown; do not add fallback global owners that create competing lifecycles. - `AppSettings` keys include preferences and encoded repository blobs. Preserve names, defaults, string/binary encodings, migrations, and import-time registration. Distinguish desired preferences from confirmed host effects; - startup-registration success is persisted only after its helper reports success. + startup-registration success is persisted only after its helper reports success. Settings storage and cached + repository objects are distinct lifetimes: changing a QSettings identity does not reconstruct `Storage` backends. + Tests that replace settings must isolate both boundaries before exercising cleanup or restoration. - Keep proxy, DNS, routing, TUN, startup registration, session callbacks, external commands, and platform detection here or behind a runtime boundary so tests can replace them completely. Windows, macOS, Linux, Flatpak, AppImage, and older platform paths are distinct capabilities; never generalize from the current host. diff --git a/Furious/Interface/AGENTS.md b/Furious/Interface/AGENTS.md index 99a0e2ea..dd900a58 100644 --- a/Furious/Interface/AGENTS.md +++ b/Furious/Interface/AGENTS.md @@ -1,7 +1,7 @@ # Interface guidance -Inherit the root and package guides. This file preserves dependency-light contracts that multiple implementations can -satisfy without importing application composition or concrete backends. +Inherit `Furious/AGENTS.md` and its root ancestor. This file preserves dependency-light contracts that multiple +implementations can satisfy without importing application composition or concrete backends. - This package defines dependency-light contracts shared across layers. It does not import Qt presentation, controllers, services, repositories, plugins, or concrete backends; a contract may depend on a small model/constant @@ -27,8 +27,9 @@ satisfy without importing application composition or concrete backends. - Runtime liveness is observational: querying it must not consume an exit, transfer ownership, or dispatch callbacks. A zero process exit can still be an unexpected connection failure; requested stop and raw exit success are different facts. Keep semantic startup errors separate from process codes and readiness timeouts. Define - cleanup-failure semantics without assuming every runtime owns a subprocess; bounded stop/dispose requirements - must remain meaningful for an in-process implementation as well as a child process that resists termination. + cleanup-failure semantics without assuming every runtime owns a subprocess. Bounded stop/dispose is a contract to + verify, not a guarantee supplied by the base class: third-party work may be non-cooperative. Report known violations + at their implementation/owner boundary rather than weakening the interface to bless an unreleased resource. - Verify cheap/import-independent contracts plus representative runtime, storage, editor, application-exit, encoding, and configuration implementations. Update this guide when a contract intentionally changes, together with all implementers and compatibility tests. Start with `tests/test_interface.py` and diff --git a/Furious/Models/AGENTS.md b/Furious/Models/AGENTS.md index f6b04f93..8bcc70c8 100644 --- a/Furious/Models/AGENTS.md +++ b/Furious/Models/AGENTS.md @@ -1,7 +1,7 @@ # Model guidance -Inherit the root and package guides. This scope owns dependency-light domain shape and identity, never live persistence, -Qt presentation, plugin discovery, or workflow execution. +Inherit `Furious/AGENTS.md` and its root ancestor. This scope owns dependency-light domain shape and identity, +never live persistence, Qt presentation, plugin discovery, or workflow execution. ## Domain shape and identity @@ -12,8 +12,10 @@ Qt presentation, plugin discovery, or workflow execution. distinct and preserve useful context through callers. Successful generic mapping construction is not protocol validation: backend acceptance belongs to the selected capability, and serializability is a separate check. - `ServerProfile` separates connection data from `ProfileMetadata`. `fromConfiguration()` copies a bare configuration - but returns an already-supplied profile unchanged; the direct dataclass constructor does not imply copying. Choose explicit copy semantics before independent editing or worker handoff. Display name, - profile ID, subscription ownership/key, latency, speed, annotations, and local flags never become core fields. + but returns an already-supplied profile unchanged; the direct dataclass constructor does not imply copying. A type + conversion is therefore not an isolation boundary. Choose explicit copy semantics before independent editing or + worker handoff. Display name, profile ID, subscription ownership/key, latency, speed, annotations, and local flags + never become core fields. - Preserve unknown metadata and legacy aliases across load/save. `independentCopy()` creates a manual profile with a new ID and no subscription owner; a runtime `deepcopy()` preserves identity while isolating mutable preparation. - Treat serialized and plugin-provided mappings as untrusted values. Normalize only documented compatibility aliases, diff --git a/Furious/Plugins/AGENTS.md b/Furious/Plugins/AGENTS.md index 6fb6a46c..1e3ef082 100644 --- a/Furious/Plugins/AGENTS.md +++ b/Furious/Plugins/AGENTS.md @@ -1,7 +1,8 @@ # Plugin guidance -Inherit the root and package guides; consult Interface guidance for runtime/storage contracts. This scope owns -capability definitions, atomic registration, dispatch, and plugin lifecycle; backend policy remains in each implementation. +Inherit `Furious/AGENTS.md` and its root ancestor; consult Interface guidance for runtime/storage contracts. +This scope owns capability definitions, atomic registration, dispatch, and plugin lifecycle; backend policy +remains in each implementation. ## Contracts and registry @@ -34,8 +35,9 @@ capability definitions, atomic registration, dispatch, and plugin lifecycle; bac - Evolve contracts additively when practical. Before a breaking change, inspect external discovery, compatibility exports, every bundled implementation, tests, and compiled inclusion; do not infer compatibility from built-ins alone. - A capability contract is generic only when an external plugin can satisfy it without importing private application - state. Backend-specific defaults, settings keys, document branches, and host assumptions stay behind the provider - rather than becoming undeclared registry requirements. + state. Backend-specific defaults, settings keys, document branches, and host assumptions stay behind the provider. + Capability presence advertises an operation, not a configured target or successful execution; callers must handle + absence, unavailable configuration, and operation failure separately (notably statistics, export, and probes). - API-version-3 runtime factories return `PreparedRuntime` directly. The runtime is fully prepared before return, starts with zero arguments, raises typed startup failures, and exposes readiness separately. An alternate result shape requires an explicit contract/version migration, not an implicit adapter inferred from built-in factories. diff --git a/Furious/Qt/AGENTS.md b/Furious/Qt/AGENTS.md index 7bb8ed6f..04ff9305 100644 --- a/Furious/Qt/AGENTS.md +++ b/Furious/Qt/AGENTS.md @@ -3,8 +3,8 @@ Use the `manage-qt-pyside6-lifetimes` skill for QObject ownership, transient/reusable UI, signal retention, or packaged PySide6 lifetime work. -Inherit the root and package guides. This scope owns reusable Qt presentation, translation/theme behavior, and lifetime -primitives; pages and services consume them without creating parallel registries. +Inherit `Furious/AGENTS.md` and its root ancestor. This scope owns reusable Qt presentation, translation/theme +behavior, and lifetime primitives; pages and services consume them without creating parallel registries. ## Canonical presentation @@ -53,8 +53,9 @@ primitives; pages and services consume them without creating parallel registries arbitrary worker calls to the GUI thread; choose an explicit queued owner-thread delivery boundary. A surviving Python wrapper can already be natively invalid, so callback freshness and `shiboken6.isValid()` address different failure modes. Neither replaces the strong owner required while asynchronous UI remains active. -- `AppQAction.callback` is strong by design, so the action owner cannot outlive the captured receiver. An action - also owns a submenu supplied without a QWidget parent and schedules its native deletion when the action dies; +- `AppQAction.callback` is strong by design, so its owner must not outlive the captured receiver; construction alone + does not enforce that requirement. An action also owns a submenu supplied without a QWidget parent and schedules + its native deletion when the action dies; `QAction.setMenu()` alone does not establish parent ownership. Explicitly parented menus retain their chosen owner. - Every `QNetworkReply` has one manager/context owner, one freshness rule, and one terminal deletion path. Request context must also be released when native destruction skips `finished`, including manager-first teardown with @@ -78,6 +79,8 @@ primitives; pages and services consume them without creating parallel registries - For lifetime-sensitive changes, repeat open/close/accept/reject paths and assert destroyed signals, weak wrappers, registries, timers, callbacks, replies, threads, handles, and child counts return to baseline. Run a representative Nuitka probe when compiled callback retention or packaged-only behavior is part of the defect. + Retained Python wrappers may already be invalid: count native destruction independently, including owner-first + teardown. A pass under diagnostic compiler flags does not establish behavior under ordinary release flags. Start with `tests/test_qt_lifetime.py`, `tests/test_dialog_geometry.py`, and `tests/test_main_window_geometry.py`; use the `tests/fixtures/editor_lifetime_probe.py` fixture for compiled investigation. Treat unrun packaged probes as unverified, and update these rules when measured ownership or the toolchain changes. diff --git a/Furious/Repository/AGENTS.md b/Furious/Repository/AGENTS.md index a9fa0290..eef813be 100644 --- a/Furious/Repository/AGENTS.md +++ b/Furious/Repository/AGENTS.md @@ -1,7 +1,8 @@ # Repository guidance -Inherit the root and `Furious/AGENTS.md`. Consult the Interface and Models guides when changing their contracts. -This scope owns restoration, migration, ordering, and persistence; workflows and presentation remain outside it. +Inherit `Furious/AGENTS.md` and its root ancestor. Consult the Interface and Models guides when changing their +contracts. This scope owns restoration, migration, ordering, and persistence; workflows and presentation remain +outside it. - Repositories restore, migrate, order, and persist profiles, subscriptions, routings, and TUN settings. They do not own network workflows, controller state, test schedulers, or presentation. @@ -9,7 +10,10 @@ This scope owns restoration, migration, ordering, and persistence; workflows and Do not add a second cache/snapshot authority. Prefer named repository mutations so validation and commit boundaries can move behind the repository over time. - Preserve stable profile/subscription IDs, subscription ownership/key, ordering, unknown fields, and legacy schemas. - Active row/index and display text are compatibility/presentation state, not identity. + Active row/index and display text are compatibility/presentation state, not identity. Record-shape dispatch and + metadata precedence are migration behavior: legacy `UserServer` aliases override nested metadata, and explicit + top-level current fields then override those aliases. Preserve this order and unknown extras unless a tested + migration deliberately changes it; do not treat every duplicate key as interchangeable. - A restore failure remains observable. Automatic cleanup must not replace unreadable persisted bytes with an empty fallback; only an explicit successful replacement may do so. Root decoding, individual-record hydration, and later serialization are separate failure boundaries. Test malformed records inside a valid root as well as malformed diff --git a/Furious/Service/AGENTS.md b/Furious/Service/AGENTS.md index 7cadb111..509c6020 100644 --- a/Furious/Service/AGENTS.md +++ b/Furious/Service/AGENTS.md @@ -1,7 +1,7 @@ # Service guidance -Inherit the root and package guides. Consult Models/Repository for data contracts, Plugins/Core for execution, and Qt -for lifetime primitives. This scope owns multi-stage workflows and temporary resources. +Inherit `Furious/AGENTS.md` and its root ancestor. Consult Models/Repository for data contracts, Plugins/Core +for execution, and Qt for lifetime primitives. This scope owns multi-stage workflows and temporary resources. ## Workflow ownership @@ -68,10 +68,13 @@ for lifetime primitives. This scope owns multi-stage workflows and temporary res a new first-retained sequence so presenters can prune their prefix without rebuilding history. Capture entries and the next cursor atomically, and coalesce notifications without losing producer updates. - Metrics sampling owns its worker/future generation and rejects results after disconnect, disablement, replacement, - or shutdown. Cancellation cannot stop an already-running plugin query: monitor contracts must bound blocking work. - Normalize cumulative-counter resets before history aggregation; clearing usage must not erase speed history. + or shutdown. Normalize cumulative-counter resets before history aggregation; clearing usage must not erase speed + history. History contains finite values for registered metrics on a monotonic timeline. A missing metric sample is not a - measured zero; preserve that distinction when adding providers or aggregating sparse series. + measured zero; preserve that distinction when adding providers or aggregating sparse series. Closing executor + admission or cancelling a future does not terminate a query already inside plugin code; test stale-result suppression + separately from worker completion. Monitor contracts must bound blocking work; report non-returning providers as a + shutdown limitation, not successful cancellation. ## Profile testing diff --git a/Furious/Utility/AGENTS.md b/Furious/Utility/AGENTS.md index 2bd451b2..0ff28a71 100644 --- a/Furious/Utility/AGENTS.md +++ b/Furious/Utility/AGENTS.md @@ -1,7 +1,7 @@ # Outer process guidance -Inherit the root and package guides. This scope preserves the exact outer child-process/crash protocol and is not a -general-purpose utility bucket. +Inherit `Furious/AGENTS.md` and its root ancestor. This scope preserves the exact outer child-process/crash +protocol and is not a general-purpose utility bucket. - `Utility` owns the child-side wrapper used by the outer application process and crash/exit translation. It is not a miscellaneous helper namespace and does not own application composition, repositories, runtimes, or UI policy. @@ -17,7 +17,8 @@ general-purpose utility bucket. - Shared crash status is a synchronized Boolean plus the child's semantic exit result; set the flag only after the diagnostic file is written successfully. Text may include retained logs plus a traceback, so the Boolean channel does not bound the crash file's size or sanitize its contents. Keep crash-write failure separate from the primary - exit result, and test reporting both with and without a constructed application/log manager. + exit result: the flag proves only that a file write completed, not that the child succeeded or the report can be + parsed as an exit protocol. Test reporting both with and without a constructed application/log manager. - Fallback presentation runs in the parent after a nonzero child result. It constructs a Qt application for the report but does not call the ordinary application `run()` initialization. Keep that constructor dependency in failure-path tests, and preserve the original result when evolving reporting failures rather than adding a supervisor. diff --git a/Furious/Widget/AGENTS.md b/Furious/Widget/AGENTS.md index ba27620e..6c934cd4 100644 --- a/Furious/Widget/AGENTS.md +++ b/Furious/Widget/AGENTS.md @@ -1,8 +1,9 @@ # Reusable widget guidance -Inherit the root and package guides; consult `Furious/Qt/AGENTS.md` for shared lifetime/presentation contracts. This -scope covers reusable controls and model/view adapters below page composition. Persistent widgets currently host -some service owners; that construction detail does not make every view an independent workflow authority. +Inherit `Furious/AGENTS.md` and its root ancestor; consult `Furious/Qt/AGENTS.md` for shared +lifetime/presentation contracts. This scope covers reusable controls and model/view adapters below page +composition. Persistent widgets currently host some service owners; that construction detail does not make every +view an independent workflow authority. ## Presentation and identity @@ -17,8 +18,10 @@ some service owners; that construction detail does not make every view an indepe to a dialog or event-loop turn; an ordinary QModelIndex/source row may become invalid or refer to another item. Resolve a multi-target confirmation independently for each captured ID: targets may move or disappear while it is open, and later selection must not change the command. Map resolved objects back through the proxy when restoring - focus. Recursively scope table-owned menu - shortcuts as `WidgetShortcut` so focused editors and other surfaces keep their own shortcut semantics. + focus. Recursively scope table-owned menu shortcuts as `WidgetShortcut` so focused editors and other surfaces + keep their own shortcut semantics. Selection identity, current keyboard index, and selection painting are separate: + keeping targets highlighted while a command button/menu has focus must not change selection or steal editor focus. + Exercise the button-focus interval before popup display as well as the open menu to catch highlight flicker. ## Workflow and lifetime boundaries diff --git a/Furious/Window/AGENTS.md b/Furious/Window/AGENTS.md index bf7c414e..a5559eb1 100644 --- a/Furious/Window/AGENTS.md +++ b/Furious/Window/AGENTS.md @@ -1,7 +1,8 @@ # Window and page guidance -Inherit the root and package guides. Consult Qt/Widget for presentation and Controllers/Service for shared owners. -This scope owns persistent page composition and top-level presentation, not shared domain state. +Inherit `Furious/AGENTS.md` and its root ancestor. Consult Qt/Widget for presentation and Controllers/Service +for shared owners. This scope owns persistent page composition and top-level presentation, not shared domain +state. ## Composition and shared state @@ -40,9 +41,10 @@ This scope owns persistent page composition and top-level presentation, not shar secret-bearing QR content. Reuse plugin export semantics and never log the encoded URI. - Search debounce belongs to the persistent page: clear/submit cancels pending work, hide stops it, and show applies only the current query. Find shortcuts are page-scoped; document editing shortcuts stay with their document widget. -- LogPage's optional Pause/Resume Updates control and logic are currently commented out. Its restoration notes and - the two retained pause tests in `tests/test_ui_behavior.py` describe the intended contract if re-enabled: freeze - presentation/filters only, keep collection bounded, and resume from retained entries after clear/eviction/navigation. +- Optional log freezing is presentation policy, not a collector lifecycle. Pause/Resume Updates is currently disabled + in source; its restoration notes and commented cases in `tests/test_ui_behavior.py` are design references, not + executed coverage. If restored, verify frozen presentation/filter behavior and catch-up after clear, eviction, and + navigation while collection stays bounded. Do not present disabled behavior as an active product guarantee. - Log views keep per-filter cursors and catch up on visibility; metrics pages derive series from shared raw history. Switching pages, ranges, or filters must not reset collection or create a second history. Metric buckets use the shared monotonic timeline: moving the visible range must not regroup unchanged historical samples. Preserve missing diff --git a/Icons/AGENTS.md b/Icons/AGENTS.md index 26643e35..dc30bae8 100644 --- a/Icons/AGENTS.md +++ b/Icons/AGENTS.md @@ -11,7 +11,8 @@ resource-manifest contract; it does not govern general UI layout. - Preserve license/provenance and the `Resources.qrc` alias contract. Any add, removal, rename, or alias change updates all consumers and the manifest, then regenerates `Furious/Frozenlib/AppResources.py` with the selected environment's `pyside6-rcc Resources.qrc -o Furious/Frozenlib/AppResources.py`. Never hand-edit generated resource - code; inspect compiler-version churn separately from the intended alias/asset change. + code. Editing the bytes of an existing manifest input also requires regeneration even if its path and alias stay + unchanged. Inspect compiler-version churn separately from the intended asset change. - Treat the alias as the application-facing identity and the source path as an implementation detail. Search both before replacement so an apparently unused file is not removed while still generated or consumed through an alias. Selecting an already bundled Bootstrap icon normally changes its consumer only; it does not require regeneration or another diff --git a/tests/AGENTS.md b/tests/AGENTS.md index af61accc..8be12972 100644 --- a/tests/AGENTS.md +++ b/tests/AGENTS.md @@ -51,8 +51,10 @@ and test-tier selection; test convenience never weakens a production invariant. - Source-only tests and an offscreen platform do not prove a packaged Qt runtime. Compiler-sensitive changes need native lifecycle tests and the compiled fixture documented in `tests/README.md`, including accept/reject/close and owner-first teardown. An unavailable private Nuitka counter is unknown, not measured zero; combine toolchain - inspection with native destruction, weak-wrapper and registry evidence. Report skipped/unavailable targets. - Release artifact checks do not execute this source behavioral suite. + inspection with native destruction, weak-wrapper and registry evidence. Record the interpreter, binding/compiler, + target, and relevant build flags with results: diagnostic flags can change the failing behavior and are not a + substitute for the ordinary release build. Report skipped/unavailable targets and distinguish commented test + examples from discovered tests. Release artifact checks do not execute this source behavioral suite. - Separate deterministic correctness/scale assertions from performance measurements. Opt-in stress tests may gate relative scaling or resource bounds; document the measured contract and environment rather than treating one machine's absolute timing as a portable product requirement.