要点: PauseやPartition、Expiry後にProcessがOwnerかをLockだけでは証明できません。
課題
Leaseを失った停止Workerが再開すると、新Ownerと同時に書けます。Resource側の拒否が必要です。
単純な対策だけでは不十分な理由
Network DelayによりClientはOwnershipを断定できません。
At-least-onceとIdempotencyがLeader Electionより安全な場合があります。
処理フロー
Lease要求→Coordinator
Fencing Token→Worker
有限Work→Resource
古いToken拒否
アーキテクチャ上の判断
Ownership Partition
ShardをWorkerへ割当てLockを減らします。
Monotonic Fencing
Storageで最終Tokenと比較します。
Critical Sectionを有限化
Leaseより短いDeadlineを使います。
さらに深く考える
TTLはOwnershipではない
Storage Tokenが実行中Codeを拒否します。
Product ConflictをLockで隠さない
共同編集にはVersionとConflict UXを使います。
実装手順
- PartitioningやIdempotencyでLockを減らします。
- 期限付きLeaseと増加Tokenを使います。
- Resourceが古いTokenをAtomicに拒否します。
技術例: Fenced Update
lease = coordinator.acquire(resourceId, ttl = 10s)
result = compute(deadline = lease.expiresAt - 2s)
UPDATE resource
SET value = :result, fence = :token
WHERE id = :id AND fence < :tokenCoordinator Lockだけでは停止した旧Ownerの再開を防げません。
想定すべき障害パターン
- PauseがLeaseを超えます。
- Coordinator Quorumが失われます。
- 外部CallがLease移動後に完了します。
監視すべきシグナル
| シグナル | 確認する理由 |
|---|---|
| Acquire・Renew Failure | 競合を示します。 |
| Stale Token Reject | 旧Ownerの封じ込めを示します。 |
| Critical Duration | Lease仮定違反を検出します。 |
設計の検証方法
- HolderをTTL超過Pauseします。
- CoordinatorだけPartitionします。
- 増加TokenだけCommitするか試験します。
安全なRollout計画
IdempotencyとOptimistic Versionを先行し、必要OperationだけFencingへ移行します。
本番前チェックリスト
- Clock仮定を最小化します。
- Renew失敗時は新Workを止めます。
- 長OperationをCheckpoint化します。
まとめ
LockはAttemptを調整し、ResourceのFencingがCorrectnessを守ります。
