Skip to content

Commit b52a203

Browse files
docs(adr): enforce MADR on ADR-0009 and ADR-0011; extract design specs to /docs/design; update cross-references
Co-authored-by: Junie <junie@jetbrains.com>
1 parent ad6fc92 commit b52a203

5 files changed

Lines changed: 257 additions & 127 deletions

File tree

Lines changed: 55 additions & 59 deletions
Original file line numberDiff line numberDiff line change
@@ -1,11 +1,17 @@
1-
# ADR-0009: WebSocket Communication Protocol
1+
---
2+
status: accepted
3+
date: 2026-02-11
4+
title: WebSocket Communication Protocol
5+
decision-makers:
6+
consulted:
7+
informed:
8+
---
29

3-
**Status:** Accepted
4-
**Date:** 2026-02-11
10+
# WebSocket Communication Protocol
511

612
---
713

8-
## Context
14+
## Context and Problem Statement
915

1016
Tank Royale needs real-time bidirectional communication between server and clients (bots, observers) that supports:
1117

@@ -18,7 +24,7 @@ Tank Royale needs real-time bidirectional communication between server and clien
1824

1925
---
2026

21-
## Decision
27+
## Decision Outcome
2228

2329
Use **WebSocket protocol with JSON messages** for all server-client communication.
2430

@@ -30,7 +36,46 @@ Use **WebSocket protocol with JSON messages** for all server-client communicatio
3036

3137
---
3238

33-
## Rationale
39+
### Consequences
40+
41+
- ✅ Real-time communication at 30 TPS
42+
- ✅ Cross-platform bot development
43+
- ✅ Browser-based clients possible
44+
- ✅ Simple deployment (no broker required)
45+
- ❌ JSON parsing overhead vs binary protocols
46+
- ❌ Schema evolution requires coordination
47+
48+
## Considered Options
49+
50+
- WebSocket + JSON (chosen)
51+
- HTTP REST + polling
52+
- gRPC
53+
- Custom TCP/UDP protocol
54+
- Message Queue (brokered)
55+
56+
## Pros and Cons of the Options
57+
58+
### WebSocket + JSON (chosen)
59+
60+
Good, because real-time bidirectional communication, browser support, language-agnostic JSON, schema validation.
61+
62+
Bad, because JSON overhead versus binary formats; schema evolution coordination required.
63+
64+
### HTTP REST + polling
65+
66+
Bad, because too much latency for 30 TPS; server push awkward.
67+
68+
### gRPC
69+
70+
Good, because strong contracts and streaming; Bad, because poor browser support and higher deployment complexity.
71+
72+
### Custom TCP/UDP
73+
74+
Good, because low overhead; Bad, because reinvents protocol features; no browser support; higher maintenance burden.
75+
76+
### Message Queue
77+
78+
Good, decoupling via broker; Bad, unnecessary operational complexity for this use case.
3479

3580
**Why WebSocket:**
3681

@@ -55,57 +100,8 @@ Use **WebSocket protocol with JSON messages** for all server-client communicatio
55100

56101
---
57102

58-
## Implementation
59-
60-
**Connection flow:**
61-
62-
```
63-
Bot → Server: WebSocket Connect
64-
Server → Bot: server-handshake {sessionId}
65-
Bot → Server: bot-handshake {sessionId, name}
66-
Server → Bot: game-started-event
67-
Loop: Server → Bot: tick-event, Bot → Server: bot-intent
68-
```
69-
70-
**Example messages:**
71-
72-
```json
73-
// Server → Bot
74-
{
75-
"type": "tick-event-for-bot",
76-
"turnNumber": 42,
77-
"botState": {
78-
...
79-
},
80-
"events": [
81-
...
82-
]
83-
}
84-
85-
// Bot → Server
86-
{
87-
"type": "bot-intent",
88-
"turnRate": 5,
89-
"targetSpeed": 8,
90-
"firepower": 3
91-
}
92-
```
93-
94-
---
95-
96-
## Consequences
97-
98-
- ✅ Real-time communication at 30 TPS
99-
- ✅ Cross-platform bot development
100-
- ✅ Browser-based clients possible
101-
- ✅ Simple deployment (no broker required)
102-
- ❌ JSON parsing overhead vs binary protocols
103-
- ❌ Schema evolution requires coordination
104-
105-
---
106-
107-
## References
103+
## More Information
108104

109-
- [WebSocket RFC 6455](https://tools.ietf.org/html/rfc6455)
110-
- [Schema YAML Definitions](/schema/schemas/README.md) — Raw YAML schema files
111-
- [Protocol Flow Diagrams](/docs/architecture/models/flows/README.md) — Sequence diagrams for all protocol flows
105+
- Detailed protocol design, flows, and examples: `/docs/design/websocket-protocol.md`
106+
- Schema YAML Definitions: `/schema/schemas/README.md`
107+
- Protocol Flow Diagrams: `/docs/architecture/models/flows/README.md`
Lines changed: 44 additions & 68 deletions
Original file line numberDiff line numberDiff line change
@@ -1,26 +1,32 @@
1-
# ADR-0011: Real-Time Game Loop Architecture
1+
---
2+
status: accepted
3+
date: 2026-02-11
4+
title: Real-Time Game Loop Architecture
5+
decision-makers:
6+
consulted:
7+
informed:
8+
---
29

3-
**Status:** Accepted
4-
**Date:** 2026-02-11
10+
# Real-Time Game Loop Architecture
511

612
---
713

8-
## Context
14+
## Context and Problem Statement
915

1016
Tank Royale is a real-time programming game where multiple bots battle simultaneously.
1117

1218
**Problem:** How to synchronize actions of multiple bots while ensuring deterministic, fair gameplay?
1319

14-
**Requirements:**
20+
## Decision Drivers
1521
- Consistent frame rate (30 TPS target)
1622
- Deterministic physics (reproducible results)
1723
- Fair synchronization (all bots see same state)
18-
- Handle bot timeouts gracefully
19-
- Support pause/resume for debugging
24+
- Graceful handling of bot timeouts
25+
- Support for pause/resume for debugging
2026

2127
---
2228

23-
## Decision
29+
## Decision Outcome
2430

2531
Use a **turn-based discrete tick loop** at **30 TPS** with:
2632
- Server as authoritative game state manager
@@ -30,14 +36,31 @@ Use a **turn-based discrete tick loop** at **30 TPS** with:
3036

3137
---
3238

33-
## Rationale
39+
## Considered Options
40+
- Discrete tick-based loop at fixed 30 TPS (chosen)
41+
- Continuous real-time loop
42+
- Event-driven async processing
43+
- Client-side lockstep synchronization
44+
- Hybrid tick + event approach
45+
46+
## Pros and Cons of the Options
47+
48+
### Discrete tick-based loop at 30 TPS (chosen)
49+
Good, because deterministic, fair synchronization, predictable performance, and robust timeout handling.
50+
51+
Bad, because fixed frame rate and quantized movement.
3452

35-
**Why tick-based loop:**
36-
-**Deterministic**: Same inputs → same outputs (reproducible)
37-
-**Fair synchronization**: All bots receive identical game state simultaneously
38-
-**Timeout handling**: Bots can't stall the game (fixed deadline)
39-
-**Predictable performance**: 30 TPS = ~33ms per turn budget
40-
-**Network-friendly**: 30 TPS matches typical latency constraints
53+
### Continuous real-time
54+
Bad, because non-deterministic and synchronization issues.
55+
56+
### Event-driven async
57+
Bad, because race conditions and unfair network advantages.
58+
59+
### Client-side lockstep
60+
Bad, because slow clients can stall the entire game.
61+
62+
### Hybrid tick + event
63+
Bad, because added complexity without clear benefit in this context.
4164

4265
### Synchronization Pattern
4366

@@ -75,60 +98,13 @@ sequenceDiagram
7598

7699
---
77100

78-
## Implementation
79-
80-
### Game Loop State Machine
81-
82-
```mermaid
83-
stateDiagram-v2
84-
[*] --> WAIT_FOR_PARTICIPANTS: Server starts
85-
WAIT_FOR_PARTICIPANTS --> WAIT_FOR_READY: All bots connected
86-
WAIT_FOR_READY --> GAME_RUNNING: All bots ready
87-
GAME_RUNNING --> GAME_PAUSED: Pause requested
88-
GAME_PAUSED --> GAME_RUNNING: Resume requested
89-
GAME_RUNNING --> GAME_STOPPED: Battle ends
90-
GAME_STOPPED --> [*]
91-
92-
note right of GAME_RUNNING
93-
Main tick loop: 30 iterations/sec
94-
end note
95-
```
96-
97-
### Per-Tick Execution
98-
99-
```kotlin
100-
fun executeTurn() {
101-
// 1. Send tick events to all bots (same game state)
102-
bots.forEach { it.sendTickEvent(gameState) }
103-
104-
// 2. Collect intents with timeout (~30ms)
105-
val intents = bots.associateWith { bot ->
106-
try {
107-
bot.receiveIntent(timeout = botTimeoutMs)
108-
} catch (e: TimeoutException) {
109-
bot.sendSkippedTurnEvent()
110-
null // Late response
111-
}
112-
}
113-
114-
// 3. Apply all valid intents to physics
115-
applyIntents(intents.filterNotNull())
116-
updatePhysics()
117-
checkCollisions()
118-
119-
// 4. Maintain 30 TPS
120-
sleepToMaintainTPS()
121-
}
122-
```
101+
## More Information
123102

124-
**Configuration:**
125-
```bash
126-
java -jar server.jar --tps=30 --turn-timeout=30 --max-inactivity=30
127-
```
103+
- Detailed design, diagrams, and pseudo-code: `/docs/design/game-loop-architecture.md`
128104

129105
---
130106

131-
## Consequences
107+
### Consequences
132108

133109
- ✅ Deterministic physics (fair competition)
134110
- ✅ Timeout enforcement prevents game stalling
@@ -141,8 +117,8 @@ java -jar server.jar --tps=30 --turn-timeout=30 --max-inactivity=30
141117

142118
---
143119

144-
## References
120+
## More Information
145121

146-
- [Game Loop Patterns](https://gameprogrammingpatterns.com/game-loop.html)
147-
- [Server Implementation](/server/README.md)
122+
- Game Loop Patterns: https://gameprogrammingpatterns.com/game-loop.html
123+
- Server Implementation: `/server/README.md`
148124

docs/design/README.md

Lines changed: 14 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,14 @@
1+
# Design Documents
2+
3+
This directory contains detailed design documents that complement the Architecture Decision Records (ADRs) in `../decisions/`.
4+
5+
- ADRs capture the decision, context, options, and rationale (MADR format).
6+
- Design docs here capture specifications, flow details, diagrams, examples, and implementation-oriented material that would otherwise bloat an ADR.
7+
8+
Conventions:
9+
- Keep ADRs focused; put detailed specs here and link from ADRs under “More Information”.
10+
- Use descriptive filenames; cross-link with absolute project-root relative paths (starting with `/docs/…`).
11+
12+
Index:
13+
- [WebSocket Protocol](./websocket-protocol.md)
14+
- [Real-Time Game Loop](./game-loop-architecture.md)

0 commit comments

Comments
 (0)