Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Feat/deadlines over time intervals #42

Merged
merged 9 commits into from
Apr 10, 2022
Merged
Original file line number Diff line number Diff line change
@@ -1,4 +1,5 @@
using Kysect.Tamgly.Core.ValueObjects;
using Kysect.Tamgly.Core.Entities.Deadlines;
using Kysect.Tamgly.Core.Entities.TimeIntervals;

namespace Kysect.Tamgly.Core.Entities.Backlogs;

Expand Down Expand Up @@ -30,9 +31,9 @@ public static DailyWorkItemBacklog Create(IReadOnlyCollection<WorkItem> workItem
{
ArgumentNullException.ThrowIfNull(workItems);

WorkItemBacklog dailyBacklog = WorkItemBacklog.Create(WorkItemDeadline.Create(WorkItemDeadlineType.Day, time), workItems);
WorkItemBacklog weeklyBacklog = WorkItemBacklog.Create(WorkItemDeadline.Create(WorkItemDeadlineType.Week, time), workItems);
WorkItemBacklog monthlyBacklog = WorkItemBacklog.Create(WorkItemDeadline.Create(WorkItemDeadlineType.Month, time), workItems);
WorkItemBacklog dailyBacklog = WorkItemBacklog.Create(new WorkItemDeadline(new TamglyDay(time)), workItems);
WorkItemBacklog weeklyBacklog = WorkItemBacklog.Create(new WorkItemDeadline(new TamglyWeek(time)), workItems);
WorkItemBacklog monthlyBacklog = WorkItemBacklog.Create(new WorkItemDeadline(new TamglyMonth(time)), workItems);
return new DailyWorkItemBacklog(dailyBacklog, weeklyBacklog, monthlyBacklog);
}
}
Original file line number Diff line number Diff line change
@@ -1,4 +1,5 @@
using Kysect.Tamgly.Core.ValueObjects;
using Kysect.Tamgly.Core.Entities.Deadlines;
using Kysect.Tamgly.Core.Entities.TimeIntervals;

namespace Kysect.Tamgly.Core.Entities.Backlogs;

Expand All @@ -22,7 +23,7 @@ public static MonthlyWorkItemBacklog Create(IReadOnlyCollection<WorkItem> workIt
{
ArgumentNullException.ThrowIfNull(workItems);

WorkItemBacklog weeklyBacklog = WorkItemBacklog.Create(WorkItemDeadline.Create(WorkItemDeadlineType.Month, time), workItems);
WorkItemBacklog weeklyBacklog = WorkItemBacklog.Create(new WorkItemDeadline(new TamglyMonth(time)), workItems);
return new MonthlyWorkItemBacklog(weeklyBacklog);
}
}
Original file line number Diff line number Diff line change
@@ -1,4 +1,5 @@
using Kysect.Tamgly.Core.ValueObjects;
using Kysect.Tamgly.Core.Entities.Deadlines;
using Kysect.Tamgly.Core.Entities.TimeIntervals;

namespace Kysect.Tamgly.Core.Entities.Backlogs;

Expand Down Expand Up @@ -26,8 +27,8 @@ public static WeeklyWorkItemBacklog Create(IReadOnlyCollection<WorkItem> workIte
{
ArgumentNullException.ThrowIfNull(workItems);

WorkItemBacklog weeklyBacklog = WorkItemBacklog.Create(WorkItemDeadline.Create(WorkItemDeadlineType.Week, time), workItems);
WorkItemBacklog monthlyBacklog = WorkItemBacklog.Create(WorkItemDeadline.Create(WorkItemDeadlineType.Month, time), workItems);
WorkItemBacklog weeklyBacklog = WorkItemBacklog.Create(new WorkItemDeadline(new TamglyWeek(time)), workItems);
WorkItemBacklog monthlyBacklog = WorkItemBacklog.Create(new WorkItemDeadline(new TamglyMonth(time)), workItems);
return new WeeklyWorkItemBacklog(weeklyBacklog, monthlyBacklog);
}
}
Original file line number Diff line number Diff line change
@@ -1,5 +1,5 @@
using Kysect.Tamgly.Core.Tools;
using Kysect.Tamgly.Core.ValueObjects;
using Kysect.Tamgly.Core.Entities.Deadlines;
using Kysect.Tamgly.Core.Tools;

namespace Kysect.Tamgly.Core.Entities.Backlogs;

Expand Down
Original file line number Diff line number Diff line change
@@ -0,0 +1,55 @@
using Kysect.Tamgly.Core.Entities.TimeIntervals;
using Kysect.Tamgly.Core.Tools;

namespace Kysect.Tamgly.Core.Entities.Deadlines;

public class WorkItemDeadline
{
public static WorkItemDeadline NoDeadline { get; } = new WorkItemDeadline();

private readonly ITimeInterval? _timeInterval;
private readonly WorkItemDeadlineType _deadlineType;

public WorkItemDeadline()
{
_timeInterval = null;
_deadlineType = WorkItemDeadlineType.NoDeadline;
}

public WorkItemDeadline(TamglyDay day)
{
_timeInterval = day;
_deadlineType = WorkItemDeadlineType.Day;
}

public WorkItemDeadline(TamglyWeek week)
{
_timeInterval = week;
_deadlineType = WorkItemDeadlineType.Week;
}

public WorkItemDeadline(TamglyMonth month)
{
_timeInterval = month;
_deadlineType = WorkItemDeadlineType.Month;
}

public bool MatchedWith(WorkItemDeadline other)
{
if (_deadlineType != other?._deadlineType)
return false;
if (_timeInterval is null)
return other._timeInterval is null;
return _timeInterval.Equals(other._timeInterval);
}

public int GetDaysBeforeDeadlineCount()
{
if (_timeInterval is null)
throw new TamglyException($"Cannot count days before deadline. Deadline type is {WorkItemDeadlineType.NoDeadline}");

DateOnly firstDay = TamglyTime.MaxOf(_timeInterval.Start, TamglyTime.TodayDate);
int daysBeforeDeadlineCount = firstDay.DaysTo(_timeInterval.End);
return Math.Max(daysBeforeDeadlineCount, 0);
}
}
Original file line number Diff line number Diff line change
@@ -1,4 +1,4 @@
namespace Kysect.Tamgly.Core.ValueObjects;
namespace Kysect.Tamgly.Core.Entities.Deadlines;

public enum WorkItemDeadlineType
{
Expand Down
Original file line number Diff line number Diff line change
@@ -0,0 +1,34 @@
using Kysect.Tamgly.Core.Entities.TimeIntervals;
using Kysect.Tamgly.Core.Tools;

namespace Kysect.Tamgly.Core.Entities.RepetitiveWorkItems;

public class DailyEachMonthRepetitiveInterval : IRepetitiveInterval
{
private readonly TimeInterval _interval;
private readonly int _period;
private readonly int _selectedDay;

public DailyEachMonthRepetitiveInterval(TimeInterval interval, int period, int selectedDay)
{
_interval = interval;
_period = period;
_selectedDay = selectedDay;
}

public IReadOnlyCollection<DateOnly> EnumeratePointOnInterval()
{
List<DateOnly> result = new List<DateOnly>();
for (DateOnly currentMonthStart = TamglyTime.GetMonthStart(_interval.Start); currentMonthStart < _interval.End; currentMonthStart = currentMonthStart.AddMonths(_period))
{
DateOnly currentDay = currentMonthStart.ReplaceDayWith(_selectedDay);

if (!_interval.Contains(currentDay))
continue;

result.Add(currentDay);
}

return result;
}
}
Original file line number Diff line number Diff line change
@@ -0,0 +1,35 @@
using Kysect.Tamgly.Core.Entities.TimeIntervals;

namespace Kysect.Tamgly.Core.Entities.RepetitiveWorkItems;

public class DailyEachWeekRepetitiveInterval : IRepetitiveInterval
{
private readonly TimeInterval _interval;
private readonly int _period;
private readonly SelectedDayOfWeek _selectedDayOfWeek;

public DailyEachWeekRepetitiveInterval(TimeInterval interval, int period, SelectedDayOfWeek selectedDayOfWeek)
{
_interval = interval;
_period = period;
_selectedDayOfWeek = selectedDayOfWeek;
}

public IReadOnlyCollection<DateOnly> EnumeratePointOnInterval()
{
var result = new List<DateOnly>();
for (var currentWeekStart = new TamglyWeek(_interval.Start); currentWeekStart.Start < _interval.End; currentWeekStart = currentWeekStart.AddWeek(_period))
{
foreach (DateOnly currentDay in currentWeekStart.EnumerateDays())
{
if (!_interval.Contains(currentDay))
continue;

if (_selectedDayOfWeek.Contains(currentDay))
result.Add(currentDay);
}
}

return result;
}
}
Original file line number Diff line number Diff line change
@@ -0,0 +1,25 @@
using Kysect.Tamgly.Core.Entities.TimeIntervals;

namespace Kysect.Tamgly.Core.Entities.RepetitiveWorkItems;

public class DailyPeriodicRepetitiveInterval : IRepetitiveInterval
{
private readonly TimeInterval _interval;

FrediKats marked this conversation as resolved.
Show resolved Hide resolved
private readonly int _period;

public DailyPeriodicRepetitiveInterval(TimeInterval interval, int period)
{
_interval = interval;
_period = period;
}

public IReadOnlyCollection<DateOnly> EnumeratePointOnInterval()
{
List<DateOnly> result = new List<DateOnly>();
for (DateOnly current = _interval.Start; current < _interval.End; current = current.AddDays(_period))
result.Add(current);

return result;
}
}
Original file line number Diff line number Diff line change
@@ -0,0 +1,6 @@
namespace Kysect.Tamgly.Core.Entities.RepetitiveWorkItems;

public interface IRepetitiveInterval
{
IReadOnlyCollection<DateOnly> EnumeratePointOnInterval();
}
Original file line number Diff line number Diff line change
@@ -0,0 +1,10 @@
namespace Kysect.Tamgly.Core.Entities.RepetitiveWorkItems;

public enum RepetitiveIntervalType
{
DailyPeriodic = 1,
DailyEachWeek,
DailyEachMonth,
Weekly,
Monthly
}
Original file line number Diff line number Diff line change
@@ -0,0 +1,31 @@
namespace Kysect.Tamgly.Core.Entities.RepetitiveWorkItems;

[Flags]
public enum SelectedDayOfWeek
{
Monday = 2 << 0,
Tuesday = 2 << 1,
Wednesday = 2 << 2,
Thursday = 2 << 3,
Friday = 2 << 4,
Saturday = 2 << 5,
Sunday = 2 << 6,
}

public static class SelectedDayOfWeekExtensions
{
public static bool Contains(this SelectedDayOfWeek selectedDayOfWeek, DateOnly date)
{
return date.DayOfWeek switch
{
DayOfWeek.Sunday => selectedDayOfWeek.HasFlag(SelectedDayOfWeek.Sunday),
DayOfWeek.Monday => selectedDayOfWeek.HasFlag(SelectedDayOfWeek.Monday),
FrediKats marked this conversation as resolved.
Show resolved Hide resolved
DayOfWeek.Tuesday => selectedDayOfWeek.HasFlag(SelectedDayOfWeek.Tuesday),
DayOfWeek.Wednesday => selectedDayOfWeek.HasFlag(SelectedDayOfWeek.Wednesday),
DayOfWeek.Thursday => selectedDayOfWeek.HasFlag(SelectedDayOfWeek.Thursday),
DayOfWeek.Friday => selectedDayOfWeek.HasFlag(SelectedDayOfWeek.Friday),
DayOfWeek.Saturday => selectedDayOfWeek.HasFlag(SelectedDayOfWeek.Saturday),
_ => throw new ArgumentOutOfRangeException($"Invalid day of week for {date}: {date.DayOfWeek}")
};
}
}
Original file line number Diff line number Diff line change
@@ -1,20 +1,7 @@
using Kysect.Tamgly.Core.ValueObjects;

namespace Kysect.Tamgly.Core.Entities.TimeIntervals;
namespace Kysect.Tamgly.Core.Entities.TimeIntervals;

public interface ITimeInterval
{
WorkItemDeadlineType DeadlineType { get; }
int Number { get; }
DateOnly Start { get; }

/// <summary>
/// End day is not included
/// </summary>
DateOnly End { get; }

bool Contains(DateOnly dateTime)
{
return Start <= dateTime && dateTime < End;
}
}
Original file line number Diff line number Diff line change
@@ -1,47 +1,34 @@
using Kysect.Tamgly.Core.ValueObjects;
using Kysect.Tamgly.Core.Tools;

namespace Kysect.Tamgly.Core.Entities.TimeIntervals;

public class TamglyDay : ITimeInterval, IEquatable<TamglyDay>
public readonly struct TamglyDay : IEquatable<TamglyDay>, ITimeInterval
{
public WorkItemDeadlineType DeadlineType => WorkItemDeadlineType.Day;

public int Number { get; }
public DateOnly Start { get; }
public DateOnly End { get; }

public TamglyDay(int number)
public TamglyDay(DateOnly start)
{
Number = number;
Start = TamglyTime.ZeroDay.AddDays(Number);
End = Start.AddDays(1);
}
TamglyTime.EnsureDateIsSupported(start);

public static TamglyDay FromDate(DateOnly dateTime)
{
return new TamglyDay(TamglyTime.ZeroDay.DaysTo(dateTime));
Number = TamglyTime.ZeroDay.DaysTo(start);
Start = start;
End = start;
}

public override int GetHashCode()
public bool Equals(TamglyDay other)
{
return Number;
return Number == other.Number;
}

public bool Equals(TamglyDay? other)
public override bool Equals(object? obj)
{
if (ReferenceEquals(null, other))
return false;
if (ReferenceEquals(this, other))
return true;
return Number == other.Number;
return obj is TamglyDay other && Equals(other);
}

public override bool Equals(object? obj)
public override int GetHashCode()
{
if (ReferenceEquals(null, obj))
return false;
if (ReferenceEquals(this, obj))
return true;
return obj is TamglyDay day && Equals(day);
return Number;
}
}
Loading