Skip to content

Commit 1da0b91

Browse files
committed
Refactoring the read so it's testable
1 parent c5ecb4c commit 1da0b91

7 files changed

Lines changed: 3649 additions & 136 deletions

File tree

Lines changed: 59 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,59 @@
1+
using System;
2+
using System.Threading.Tasks;
3+
using BackendConfiguration.Pn.Integration.Test;
4+
using NUnit.Framework;
5+
using TimePlanning.Pn.Infrastructure.Helpers;
6+
using Microting.TimePlanningBase.Infrastructure.Data.Entities;
7+
8+
namespace TimePlanning.Pn.Test;
9+
10+
[TestFixture]
11+
public class PlanRegistrationHelperReadBySiteAndDateTests : TestBaseSetup
12+
{
13+
14+
[TestCase("2025-05-17 00:00:00.000")]
15+
[TestCase("2025-05-18 00:00:00.000")]
16+
public async Task ReadBySiteAndDate_FindsEntry_ForEachHour(string dateString)
17+
{
18+
// Arrange
19+
int sdkSiteId = 1;
20+
var date = DateTime.Parse(dateString);
21+
var planRegistration = new PlanRegistration
22+
{
23+
Date = date,
24+
SdkSitId = sdkSiteId,
25+
};
26+
await planRegistration.Create(TimePlanningPnDbContext).ConfigureAwait(false);
27+
28+
// Act
29+
var result = await PlanRegistrationHelper.ReadBySiteAndDate(TimePlanningPnDbContext, sdkSiteId, date, null);
30+
31+
// Assert
32+
Assert.That(result, Is.Not.Null);
33+
Assert.That(date, Is.EqualTo(result.Date));
34+
Assert.That(dateString, Is.EqualTo(result.Date.ToString("yyyy-MM-dd HH:mm:ss.fff")));
35+
Assert.That(sdkSiteId, Is.EqualTo(result.SdkSiteId));
36+
}
37+
38+
39+
[TestCase("2025-05-17 00:00:00.000")]
40+
[TestCase("2025-05-18 00:00:00.000")]
41+
public async Task ReadBySiteAndDate_ReturnsNewModel_WhenNoEntryFound(string dateString)
42+
{
43+
// Arrange
44+
int sdkSiteId = 2;
45+
var date = DateTime.Parse(dateString);
46+
47+
// Act
48+
var result = await PlanRegistrationHelper.ReadBySiteAndDate(TimePlanningPnDbContext, sdkSiteId, date, null);
49+
50+
// Assert
51+
Assert.That(result, Is.Not.Null);
52+
Assert.That(date, Is.EqualTo(result.Date));
53+
Assert.That(sdkSiteId, Is.EqualTo(result.SdkSiteId));
54+
Assert.That(dateString, Is.EqualTo(result.Date.ToString("yyyy-MM-dd HH:mm:ss.fff")));
55+
Assert.That(result.PlanHours, Is.EqualTo(0));
56+
Assert.That(result.Shift1Start, Is.EqualTo(0));
57+
Assert.That(result.Shift1Stop, Is.EqualTo(0));
58+
}
59+
}

eFormAPI/Plugins/TimePlanning.Pn/TimePlanning.Pn.Test/SQL/420_SDK.sql

Lines changed: 2778 additions & 0 deletions
Large diffs are not rendered by default.

eFormAPI/Plugins/TimePlanning.Pn/TimePlanning.Pn.Test/SQL/420_eform-angular-time-planning-plugin.sql

Lines changed: 518 additions & 0 deletions
Large diffs are not rendered by default.
Lines changed: 124 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,124 @@
1+
using System;
2+
using System.IO;
3+
using System.Threading.Tasks;
4+
using DotNet.Testcontainers.Containers;
5+
using eFormCore;
6+
using Microsoft.EntityFrameworkCore;
7+
using Microting.eForm.Infrastructure;
8+
using Microting.TimePlanningBase.Infrastructure.Data;
9+
using NUnit.Framework;
10+
using Testcontainers.MariaDb;
11+
12+
namespace BackendConfiguration.Pn.Integration.Test;
13+
14+
public class TestBaseSetup
15+
{
16+
private readonly MariaDbContainer _mariadbTestcontainer = new MariaDbBuilder()
17+
.WithDatabase(
18+
"myDb").WithUsername("bla").WithPassword("secretpassword")
19+
.WithEnvironment("MYSQL_ROOT_PASSWORD", "Qq1234567$")
20+
.WithCommand("--max_allowed_packet", "32505856")
21+
.Build();
22+
23+
protected MicrotingDbContext? DbContext;
24+
25+
protected TimePlanningPnDbContext? TimePlanningPnDbContext;
26+
protected MicrotingDbContext? MicrotingDbContext;
27+
28+
private TimePlanningPnDbContext GetTimePlanningPnDbContext(string connectionStr)
29+
{
30+
var optionsBuilder = new DbContextOptionsBuilder<TimePlanningPnDbContext>();
31+
32+
optionsBuilder.UseMySql(
33+
connectionStr.Replace("myDb", "420_eform-angular-items-planning-plugin").Replace("bla", "root"),
34+
new MariaDbServerVersion(
35+
ServerVersion.AutoDetect(connectionStr)),
36+
mySqlOptionsAction: builder => {
37+
builder.EnableRetryOnFailure();
38+
builder.TranslateParameterizedCollectionsToConstants();
39+
});
40+
41+
var backendConfigurationPnDbContext = new TimePlanningPnDbContext(optionsBuilder.Options);
42+
var file = Path.Combine("SQL", "420_eform-angular-time-planning-plugin.sql");
43+
var rawSql = File.ReadAllText(file);
44+
45+
backendConfigurationPnDbContext.Database.EnsureCreated();
46+
backendConfigurationPnDbContext.Database.ExecuteSqlRaw(rawSql);
47+
backendConfigurationPnDbContext.Database.Migrate();
48+
49+
return backendConfigurationPnDbContext;
50+
}
51+
52+
private MicrotingDbContext GetContext(string connectionStr)
53+
{
54+
var dbContextOptionsBuilder = new DbContextOptionsBuilder();
55+
56+
dbContextOptionsBuilder.UseMySql(connectionStr.Replace("myDb", "420_SDK").Replace("bla", "root")
57+
, new MariaDbServerVersion(
58+
ServerVersion.AutoDetect(connectionStr)),
59+
mySqlOptionsAction: builder => {
60+
builder.EnableRetryOnFailure();
61+
builder.TranslateParameterizedCollectionsToConstants();
62+
});
63+
var microtingDbContext = new MicrotingDbContext(dbContextOptionsBuilder.Options);
64+
var file = Path.Combine("SQL", "420_SDK.sql");
65+
var rawSql = File.ReadAllText(file);
66+
67+
microtingDbContext.Database.EnsureCreated();
68+
microtingDbContext.Database.ExecuteSqlRaw(rawSql);
69+
microtingDbContext.Database.Migrate();
70+
71+
return microtingDbContext;
72+
}
73+
74+
protected async Task<Core> GetCore()
75+
{
76+
var core = new Core();
77+
await core.StartSqlOnly(_mariadbTestcontainer.GetConnectionString().Replace("myDb", "420_SDK")
78+
.Replace("bla", "root"));
79+
return core;
80+
}
81+
82+
[SetUp]
83+
public async Task Setup()
84+
{
85+
if (_mariadbTestcontainer.State == TestcontainersStates.Undefined)
86+
{
87+
await _mariadbTestcontainer.StartAsync();
88+
}
89+
90+
// ConnectionString = _mariadbTestcontainer.GetConnectionString();
91+
92+
DbContext = GetContext(_mariadbTestcontainer.GetConnectionString());
93+
94+
DbContext!.Database.SetCommandTimeout(300);
95+
// Console.WriteLine($"{DateTime.Now} : Starting MariaDb Container...");
96+
// await _mariadbTestcontainer.StartAsync();
97+
// Console.WriteLine($"{DateTime.Now} : Started MariaDb Container");
98+
//
99+
TimePlanningPnDbContext = GetTimePlanningPnDbContext(_mariadbTestcontainer.GetConnectionString());
100+
//
101+
// TimePlanningPnDbContext!.Database.SetCommandTimeout(300);
102+
//
103+
// MicrotingDbContext = GetContext(_mariadbTestcontainer.GetConnectionString());
104+
//
105+
// MicrotingDbContext!.Database.SetCommandTimeout(300);
106+
107+
}
108+
109+
[OneTimeTearDown]
110+
public async Task OneTimeTearDown()
111+
{
112+
Console.WriteLine($"{DateTime.Now} : Stopping MariaDb Container...");
113+
await _mariadbTestcontainer.StopAsync();
114+
await _mariadbTestcontainer.DisposeAsync();
115+
Console.WriteLine($"{DateTime.Now} : Stopped MariaDb Container");
116+
}
117+
118+
[TearDown]
119+
public async Task TearDown()
120+
{
121+
await TimePlanningPnDbContext!.DisposeAsync();
122+
// await MicrotingDbContext!.DisposeAsync();
123+
}
124+
}

eFormAPI/Plugins/TimePlanning.Pn/TimePlanning.Pn.Test/TimePlanning.Pn.Test.csproj

Lines changed: 17 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -10,10 +10,27 @@
1010
<PackageReference Include="Microsoft.NET.Test.Sdk" Version="17.13.0" />
1111
<PackageReference Include="NUnit" Version="4.3.2" />
1212
<PackageReference Include="NUnit3TestAdapter" Version="5.0.0" />
13+
<PackageReference Include="Testcontainers" Version="4.4.0" />
14+
<PackageReference Include="Testcontainers.MariaDb" Version="4.4.0" />
1315
</ItemGroup>
1416

1517
<ItemGroup>
1618
<ProjectReference Include="..\TimePlanning.Pn\TimePlanning.Pn.csproj" />
1719
</ItemGroup>
1820

21+
<ItemGroup>
22+
<Folder Include="SQL\" />
23+
</ItemGroup>
24+
25+
<ItemGroup>
26+
<None Remove="SQL\420_eform-angular-time-planning-plugin.sql" />
27+
<EmbeddedResource Include="SQL\420_eform-angular-time-planning-plugin.sql">
28+
<CopyToOutputDirectory>Always</CopyToOutputDirectory>
29+
</EmbeddedResource>
30+
<None Remove="SQL\420_SDK.sql" />
31+
<EmbeddedResource Include="SQL\420_SDK.sql">
32+
<CopyToOutputDirectory>Always</CopyToOutputDirectory>
33+
</EmbeddedResource>
34+
</ItemGroup>
35+
1936
</Project>

eFormAPI/Plugins/TimePlanning.Pn/TimePlanning.Pn/Infrastructure/Helpers/PlanRegistrationHelper.cs

Lines changed: 148 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -12,6 +12,7 @@
1212
using Microting.TimePlanningBase.Infrastructure.Data.Entities;
1313
using Sentry;
1414
using TimePlanning.Pn.Infrastructure.Models.Planning;
15+
using TimePlanning.Pn.Infrastructure.Models.WorkingHours.Index;
1516
using TimePlanning.Pn.Services.TimePlanningPlanningService;
1617

1718
namespace TimePlanning.Pn.Infrastructure.Helpers;
@@ -768,4 +769,151 @@ public static async Task<TimePlanningPlanningModel> UpdatePlanRegistrationsInPer
768769

769770
return siteModel;
770771
}
772+
773+
public static async Task<TimePlanningWorkingHoursModel> ReadBySiteAndDate(
774+
TimePlanningPnDbContext dbContext, int sdkSiteId, DateTime dateTime,
775+
string token)
776+
{
777+
if (token != null)
778+
{
779+
var registrationDevice = await dbContext.RegistrationDevices
780+
.Where(x => x.Token == token).FirstOrDefaultAsync();
781+
if (registrationDevice == null)
782+
{
783+
return null;
784+
}
785+
}
786+
787+
// var today = DateTime.UtcNow;
788+
var midnight = dateTime;
789+
790+
var planRegistration = await dbContext.PlanRegistrations
791+
.Where(x => x.Date == midnight)
792+
.Where(x => x.SdkSitId == sdkSiteId)
793+
.Where(x => x.WorkflowState != Constants.WorkflowStates.Removed)
794+
.FirstOrDefaultAsync();
795+
796+
if (planRegistration == null)
797+
{
798+
var newTimePlanningWorkingHoursModel = new TimePlanningWorkingHoursModel
799+
{
800+
SdkSiteId = sdkSiteId,
801+
Date = midnight,
802+
PlanText = "",
803+
PlanHours = 0,
804+
Shift1Start = 0,
805+
Shift1Stop = 0,
806+
Shift1Pause = 0,
807+
Shift2Start = 0,
808+
Shift2Stop = 0,
809+
Shift2Pause = 0,
810+
NettoHours = 0,
811+
FlexHours = 0,
812+
SumFlexStart = 0,
813+
SumFlexEnd = 0,
814+
PaidOutFlex = "0",
815+
Message = 0,
816+
CommentWorker = "",
817+
CommentOffice = "",
818+
CommentOfficeAll = "",
819+
Shift1PauseNumber = 0,
820+
Shift2PauseNumber = 0,
821+
};
822+
823+
return newTimePlanningWorkingHoursModel;
824+
825+
// return new OperationDataResult<TimePlanningWorkingHoursModel>(false, "Plan registration not found",
826+
// null);
827+
}
828+
829+
var timePlanningWorkingHoursModel = new TimePlanningWorkingHoursModel
830+
{
831+
SdkSiteId = sdkSiteId,
832+
Date = planRegistration.Date,
833+
PlanText = planRegistration.PlanText,
834+
PlanHours = planRegistration.PlanHours,
835+
Shift1Start = planRegistration.Start1Id,
836+
Shift1Stop = planRegistration.Stop1Id,
837+
Shift1Pause = planRegistration.Pause1Id,
838+
Shift2Start = planRegistration.Start2Id,
839+
Shift2Stop = planRegistration.Stop2Id,
840+
Shift2Pause = planRegistration.Pause2Id,
841+
NettoHours = planRegistration.NettoHours,
842+
FlexHours = planRegistration.Flex,
843+
SumFlexStart = planRegistration.SumFlexStart,
844+
SumFlexEnd = planRegistration.SumFlexEnd,
845+
PaidOutFlex = planRegistration.PaiedOutFlex.ToString(),
846+
Message = planRegistration.MessageId,
847+
CommentWorker = planRegistration.WorkerComment,
848+
CommentOffice = planRegistration.CommentOffice,
849+
CommentOfficeAll = planRegistration.CommentOfficeAll,
850+
Start1StartedAt = planRegistration.Start1StartedAt,
851+
Stop1StoppedAt = planRegistration.Stop1StoppedAt,
852+
Pause1StartedAt = planRegistration.Pause1StartedAt,
853+
Pause1StoppedAt = planRegistration.Pause1StoppedAt,
854+
Start2StartedAt = planRegistration.Start2StartedAt,
855+
Stop2StoppedAt = planRegistration.Stop2StoppedAt,
856+
Pause2StartedAt = planRegistration.Pause2StartedAt,
857+
Pause2StoppedAt = planRegistration.Pause2StoppedAt,
858+
Pause10StartedAt = planRegistration.Pause10StartedAt,
859+
Pause10StoppedAt = planRegistration.Pause10StoppedAt,
860+
Pause11StartedAt = planRegistration.Pause11StartedAt,
861+
Pause11StoppedAt = planRegistration.Pause11StoppedAt,
862+
Pause12StartedAt = planRegistration.Pause12StartedAt,
863+
Pause12StoppedAt = planRegistration.Pause12StoppedAt,
864+
Pause13StartedAt = planRegistration.Pause13StartedAt,
865+
Pause13StoppedAt = planRegistration.Pause13StoppedAt,
866+
Pause14StartedAt = planRegistration.Pause14StartedAt,
867+
Pause14StoppedAt = planRegistration.Pause14StoppedAt,
868+
Pause15StartedAt = planRegistration.Pause15StartedAt,
869+
Pause15StoppedAt = planRegistration.Pause15StoppedAt,
870+
Pause16StartedAt = planRegistration.Pause16StartedAt,
871+
Pause16StoppedAt = planRegistration.Pause16StoppedAt,
872+
Pause17StartedAt = planRegistration.Pause17StartedAt,
873+
Pause17StoppedAt = planRegistration.Pause17StoppedAt,
874+
Pause18StartedAt = planRegistration.Pause18StartedAt,
875+
Pause18StoppedAt = planRegistration.Pause18StoppedAt,
876+
Pause19StartedAt = planRegistration.Pause19StartedAt,
877+
Pause19StoppedAt = planRegistration.Pause19StoppedAt,
878+
Pause100StartedAt = planRegistration.Pause100StartedAt,
879+
Pause100StoppedAt = planRegistration.Pause100StoppedAt,
880+
Pause101StartedAt = planRegistration.Pause101StartedAt,
881+
Pause101StoppedAt = planRegistration.Pause101StoppedAt,
882+
Pause102StartedAt = planRegistration.Pause102StartedAt,
883+
Pause102StoppedAt = planRegistration.Pause102StoppedAt,
884+
Pause20StartedAt = planRegistration.Pause20StartedAt,
885+
Pause20StoppedAt = planRegistration.Pause20StoppedAt,
886+
Pause21StartedAt = planRegistration.Pause21StartedAt,
887+
Pause21StoppedAt = planRegistration.Pause21StoppedAt,
888+
Pause22StartedAt = planRegistration.Pause22StartedAt,
889+
Pause22StoppedAt = planRegistration.Pause22StoppedAt,
890+
Pause23StartedAt = planRegistration.Pause23StartedAt,
891+
Pause23StoppedAt = planRegistration.Pause23StoppedAt,
892+
Pause24StartedAt = planRegistration.Pause24StartedAt,
893+
Pause24StoppedAt = planRegistration.Pause24StoppedAt,
894+
Pause25StartedAt = planRegistration.Pause25StartedAt,
895+
Pause25StoppedAt = planRegistration.Pause25StoppedAt,
896+
Pause26StartedAt = planRegistration.Pause26StartedAt,
897+
Pause26StoppedAt = planRegistration.Pause26StoppedAt,
898+
Pause27StartedAt = planRegistration.Pause27StartedAt,
899+
Pause27StoppedAt = planRegistration.Pause27StoppedAt,
900+
Pause28StartedAt = planRegistration.Pause28StartedAt,
901+
Pause28StoppedAt = planRegistration.Pause28StoppedAt,
902+
Pause29StartedAt = planRegistration.Pause29StartedAt,
903+
Pause29StoppedAt = planRegistration.Pause29StoppedAt,
904+
Pause200StartedAt = planRegistration.Pause200StartedAt,
905+
Pause200StoppedAt = planRegistration.Pause200StoppedAt,
906+
Pause201StartedAt = planRegistration.Pause201StartedAt,
907+
Pause201StoppedAt = planRegistration.Pause201StoppedAt,
908+
Pause202StartedAt = planRegistration.Pause202StartedAt,
909+
Pause202StoppedAt = planRegistration.Pause202StoppedAt,
910+
Shift1PauseNumber = planRegistration.Shift1PauseNumber,
911+
Shift2PauseNumber = planRegistration.Shift2PauseNumber
912+
};
913+
914+
return timePlanningWorkingHoursModel;
915+
// return new OperationDataResult<TimePlanningWorkingHoursModel>(true, "Plan registration found",
916+
// timePlanningWorkingHoursModel);
917+
}
918+
771919
}

0 commit comments

Comments
 (0)