Refactor world simulation and API to enhance world state management; introduce StoredWorldDto for internal bookkeeping, improve synchronization between simulation and API data, and implement new simulation options for idle and catch-up behavior. Update documentation to reflect changes in data structures and API endpoints.

This commit is contained in:
Leonid Pershin
2026-08-16 23:28:29 +03:00
parent 2a8b7b49b3
commit cb5117edba
23 changed files with 639 additions and 121 deletions
@@ -43,6 +43,39 @@ public sealed class GameTimeTests
Assert.Equal(new DateTime(2012, 4, 24, 18, 0, 0, DateTimeKind.Unspecified), next);
}
[Fact]
public void LimitCatchUp_trims_a_step_to_the_game_time_it_is_allowed_to_bank()
{
var cap = TimeSpan.FromHours(24);
// At x1 a day of game time is 288 real seconds, so a week of downtime comes back trimmed to that.
var trimmed = GameTime.LimitCatchUp(TimeSpan.FromDays(7), timeScale: 1, cap);
Assert.Equal(288, trimmed.TotalSeconds, 1);
Assert.Equal(cap, GameTime.Advance(GameTime.DefaultStart, trimmed, 1, false) - GameTime.DefaultStart);
// Four times the speed banks the same day of game time in a quarter of the wall clock.
Assert.Equal(72, GameTime.LimitCatchUp(TimeSpan.FromDays(7), timeScale: 4, cap).TotalSeconds, 1);
}
[Fact]
public void LimitCatchUp_leaves_an_ordinary_tick_alone()
{
var tick = TimeSpan.FromMilliseconds(100);
Assert.Equal(tick, GameTime.LimitCatchUp(tick, 1, TimeSpan.FromHours(24)));
// Five seconds is what an idle world banks between lazy ticks; it must survive untouched too.
var lazy = TimeSpan.FromSeconds(5);
Assert.Equal(lazy, GameTime.LimitCatchUp(lazy, 4, TimeSpan.FromHours(24)));
}
[Fact]
public void LimitCatchUp_treats_a_non_positive_cap_as_no_cap()
{
var week = TimeSpan.FromDays(7);
Assert.Equal(week, GameTime.LimitCatchUp(week, 1, TimeSpan.Zero));
Assert.Equal(week, GameTime.LimitCatchUp(week, 1, TimeSpan.FromHours(-1)));
}
[Fact]
public void DefaultStart_is_morning_of_12_April_2012()
{