Skip to content

Commit

Permalink
Add SecurityExchangeHours.Update method to set without changing the r…
Browse files Browse the repository at this point in the history
…eference
  • Loading branch information
jhonabreul committed Mar 13, 2024
1 parent c6cd06a commit 1dd06c9
Show file tree
Hide file tree
Showing 4 changed files with 38 additions and 17 deletions.
2 changes: 1 addition & 1 deletion Common/Securities/SecurityExchange.cs
Original file line number Diff line number Diff line change
Expand Up @@ -31,7 +31,7 @@ public class SecurityExchange
/// <summary>
/// Gets the <see cref="SecurityExchangeHours"/> for this exchange
/// </summary>
public SecurityExchangeHours Hours { get; internal set; }
public SecurityExchangeHours Hours { get; private set; }

/// <summary>
/// Gets the time zone for this exchange
Expand Down
48 changes: 34 additions & 14 deletions Common/Securities/SecurityExchangeHours.cs
Original file line number Diff line number Diff line change
Expand Up @@ -32,19 +32,19 @@ namespace QuantConnect.Securities
/// </remarks>
public class SecurityExchangeHours
{
private readonly HashSet<long> _holidays;
private readonly IReadOnlyDictionary<DateTime, TimeSpan> _earlyCloses;
private readonly IReadOnlyDictionary<DateTime, TimeSpan> _lateOpens;
private HashSet<long> _holidays;
private IReadOnlyDictionary<DateTime, TimeSpan> _earlyCloses;
private IReadOnlyDictionary<DateTime, TimeSpan> _lateOpens;

// these are listed individually for speed
private readonly LocalMarketHours _sunday;
private readonly LocalMarketHours _monday;
private readonly LocalMarketHours _tuesday;
private readonly LocalMarketHours _wednesday;
private readonly LocalMarketHours _thursday;
private readonly LocalMarketHours _friday;
private readonly LocalMarketHours _saturday;
private readonly Dictionary<DayOfWeek, LocalMarketHours> _openHoursByDay;
private LocalMarketHours _sunday;
private LocalMarketHours _monday;
private LocalMarketHours _tuesday;
private LocalMarketHours _wednesday;
private LocalMarketHours _thursday;
private LocalMarketHours _friday;
private LocalMarketHours _saturday;
private Dictionary<DayOfWeek, LocalMarketHours> _openHoursByDay;
private static List<DayOfWeek> daysOfWeek = new List<DayOfWeek>() {
DayOfWeek.Sunday,
DayOfWeek.Monday,
Expand All @@ -58,7 +58,7 @@ public class SecurityExchangeHours
/// <summary>
/// Gets the time zone this exchange resides in
/// </summary>
public DateTimeZone TimeZone { get; }
public DateTimeZone TimeZone { get; private set; }

/// <summary>
/// Gets the holidays for the exchange
Expand Down Expand Up @@ -94,7 +94,7 @@ public HashSet<DateTime> Holidays
/// This does NOT account for extended market hours and only
/// considers <see cref="MarketHoursState.Market"/>
/// </summary>
public TimeSpan RegularMarketDuration { get; }
public TimeSpan RegularMarketDuration { get; private set; }

/// <summary>
/// Checks whether the market is always open or not
Expand Down Expand Up @@ -129,9 +129,15 @@ public SecurityExchangeHours(
Dictionary<DayOfWeek, LocalMarketHours> marketHoursForEachDayOfWeek,
IReadOnlyDictionary<DateTime, TimeSpan> earlyCloses,
IReadOnlyDictionary<DateTime, TimeSpan> lateOpens)
{
var holidays = holidayDates.Select(x => x.Date.Ticks).ToHashSet();
Initialize(timeZone, holidays, marketHoursForEachDayOfWeek, earlyCloses, lateOpens);
}

private void Initialize(DateTimeZone timeZone, HashSet<long> holidays, Dictionary<DayOfWeek, LocalMarketHours> marketHoursForEachDayOfWeek, IReadOnlyDictionary<DateTime, TimeSpan> earlyCloses, IReadOnlyDictionary<DateTime, TimeSpan> lateOpens)
{
TimeZone = timeZone;
_holidays = holidayDates.Select(x => x.Date.Ticks).ToHashSet();
_holidays = holidays;
_earlyCloses = earlyCloses;
_lateOpens = lateOpens;
_openHoursByDay = marketHoursForEachDayOfWeek;
Expand Down Expand Up @@ -599,5 +605,19 @@ public DateTime GetNextTradingDay(DateTime date)

return date;
}

/// <summary>
/// Sets the exchange hours to be the same as the given exchange hours without changing the reference
/// </summary>
/// <param name="other">The hours to set</param>
internal void Update(SecurityExchangeHours other)
{
if (other == null)
{
return;
}

Initialize(other.TimeZone, other._holidays, other._openHoursByDay, other._earlyCloses, other._lateOpens);
}
}
}
3 changes: 2 additions & 1 deletion Engine/RealTime/LiveTradingRealTimeHandler.cs
Original file line number Diff line number Diff line change
Expand Up @@ -197,7 +197,8 @@ protected virtual void UpdateMarketHours(Security security)
? SecurityExchangeHours.AlwaysOpen(security.Exchange.TimeZone)
: MarketHoursDatabase.GetExchangeHours(security.Symbol.ID.Market, security.Symbol, security.Symbol.ID.SecurityType);

security.Exchange.Hours = hours;
// Use Update method to avoid replacing the reference
security.Exchange.Hours.Update(hours);
}

/// <summary>
Expand Down
2 changes: 1 addition & 1 deletion Tests/Common/Scheduling/ScheduleManagerTests.cs
Original file line number Diff line number Diff line change
Expand Up @@ -156,7 +156,7 @@ public void TriggersWeeklyScheduledEventsEachWeekLive()
// Start
handler.SetTime(time);

finished.Wait();
finished.Wait(TimeSpan.FromSeconds(15));

handler.Exit();

Expand Down

0 comments on commit 1dd06c9

Please sign in to comment.