دسکتاپ، Worker و محاسبات محلی · فصل ۲ — Supervisor، Executor و Coordinator · 181
Local Coordinator Skeleton and Protocol Role
Design a transport-neutral local coordinator skeleton with explicit component roles, versioned request/response envelopes, request correlation, typed errors, idempotency semantics for retryable operations, capability/role checks, bounded timeouts, and compatibility rules that keep supervisor orchestration separate from executor implementation. میتواند «Local Coordinator Skeleton و Protocol Role» را برای یک node محلی با identity، state، privilege و recovery boundary مناسب طراحی کند.
Lesson summary
Design a transport-neutral local coordinator skeleton with explicit component roles, versioned request/response envelopes, request correlation, typed errors, idempotency semantics for retryable operations, capability/role checks, bounded timeouts, and compatibility rules that keep supervisor orchestration separate from executor implementation.
میتواند «Local Coordinator Skeleton و Protocol Role» را برای یک node محلی با identity، state، privilege و recovery boundary مناسب طراحی کند.
This lesson produces
میتواند «Local Coordinator Skeleton و Protocol Role» را برای یک node محلی با identity، state، privilege و recovery boundary مناسب طراحی کند.
Who it is for
Foundation
Use a guided lesson-specific evidence matrix and one worked negative case.
Repair
Re-run only the failed owned dimension with a smaller deterministic synthetic fixture.
Experienced
Start from mixed authority/policy/evidence records; require explicit trade-offs and provenance.
Prerequisites
1. The real problem: a successful socket is not a correct protocol
When a supervisor and executor share in-process objects, ad-hoc JSON, or fire-and-forget messages, a dropped connection or simple retry can execute the same state-changing operation twice. This lesson produces Local Coordinator Protocol Envelope & Role Contract v1: a transport-neutral contract with explicit roles, protocol version, request identity, deadline, capability context, typed result/error states, and retry semantics so the system can tell what was requested, accepted, executed, and returned.
2. LOC-008 owns the coordinator protocol boundary
This lesson owns the coordinator/supervisor/executor roles and the protocol envelope between them. Worker enrollment and short-lived identity belong to LOC-009; health telemetry belongs to LOC-010; executor sandbox internals belong to LOC-007. A successful local transport proves only that a delivery path worked. It does not prove authorization, execution success, or worker health.
3. Separate roles before designing the message schema
The supervisor orchestrates and requests work. The coordinator validates, correlates, performs bounded routing, and maintains protocol state. The executor performs operations inside its own authority boundary. If the coordinator imports executor implementation details directly, the process boundary stops being a meaningful protocol boundary and versioning/recovery become difficult to audit.
4. What JSON-RPC contributes as a reference pattern
JSON-RPC 2.0 uses an id in a Request to correlate the Response. A Notification omits id and the server does not send a response for it. MAKNOW is not required to use JSON-RPC; the lesson uses this distinction only as a reference pattern for separating confirmable requests from messages whose contract does not require confirmation.
5. Every envelope needs explicit version and identity
At minimum retain protocol_version, message_type, operation, request_id, correlation_id, sender/receiver role, and payload schema. Do not infer the version from a transport path or implicit method name. Request identity should remain stable across retries so a response, duplicate, or timeout can be tied back to the original intent.
6. A retryable state change needs idempotency semantics
For retryable state-changing operations, define an idempotency_key and duplicate rule. If the connection drops after acceptance and the supervisor retries with a new identity, the executor may start the same job twice. Reusing the same idempotency identity should let the system replay a prior result, mark the request as duplicate, or query status instead of blindly re-executing it.
7. Limit notification semantics to effects that need no confirmation
Because a notification has no response, it is a poor fit for an operation whose success or failure must be audited. If start_job requires confirmed acceptance/result semantics, notification behavior is insufficient. Fire-and-forget should be restricted to effects where missing confirmation is explicitly acceptable and does not leave important authority or state ambiguous.
8. Deadline and timeout belong inside the contract
Carry a deadline in the envelope and preserve timeout as a typed state. After the deadline, a late response must not silently become ordinary success. The protocol should define whether the server-side operation may still be running, whether a status query is required, and whether retry is allowed. Timeout means the result was not established within the expected window, not that execution definitely never happened.
9. Check role/capability before dispatch
The coordinator compares the operation with sender role, receiver role, and role_capability before dispatch. A valid method name from a role without the required capability yields DENIED. This lesson does not build a complete authorization system; it ensures the protocol skeleton does not treat a local transport as sufficient authority.
10. Typed errors are better than ambiguous exceptions
A response should contain either a success result or a typed error while preserving correlation identity. error_code and bounded detail should be sufficient for recovery and audit. DENIED, TIMEOUT, DUPLICATE, and INCOMPATIBLE must not collapse into one generic failure because each state has different retry and recovery semantics.
11. What Protocol Buffers contributes to compatibility reasoning
In Protocol Buffers, a field number identifies a field on the wire and must not be reused. When a field is removed, reserving its number prevents an incompatible later reuse. MAKNOW does not require protobuf; it uses this constraint as a compatibility pattern: an added optional field should not break an older peer, and a retired field must not reappear later with a new meaning.
12. Unknown and retired fields need explicit rules
Version evolution requires an unknown_field_rule and a reserved_field rule. An older peer may ignore a new optional field only when the semantic core remains valid. If a retired field was required for correctness, ignoring its absence is not enough; the result must remain INCOMPATIBLE or require migration.
13. Transport binding must not define protocol semantics
A Unix-domain socket, Windows named pipe, or another local transport is only the carrier. request_id, version, deadline, role checks, idempotency, typed result/error, and audit semantics must survive a transport change. Transport-specific ACL or authentication may add evidence, but the protocol contract must not become identical to the transport API.
14. Deterministic failure probes
Break four tempting shortcuts: (1) a state-changing notification with no confirmation; (2) a retry with a new request identity after uncertain acceptance; (3) a sender role that lacks the operation capability; and (4) an old peer faced with an incompatible schema or reused retired field. Also test deadline expiry and duplicate replay. The learner lab exposes evidence, not the final labels.
15. Transfer: Unix socket → Windows local transport plus schema evolution
Replace the Unix-domain socket with a Windows local transport, then add one optional response field and retire an old field. Keep protocol versioning, request identity, role/capability checks, deadline, typed errors, duplicate handling, and audit semantics stable. Because both transport and schema evidence changed, compatibility is recomputed from the new evidence rather than copied from the baseline.
Assessment
There is no answer key in this lesson pack; answer it yourself and mark honestly. "Needs review" sends the lesson to your review queue.
Q1 application
Construct a versioned coordinator request/response envelope for a retryable local start_job operation.
Q2 diagnosis
Explain why a dropped connection after acceptance cannot be repaired by sending the same state-changing intent with a fresh request identity.
Q3 decision
Issue a typed result when the sender lacks the operation capability or the request deadline has expired.
Q4 transfer
Move the same contract from a Unix-domain socket to a Windows local transport while adding an optional response field and reserving a retired field.
Assessment rubric
- Role boundary — critical: supervisor, coordinator, and executor responsibilities remain distinct.
- Correlation — critical: request/response identity is explicit and retry-safe.
- Idempotency — critical: retryable state changes cannot be blindly executed twice.
- Capability/deadline — critical: unauthorized or expired requests remain typed non-success states.
- Compatibility — critical: version evolution preserves optional-field and retired-field rules.
- Transfer — critical: transport changes without changing protocol semantics.
References & freshness
Case studies
Lesson visuals
Lab files
Implement evaluate_protocol(case) in starter.py. Keep protocol version, role/capability, correlation, idempotency/duplicate state, deadline, compatibility, decision, and reason separate.
The eight fixtures are synthetic and offline. They do not contain final decision labels. case_08 is the transfer: Windows local transport plus an added optional response field and a retired field that remains reserved. Run python run_checks.py to verify only learner-visible structure.