QuantConnect/Lean

Exposure Samples Might Not Go Back to Zero

Closed this issue · 2 comments

Expected Behavior

Futures contracts automatically delist at expiry

Actual Behavior

The following algorithm maintains Futures exposure long after the contracts should have expired.
image

Potential Solution

N/A

Reproducing the Problem

https://www.quantconnect.com/terminal/processCache?request=embedded_backtest_76290f597a03506e9231c8b10b83eba2.html

System Information

QC Cloud

Checklist

  • I have completely filled out this template
  • I have confirmed that this issue exists on the current master branch
  • I have confirmed that this is not a duplicate issue by searching issues
  • I have provided detailed steps to reproduce the issue

SampleExposure uses Algorithm.Portfolio.Values which is filtering out removed assets because it enumerates SecurityManager underneath -> we should make sure we sample back to zero for each security type if there no longer is any holding for that type

Initially, we thought the reason behind the bug was because SampleExposure used Algorithm.Portfolio.Values which was filtering out the expired futures. Thus, when the future was removed, the Future exposure remained with the last value computed, not going back to zero. However, after debugging the algo reproducing the issue, we found that this idea wasn't true as the Future exposure plot keeps receiving points different from zero even after the future has expired. Indeed, in the plot shared by Derek, Future exposure has the same value from nearly October 2 2012 until 2024.

In contrast, while debugging that algo we found that some futures were not being delisted after expiring, so they were not removed from Algorithm.Securities and we kept receiving their holdings in SampleExposure and thus the Future exposure plot kept receiving new points. Furthermore, while reviewing the logs from the algo ran in the cloud, we confirmed no delisting event was in the logs.

Therefore, we looked into to find why this was happening and we found that the COMEX Gold Futures were not being delisted as in their configuration isInternalFeed was set to true instead of false, thus when the timeSlice with the Delisted object was created in SubscriptionSynchronizer, the slice didn't have any data. Therefore, the delisting object was never processed. Besides, since isInternalFeed was true, data was not emitted.