LocalEndpoint / Endpoint Strategy

C\ Desktop to Python, TypeScript, and Rust Contract Parity

Report summary

To achieve secure, robust, and idiomatically consistent communication between the LocalEndpoint Connect Windows desktop application and a distributed web ecosystem spanning Python, TypeScript, and Rust, this analysis recommends a Hybrid Schema-as-Code architecture. [Proposal] The protocol must stand

Status
Research archive item
Category
LocalEndpoint / Endpoint Strategy
Length
5,520 words
Reading time
26 minutes
Report type
evaluation

Key topics

  • LocalEndpoint / Endpoint Strategy
  • LocalEndpoint
  • Endpoint Strategy
  • AI
  • Agentic Web
  • .NET
  • SQL
  • TypeScript
  • Python

Research provenance

Archive status
Research archive item
Content identity
sha256:36f433bfcb8acf4c1b76e082750ddadf9565cbdf0d0ee3c5479644bcb098c6bf

For citation, use the report title and canonical URL. Archival presence does not establish authorship or promote report statements into portfolio evidence.

This page renders the archived Markdown as safe, formatted HTML. It is background research and does not become a portfolio claim without evidence review.

Full report

On this page

1. Executive Recommendation

To achieve secure, robust, and idiomatically consistent communication between the LocalEndpoint Connect Windows desktop application and a distributed web ecosystem spanning Python, TypeScript, and Rust, this analysis recommends a Hybrid Schema-as-Code architecture. \[Proposal\] The protocol must standardize on JSON Schema Draft 2020-12 as the unified source of truth, utilizing OpenAPI 3.1 for synchronous HTTP Representational State Transfer (REST) coordination and AsyncAPI 3.0 for asynchronous message broker and WebSocket streams1. \[Distributed-systems synthesis\] To eliminate serialization drift and preserve cryptographic signatures across these diverse language runtimes, all payloads must undergo strict canonicalization according to the JSON Canonicalization Scheme (JCS) defined in RFC 87853. Security must be strictly sender-constrained at the application layer using OAuth 2.0 with Proof Key for Code Exchange (PKCE) for native desktop enrollment via loopback interfaces5, paired with Demonstrating Proof-of-Possession (DPoP) for all subsequent remote command dispatching7. Furthermore, this architecture explicitly rejects the industry myth of transport-level "exactly-once" delivery. \[Protocol requirement\] System reliability must instead rely on at-least-once transport delivery combined with at-most-once local execution, enforced exclusively on the C\# desktop through durable Transactional Inbox and Outbox patterns backed by local ACID (Atomicity, Consistency, Isolation, Durability) database transactions10. The C\# desktop remains the ultimate execution authority, retaining absolute veto power over any remote command through a strictly enforced, default-deny local policy engine.

2. Scope, Owner-Supplied Facts, and Zero-Access Declaration

This analysis operates under a strict zero-access boundary. \[Platform fact\] No real-world product repositories, production endpoint addresses, database schemas, internal telemetry, or proprietary credentials associated with LocalEndpoint Connect or its affiliated domains have been inspected, probed, or extracted. All endpoints, payloads, class names, and identifiers discussed herein are synthetic and scoped under the example.invalid top-level domain. The architecture accepts several immutable constraints regarding the technology stack and operational topology. \[Platform fact\] The final execution authority rests exclusively with the native Windows desktop client written in C\#/.NET. Remote use requires prior desktop enrollment, authenticated account access, and explicit remote enablement. \[Protocol requirement\] The desktop installation retains absolute veto power over remote execution requests, enforcing local policy engine constraints that cannot be silently bypassed by remote website coordinators. Local-only features remain fully functional in completely disconnected environments. The server-side topology spans Python for website components, TypeScript operating in both isolated browser contexts and server-side worker runtimes, and Rust for high-throughput backend services. Python is strictly a backend service and is not deployed as a desktop sidecar.

3. Research Method and Source Quality

The architectural synthesis relies exclusively on peer-reviewed distributed systems literature, standard tracking documents, and official platform documentation. \[External guidance\] The primary references driving this design include Internet Engineering Task Force (IETF) Request for Comments (RFC) standards, specifically RFC 9449 for DPoP8, RFC 8785 for JCS3, RFC 9457 for Problem Details13, and RFC 8252 for Native App OAuth flows5. \[External guidance\] Identity and authentication lifecycle management aligns with NIST Special Publication 800-63B guidelines regarding phishing-resistant authenticators and token lifecycles. API validation strategies directly address the OWASP API Security Top 10 vulnerabilities, particularly mitigating Broken Object Level Authorization (BOLA) and Server-Side Request Forgery (SSRF) through strict payload schemas and cryptographic binding. Furthermore, reliability models are drawn from established cloud architecture patterns regarding idempotent consumer design and outbox event publishing11.

4. Trust Boundaries and Actor Identities

In a distributed topology spanning browser environments, backend orchestrators, and native desktop clients, delineating trust boundaries is paramount to preventing privilege escalation and confused deputy attacks.

Distinct Trust Boundaries and Authentication

\[Distributed-systems synthesis\] The browser executing TypeScript represents a highly volatile, untrusted boundary. Subject to cross-site scripting (XSS) and cross-origin resource sharing (CORS) constraints, the browser cannot safely store persistent symmetric secrets or long-lived bearer tokens5. \[Protocol requirement\] Any claims asserted by the browser (such as identity or authorization state) must be treated as hostile until independently verified by the backend account service. The website backend, encompassing Python API gateways and Rust message brokers, represents a semi-trusted orchestration boundary. \[Protocol requirement\] The account service authenticates the human operator and service workloads. The dispatch coordinator validates incoming envelopes and routes them to the message broker. However, the backend lacks the contextual awareness and physical security required to mandate local operating system side effects. The message broker itself acts as an untrusted transport mechanism; it facilitates routing but must not be relied upon for message confidentiality or tamper-resistance without application-layer payload signatures. \[Platform fact\] The C\# Windows desktop application constitutes the highest trust boundary. It resides behind the physical and network perimeter of the user's local operating system. The desktop encompasses the local policy engine, which evaluates all remote commands against local heuristics, category limits, and explicit user approvals. Below the C\# application sits the local executor, an isolated operating system sub-context operating with the minimum privileges necessary to execute approved actions.

Identity Taxonomy and Local Veto Power

Establishing clear identity distinctions prevents cross-tenant data leakage and ensures auditable revocation.

Identity ConceptOrigin & Authentication ComponentPurpose & Scope
TenantAccount ServiceGlobally unique identifier representing an organizational or billing boundary.
AccountAccount Service (IdP)Identifies the human operator. Authenticated via WebAuthn or standard credentials.
DeviceC\# DesktopHardware-bound UUID generated on the desktop using machine-specific seeds encrypted with DPAPI17.
SessionAccount ServiceShort-lived credential representing an active web or desktop connection, sender-constrained via DPoP7.
RequestClient (Browser/Desktop)Edge-to-edge correlation tracer for synchronous HTTP operations.
ActionDispatch CoordinatorImmutable UUIDv4 assigned to a specific remote command intent.
PolicyLocal Policy EngineReferences the local rule pattern applied by the desktop to approve or deny an action.
AuditAudit Service / DesktopGlobally unique tracer for compliance logging, linking an action to a device and policy.

\[Protocol requirement\] Even when an account owner grants broad remote authority, decisions regarding file system access, network port binding, and specific application execution remain strictly bound to the local desktop policy. The remote caller may not silently bypass the desktop policy engine. \[Distributed-systems synthesis\] To ensure local-only use remains fully functional when hosted components are unavailable, the desktop application stores local policy definitions in an encrypted, offline-capable SQLite database. When network connectivity drops, the C\# desktop seamlessly routes local automation triggers directly to the local executor without requiring backend token validation.

5. Contract Source-of-Truth Decision

Selecting a normative source of truth for protocol definition requires balancing compile-time type safety, schema evolution guardrails, wire efficiency, and tooling maturity across four distinct language runtimes.

Interface Definition Evaluation

The analysis compared several prominent interface definition languages (IDLs):

TechnologyStrengthsLimitationsDecision
OpenAPI 3.1 \+ JSON SchemaHuman-readable, native web browser support, massive tooling ecosystem. Full JSON Schema 2020-12 alignment2.Payload sizes are larger than binary formats; lacks native async modeling20.Selected for Sync
AsyncAPI 3.0Decouples channels and operations natively. Fully supports JSON Schema1.Tooling is less mature than OpenAPI21.Selected for Async
Protobuf / gRPCMaximum serialization efficiency, strict forward/backward compatibility22.Binary opacity complicates browser debugging. Requires gRPC-Web proxy for browsers20.Rejected
AWS SmithyProtocol-agnostic, excellent resource modeling24.Python/Rust SDK generation is AWS-centric and complex. Lossy OpenAPI conversion26.Rejected

\[Proposal\] The architecture standardizes on a combination of OpenAPI 3.1 for synchronous HTTP endpoints and AsyncAPI 3.0 for asynchronous event streams. Both specifications will reference a unified repository of JSON Schema Draft 2020-12 definitions. \[Protocol requirement\] Generated C\#, Python, TypeScript, and Rust data transfer objects (DTOs) must coexist with thin, handwritten domain adapters. This ensures that generated models act purely as an anti-corruption layer at the network boundary, preventing transient schema changes from infecting core business logic.

Canonical Serialization and Data Rules

\[Protocol requirement\] To facilitate stable payload hashing, idempotency validation, and cryptographic signature verification across disparate languages, all runtimes must implement the JSON Canonicalization Scheme (JCS) defined in RFC 87853. Standard JSON serializers introduce fatal nondeterminism due to arbitrary dictionary key sorting, whitespace variations, and floating-point numeric representations28. The following rules apply to all payload generation:

  • Field Names: CamelCase exclusively.
  • Unicode: Strings are normalized to UTF-8 Normalization Form C (NFC).
  • Property Sorting: Keys must be lexicographically sorted based on raw UTF-16 code units3.
  • Timestamps & Durations: Serialized strictly as ISO-8601 UTC strings with exactly three millisecond digits (e.g., YYYY-MM-DDTHH:mm:ss.sssZ).
  • Decimal Values: Serialized as strings (e.g., "149.50") to prevent IEEE 754 precision loss across Python, Node.js, and C\# boundaries3.
  • Integers: Constrained to the safe I-JSON bounds of [Figure omitted from source export] to [Figure omitted from source export]3.
  • Enums: Modeled exclusively as string-backed variants.
  • Unions: Translated to tagged unions using JSON Schema oneOf.
  • Nullability & Optional Fields: Properties with null values are omitted entirely from the serialized byte array to ensure consistent canonical hashes.
  • Maps: Constrained to string keys only.
  • Unknown Properties: Rejected during strict validation at the trust boundary.

\[Distributed-systems synthesis\] In continuous integration (CI), schema linting utilizes tools like Spectral to enforce OpenAPI/AsyncAPI conventions. Breaking-change detection relies on structural diffing tools (e.g., oasdiff) to prevent the removal or alteration of existing fields. Generated code is committed to a locked artifact repository to guarantee deterministic, reproducible builds across the four runtimes.

6. Normative Resource and Envelope Profile

All communication relies on generic resource envelopes that standardize intent, tracing, and status reporting without coupling the transport layer to specific product features.

API and Resource Semantics

\[Proposal\] The architecture exposes generic REST resources modeled via standard HTTP methods:

  • Creation: POST (e.g., dispatching an ActionRequest).
  • Idempotent Replacement: PUT (e.g., updating a PluginMetadata catalog).
  • Partial Update: PATCH (e.g., updating Account preferences).
  • Queries: GET (e.g., fetching EnrolledDevices).
  • Append-Only Events: POST to an immutable stream (e.g., AuditEvents, MemoryRecords).
  • Cancellation: POST to a dedicated {id}/cancel sub-resource, as HTTP DELETE semantics imply resource removal rather than state transition.

Identifiers and Error Envelopes

\[Protocol requirement\] Requests are tracked using distinct identifiers:

  • CorrelationId: Traces a single operational flow across multiple microservices.
  • CausationId: Points to the specific message that triggered a downstream event.
  • IdempotencyId: Client-generated UUID ensuring safe POST retries32.

\[Protocol requirement\] When requests fail, the system returns error envelopes conforming to RFC 9457: Problem Details for HTTP APIs13. This provides stable machine codes alongside safe human explanations:

JSON { "type": "https://api.example.invalid/errors/policy-veto", "title": "Local Policy Denial", "status": 403, "detail": "Execution of 'script.ps1' denied by desktop policy engine.", "instance": "urn:uuid:9029-abc-1234" }

Pagination, Concurrency, and Transports

\[Protocol requirement\] Pagination for large collections utilizes cursor-based navigation (e.g., ?cursor=eyJvZmZzZX...) with finite cursor lifetimes. Optimistic concurrency utilizes standard HTTP ETag headers and If-Match preconditions, returning HTTP 412 (Precondition Failed) upon conflict. \[Distributed-systems synthesis\] For interaction types:

  • Ordinary Polling: Used only as a fallback for the desktop if persistent connections fail.
  • Server-Sent Events (SSE): Recommended for pushing ActionReceipt status updates to the browser TypeScript client due to native reconnect capabilities and unidirectional data flow.
  • WebSockets: Recommended for the bidirectional control channel between the C\# desktop and the dispatch coordinator, enabling low-latency command delivery and immediate acknowledgement1.

7. Authentication, Enrollment, and Secret Handling

Securing the perimeter requires specialized authentication flows tailored to the distinct capabilities of browsers, server workloads, and native desktop applications.

Native Desktop Enrollment and DPoP

\[Protocol requirement\] To resist phishing, session swapping, and code interception, the C\# desktop application authenticates using the OAuth 2.0 Authorization Code flow with PKCE, adhering strictly to RFC 8252 for Native Apps5. \[Platform fact\] The desktop generates a high-entropy PKCE code challenge and spawns the operating system's default browser. The user authenticates within the secure browser context, ensuring the C\# application never handles raw credentials. Upon success, the authorization server redirects to a dynamic, ephemeral local loopback interface (e.g., http://127.0.0.1:49215) monitored by the C\# application6. \[Protocol requirement\] Standard bearer tokens are vulnerable to replay if exfiltrated. The system utilizes Demonstrating Proof-of-Possession (DPoP) per RFC 94497. During enrollment, the C\# desktop generates a local asymmetric key pair (ES256). The authorization server binds the issued access token to the public key's SHA-256 thumbprint (the cnf claim)8. For every subsequent API request, the client computes a new DPoP proof JWT containing:

  • htm: The HTTP method.
  • htu: The exact target URI.
  • jti: A unique proof identifier to prevent replay.
  • iat: An issued-at timestamp.
  • ath: The base64url-encoded SHA-256 hash of the access token7.

Secret Storage and Revocation

\[Platform fact\] The C\# desktop application stores its DPoP private keys and access tokens securely using the Windows Credential Manager, wrapped via the Data Protection API (DPAPI)17. \[Protocol requirement\] The storage scope must be strictly set to DataProtectionScope.CurrentUser to prevent extraction by other users on the same machine17. In the browser, DPoP keys must be generated using the Web Crypto API with the extractable: false flag to prevent exfiltration via XSS. Hosted Python and Rust services obtain secrets dynamically from AWS Secrets Manager or Azure Key Vault during startup, caching them strictly in memory without embedding them in static configuration files. \[Protocol requirement\] Revocation flows differ based on context. An account sign-out or password reset immediately invalidates all backend session references, causing subsequent DPoP validation checks to fail with HTTP 401\. If a device is marked lost, the backend publishes a revocation event. \[Distributed-systems synthesis\] Crucially, account authorization is entirely separate from local desktop capability approval. A fully authenticated backend request can still be denied by the desktop policy engine if the local user clicks "Deny" on a real-time prompt or if the command violates persistent lockdown rules. Both remote authentication and local policy approval must independently succeed.

8. Protected Remote Command Lifecycle

The lifecycle of a protected remote command spans intent, dispatch, local evaluation, and final execution, requiring resilient state machines on both the server and desktop.

Remote Operation State Machines

Server-Side State Machine:

StateTriggerNext Possible States
QUEUEDRequest received & validatedDELIVERED, CANCELLED, EXPIRED
DELIVEREDAck received from brokerEXECUTING, APPROVED, DENIED, CANCELLED
EXECUTINGDesktop signals execution startCOMPLETED, FAILED, OUTCOME\_UNKNOWN
COMPLETEDSuccess receipt from desktopTerminal
FAILEDError receipt or timeoutTerminal

Desktop-Side State Machine:

StateTriggerNext Possible States
RECEIVEDWebSocket message parsedEVALUATING
EVALUATINGPolicy engine checks constraintsAPPROVED, DENIED
APPROVEDLocal checks passEXECUTING
EXECUTINGProcess spawnedCOMPLETED, FAILED, CANCELLED

Broad Authority vs. Local Denials and Replay Defenses

\[Protocol requirement\] The architecture protects against replay and duplicate delivery through the client-generated Idempotency-Key and the immutable ActionId. Stale grants are mitigated by strict expiry timestamps embedded in the command envelope. Cross-tenant access is algorithmically blocked by BOLA checks matching the DeviceId to the authenticated TenantId on the backend. \[Distributed-systems synthesis\] Broad user-granted remote authority coexists with desktop-side denials through a strict hierarchy. The backend orchestrator assumes authority is valid until the desktop explicitly rejects the payload. The desktop evaluates the payload against category limits (e.g., maximum allowed CPU time) and app-specific approvals. If an emergency stop is triggered locally, all queued actions transition to DENIED and future deliveries are dropped.

Cancellation Semantics and Reporting Certainty

\[Distributed-systems synthesis\] Cancellation semantics depend heavily on timing:

  • Before Dispatch: The server transitions the action to CANCELLED; the desktop never sees it.
  • After Delivery / During Execution: The server forwards a cancellation signal. The desktop attempts a graceful abort via CancellationToken. If successful, it reports CANCELLED.
  • After Side Effect: Cancellation is impossible. The desktop reports COMPLETED and the server rejects the late cancellation request.

\[Protocol requirement\] The website must not overstate certainty. Status strings map exactly to known facts. If the desktop disconnects during EXECUTING and fails to reconnect within the lease window, the server must transition the state to OUTCOME\_UNKNOWN. Network partitions, clock skew, and process restarts do not invalidate the authority of a completed action, but they demand that the UI reflects the ambiguity of the network partition to the user.

9. Reliability, Idempotency, and Honest Guarantees

In distributed environments spanning cloud infrastructure and local desktop networks, generic transport-level exactly-once execution is a mathematically impossible claim.

Delivery Guarantees and The Myth of Exactly-Once Transport

\[Distributed-systems synthesis\] Protocols such as Kafka, RabbitMQ, or WebSockets can, at best, guarantee at-least-once delivery under network partitions38. If the desktop receives a message, executes a script, and crashes before sending the acknowledgment back to the broker, the broker will redeliver the message upon reconnection. Transport-level exactly-once claims do not prove exactly-once desktop effects because they cannot guarantee atomicity between the message acknowledgment and the physical side effect on the host operating system39.

Transactional Inbox and Outbox Patterns

\[Protocol requirement\] To guarantee at-most-once local execution, the C\# desktop must implement a Transactional Inbox11. When a command arrives, the desktop opens a local SQLite ACID transaction. It attempts to insert the ActionId into the Inbox table. If a unique constraint violation occurs, the message is a duplicate and is silently acknowledged without execution11. If the insert succeeds, the command is scheduled for execution. \[Protocol requirement\] When reporting results, the desktop writes the result to a local Outbox table within the same database transaction as the final state update16. A background worker reads the Outbox and pushes HTTP requests to the backend. This guarantees that network failures do not result in lost execution receipts. Ambiguous outcomes are reconciled by the server polling the desktop's audit history upon reconnection.

Retry Classification and Backoff

\[Protocol requirement\] All mutating remote requests must include an Idempotency-Key (a UUIDv4)32. The server caches the response for a defined retention window (e.g., 24 hours), returning the cached response for duplicate requests33. Retries are strictly classified:

HTTP StatusClassificationRetry Behavior
408, 429, 502, 503, 504Transient / Rate LimitExponential backoff with full jitter. Respect Retry-After header.
401, 403Auth / Policy FailureFatal. Do not retry. Trigger re-authentication or prompt user.
400, 404, 422Client / Validation ErrorFatal. Dead-letter the message.
409, 412Conflict / ConcurrencyFatal. Fetch latest state and resolve conflict manually.

\[Distributed-systems synthesis\] Per-device ordering boundaries dictate that actions requiring sequential execution are queued behind a lease. Unrelated work on the desktop may proceed concurrently if it does not share the same resource lease. Account state and audit history require strong consistency (ACID), whereas dispatch states tolerate eventual consistency.

10. Privacy and Data Minimization

Enforcing the principle of data minimization ensures that telemetry and logs cannot become vectors for credential exposure or PII leakage.

Allowlists and Prohibited Content

\[Protocol requirement\] Before any remote request, memory record, agent message, or telemetry diagnostic is serialized, it must pass through a strict default-deny allowlist. The system explicitly prohibits the following content classes from traversing the network:

  • Raw cryptographic credentials or session tokens.
  • Unrestricted file paths or private file contents.
  • Unredacted user prompts, browser history, or email bodies.
  • Screen captures or raw model outputs.

Field Limits, Retention, and Logging

\[Protocol requirement\] Explicit purpose and data classification are enforced via JSON Schema metadata tags (e.g., "x-data-classification": "PII"). String fields must enforce strict maxLength boundaries. Data retention policies mandate hard deletion of intermediate broker queues after a short TTL, with regional controls pinning database storage to specific geographic jurisdictions based on tenant requirements. \[Protocol requirement\] Operational logging must be fundamentally body-free to support reliability investigation without compromising privacy. Logs must only contain structured metadata—TenantId, DeviceId, CorrelationId, latency durations, retry counts, and HTTP status codes—completely omitting ActionEnvelope payload bodies8. Browser and server validation provide fast-fail feedback to the user but do not replace the mandatory C\# desktop validation and authorization checks, which act as the final security gate.

11. C# Desktop Implementation Guidance

The LocalEndpoint Connect desktop application acts as the resilient edge node, bridging modern async paradigms with native Windows security primitives.

Idiomatic .NET Parity

\[Platform fact\] Network requests utilize System.Net.Http.HttpClient integrated with Microsoft.Extensions.Resilience for pipeline management (handling circuit breaking and outbox retries). Asynchronous streams leveraging IAsyncEnumerable\<T\> efficiently process incoming WebSocket commands. \[Protocol requirement\] Every long-running operation must accept a CancellationToken mapped to the dispatch coordinator's abort signal, ensuring immediate resource cleanup without blocking the UI thread (SynchronizationContext). \[Protocol requirement\] To satisfy JCS requirements, the C\# client cannot rely on the default non-deterministic System.Text.Json serialization for payload hashing. It must utilize an RFC 8785 compliant canonicalizer (e.g., Baqhub.Packages.JsonCanonicalization) to guarantee that the signature generated over the bytes exactly matches the backend's validation bytes3. Discriminated unions are modeled using abstract base records and pattern matching. DPAPI integration for token storage relies on P/Invoke wrappers to advapi32.dll (CredWrite, CredRead) targeting the Windows Credential Store, ensuring JIT-safe memory zeroing of sensitive buffers after use43.

Interface Sketch (C#)

C\# public async Task\<ActionReceipt\> DispatchActionAsync( Guid deviceId, ActionEnvelope envelope, string dpopProof, string token, CancellationToken ct) { var request \= new HttpRequestMessage(HttpMethod.Post, $"/v1/devices/{deviceId}/actions"); request.Headers.Authorization \= new AuthenticationHeaderValue("DPoP", token); request.Headers.Add("DPoP", dpopProof); request.Headers.Add("Idempotency-Key", envelope.IdempotencyKey.ToString());

// Canonicalize via RFC 8785 strict serializer request.Content \= new ByteArrayContent(JcsSerializer.Serialize(envelope)); request.Content.Headers.ContentType \= new MediaTypeHeaderValue("application/json");

using var response \= await \_httpClient.SendAsync(request, ct); if (\!response.IsSuccessStatusCode) { var problem \= await JsonSerializer.DeserializeAsync\<ProblemDetails\>(await response.Content.ReadAsStreamAsync(ct), cancellationToken: ct); throw new ProblemDetailsException(problem); } return await JsonSerializer.DeserializeAsync\<ActionReceipt\>(await response.Content.ReadAsStreamAsync(ct), cancellationToken: ct); }

12. Python Service Implementation Guidance

The Python components manage website routing, AI orchestrations, and REST coordination.

Idiomatic Python Parity

\[Platform fact\] Python leverages asyncio for the web gateway. Incoming payloads are validated against the OpenAPI-derived schemas utilizing Pydantic v245. Pydantic ensures rigorous static-type enforcement at runtime, safely coercing valid primitives and rejecting malformed envelopes. \[Distributed-systems synthesis\] Dependency drift in Python is managed via strict lockfiles (e.g., Poetry or uv). \[Protocol requirement\] To validate incoming DPoP signatures, the Python middleware uses the pure-Python rfc8785 package to canonicalize the request body, computing the hash to verify against the DPoP ath claim, and subsequently validating the JWT signature using the ECDSA public key extracted from the cnf claim8. Python's asyncio.CancelledError must be explicitly caught to ensure database connections and partial states are rolled back safely48.

Interface Sketch (Python)

Python async def dispatch\_action(self, device\_id: uuid.UUID, envelope: ActionEnvelope, dpop\_proof: str, token: str) \-\> dict: headers \= { "Authorization": f"DPoP {token}", "DPoP": dpop\_proof, "Idempotency-Key": str(envelope.idempotency\_key), "Content-Type": "application/json" } try: response \= await self.\_client.post(f"/v1/devices/{device\_id}/actions", content=rfc8785.dumps(envelope.to\_dict()), headers=headers) if response.status\_code \== 202: return response.json()

problem \= response.json() raise ProblemDetailsException(problem\["type"\], problem\["title"\], problem\["status"\], problem\["detail"\]) except asyncio.CancelledError: raise

13. Browser and Server TypeScript Guidance

TypeScript implementations diverge significantly based on their runtime trust boundaries.

Browser TypeScript

\[Protocol requirement\] Browser clients have no secure hardware storage. DPoP key pairs must be generated utilizing window.crypto.subtle.generateKey with the extractable: false attribute, guaranteeing the private key remains locked inside the browser's cryptographic module, immune to JavaScript-based XSS exfiltration8. Tokens are kept strictly in ephemeral worker scopes. To bypass CORS complexity and CSRF vulnerabilities, the browser relies solely on DPoP Authorization headers rather than ambient cookies. Cancellation is mapped to the standard AbortController API.

Server TypeScript

\[Platform fact\] Server-side TypeScript (Node.js or Bun) has access to robust memory and cloud secret managers. Payload validation utilizes Zod to map static TypeScript definitions to runtime enforcement rules, protecting against static type evasion. Server TypeScript manages the Server-Sent Events (SSE) connections pushing ActionReceipt updates, handling AbortSignal events to gracefully terminate connections.

Interface Sketch (TypeScript)

TypeScript async dispatchAction(deviceId: string, envelope: ActionEnvelope, dpopProof: string, token: string, signal?: AbortSignal): Promise\<ActionReceipt\> { const response \= await this.fetchFn(\/v1/devices/${deviceId}/actions\, { method: "POST", headers: { "Authorization": \DPoP ${token}\, "DPoP": dpopProof, "Idempotency-Key": envelope.idempotencyKey, "Content-Type": "application/json" }, body: canonicalize(envelope), // RFC 8785 strict canonicalization signal });

if (response.ok) return await response.json() as ActionReceipt;

const problem \= await response.json(); throw new ProblemDetailsError(problem.type, problem.title, response.status, problem.detail); }

14. Rust Service Implementation Guidance

Rust is deployed for message brokering and critical workers where latency, memory safety, and high-throughput concurrency are paramount.

Idiomatic Rust Parity

\[Platform fact\] Rust leverages the borrow checker to enforce strict ownership. Errors are modeled idiomatically using the thiserror crate, converting Problem Details into strongly-typed Result\<T, E\> enumerations. Payload serialization utilizes serde and serde\_json, paired with serde\_json\_canonicalizer to ensure 100% RFC 8785 compliance when computing payload hashes for validation50. \[Distributed-systems synthesis\] Rust's asynchronous runtime, Tokio, presents unique cancellation safety challenges. When a Tokio future is dropped (e.g., due to a closed client connection triggering a tokio::select\! macro cancellation), execution halts immediately at the exact .await point53. \[Protocol requirement\] To prevent database corruption from partial writes, all database updates must be wrapped in atomic SQL transactions. If a future is canceled mid-flight, the Drop trait automatically rolls back the uncommitted transaction, preserving data integrity54. Graceful shutdown is managed explicitly using tokio\_util::sync::CancellationToken57.

Interface Sketch (Rust)

Rust pub async fn dispatch\_action(&self, device\_id: Uuid, envelope: \&ActionEnvelope, dpop\_proof: &str, token: &str) \-\> Result\<ActionReceipt, ClientError\> { let response \= self.client.post(&format\!("/v1/devices/{}/actions", device\_id)) .header("Authorization", format\!("DPoP {}", token)) .header("DPoP", dpop\_proof) .header("Idempotency-Key", envelope.idempotency\_key.to\_string()) .body(serde\_json\_canonicalizer::to\_vec(envelope)?) // RFC 8785 canonical bytes .send() .await?;

if response.status().is\_success() { Ok(response.json::\<ActionReceipt\>().await?) } else { let problem \= response.json::\<ProblemDetails\>().await?; Err(ClientError::ApiProblem(problem.title, problem.status, problem.detail)) } }

15. Cross-Language Parity and Conformance Corpus

Achieving seamless interoperability across C\#, Python, TypeScript, and Rust necessitates deterministic, automated verification. Unavoidable runtime differences (e.g., Python's dynamic typing vs. Rust's strict compilation, .NET's UI thread synchronization) are mitigated by enforcing parity exclusively at the network boundary. \[Protocol requirement\] The project maintains a repository-neutral "Golden Conformance Corpus" containing thousands of synthetic JSON test vectors30. The corpus includes:

  1. Valid nested JSON objects and their mathematically proven JCS-canonicalized byte arrays3.
  2. DPoP JWTs signed with known ES256 private keys, alongside matching authorization headers.
  3. Problem Details objects mapped to specific error scenarios.
  4. Edge cases: missing Idempotency-Key headers, expired timestamps, and malformed schemas.

\[Protocol requirement\] Continuous Integration (CI) pipelines in all four language repositories must consume this exact corpus. A deterministic fake server and fake desktop transport will be designed to simulate success, timeouts, reordered events, and cancellation races without requiring live network access. Furthermore, utilizing Property-Based Testing frameworks (e.g., proptest in Rust, Hypothesis in Python, fast-check in TypeScript, and FsCheck in C\#) will generate randomized, valid permutations of action envelopes, identifying rare edge-case panics in parsing and deserialization logic58.

16. Evolution, Deployment, and Rollback

Managing schemas across distributed edge clients and cloud backends requires strict compatibility guardrails to prevent widespread outages. \[Protocol requirement\] Schema evolution follows an append-only discipline. Developers may add optional fields to an ActionEnvelope, but renaming existing fields, altering data types, or deleting fields constitutes a breaking change. Breaking changes require a major API version increment in the URI (e.g., /v2/devices/...). Unknown fields encountered by older clients must be safely ignored without failing deserialization, providing downgrade resistance. \[Platform fact\] Deployments utilize canary rollouts. Proxies inspect HTTP Accept headers for version negotiation (e.g., Accept: application/vnd.example.v2+json) to route traffic to newer API versions. Because the C\# desktop updates asynchronously via user action, the backend must support dual-reading older API schema versions for a minimum 90-day deprecation window. Emergency disablement is governed by strict kill switches that force hard upgrades for security-critical vulnerabilities.

17. Open Product Decisions and Validation Questions

While this architectural specification establishes the cryptographic and topological framework, several operational thresholds require internal product-owner validation. The following ledger separates known requirements from assumptions requiring verification:

  • Local Engine Override: Can the account owner provide multi-factor authentication (MFA) on the browser to override a local policy engine denial, or does the local policy engine have absolute, non-bypassable veto power? (Assumption: Absolute veto power; requires product security validation).
  • Persistent Policy Lifetime: How long can a "carefully disclosed persistent approval" remain valid inside the desktop local policy engine before demanding explicit user re-authorization?
  • Message Broker Backing: What specific message broker (e.g., Kafka, RabbitMQ, NATS) is backing the delivery mechanism, and what is its specific retention window for disconnected offline desktop catch-up?11
  • Secret Retrieval Performance: What is the target latency and error-recovery behavior when the website backend retrieves configuration secrets from the cloud vault under peak load?
  • Desktop Throttling: What are the dynamic resource exhaustion thresholds (CPU/RAM) that would trigger automatic 429 Retry-After backpressure from the desktop executor to the dispatch coordinator?

18. Limitations and Sources

\[Distributed-systems synthesis\] This architecture inherently relies on eventual consistency for remote state tracking. During a complete network partition or ISP failure, remote coordination is physically impossible. However, the strict separation of local capabilities ensures that the C\# desktop's local-only features remain fully functional without backend dependency. The performance overhead of computing DPoP signatures per request introduces a negligible CPU cost but prevents token extraction scaling. This report integrates facts synthesized from IETF standards, including RFC 9449 (DPoP), RFC 8785 (JCS), RFC 9457 (Problem Details), and RFC 8252 (Native Apps).

Works cited

  1. 3.0.0 | AsyncAPI Initiative for event-driven APIs, https://www.asyncapi.com/docs/reference/specification/v3.0.0
  2. OpenAPI 3.1 vs 3.0: Governance & Contract Testing (2026), https://totalshiftleft.ai/blog/openapi-3-1-vs-3-0-what-changed-for-testing
  3. RFC 8785: JSON Canonicalization Scheme (JCS), https://www.rfc-editor.org/info/rfc8785/
  4. RFC 8785 \- JSON Canonicalization Scheme (JCS) \- IETF Datatracker, https://datatracker.ietf.org/doc/html/rfc8785
  5. RFC 8252 \- OAuth 2.0 for Native Apps \- Datatracker \- IETF, https://datatracker.ietf.org/doc/html/rfc8252
  6. Support http://localhost (loopback) redirect URIs for OAuth apps — RFC 8252 \- Product \- Asana Forum, https://forum.asana.com/t/support-http-localhost-loopback-redirect-uris-for-oauth-apps-rfc-8252/1136224
  7. Demonstrating Proof of Possession (DPoP) \- About Corppass, https://docs.corppass.gov.sg/technical-specifications/technical-concepts/demonstrating-proof-of-possession-dpop
  8. DPoP (RFC 9449\) explained: How sender-constrained OAuth tokens make token theft a non-event \- WorkOS, https://workos.com/blog/dpop-rfc-9449-explained
  9. OAuth DPoP | FusionAuth Docs, https://fusionauth.io/docs/lifecycle/authenticate-users/oauth/dpop
  10. How to implement the Outbox pattern in Go and Postgres : r/golang \- Reddit, https://www.reddit.com/r/golang/comments/1s606df/how\_to\_implement\_the\_outbox\_pattern\_in\_go\_and/
  11. Transactional Inbox and Outbox Patterns: Practical Guide for Reliable Messaging \- bool.dev, https://bool.dev/blog/detail/inbox-and-outbox-patterns
  12. RFC 9449 \- OAuth 2.0 Demonstrating Proof of Possession (DPoP) \- IETF Datatracker, https://datatracker.ietf.org/doc/html/rfc9449
  13. Understanding RFC 9457: Problem Details for HTTP APIs | by Muhammad Umair \- Medium, https://medium.com/@mhd.umair/understanding-rfc-9457-problem-details-for-http-apis-6bdb675e685f
  14. RFC 9457: Problem Details for HTTP APIs, https://www.rfc-editor.org/info/rfc9457/
  15. RFC 8252: OAuth 2.0 for Native and Mobile Apps \- YouTube, https://www.youtube.com/watch?v=l6zGU5tb8WM
  16. Implement the Transactional Outbox Pattern by Using Azure Cosmos DB \- Microsoft Learn, https://learn.microsoft.com/en-us/azure/architecture/databases/guide/transactional-out-box-cosmos
  17. DpapiDataProtector Class (System.Security.Cryptography) | Microsoft Learn, https://learn.microsoft.com/en-us/dotnet/api/system.security.cryptography.dpapidataprotector?view=netframework-4.8.1
  18. Key encryption at rest in Windows and Azure using ASP.NET Core | Microsoft Learn, https://learn.microsoft.com/en-us/aspnet/core/security/data-protection/implementation/key-encryption-at-rest?view=aspnetcore-10.0
  19. OpenAPI 3.1 vs 3.0: what's new and what to use in 2026, https://sourced.sh/blog/openapi-3-1-vs-3-0-what-to-use
  20. Avro vs Protobuf vs JSON Schema: Kafka Serialization Compared (2026) | Conduktor, https://www.conduktor.io/glossary/avro-vs-protobuf-vs-json-schema
  21. Tools | AsyncAPI Initiative for event-driven APIs, https://www.asyncapi.com/tools?langs=TypeScript
  22. Protobuf vs JSON: Choosing the Right API Serialization Format \- Zuplo, https://zuplo.com/learning-center/protobuf-vs-json-api-serialization
  23. Moving from JSON to Protocol Buffers(Protobuf): When and Why? | by Damini Bansal, https://daminibansal.medium.com/moving-from-json-to-protocol-buffers-protobuf-when-and-why-ea61701072eb
  24. Smithy: Build services. Build SDKs. Build with Smithy., https://smithy.io/
  25. The Anatomy of a Service \- Smithy Rust, https://smithy-lang.github.io/smithy-rs/design/server/anatomy.html
  26. Converting Smithy to OpenAPI, https://smithy.io/2.0/guides/model-translations/converting-to-openapi.html
  27. \[PROPOSAL\] Replace Smithy with a native OpenAPI spec \#189 \- GitHub, https://github.com/opensearch-project/opensearch-api-specification/issues/189
  28. json-canon: A Strict RFC 8785 Implementation in Go for Deterministic JSON, https://dev.to/lenny321/json-canon-a-strict-rfc-8785-implementation-in-go-for-deterministic-json-3mfg
  29. The JSON Canonicalisation Scheme (RFC 8785\) in action and how to secure JSON objects with HMAC \- Connect2id, https://connect2id.com/blog/how-to-secure-json-objects-with-hmac
  30. JCS Canonicalisation Discipline for Agentic-Payment Receipts \- IETF, https://www.ietf.org/archive/id/draft-hopley-x402-canonicalisation-jcs-v1-02.html
  31. Is canonical JSON signing (RFC 8785\) the right primitive for agent identity? \- Reddit, https://www.reddit.com/r/cryptography/comments/1qdzlb9/is\_canonical\_json\_signing\_rfc\_8785\_the\_right/
  32. draft-ietf-httpapi-idempotency-key-header-00, https://datatracker.ietf.org/doc/html/draft-ietf-httpapi-idempotency-key-header-00
  33. Idempotency keys in 2026: how to make REST API retries safe \- eCorpIT, https://ecorpit.com/idempotency-keys-rest-api-safe-retries-2026/
  34. Native app login flow for Internet Identity \- DFINITY Forum, https://forum.dfinity.org/t/native-app-login-flow-for-internet-identity/68219
  35. Securing applications with Demonstrating Proof-of-Possession (DPoP) \- Keycloak, https://www.keycloak.org/securing-apps/dpop
  36. Demonstrating Proof-of-Possession (DPoP) \- Auth0 Docs, https://auth0.com/docs/secure/sender-constraining/demonstrating-proof-of-possession-dpop
  37. ProtectedData Class (System.Security.Cryptography) \- Microsoft Learn, https://learn.microsoft.com/en-us/dotnet/api/system.security.cryptography.protecteddata?view=net-11.0-pp
  38. Comparing Exactly-Once Delivery Strategies for External Sinks in Stream Processing Systems, https://umu.diva-portal.org/smash/get/diva2:2076245/FULLTEXT01.pdf
  39. Exactly Once in Distributed Systems | Serverless Blog, https://serverless-architecture.io/blog/exactly-once-in-distributed-systems/
  40. Exactly-Once Semantics: Processing Data Without Duplication or Loss \- Medium, https://thedatatrait.medium.com/exactly-once-semantics-processing-data-without-duplication-or-loss-e1ab3fc55099
  41. Distributed Transaction Patterns \- Handling Transactions At Scale \- Pask Software, https://pasksoftware.com/distributed-transaction-patterns/
  42. Protobuf vs JSON: Performance, Efficiency & API Speed \- Gravitee, https://www.gravitee.io/blog/protobuf-vs-json
  43. AdysTech.CredentialManager 3.1.0 \- NuGet, https://www.nuget.org/packages/AdysTech.CredentialManager
  44. GitHub \- AdysTech/CredentialManager: C\# wrapper around CredWrite / CredRead functions to store and retreive from Windows Credential Store, https://github.com/AdysTech/CredentialManager
  45. JSON Schema | Pydantic Docs, https://pydantic.dev/docs/validation/dev/concepts/json\_schema/
  46. Json schema | Pydantic Docs, https://pydantic.dev/docs/validation/2.5/concepts/json\_schema/
  47. rfc8785 \- PyPI, https://pypi.org/project/rfc8785/
  48. JSON | Pydantic Docs, https://pydantic.dev/docs/validation/dev/concepts/json/
  49. Welcome to Pydantic, https://pydantic.dev/docs/validation/dev/get-started/
  50. evik42/serde-json-canonicalizer: JSON Canonicalization Scheme (JCS) implementation in rust on top of serde\_json \- GitHub, https://github.com/evik42/serde-json-canonicalizer
  51. Overview · Serde, https://serde.rs/
  52. serde\_json\_canonicalizer \- Rust \- Docs.rs, https://docs.rs/serde\_json\_canonicalizer
  53. Cancel safety in Rust's Future \- Asteromorph Tech Blog, https://blog.asteromorph.com/future-cancel/
  54. RFD 400 Dealing with cancel safety in async Rust \- Oxide RFD, https://rfd.shared.oxide.computer/rfd/0400
  55. Cancelling async Rust \- sunshowers, https://sunshowers.io/posts/cancelling-async-rust/
  56. Build with Naz : Rust async in practice tokio::select\!, actor pattern & cancel safety, https://developerlife.com/2024/07/10/rust-async-cancellation-safety-tokio/
  57. CancellationToken in tokio\_util::sync \- Rust \- Docs.rs, https://docs.rs/tokio-util/latest/tokio\_util/sync/struct.CancellationToken.html
  58. Finding bugs with Claude and property-based testing \- Anthropic, https://www.anthropic.com/research/property-based-testing
  59. What is Property-based Testing? \- Mayhem Security, https://www.mayhem.security/blog/what-is-property-based-testing
  60. Property-based testing \- how it works and when to use it | Antithesis Docs, https://antithesis.com/docs/resources/property\_based\_testing/
  61. Understanding Property-based Testing: An Introduction With TypeScript \- Medium, https://medium.com/@LRNZ09/property-based-testing-a-hands-on-introduction-with-typescript-c4d0703a5772
  62. Proptest: property testing in Rust \- Ivan Yurchenko, https://ivanyu.me/blog/2024/09/22/proptest-property-testing-in-rust/