Skip to content

Commit

Permalink
docs on timekeepers clocks and some api changes
Browse files Browse the repository at this point in the history
  • Loading branch information
mattiasnordqvist committed Sep 22, 2024
1 parent b79e137 commit eb6e9bf
Show file tree
Hide file tree
Showing 7 changed files with 224 additions and 60 deletions.
15 changes: 7 additions & 8 deletions DotNetThoughts.sln
Original file line number Diff line number Diff line change
Expand Up @@ -11,10 +11,10 @@ Project("{9A19103F-16F7-4668-BE54-9A1E7A4F7556}") = "DotNetThoughts.TimeKeeping.
EndProject
Project("{2150E333-8FDC-42A3-9474-1A3956D46DE8}") = "TimeKeeping", "TimeKeeping", "{695E363E-055E-4ED5-9613-587E02A67578}"
ProjectSection(SolutionItems) = preProject
ReadMe.md = ReadMe.md
TimeKeeping\ReadMe.md = TimeKeeping\ReadMe.md
EndProjectSection
EndProject
Project("{FAE04EC0-301F-11D3-BF4B-00C04F79EFBC}") = "DotNetThoughts.LocalTimeKit", "TimeKeeping\DotNetThoughts.LocalTimeKit\DotNetThoughts.LocalTimeKit.csproj", "{03DA1023-FDF4-4EF5-8951-19806434F8CA}"
Project("{9A19103F-16F7-4668-BE54-9A1E7A4F7556}") = "DotNetThoughts.LocalTimeKit", "TimeKeeping\DotNetThoughts.LocalTimeKit\DotNetThoughts.LocalTimeKit.csproj", "{03DA1023-FDF4-4EF5-8951-19806434F8CA}"
EndProject
Project("{9A19103F-16F7-4668-BE54-9A1E7A4F7556}") = "DotNetThoughts.Results", "Results\DotNetThoughts.Results\DotNetThoughts.Results.csproj", "{7032EE8C-FC18-4610-B7D6-613E552C278D}"
EndProject
Expand Down Expand Up @@ -52,7 +52,6 @@ Project("{2150E333-8FDC-42A3-9474-1A3956D46DE8}") = "Solution Items", "Solution
ReadMe.md = ReadMe.md
EndProjectSection
EndProject

Global
GlobalSection(SolutionConfigurationPlatforms) = preSolution
Debug|Any CPU = Debug|Any CPU
Expand All @@ -71,6 +70,10 @@ Global
{DF62C221-71AD-49A7-A9D8-48E31F06E27B}.Debug|Any CPU.Build.0 = Debug|Any CPU
{DF62C221-71AD-49A7-A9D8-48E31F06E27B}.Release|Any CPU.ActiveCfg = Release|Any CPU
{DF62C221-71AD-49A7-A9D8-48E31F06E27B}.Release|Any CPU.Build.0 = Release|Any CPU
{03DA1023-FDF4-4EF5-8951-19806434F8CA}.Debug|Any CPU.ActiveCfg = Debug|Any CPU
{03DA1023-FDF4-4EF5-8951-19806434F8CA}.Debug|Any CPU.Build.0 = Debug|Any CPU
{03DA1023-FDF4-4EF5-8951-19806434F8CA}.Release|Any CPU.ActiveCfg = Release|Any CPU
{03DA1023-FDF4-4EF5-8951-19806434F8CA}.Release|Any CPU.Build.0 = Release|Any CPU
{7032EE8C-FC18-4610-B7D6-613E552C278D}.Debug|Any CPU.ActiveCfg = Debug|Any CPU
{7032EE8C-FC18-4610-B7D6-613E552C278D}.Debug|Any CPU.Build.0 = Debug|Any CPU
{7032EE8C-FC18-4610-B7D6-613E552C278D}.Release|Any CPU.ActiveCfg = Release|Any CPU
Expand Down Expand Up @@ -103,10 +106,6 @@ Global
{E0E86A0B-F4CE-4E88-99CF-C54AFC1C0C58}.Debug|Any CPU.Build.0 = Debug|Any CPU
{E0E86A0B-F4CE-4E88-99CF-C54AFC1C0C58}.Release|Any CPU.ActiveCfg = Release|Any CPU
{E0E86A0B-F4CE-4E88-99CF-C54AFC1C0C58}.Release|Any CPU.Build.0 = Release|Any CPU
{03DA1023-FDF4-4EF5-8951-19806434F8CA}.Debug|Any CPU.ActiveCfg = Debug|Any CPU
{03DA1023-FDF4-4EF5-8951-19806434F8CA}.Debug|Any CPU.Build.0 = Debug|Any CPU
{03DA1023-FDF4-4EF5-8951-19806434F8CA}.Release|Any CPU.ActiveCfg = Release|Any CPU
{03DA1023-FDF4-4EF5-8951-19806434F8CA}.Release|Any CPU.Build.0 = Release|Any CPU
EndGlobalSection
GlobalSection(SolutionProperties) = preSolution
HideSolutionNode = FALSE
Expand All @@ -115,6 +114,7 @@ Global
{6B9CCBB9-73D3-4062-8317-5D54CF6B85D4} = {695E363E-055E-4ED5-9613-587E02A67578}
{917A0D7B-F7FA-4D39-B892-B9C1BA9BE284} = {695E363E-055E-4ED5-9613-587E02A67578}
{DF62C221-71AD-49A7-A9D8-48E31F06E27B} = {695E363E-055E-4ED5-9613-587E02A67578}
{03DA1023-FDF4-4EF5-8951-19806434F8CA} = {695E363E-055E-4ED5-9613-587E02A67578}
{7032EE8C-FC18-4610-B7D6-613E552C278D} = {BECD3795-EDD5-459E-BFCC-017082E1C34D}
{8CA73623-9009-4FEF-885E-84F9BBD61536} = {BECD3795-EDD5-459E-BFCC-017082E1C34D}
{02C498D0-532A-4F1D-9004-7E2E24121DF3} = {BECD3795-EDD5-459E-BFCC-017082E1C34D}
Expand All @@ -123,7 +123,6 @@ Global
{66DCA5D2-4A06-4F1A-8DBB-36118CC01A34} = {BECD3795-EDD5-459E-BFCC-017082E1C34D}
{3D9F5F06-E09D-46B4-8058-1458467E0252} = {BECD3795-EDD5-459E-BFCC-017082E1C34D}
{E0E86A0B-F4CE-4E88-99CF-C54AFC1C0C58} = {BECD3795-EDD5-459E-BFCC-017082E1C34D}
{03DA1023-FDF4-4EF5-8951-19806434F8CA} = {695E363E-055E-4ED5-9613-587E02A67578}
EndGlobalSection
GlobalSection(ExtensibilityGlobals) = postSolution
SolutionGuid = {CAA5B6BA-B6C8-4A90-B9E6-D7634295532E}
Expand Down
4 changes: 2 additions & 2 deletions TimeKeeping/DotNetThoughts.TimeKeeping.App/Pages/Timer.razor
Original file line number Diff line number Diff line change
Expand Up @@ -52,7 +52,7 @@

private void UpdateUI()
{
systemTime = clock.UtcNow();
systemTime = clock.Now();
realTime = DateTimeOffset.UtcNow;
localSystemTime = new LocalDateTime(systemTime.DateTime, TimeZoneInfo.Utc).ToTimeZone(TimeZoneInfo.Local).ToDateTimeOffsetLocal();
nairobiLocalSystemTime = new LocalDateTime(systemTime.DateTime, TimeZoneInfo.Utc).ToTimeZone(TimeZoneInfo.FindSystemTimeZoneById(selectedTimeZone)).ToDateTimeOffsetLocal();
Expand Down Expand Up @@ -139,7 +139,7 @@

private void SetBaseLine()
{
clock.SetBaseline(new DateTimeOffset(2021, 1, 1, 0, 0, 0, TimeSpan.Zero));
clock.SetNow(new DateTimeOffset(2021, 1, 1, 0, 0, 0, TimeSpan.Zero));
UpdateUI();

}
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -11,7 +11,7 @@ public void FreezeTime()
var sut = new TimeTravelersClock();
sut.Freeze(frozenTime);
sut.IsFrozen().Should().BeTrue();
sut.UtcNow().Should().Be(frozenTime);
sut.Now().Should().Be(frozenTime);
}
[Fact]
public void FreezeAgainOverridesCurrentFreeze()
Expand All @@ -22,7 +22,7 @@ public void FreezeAgainOverridesCurrentFreeze()
sut.Freeze(frozenTime);
sut.Freeze(newFrozenTime);
sut.IsFrozen().Should().BeTrue();
sut.UtcNow().Should().Be(newFrozenTime);
sut.Now().Should().Be(newFrozenTime);
}

[Fact]
Expand All @@ -31,8 +31,8 @@ public void FreezeCurrentTime()
var sut = new TimeTravelersClock();
sut.Freeze();
sut.IsFrozen().Should().BeTrue();
sut.UtcNow().Should().BeCloseTo(DateTimeOffset.Now, _allowedDeviation);
sut.UtcNow().Should().NotBeAfter(DateTimeOffset.Now);
sut.Now().Should().BeCloseTo(DateTimeOffset.Now, _allowedDeviation);
sut.Now().Should().NotBeAfter(DateTimeOffset.Now);
}

[Fact]
Expand All @@ -44,12 +44,12 @@ public void ResetFrozenTimeShouldRevertEverythingToNormal()
sut.Freeze(frozenTime);
// check arrange
sut.IsFrozen().Should().BeTrue();
sut.UtcNow().Should().Be(frozenTime);
sut.Now().Should().Be(frozenTime);
// Act
sut.Reset();
// Assert
sut.IsFrozen().Should().BeFalse();
sut.UtcNow().Should().BeCloseTo(DateTimeOffset.Now, _allowedDeviation);
sut.Now().Should().BeCloseTo(DateTimeOffset.Now, _allowedDeviation);
}

[Fact]
Expand All @@ -58,10 +58,10 @@ public void BaselineMocksNow()
var sut = new TimeTravelersClock();
var now = DateTimeOffset.Now;
var baseLine = now.AddDays(-1);
sut.SetBaseline(baseLine);
sut.UtcNow().Should().BeCloseTo(baseLine, _allowedDeviation);
sut.SetNow(baseLine);
sut.Now().Should().BeCloseTo(baseLine, _allowedDeviation);
var slept = Sleep(1000);
sut.UtcNow().Should().BeCloseTo(baseLine.Add(slept), _allowedDeviation);
sut.Now().Should().BeCloseTo(baseLine.Add(slept), _allowedDeviation);
}

[Fact]
Expand All @@ -71,15 +71,15 @@ public void AdvanceFrozenTime()
var frozenTime = new DateTimeOffset(2021, 1, 1, 0, 0, 0, TimeSpan.Zero);
sut.Freeze(frozenTime);
sut.Advance(TimeSpan.FromDays(1));
sut.UtcNow().Should().Be(new DateTimeOffset(2021, 1, 2, 0, 0, 0, TimeSpan.Zero));
sut.Now().Should().Be(new DateTimeOffset(2021, 1, 2, 0, 0, 0, TimeSpan.Zero));
}

[Fact]
public void AdvanceLiveTime()
{
var sut = new TimeTravelersClock();
sut.Advance(TimeSpan.FromDays(1));
sut.UtcNow().Should().BeCloseTo(DateTimeOffset.Now.AddDays(1), _allowedDeviation);
sut.Now().Should().BeCloseTo(DateTimeOffset.Now.AddDays(1), _allowedDeviation);
}

[Fact]
Expand All @@ -91,7 +91,7 @@ public void AdvanceFrozenTimeAndThenThaw()
sut.Advance(TimeSpan.FromDays(1));
sut.Thaw();
var slept = Sleep(1000);
sut.UtcNow().Should().BeCloseTo(frozenTime.AddDays(1).Add(slept), _allowedDeviation);
sut.Now().Should().BeCloseTo(frozenTime.AddDays(1).Add(slept), _allowedDeviation);
}

[Fact]
Expand All @@ -100,16 +100,16 @@ public void AComplicatedTest()
var sut = new TimeTravelersClock();
var baseLine = new DateTimeOffset(2021, 1, 1, 0, 0, 0, TimeSpan.Zero);
var timer = new Stopwatch(); timer.Start();
sut.SetBaseline(baseLine);
sut.UtcNow().Should().BeCloseTo(baseLine.Add(timer.Elapsed), _allowedDeviation);
sut.SetNow(baseLine);
sut.Now().Should().BeCloseTo(baseLine.Add(timer.Elapsed), _allowedDeviation);
Sleep(20);
sut.UtcNow().Should().BeCloseTo(baseLine.Add(timer.Elapsed), _allowedDeviation);
sut.Now().Should().BeCloseTo(baseLine.Add(timer.Elapsed), _allowedDeviation);
var frozen = sut.Freeze();
sut.UtcNow().Should().Be(frozen);
sut.Now().Should().Be(frozen);
var sleptWhileFrozen = Sleep(2000);
sut.Thaw();
Sleep(1000);
sut.UtcNow().Should().BeCloseTo(baseLine.Add(timer.Elapsed).Add(-sleptWhileFrozen), _allowedDeviation);
sut.Now().Should().BeCloseTo(baseLine.Add(timer.Elapsed).Add(-sleptWhileFrozen), _allowedDeviation);
}

private static TimeSpan Sleep(int milliseconds)
Expand Down
Original file line number Diff line number Diff line change
@@ -1,6 +1,6 @@
<Project Sdk="Microsoft.NET.Sdk">
<PropertyGroup>
<Version>1.2.0</Version>
<Version>1.3.0</Version>
<GenerateDocumentationFile>True</GenerateDocumentationFile>
<PackageLicenseExpression>MIT</PackageLicenseExpression>
</PropertyGroup>
Expand Down
73 changes: 65 additions & 8 deletions TimeKeeping/DotNetThoughts.TimeKeeping/SystemTime.cs
Original file line number Diff line number Diff line change
Expand Up @@ -7,6 +7,9 @@ public class SystemTime
{
private static AsyncLocal<TimeTravelersClock> _asyncLocalState = new();

/// <summary>
/// Returns the underlying <see cref="TimeTravelersClock"/> instance.
/// </summary>
public static TimeTravelersClock Clock
{
get
Expand All @@ -17,60 +20,114 @@ public static TimeTravelersClock Clock
}
}

public static DateTimeOffset SetBaseline(DateTimeOffset baseLine)
/// <summary>
/// See <see cref="TimeTravelersClock.SetNow(DateTimeOffset)"/>
/// </summary>
/// <param name="baseLine"></param>
/// <returns></returns>
public static DateTimeOffset SetNow(DateTimeOffset baseLine)
{
return Clock.SetBaseline(baseLine);
return Clock.SetNow(baseLine);
}

/// <summary>
/// See <see cref="TimeTravelersClock.SetOffset(TimeSpan)"/>
/// </summary>
/// <param name="offset"></param>
/// <returns></returns>
public static DateTimeOffset SetOffset(TimeSpan offset)
{
return Clock.SetOffset(offset);
}

/// <summary>
/// See <see cref="TimeTravelersClock.Advance(TimeSpan)"/>
/// </summary>
/// <param name="timeSpan"></param>
/// <returns></returns>
public static DateTimeOffset Advance(TimeSpan timeSpan)
{
return Clock.Advance(timeSpan);
}

/// <summary>
/// See <see cref="TimeTravelersClock.AdvanceDays(double)"/>
/// </summary>
/// <param name="days"></param>
/// <returns></returns>
public static DateTimeOffset AdvanceDays(double days)
{
return Clock.AdvanceDays(days);
}

public static DateTimeOffset UtcNow()
/// <summary>
/// See <see cref="TimeTravelersClock.Now"/>
/// </summary>
/// <returns></returns>
public static DateTimeOffset Now()
{
return Clock.UtcNow();
return Clock.Now();
}

public static DateTimeOffset Freeze(DateTimeOffset baseLine)
/// <summary>
/// See <see cref="TimeTravelersClock.Freeze(DateTimeOffset)"/>
/// </summary>
/// <param name="now"></param>
/// <returns></returns>
public static DateTimeOffset Freeze(DateTimeOffset now)
{
return Clock.Freeze(baseLine);
return Clock.Freeze(now);
}

/// <summary>
/// See <see cref="TimeTravelersClock.Freeze()"/>
/// </summary>
/// <returns></returns>
public static DateTimeOffset Freeze()
{
return Clock.Freeze();
}

/// <summary>
/// See <see cref="TimeTravelersClock.IsFrozen"/>
/// </summary>
/// <returns></returns>
public static bool IsFrozen()
{
return Clock.IsFrozen();
}

/// <summary>
/// See <see cref="TimeTravelersClock.Reset"/>
/// </summary>
/// <returns></returns>
public static DateTimeOffset Reset()
{
return Clock.Reset();
}

/// <summary>
/// See <see cref="TimeTravelersClock.Thaw"/>
/// </summary>
/// <returns></returns>
public static DateTimeOffset Thaw()
{
return Clock.Thaw();
}

public static void From(TimeTravelersClock xSystemTime)
/// <summary>
/// See <see cref="TimeTravelersClock.SyncWith(TimeTravelersClock)"/>
/// </summary>
/// <param name="otherTimeTravelersClock"></param>
public static void SyncWith(TimeTravelersClock otherTimeTravelersClock)
{
Clock.From(xSystemTime);
Clock.SyncWith(otherTimeTravelersClock);
}

/// <summary>
/// See <see cref="TimeTravelersClock.IsManipulated"/>
/// </summary>
/// <returns></returns>
public static bool IsManipulated()
{
return Clock.IsManipulated();
Expand Down
Loading

0 comments on commit eb6e9bf

Please sign in to comment.