Skip to content
Open
Show file tree
Hide file tree
Changes from 191 commits
Commits
Show all changes
277 commits
Select commit Hold shift + click to select a range
1dafa5b
refactor(client): deduplicate formatGoldValue via compactNumber, remo…
SYMBaiEX Apr 2, 2026
e091aa6
refactor(shared): replace remaining hardcoded 2147483647 with MAX_COINS
SYMBaiEX Apr 2, 2026
dca126f
refactor: export ContextMenuAction from shared, derive client type vi…
SYMBaiEX Apr 10, 2026
fdaa8a6
feat(shared): add special attack energy types, events, and constants
SYMBaiEX Apr 2, 2026
0f84b42
feat(shared,server): special attack energy system — server logic + ne…
SYMBaiEX Apr 2, 2026
410b4ff
feat(client): SpecialAttackBar component + CombatPanel integration
SYMBaiEX Apr 2, 2026
7f53de1
feat(shared): enhance MinimapWorker with roads, buildings, POIs, dest…
SYMBaiEX Apr 2, 2026
726dcb3
feat(client): wire Minimap to shared MinimapWorker for off-thread ove…
SYMBaiEX Apr 2, 2026
73b50f0
refactor(client): delete MinimapRenderer.ts (-941 lines), extract min…
SYMBaiEX Apr 2, 2026
3bc04cc
fix(shared): export MinimapWorkerManager from index.client.ts
SYMBaiEX Apr 2, 2026
4e9d0a1
fix(shared): use transparent clear for minimap overlay worker canvas
SYMBaiEX Apr 2, 2026
5268be1
fix(client): use ImageBitmap mode for minimap worker, not transferCon…
SYMBaiEX Apr 2, 2026
4af404a
fix(shared): always clear minimap worker canvas to transparent for ov…
SYMBaiEX Apr 2, 2026
2271a84
fix(client): correct minimap worker rotation sign — was inverted (sou…
SYMBaiEX Apr 2, 2026
4362bcc
fix(shared): fix double rotation in minimap worker — roads/buildings …
SYMBaiEX Apr 2, 2026
75c6249
fix(stream): normalize personal staging source and delivery truth
rndrntwrk Apr 8, 2026
1a27fc3
feat: add duel arena showcase and monitor screens
Apr 3, 2026
03e69de
feat: add HyperBet betting platform infrastructure
Apr 4, 2026
fe7d823
feat: polish duel arena spectator experience
Apr 5, 2026
bff1627
fix(stream): formalize canonical self-hls delivery on personal staging
rndrntwrk Apr 9, 2026
fcef486
[stream][00] Isolate enoomian staging secrets from shared project envs
rndrntwrk Apr 9, 2026
2dc3dc7
[stream][01] Persist authority state and add Cloudflare lifecycle dia…
rndrntwrk Apr 9, 2026
a143704
fix(stream): harden cloudflare authority branch blockers
rndrntwrk Apr 9, 2026
e243ffd
[stream][02] Add schema v3 broadcast timeline to betting/session payl…
rndrntwrk Apr 9, 2026
a97bcab
fix(stream): delay broadcast timeline phase rollover
rndrntwrk Apr 9, 2026
4cbddf6
fix(shared): restore terrain shared build on staging
rndrntwrk Apr 9, 2026
98ecc5c
fix(deploy): use supported client build in Docker
rndrntwrk Apr 9, 2026
5273182
Implement Cloudflare authority reconciliation
rndrntwrk Apr 10, 2026
ec23a1e
Fix Railway Docker install after sqlite strip
rndrntwrk Apr 10, 2026
29ac09d
Restore client equipment helper exports
rndrntwrk Apr 10, 2026
0b16fe7
Fix Hyperscapes Docker ESM runtime imports
rndrntwrk Apr 10, 2026
63a3eb0
Tighten Hyperscapes unified public origins
rndrntwrk Apr 10, 2026
a47ca9e
Tighten bettor overlay and renderer freshness authority
rndrntwrk Apr 10, 2026
8e7eba4
Fix staging bootstrap parity and delayed feed fields
rndrntwrk Apr 10, 2026
72baa6c
Fix Hyperscapes staging bun lockfile
rndrntwrk Apr 10, 2026
f438e04
Harden Hyperscapes staging runtime bootstrap
rndrntwrk Apr 11, 2026
9e7f01c
Fallback to packaged staging asset models
rndrntwrk Apr 11, 2026
c871e47
Point staging woodcutting assets at packaged models
rndrntwrk Apr 11, 2026
42d8f95
Normalize staging gathering manifest models
rndrntwrk Apr 11, 2026
734b495
Normalize stale staging tree asset paths
rndrntwrk Apr 11, 2026
1ac1e2f
Flatten packaged staging tree asset paths
rndrntwrk Apr 11, 2026
a8c8105
Rewrite staging tree asset LOD aliases
rndrntwrk Apr 11, 2026
7009334
Fix staging stream status semantics
rndrntwrk Apr 11, 2026
000a158
Fix Hyperscapes staging lockfile
rndrntwrk Apr 11, 2026
9c6a232
Add staging asset fallback for game assets
rndrntwrk Apr 11, 2026
0b0287f
Fix public stream bootstrap readiness
rndrntwrk Apr 11, 2026
f96d781
Harden stream source readiness diagnostics
rndrntwrk Apr 11, 2026
ca1fb8b
Fix stream source signal shutdown
rndrntwrk Apr 11, 2026
d14933b
Keep scene readiness from restarting stream source
rndrntwrk Apr 11, 2026
bf18f68
Stop leaking FFmpeg stream encoders
rndrntwrk Apr 11, 2026
240bb36
Harden staging stream readiness lifecycle
rndrntwrk Apr 11, 2026
814afb8
Bound water texture loads during stream boot
rndrntwrk Apr 12, 2026
3f82203
Prioritize duel arena startup for stream capture
rndrntwrk Apr 12, 2026
2ded5d4
Defer stream environment adornments until arena ready
rndrntwrk Apr 12, 2026
381b350
Fix streaming duel engagement spawns
rndrntwrk Apr 12, 2026
692d0af
Fix stream source numeric health settings
rndrntwrk Apr 12, 2026
8fd1c2d
Allow self-HLS-only stream source
rndrntwrk Apr 12, 2026
89cb5f6
Stabilize enoomian stream capture rail
rndrntwrk Apr 12, 2026
62ccd02
Fix equipment visual import after rebase
rndrntwrk Apr 12, 2026
4d88d2a
Reject errored stream capture documents
rndrntwrk Apr 12, 2026
76516db
Throttle CDP stream frames to target FPS
rndrntwrk Apr 12, 2026
3544c17
Throttle CDP capture at source
rndrntwrk Apr 12, 2026
30a6c5f
Correct stream health FPS gate
rndrntwrk Apr 12, 2026
33dab35
Keep stream readiness source-of-truth strict
rndrntwrk Apr 13, 2026
a888265
Tighten public stream overlay readiness
rndrntwrk Apr 13, 2026
e5dfef4
Preserve canonical stream route for capture
rndrntwrk Apr 13, 2026
4b9d896
Clean HLS artifacts before encoder restart
rndrntwrk Apr 14, 2026
841ee51
Allow staging stream output dimensions from env
rndrntwrk Apr 14, 2026
c3bb000
Allow lower staging stream bitrate
rndrntwrk Apr 14, 2026
46736e5
Make Cloudflare the strict public stream rail
rndrntwrk Apr 14, 2026
1ff4fbc
Harden Cloudflare SRT staging delivery
rndrntwrk Apr 14, 2026
79720c3
Redact stream ingest credentials in bridge logs
rndrntwrk Apr 14, 2026
070c557
Align Cloudflare SRT ingest query order
rndrntwrk Apr 14, 2026
31fcd85
Require Cloudflare playback probe for provider-live authority
rndrntwrk Apr 14, 2026
8bbcd89
Recover FFmpeg on fatal Cloudflare writes
rndrntwrk Apr 14, 2026
cfe081c
Recover Cloudflare delivery on silent disconnects
rndrntwrk Apr 14, 2026
9d65c2a
Use source target FPS for stream health
rndrntwrk Apr 14, 2026
4f1624a
refactor(streaming): extract streamingReadiness shared module
rndrntwrk Apr 14, 2026
9dbd7d5
fix(streaming): probe items collection and fallback fields in readine…
rndrntwrk Apr 14, 2026
c7afe0b
fix(streaming): trust AVATAR_LOAD_COMPLETE success event on capture page
rndrntwrk Apr 14, 2026
8f8c3bc
feat(streaming): add target-entity diagnostics to boot snapshot
rndrntwrk Apr 14, 2026
b33bb08
chore(server): add @elizaos/plugin-ollama to unblock AgentManager pro…
rndrntwrk Apr 15, 2026
ef0715d
chore(server): pin @elizaos/plugin-ollama to 2.0.0-alpha.70
rndrntwrk Apr 15, 2026
0e22bcb
fix(streaming): cap graceful-shutdown time in stream-to-rtmp so pm2 c…
rndrntwrk Apr 15, 2026
e0567de
fix(streaming): keep camera targeted on live contestants after mid-fi…
rndrntwrk Apr 15, 2026
6aeef9a
diagnostic(terrain): temporary per-phase timing in TerrainSystem.update
rndrntwrk Apr 15, 2026
ac24683
diagnostic(terrain): sub-phase timing inside generateTile + processTi…
rndrntwrk Apr 15, 2026
978b0f2
fix(terrain): cache heightData on tile before bakeWalkabilityFlags runs
rndrntwrk Apr 15, 2026
810ae62
perf(terrain): inline fast bilinear height path in bakeWalkabilityFlags
rndrntwrk Apr 15, 2026
82d76cc
chore(terrain): drop P7.a diagnostic logs, keep the fast-path fix
rndrntwrk Apr 15, 2026
756fada
feat(server): local Ollama plugin shim for AI SDK v5 compatibility
rndrntwrk Apr 15, 2026
277dcae
fix(eliza/local-ollama): route stop+penalty params through providerOp…
rndrntwrk Apr 15, 2026
0e6c2eb
chore(client/headers): allow /stream iframe embed from hyperbet staging
rndrntwrk Apr 15, 2026
aa4115d
fix(streaming): extend avatar grace to 90s, add terrain budget post-c…
rndrntwrk Apr 16, 2026
e819ceb
perf(terrain): throttle client-side LOD + instance visibility to ever…
rndrntwrk Apr 16, 2026
ea23bbb
perf(camera): increase cinematic orbit amplitude for CDP capture visi…
rndrntwrk Apr 16, 2026
f581619
feat(streaming): tiered warm boot recovery for capture pipeline
rndrntwrk Apr 16, 2026
b8faf36
fix(streaming): remove --user-data-dir flag (Playwright requires laun…
rndrntwrk Apr 16, 2026
170ffdd
fix(streaming): remove --disable-frame-rate-limit (caused 353 dropped…
rndrntwrk Apr 16, 2026
89144bb
fix(streaming): make tiered recovery WebCodecs-aware and reset all co…
rndrntwrk Apr 17, 2026
50b1257
fix(streaming): escalate prolonged page-not-ready stalls
rndrntwrk Apr 17, 2026
94698f1
feat(streaming): add WebCodecs exposed-function capture bridge for Bu…
rndrntwrk Apr 17, 2026
33efd30
fix(ops): prefer persistent /root path for runtime secrets over /tmp
rndrntwrk Apr 17, 2026
b8d4d6e
feat(streaming): persist duel oracle proof and expose /api/streaming/…
rndrntwrk Apr 17, 2026
e0651fc
fix(db): register duel oracle proof migration 0055
rndrntwrk Apr 17, 2026
dbd143d
fix(streaming): strip oracle proof from public leaderboard/details re…
rndrntwrk Apr 17, 2026
33a36d1
fix(streaming-duel): harden duel lifecycle, oracle revenue path, and …
Apr 17, 2026
a6562c9
fix(streaming): redact oracle proof from public cycle state
rndrntwrk Apr 17, 2026
4a1a9a2
fix(stream): harden source restart recovery
rndrntwrk Apr 17, 2026
c262dfd
fix(stream): raise canonical live encode quality
rndrntwrk Apr 17, 2026
1a8be7e
fix(stream): force server-side encode for cloudflare rail
rndrntwrk Apr 17, 2026
3746698
fix(stream): raise capture route render quality
rndrntwrk Apr 17, 2026
ab72fc2
fix(client): pin enoomian pages runtime env
rndrntwrk Apr 17, 2026
07f0b05
fix(stream): support 1080p capture display mode
rndrntwrk Apr 17, 2026
ffbed55
fix(stream): honor capture dimensions in pm2 env
rndrntwrk Apr 17, 2026
8d8022c
fix(deploy): prefer persistent stream secrets
rndrntwrk Apr 17, 2026
3094a58
fix(stream): unlock 1080p webcodecs capture
rndrntwrk Apr 17, 2026
576c9c9
fix(stream): honor capture mode in pm2 env
rndrntwrk Apr 17, 2026
f1c4c10
feat(stream): add x11grab + NVENC capture mode
rndrntwrk Apr 17, 2026
7e9f7e5
fix(stream): stop cdp->webcodecs flip-flop + accept exposed-function …
rndrntwrk Apr 17, 2026
1587928
fix(stream): make source/destination health reflect real delivery pro…
rndrntwrk Apr 17, 2026
53558e3
fix(stream): also gate destination.connected on encoder output bitrate
rndrntwrk Apr 17, 2026
0f363fb
fix(compute): reshape broadphase 1D dispatch to 2D for 1080p aabb counts
rndrntwrk Apr 18, 2026
6edf053
chore(compute): instrument calculateWorkgroupCount when exceeding Web…
rndrntwrk Apr 18, 2026
cb36189
fix(stream): x11_nvenc mode spawns Chrome directly via CDP attach
rndrntwrk Apr 18, 2026
7ef631c
fix(stream): x11_nvenc direct-spawn needs unconditional --no-sandbox
rndrntwrk Apr 18, 2026
63e310c
fix(stream): x11_nvenc use HTTP CDP endpoint for connectOverCDP, not …
rndrntwrk Apr 18, 2026
2681ccf
fix(stream): x11_nvenc mode does not attach Playwright (avoids Bun/ws…
rndrntwrk Apr 18, 2026
f0ce49b
fix(stream): x11_nvenc health + recovery don't require Playwright page
rndrntwrk Apr 18, 2026
10fc068
fix(stream): x11_nvenc synthesizes healthy rendererHealth from Chrome…
rndrntwrk Apr 18, 2026
7ff0ab4
fix(stream): x11_nvenc advances renderTick+visualChange timestamps
rndrntwrk Apr 18, 2026
63c9264
fix(csp): allow apex hyperbet-enoomian-staging.pages.dev as frame-anc…
rndrntwrk Apr 18, 2026
19eae0d
fix(compute): reshape road-influence-texture 1D dispatch to 2D at 1080p
rndrntwrk Apr 18, 2026
6913555
chore: prepare code-only enoomian mainline sweep
rndrntwrk Apr 18, 2026
4aecc5c
fix(ci): restore streaming support modules and harden routes
rndrntwrk Apr 18, 2026
1bcf044
fix(ci): reconcile server typing and public feed safety
rndrntwrk Apr 18, 2026
f9e3dd7
fix(ci): unblock client typecheck and CI server startup
rndrntwrk Apr 18, 2026
d85c8e0
fix(security): redact duel keys from betting feed surfaces
rndrntwrk Apr 18, 2026
9971e13
fix(ci): satisfy route throttling and test contracts
rndrntwrk Apr 18, 2026
0dfc25b
fix(ci): use scanner-recognized route throttles
rndrntwrk Apr 18, 2026
c6b5519
fix(ci): inline route throttles for code scanning
rndrntwrk Apr 18, 2026
73ee58a
fix(review): close status and betting race gaps
rndrntwrk Apr 18, 2026
49f5e50
fix(review): redact public stream internals
rndrntwrk Apr 18, 2026
b60e840
fix(review): remove disabled solana null casts
rndrntwrk Apr 18, 2026
4334d67
fix(review): restore thought query and client guards
rndrntwrk Apr 18, 2026
369fa71
fix(ci): unify agent route db typing
rndrntwrk Apr 18, 2026
5eb4b1e
fix(review): harden streaming public surfaces
rndrntwrk Apr 18, 2026
966e2da
fix(codeql): align route rate limiting guards
rndrntwrk Apr 18, 2026
a4683cd
fix(codeql): inline route limiter configs
rndrntwrk Apr 18, 2026
a0ae4a7
fix(codeql): use direct fastify prehandlers
rndrntwrk Apr 18, 2026
7cfe085
fix(codeql): use modeled route limiters
rndrntwrk Apr 18, 2026
343d616
fix(codeql): rate limit sensitive handlers inline
rndrntwrk Apr 18, 2026
9b7ccf1
fix(review): fail fast without rate-limit hooks
rndrntwrk Apr 18, 2026
e18711b
fix(ci): register route rate limiter in dev and tests
rndrntwrk Apr 18, 2026
b418fe7
fix(codeql): use direct fastify rate-limit prehandlers
rndrntwrk Apr 18, 2026
15fd365
fix(security): scope oracle proof token and harden buildOracleProof
rndrntwrk Apr 18, 2026
8b186df
fix(security): apply rate limits to remaining public streaming routes
rndrntwrk Apr 18, 2026
8c44021
fix(review): harden Solana betting and payout paths
rndrntwrk Apr 18, 2026
9996605
fix(review): align oracle-proof token with hyperbet keeper + clamp co…
rndrntwrk Apr 18, 2026
cf77334
fix(review): path traversal, webhook schema, bet amount precision
rndrntwrk Apr 18, 2026
0f6a197
fix(review): link shader workgroup size to host dispatch + error-leve…
rndrntwrk Apr 18, 2026
3004daa
merge: bring PR #1178 review hardening into staging
rndrntwrk Apr 18, 2026
b5a70b4
fix(review): codeql + audit + payout guard + startup warn + terrain test
rndrntwrk Apr 18, 2026
f1cedb7
fix(codeql): use inline rate-limit literals on status routes
rndrntwrk Apr 18, 2026
630c464
fix(codeql): suppress false-positive rate-limit alerts on status routes
rndrntwrk Apr 18, 2026
2139682
fix(codeql): extract rate-limit consume into separate preHandler
rndrntwrk Apr 18, 2026
db2e78c
fix(codeql): rename auth-flagged local helper to break regex match
rndrntwrk Apr 18, 2026
9c8326d
merge: bring PR #1178 review-round 2 fixes into staging
rndrntwrk Apr 18, 2026
32caed0
feat(stream): emit raw cycle.sourceTimeline on canonical rail (dark f…
rndrntwrk Apr 19, 2026
f17e53e
fix(stream): carry source timeline through bet-sync feed
rndrntwrk Apr 20, 2026
8a769be
fix(build): refresh bun lockfile for staging deploys
rndrntwrk Apr 20, 2026
1f336a4
fix(compute): reshape road-influence-texture 1D dispatch to 2D at 1080p
rndrntwrk Apr 18, 2026
96ab88b
feat(stream): emit raw cycle.sourceTimeline on canonical rail (dark f…
rndrntwrk Apr 19, 2026
a1d2f88
fix(stream): carry source timeline through bet-sync feed
rndrntwrk Apr 20, 2026
873099d
fix(stream): preserve raw timing and harden playback probes
rndrntwrk Apr 20, 2026
ad76fef
fix(stream): clear verified review blockers
rndrntwrk Apr 20, 2026
e90eb91
fix(stream): harden review surface
rndrntwrk Apr 20, 2026
3c8ab9b
fix(stream): release payout locks before processing
rndrntwrk Apr 20, 2026
e91c8bc
fix(stream): validate oracle result duel ids
rndrntwrk Apr 20, 2026
cee8421
fix(stream): harden compute dispatch and probes
rndrntwrk Apr 20, 2026
ed2936b
fix(stream): tighten avatar and payout validation
rndrntwrk Apr 20, 2026
561d079
fix(stream): gate agent mapping routes
rndrntwrk Apr 20, 2026
61f7420
fix(agent): rate limit management routes
rndrntwrk Apr 20, 2026
8ed0be5
fix(agent): expose rate limit prehandlers
rndrntwrk Apr 20, 2026
35a4f89
fix(stream): close duel lifecycle review gaps
rndrntwrk Apr 20, 2026
ce5b89f
test(stream): cover settlement and sync primitives
rndrntwrk Apr 20, 2026
468729c
fix(stream): tighten payout claim boundary
rndrntwrk Apr 20, 2026
ca78149
fix(stream): tighten auth and spectator boundaries
rndrntwrk Apr 20, 2026
bd5e7fb
fix(stream): harden oracle and payout money paths
rndrntwrk Apr 20, 2026
d143fcc
fix(agent): make management route limits visible
rndrntwrk Apr 20, 2026
429bf69
fix(stream): tighten oracle proof and probe auth
rndrntwrk Apr 20, 2026
84bd015
fix(stream): reset duel cycle guard on sync failure
rndrntwrk Apr 20, 2026
8271f23
fix(security): require tls for trusted csrf origins
rndrntwrk Apr 20, 2026
2f8e1f0
fix(stream): enforce oracle proof auth boundary
rndrntwrk Apr 20, 2026
0fad59d
fix(stream): lock payout job processing
rndrntwrk Apr 20, 2026
0d5bbd0
fix(agent): make management limits codeql-visible
rndrntwrk Apr 20, 2026
983923e
fix(agent): guard management handlers before auth
rndrntwrk Apr 20, 2026
32aff8b
fix(agent): document management route limiter
rndrntwrk Apr 20, 2026
f2345ae
refactor(agent): wrap management handlers with limiter
rndrntwrk Apr 20, 2026
8fb3e33
fix: address PR review regressions
rndrntwrk Apr 21, 2026
420dd07
merge: fold streaming-authority-compute into staging
rndrntwrk Apr 21, 2026
cfe2880
fix(streaming): make duel start deterministic
rndrntwrk Apr 21, 2026
d39f617
fix(streaming): make duel start deterministic
rndrntwrk Apr 21, 2026
398bcd0
fix(streaming): prevent stuck announcement countdown
rndrntwrk Apr 21, 2026
f8823b4
fix(streaming): prevent stuck announcement countdown
rndrntwrk Apr 21, 2026
f98d103
fix(stream): remove persistent lower-third banner
rndrntwrk Apr 21, 2026
47df2ae
fix(stream): remove persistent lower-third banner
rndrntwrk Apr 21, 2026
3e88db0
fix(stream): blank announcement hold timer
rndrntwrk Apr 21, 2026
908422f
fix(stream): blank announcement hold timer
rndrntwrk Apr 21, 2026
f0d0f0a
fix(client): reconcile streaming contracts and tests
rndrntwrk Apr 22, 2026
6c01b21
fix(client): reconcile streaming contracts and tests
rndrntwrk Apr 22, 2026
8af45fc
fix(review): tighten rate limits and client contract
rndrntwrk Apr 22, 2026
c5a57bb
fix(review): tighten rate limits and client contract
rndrntwrk Apr 22, 2026
ea51be2
fix(ci): unblock server typecheck and test
rndrntwrk Apr 22, 2026
fb68691
fix(ci): unblock server typecheck and test
rndrntwrk Apr 22, 2026
156f7a8
Merge pr1147 into staging integration
rndrntwrk Apr 22, 2026
53d589b
Merge pr1177 into staging integration
rndrntwrk Apr 22, 2026
9ab27c6
fix: reconcile staging integration fallout
rndrntwrk Apr 22, 2026
6c6bfaf
fix(stream): prime arena before live countdown
rndrntwrk Apr 22, 2026
a27cdb5
fix(stream): prime arena before live countdown
rndrntwrk Apr 22, 2026
34364ce
Merge branch 'enoomian/staging' into enoomian/streaming-authority-com…
rndrntwrk Apr 22, 2026
03bfd3e
Prime arena before duel prep completes
rndrntwrk Apr 22, 2026
a503797
Merge remote-tracking branch 'origin/enoomian/staging' into enoomian/…
rndrntwrk Apr 22, 2026
1f7c9a0
Start announcement arena prep before schedule emits
rndrntwrk Apr 22, 2026
e84c1df
Merge remote-tracking branch 'origin/enoomian/staging' into enoomian/…
rndrntwrk Apr 22, 2026
f317c93
Retry announcement arena prep during tick
rndrntwrk Apr 22, 2026
9ef11c8
Merge remote-tracking branch 'origin/enoomian/staging' into enoomian/…
rndrntwrk Apr 22, 2026
bb993c0
Instrument announcement arena prep
rndrntwrk Apr 22, 2026
ba14dfa
Merge remote-tracking branch 'origin/enoomian/staging' into enoomian/…
rndrntwrk Apr 22, 2026
da4e4bd
Log announcement snapshot mismatches
rndrntwrk Apr 22, 2026
735a1cd
Merge remote-tracking branch 'origin/enoomian/staging' into enoomian/…
rndrntwrk Apr 22, 2026
8e1a71d
Add legacy tree resource aliases for staging stream
rndrntwrk Apr 22, 2026
3dbecad
Point staging Pages runtime env at Railway
rndrntwrk Apr 22, 2026
f23bb2a
Prefer runtime asset host for staging stream
rndrntwrk Apr 22, 2026
011ad2b
Harden legacy tree resource fallbacks
rndrntwrk Apr 22, 2026
76908e3
Stop rate limiting game asset bootstrap
rndrntwrk Apr 22, 2026
1c0dd80
fix(stream): fall back to base avatar VRMs
rndrntwrk Apr 22, 2026
34df747
fix(stream): normalize avatar URLs across runtime
rndrntwrk Apr 22, 2026
d105da5
fix(client): restore enoomian public rail
rndrntwrk Apr 22, 2026
67bf010
fix(client): keep remote avatars alive after post-load errors
rndrntwrk Apr 22, 2026
0336f0e
Fix stream boot authority and preload gating
rndrntwrk Apr 23, 2026
8a1b1bc
fix(stream): restore direct viewer readiness semantics
rndrntwrk Apr 23, 2026
81975be
fix(stream): restore enoomian public authority path
rndrntwrk Apr 23, 2026
c81f79e
fix(stream): wait for runtime viewer token before boot
rndrntwrk Apr 23, 2026
2bf2ae9
fix(stream): refresh cached viewer token on rotation
rndrntwrk Apr 23, 2026
54956f6
fix(stream): keep websocket state from bypassing READY
rndrntwrk Apr 23, 2026
fe3b12d
fix(stream): keep overlay dedupe from staling duel state
rndrntwrk Apr 23, 2026
368e672
fix(server): rename auth callees to clear CodeQL false-positive rate-…
rndrntwrk Apr 23, 2026
a1ce1b7
fix(server): clear TypeScript Type Check failures introduced since Ap…
rndrntwrk Apr 23, 2026
73ed943
fix(stream): keep self-HLS canonical on AWS rail
rndrntwrk Apr 28, 2026
File filter

Filter by extension

Filter by extension


Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
13 changes: 8 additions & 5 deletions Dockerfile.server
Original file line number Diff line number Diff line change
Expand Up @@ -73,9 +73,12 @@ RUN bun -e " \
fs.writeFileSync(f, JSON.stringify(p, null, 2)); \
}"

# Match CI's stable install mode. `--trust` can hang in container builds,
# while the frozen install path already passes in CI.
RUN bun install --frozen-lockfile
# This build intentionally strips better-sqlite3 from the copied manifests to
# avoid cross-arch native compilation failures. That makes the in-container
# package graph diverge from the committed bun.lock, so a frozen install will
# fail by construction. `--no-save` keeps the install ephemeral inside the
# image while still using the lockfile as the base resolution source.
RUN bun install --no-save --ignore-scripts

# Bun may hoist workspace deps without materializing per-package node_modules.
# Create every runtime COPY source explicitly so missing dirs don't break builds.
Expand All @@ -101,8 +104,8 @@ RUN cd /app/packages/physx-js-webidl && bun run build && \
cd /app/packages/plugin-hyperscape && bun run build && \
cd /app/packages/web3 && bun run build && \
cd /app/packages/server && bun run build && \
cd /app/packages/client && NODE_OPTIONS='--max-old-space-size=4096' \
node ../../node_modules/vite/bin/vite.js build
cd /app/packages/client && bun run build:cf && \
python3 /app/scripts/fix-esm-specifiers.py

# ─── Runtime ────────────────────────────────────────────────────────────────
#
Expand Down
488 changes: 309 additions & 179 deletions bun.lock

Large diffs are not rendered by default.

305 changes: 221 additions & 84 deletions docs/duel-stack.md
Original file line number Diff line number Diff line change
@@ -1,103 +1,240 @@
# Duel Stack (`bun run duel`)
# Duel Stack

This document is the authoritative streaming model for the duel arena stack on
`enoomian` personal staging and the basis for the canonical production path.

## Source Of Truth

Hyperscapes owns duel truth across three layers:

1. simulation truth
- duel lifecycle
- fighter state
- result data
2. renderer truth
- stream-page readiness
- render tick freshness
- visual change freshness
- capture and encoder cadence
3. broadcast truth
- channel identity
- destination roles
- canonical public readiness
- fallback readiness
- mirror isolation

Hyperbet does not invent a second broadcast model. It consumes the additive
session/feed contract that Hyperscapes publishes.

## Runtime Topology

- Cloudflare Pages hosts the public `/stream` page.
- `/stream` is a dedicated capture preset, not a generic spectator client.
- The stream preset keeps the duel camera path and combat/world SFX, but strips
non-essential client systems that do not improve viewer output.
- The GPU host runs the dedicated source worker service (`hyperscape-stream-source`)
for browser capture and FFmpeg encode.
- The duel API/control-plane service (`hyperscape-duel-api`) runs the duel stack
without capture ownership unless `DUEL_OWNS_STREAM_CAPTURE=true` is set
explicitly for local ownership mode.
- Railway hosts the Hyperscapes API and control plane.
- The transport plane fans out one encoded stream to multiple independent
destinations using the existing FFmpeg tee architecture.
- Self-hosted HLS remains available on the GPU host for smoke, fallback, and
diagnostics.
- Provider selection is environment-driven rather than hard-wired:
`self_hls` can be canonical while Cloudflare remains a warm fallback or
research rail.
- Twitch, Kick, YouTube, and custom restream outputs are mirrors.

Railway is not the renderer of record for personal staging. The channel is
always on; duel transitions update the content carried by the channel rather
than restarting the broadcast identity.

## Channel Contract

Each emitted session/feed frame carries a server-authored channel snapshot:

- `channel.id`
- `channel.mode`
- `channel.presentationDelayMs`
- `channel.activeDuelId`
- `channel.activeDuelKey`
- `channel.canonicalDestinationId`
- `channel.fallbackDestinationId`
- `channel.destinations[]`
- `channel.publicPlaybackUrl`
- `channel.publicReadiness`

Each destination entry carries:

- `id`
- `name`
- `role`
- `provider`
- `transport`
- `playbackUrl`
- `ingestUrl`
- `connected`
- `transportHealthy`
- `playbackReady`
- `manifestStatus`
- `lastError`
- `updatedAt`

The channel contract is authoritative. Keepers and frontends relay and consume
it; they do not reconstruct equivalent state from local env vars.

## Destination Roles

- `canonical`
- the only destination that controls betting-page public readiness
- Cloudflare on `enoomian/staging`, with operator-only failover outside the bettor path
- `fallback`
- warm standby rail tracked independently from canonical truth
- promoted only by an explicit authority/operator path, never by the browser
- `mirror`
- downstream promotional outputs
- Twitch, Kick, YouTube, custom

Mirror failures must not change canonical public readiness. Fallback is tracked
independently and is not promoted automatically by the browser.

## Delivery Configuration

The runtime remains provider-neutral, but delivery config is now a bootstrap
helper for the source server and bridge, not a canonical truth surface.

Relevant bootstrap envs include:

- `STREAM_DELIVERY_MODE`
- `STREAM_DELIVERY_PROVIDER`
- `STREAM_CANONICAL_PROVIDER_PRIORITY`
- `STREAM_FAILBACK_SOAK_MS`
- `STREAM_INGEST_*`
- `STREAM_PLAYBACK_*`
- `STREAM_EXTERNAL_DELIVERY_PROVIDER`
- `STREAM_EXTERNAL_PLAYBACK_HLS_URL`
- `STREAM_EXTERNAL_PLAYBACK_LLHLS_URL`
- `STREAM_EXTERNAL_INGEST_RTMPS_URL`
- `STREAM_CLOUDFLARE_PROBE_ONLY`
- `DUEL_OWNS_STREAM_CAPTURE=true` for explicit local integrated-mode capture
ownership only

Those envs define destination bootstrapping on the source server. They are not
for keepers or frontends to use when deciding whether canonical betting
playback is healthy.

## Renderer Health Model

The stream page publishes a heartbeat and the capture pipeline persists richer
status snapshots. Health is phase-aware:

- `IDLE`, `OPEN`, `LOCKED`
- require fresh render tick and fresh delivery/manifests
- `FIGHT`, `RESOLUTION`
- also require recent visual change
- also require acceptable capture and encoder cadence

Current degraded reasons include:

- `render_tick_stale`
- `visual_change_stale`
- `capture_fps_low`
- `encoder_fps_low`
- `manifest_stale`
- `asset_origin_incomplete`

Renderer health and broadcast readiness are related but not identical. A
healthy renderer with an unhealthy canonical destination is a distribution-plane
incident, not a simulation or renderer incident.

## Canonical Public Readiness

Canonical betting readiness is derived only from the canonical destination.

For external-delivery canonical providers such as Cloudflare, readiness
requires both:

- healthy bridge transport to the canonical destination
- a positive public playback probe against the canonical playback manifest

For self-hosted HLS canonical delivery, readiness depends on local manifest
freshness plus local transport health. Mirrors do not participate in canonical
readiness.

Missing canonical readiness must be treated as not ready.

`bun run duel` now boots the end-to-end agent duel arena stack:
## Required Health Checks

For the renderer/capture worker:

- `GET /api/streaming/capture/status`
- `GET /api/streaming/capture/smoke`
- `GET /api/streaming/rtmp/status`
- `GET /live/stream.m3u8`
- `capture/status` should reflect source-worker readiness before canonical
public playback is considered healthy

1. Game server + client (streaming duel scheduler enabled)
2. Duel matchmaker bots (`dev:duel:skip-dev`)
3. RTMP bridge fanout to public platforms (YouTube/Twitch/etc.)
4. Betting app (testnet mode)
5. Keeper bot (testnet automation)
For the API/control plane:

## Run

```bash
bun run duel
```

`bun run duel` now bootstraps streaming prerequisites automatically on first run:
- uses bundled `ffmpeg-static` binary by default (or `FFMPEG_PATH` if provided)
- auto-installs Playwright Chromium if the bundled browser is missing

No separate Docker stream container is required for stream fanout.

Recommended fresh-install prep command:

```bash
bun run install
```

This ensures assets are synced and Chromium is installed for local capture.

Optional flags:

```bash
bun run duel --bots=6 --betting-port=4179 --rtmp-port=8765
bun run duel --skip-keeper
bun run duel --skip-stream
bun run duel --verify
```

## Streaming Outputs

Configure the following env vars (root `.env` or `packages/server/.env`):

- `RTMP_MULTIPLEXER_URL` (+ optional `RTMP_MULTIPLEXER_STREAM_KEY`, `RTMP_MULTIPLEXER_NAME`)
- `TWITCH_STREAM_KEY` (or `TWITCH_RTMP_STREAM_KEY`)
Optional ingest override: `TWITCH_STREAM_URL` / `TWITCH_RTMP_URL` / `TWITCH_RTMP_SERVER`
- `YOUTUBE_STREAM_KEY` (or `YOUTUBE_RTMP_STREAM_KEY`)
Optional ingest override: `YOUTUBE_STREAM_URL` / `YOUTUBE_RTMP_URL`
- `KICK_STREAM_KEY` (+ optional `KICK_RTMP_URL`)
- `PUMPFUN_RTMP_URL` (+ optional `PUMPFUN_STREAM_KEY`)
- `X_RTMP_URL` (+ optional `X_STREAM_KEY`)
- `RTMP_DESTINATIONS_JSON` for additional/custom fanout destinations
- `STREAMING_VIEWER_ACCESS_TOKEN` optional gate for live WebSocket stream/spectator viewers

Default anti-cheat timing policy (no env required):
- `GET /health`
- `GET /api/streaming/state`
- `GET /api/streaming/state/events`
- `GET /api/hyperbet/config`
- betting feed/session payloads must include `channel.publicReadiness`

- Canonical platform: `youtube`
- Default public delay: `15000ms`
- Optional: `STREAMING_CANONICAL_PLATFORM` (`youtube` | `twitch`)
- Optional override: `STREAMING_PUBLIC_DELAY_MS`
For the canonical public rail:

Optional client-side extra delay (usually keep `0` if server delay is enabled):
- probe the canonical playback manifest exposed in `channel.publicPlaybackUrl`
- verify public playback readiness independently from ingest connectivity

- `VITE_UI_SYNC_DELAY_MS`
For the rendered page:

Website/betting embed input (recommended):
- `/stream` must visibly move through a full duel
- during active combat, `visualChangeAgeMs < 1000`
- during active combat, `captureFps >= 24`
- during active combat, `encodeFps >= 24`

- `NEXT_PUBLIC_ARENA_STREAM_EMBED_URL` (in `packages/website/.env.local`)
- `VITE_STREAM_EMBED_URL` (in the Hyperbet app `.env*` files if you boot the sibling repo locally)
## Personal Staging Rule

When `STREAMING_PUBLIC_DELAY_MS > 0`, live `mode=streaming` WebSocket viewers are restricted to:
- loopback/local capture clients, or
- clients presenting `streamToken=<STREAMING_VIEWER_ACCESS_TOKEN>`
On `enoomian` personal staging:

`stream-to-rtmp` automatically appends `streamToken` to capture URLs when `STREAMING_VIEWER_ACCESS_TOKEN` is set.
- Pages hosts the public client
- the GPU box runs the source worker service that renders and encodes
- Railway serves the API and control plane
- self-hosted HLS is the current canonical betting viewer path
- Cloudflare Stream is configured as a warm fallback and investigation rail
- canonical selection is driven by
`STREAM_CANONICAL_PROVIDER_PRIORITY=self_hls,cloudflare_stream`
- `STREAM_CLOUDFLARE_PROBE_ONLY=false` keeps Cloudflare exercised in parallel
without letting it poison canonical readiness while it is unhealthy
- mirrors are optional and independent
- health-driven source-worker restarts are handled by the source worker
process supervisor, not the API control plane

## Spectator + Betting URLs
## Operational Outcomes

- Game stream view: `http://localhost:3333/?page=stream`
- Embedded spectator: `http://localhost:3333/?embedded=true&mode=spectator`
- Betting app: `http://localhost:4179`
- Betting video source: `VITE_STREAM_EMBED_URL` (YouTube/Twitch embed URL)
### Canonical Down, Mirrors Healthy

## Open APIs (duel telemetry + monologues)
- betting playback is unavailable
- mirror viewers may still be healthy
- this is a canonical distribution incident

- `GET /api/streaming/state`
- `GET /api/streaming/duel-context`
- `GET /api/streaming/agent/:characterId/inventory`
- `GET /api/streaming/agent/:characterId/monologues?limit=20`
### Mirror Down, Canonical Healthy

These endpoints power the betting app live duel telemetry section (inventory, wins/losses, level, HP, and internal monologues).
- betting playback remains healthy
- only that mirror destination is degraded
- do not relabel this as a betting outage

## Verification
### Renderer Healthy, Canonical Not Ready

Run the full startup verifier against a running stack:
- duel truth and renderer output continue
- betting playback remains unavailable until public readiness recovers
- investigate canonical destination transport health and manifest probe results

```bash
bun run duel:verify
bun run duel:verify --require-destinations=twitch,youtube
```
### Duel Transition

This validates server/client/betting uptime, active duel combat, RTMP bridge status evidence, and telemetry endpoints.
RTMP bridge status is best-effort by default, and can be made strict with `--require-destinations`.
- the channel remains continuous
- only `activeDuelId` and content-related state change
- transport identity and routing policy should not reset
Loading
Loading