Skip to content

Commit

Permalink
Merge pull request #123 from anselantz/EN_JM
Browse files Browse the repository at this point in the history
EN_JM Adding Holidays for Jamaica
  • Loading branch information
joaomatossilva authored Sep 28, 2023
2 parents ebbd3ce + f34f4e2 commit 84040b6
Show file tree
Hide file tree
Showing 5 changed files with 186 additions and 16 deletions.
13 changes: 8 additions & 5 deletions src/DateTimeExtensions/DateTimeExtensions.csproj
Original file line number Diff line number Diff line change
Expand Up @@ -3,7 +3,7 @@
<Description>This project is a merge of several common DateTime operations on the form of extensions to System.DateTime, including natural date difference text (precise and human rounded), holidays and working days calculations on several culture locales. Feedback will be much appreciated.</Description>
<AssemblyTitle>DateTime Extensions</AssemblyTitle>
<Authors>Joao Matos Silva</Authors>
<TargetFrameworks>netstandard1.3;netstandard2.0;net462</TargetFrameworks>
<TargetFrameworks>netstandard2.0;net461</TargetFrameworks>
<AssemblyName>DateTimeExtensions</AssemblyName>
<PackageId>DateTimeExtensions</PackageId>
<PackageTags>Natural;Date;Time;Relative;Calendar;Holiday;Workingday;DateTime</PackageTags>
Expand All @@ -14,21 +14,18 @@
<GenerateAssemblyConfigurationAttribute>false</GenerateAssemblyConfigurationAttribute>
<GenerateAssemblyCompanyAttribute>false</GenerateAssemblyCompanyAttribute>
<GenerateAssemblyProductAttribute>false</GenerateAssemblyProductAttribute>
<VersionPrefix>5.6.1</VersionPrefix>
<VersionPrefix>5.7.0</VersionPrefix>
<PackageIconUrl>https://github.com/joaomatossilva/DateTimeExtensions/raw/master/assets/datetimeextensions-60-logo.png</PackageIconUrl>
<PublishRepositoryUrl>true</PublishRepositoryUrl>
<AllowedOutputExtensionsInPackageBuildOutputFolder>$(AllowedOutputExtensionsInPackageBuildOutputFolder);.pdb</AllowedOutputExtensionsInPackageBuildOutputFolder>
<FileUpgradeFlags>40</FileUpgradeFlags>
<UpgradeBackupLocation>C:\Users\Alsay\Desktop\DateTimeExtensions\Backup\src\DateTimeExtensions\</UpgradeBackupLocation>
<OldToolsVersion>2.0</OldToolsVersion>
</PropertyGroup>
<ItemGroup Condition=" '$(TargetFramework)' == 'netstandard1.3' ">
<PackageReference Include="System.Diagnostics.Debug" Version="4.3.0" />
<PackageReference Include="System.Linq" Version="4.3.0" />
<PackageReference Include="System.Reflection" Version="4.3.0" />
<PackageReference Include="System.Reflection.Extensions" Version="4.3.0" />
<PackageReference Include="System.Resources.ResourceManager" Version="4.3.0" />
<PackageReference Include="System.Runtime" Version="4.3.1" />
<PackageReference Include="System.Runtime.Extensions" Version="4.3.1" />
<PackageReference Include="System.Text.RegularExpressions" Version="4.3.1" />
<PackageReference Include="System.Globalization.Calendars" Version="4.3.0" />
Expand All @@ -37,6 +34,12 @@
<Reference Include="System" />
<Reference Include="Microsoft.CSharp" />
</ItemGroup>
<ItemGroup>
<PackageReference Include="Microsoft.NETFramework.ReferenceAssemblies.net461" Version="1.0.3">
<PrivateAssets>all</PrivateAssets>
<IncludeAssets>runtime; build; native; contentfiles; analyzers; buildtransitive</IncludeAssets>
</PackageReference>
</ItemGroup>
<ItemGroup>
<Compile Update="WorkingDays\HolidayNames.Designer.cs">
<DesignTime>True</DesignTime>
Expand Down
16 changes: 16 additions & 0 deletions src/DateTimeExtensions/WorkingDays/ChristianHolidays.cs
Original file line number Diff line number Diff line change
Expand Up @@ -125,6 +125,22 @@ public static Holiday Easter
}
}

//source: https://en.wikipedia.org/wiki/Ash_Wednesday
//
private static Holiday ashWednesday;
public static Holiday AshWednesday
{
get
{
if (ashWednesday == null)
{
ashWednesday = new EasterBasedHoliday("AshWednesday", -46);
}
return ashWednesday;
}
}


private static Holiday carnival;

public static Holiday Carnival
Expand Down
Original file line number Diff line number Diff line change
@@ -0,0 +1,132 @@
#region License

//
// Copyright (c) 2011-2012, João Matos Silva <[email protected]>
//
// Licensed under the Apache License, Version 2.0 (the "License");
// you may not use this file except in compliance with the License.
// You may obtain a copy of the License at
//
// http://www.apache.org/licenses/LICENSE-2.0
//
// Unless required by applicable law or agreed to in writing, software
// distributed under the License is distributed on an "AS IS" BASIS,
// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
// See the License for the specific language governing permissions and
// limitations under the License.
//

#endregion

using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using DateTimeExtensions.Common;

namespace DateTimeExtensions.WorkingDays.CultureStrategies
{
[Locale("en-JM")]
public class EN_JMHolidayStrategy : HolidayStrategyBase, IHolidayStrategy
{
public EN_JMHolidayStrategy()
{
this.InnerHolidays.Add(GlobalHolidays.NewYear);
this.InnerHolidays.Add(ChristianHolidays.AshWednesday);
this.InnerHolidays.Add(ChristianHolidays.GoodFriday);
this.InnerHolidays.Add(ChristianHolidays.EasterMonday);

this.InnerHolidays.Add(LaborDay);
this.InnerHolidays.Add(EmancipationDay);
this.InnerHolidays.Add(IndependenceDay);
this.InnerHolidays.Add(NationalHeroesDay);

this.InnerHolidays.Add(ChristianHolidays.Christmas);
this.InnerHolidays.Add(GlobalHolidays.BoxingDay);
}
protected override IDictionary<DateTime, Holiday> BuildObservancesMap(int year)
{
IDictionary<DateTime, Holiday> holidayMap =
this.InnerHolidays.Select(h => new { Date = h.GetInstance(year), Holiday = h })
.Where(h => h.Date.HasValue)
.GroupBy(h => h.Date).Select(g => new { Date = g.Key, g.First().Holiday })
.ToDictionary(k => k.Date.Value, v => v.Holiday);


if (holidayMap.Any(h => h.Key.DayOfWeek == DayOfWeek.Sunday))
{//Holidays falling on Sunday is observed on Monday
var sundayHolidays = holidayMap.OrderBy(d => d.Key).Where(s => s.Key.DayOfWeek == DayOfWeek.Sunday);
foreach (var h in sundayHolidays)
{
var sundayHoliday = h;

var observation = new NthDayOfWeekAfterDayHoliday(sundayHoliday.Value.Name + " Observed", 1, DayOfWeek.Monday, sundayHoliday.Value);
var dateObserved = observation.GetInstance(year);

if (holidayMap.ContainsKey(dateObserved.Value))
{//if a holiday is already observed on the new date, remove from map and find new date of observance
var existingMondayHoliday = holidayMap.First(m => m.Key == dateObserved);
holidayMap.Remove(dateObserved.Value);

var observedOn = dateObserved.Value.AddDays(1);//New Date for removed holiday
while (holidayMap.ContainsKey(observedOn) && observedOn.DayOfWeek != DayOfWeek.Sunday)
observedOn.AddDays(1);//check for all existing holidays to find free date

var daysAfter = existingMondayHoliday.Key.GetDiff(observedOn).Days;
var holidayMoved = new NthDayOfWeekAfterDayHoliday(existingMondayHoliday.Value.Name + " Observed", daysAfter, observedOn.DayOfWeek, existingMondayHoliday.Value);

var newObservedDate = holidayMoved.GetInstance(year);

holidayMap.Add(newObservedDate.Value, holidayMoved);
}
holidayMap.Remove(sundayHoliday.Key);
holidayMap.Add(dateObserved.Value, observation);
}


}
return holidayMap;
}

private Holiday laborDay;
public Holiday LaborDay
{
get
{
if (laborDay == null)
laborDay = new FixedHoliday("Labor Day", 5, 23);
return laborDay;
}
}
private Holiday emancipationDay;
public Holiday EmancipationDay
{
get
{
if (emancipationDay == null)
emancipationDay = new FixedHoliday("Emancipation Day", 8, 1);
return emancipationDay;
}
}
private Holiday independenceDay;
public Holiday IndependenceDay
{
get
{
if (independenceDay == null)
independenceDay = new FixedHoliday("Independence Day", 8, 6);
return independenceDay;
}
}
private Holiday nationalHeroesDay;
public Holiday NationalHeroesDay
{
get
{
if (nationalHeroesDay == null)
nationalHeroesDay = new NthDayOfWeekInMonthHoliday("National Heroes Day", 3, DayOfWeek.Monday, 10, CountDirection.FromFirst);
return nationalHeroesDay;
}
}
}
}
17 changes: 6 additions & 11 deletions tests/DateTimeExtensions.Tests/DateTimeExtensions.Tests.csproj
Original file line number Diff line number Diff line change
@@ -1,10 +1,10 @@
<Project Sdk="Microsoft.NET.Sdk" ToolsVersion="Current">
<PropertyGroup>
<TargetFrameworks>netcoreapp1.0;net462</TargetFrameworks>
<TargetFrameworks>netcoreapp2.0;net461</TargetFrameworks>
<AssemblyName>DateTimeExtensions.Tests</AssemblyName>
<PackageId>DateTimeExtensions.Tests</PackageId>
<GenerateRuntimeConfigurationFiles>true</GenerateRuntimeConfigurationFiles>
<PackageTargetFallback Condition=" '$(TargetFramework)' == 'netcoreapp1.0' ">$(PackageTargetFallback);dnxcore50;portable-net45+win8</PackageTargetFallback>
<PackageTargetFallback Condition=" '$(TargetFramework)' == 'netcoreapp1.0' ">$(PackageTargetFallback);dnxcore50;portable-net461+win8</PackageTargetFallback>
<RuntimeFrameworkVersion Condition=" '$(TargetFramework)' == 'netcoreapp1.0' ">1.1.1</RuntimeFrameworkVersion>
<GenerateAssemblyConfigurationAttribute>false</GenerateAssemblyConfigurationAttribute>
<GenerateAssemblyCompanyAttribute>false</GenerateAssemblyCompanyAttribute>
Expand All @@ -17,16 +17,11 @@
<ProjectReference Include="..\..\src\DateTimeExtensions\DateTimeExtensions.csproj" />
</ItemGroup>
<ItemGroup>
<PackageReference Include="Microsoft.NET.Test.Sdk" Version="15.0.0" />
<PackageReference Include="Nunit" Version="3.11.0" />
<PackageReference Include="Microsoft.NET.Test.Sdk" Version="17.5.0" />
<PackageReference Include="Moq" Version="4.10.1" />
<PackageReference Include="NUnit3TestAdapter" Version="3.12.0" />
</ItemGroup>
<ItemGroup Condition=" '$(TargetFramework)' == 'net451' ">
<PackageReference Include="Microsoft.NETCore.Platforms" Version="1.1.0" />
<Reference Include="System" />
<Reference Include="Microsoft.CSharp" />
</ItemGroup>
<PackageReference Include="NUnit" Version="3.13.3" />
<PackageReference Include="NUnit3TestAdapter" Version="4.4.2" />
</ItemGroup>
<ItemGroup>
<Service Include="{82a7f48d-3b50-4b1e-b82e-3ada8210c358}" />
</ItemGroup>
Expand Down
24 changes: 24 additions & 0 deletions tests/DateTimeExtensions.Tests/enJMHolidaysTests.cs
Original file line number Diff line number Diff line change
@@ -0,0 +1,24 @@
using DateTimeExtensions.WorkingDays;
using NUnit.Framework;
using System;

namespace DateTimeExtensions.Tests
{
[TestFixture]
internal class enJMHolidaysTests
{
private readonly WorkingDayCultureInfo dateTimeCulture = new WorkingDayCultureInfo("en-JM", "Jamaica");
[Test]
public void SundayChristmass2022()
{//Holiday's falling on Sunday are observed on the following monday.
//boxing day was the 26th, a monday, which would result in a clash, hence the clashing holiday would be observed on the following day (Tuesday)
var date = new DateTime(2022, 12, 25);
TestHoliday(dateTimeCulture, date);
}
private void TestHoliday(IWorkingDayCultureInfo workingDayCultureInfo, DateTime dateOnGregorian)
{
var isHoliday = workingDayCultureInfo.IsHoliday(dateOnGregorian);
Assert.IsTrue(isHoliday);
}
}
}

0 comments on commit 84040b6

Please sign in to comment.