Compare commits
184 Commits
| Author | SHA1 | Date | |
|---|---|---|---|
|
|
31e247689f | ||
|
|
297207badb | ||
|
|
ecb8e8da41 | ||
|
|
c6c4c1edec | ||
|
|
c02a8faedb | ||
|
|
e620d3fd7b | ||
|
|
4b6643312e | ||
|
|
4b2f203322 | ||
|
|
7eefdebae5 | ||
|
|
7f17838ad0 | ||
|
|
5a1ebcbaad | ||
|
|
552511ef58 | ||
|
|
8f2fd3d64a | ||
|
|
609deb2b03 | ||
|
|
7fb246511a | ||
|
|
745292c15a | ||
|
|
22e0e5ddf5 | ||
|
|
ef94b5affc | ||
|
|
61e8c63acd | ||
|
|
1ca7320f2f | ||
|
|
5b8e54f272 | ||
|
|
26584c2fd0 | ||
|
|
48fd4eccff | ||
|
|
75d5cbcf2a | ||
|
|
d702587ad8 | ||
|
|
c99a9dab32 | ||
|
|
8196d0b557 | ||
|
|
3ee941f329 | ||
|
|
286353b763 | ||
|
|
d5f298c235 | ||
|
|
f2c5551b1e | ||
|
|
f86a51ac3f | ||
|
|
1253cc73bd | ||
|
|
6506ff53a3 | ||
|
|
713785157e | ||
|
|
fd7048d2d1 | ||
|
|
1b66aeede1 | ||
|
|
2f80a2a6b9 | ||
|
|
68d4da8e76 | ||
|
|
538405d152 | ||
|
|
1f3fd6edbb | ||
|
|
e3783ed477 | ||
|
|
1171e4fe52 | ||
|
|
a66f279852 | ||
|
|
6575b57146 | ||
|
|
3fa700e450 | ||
|
|
7735917c83 | ||
|
|
67489eef57 | ||
|
|
241306275a | ||
|
|
773bd53525 | ||
|
|
0854ab82da | ||
|
|
2c0390fde3 | ||
|
|
32fcd94abc | ||
|
|
090ffebd03 | ||
|
|
914d0810af | ||
|
|
10902f95dd | ||
|
|
2e67b9ad4f | ||
|
|
7adf27aa61 | ||
|
|
7ea0f60905 | ||
|
|
d9c71e3d34 | ||
|
|
b040518d52 | ||
|
|
725737610a | ||
|
|
37ccee4937 | ||
|
|
0ab0abd1ca | ||
|
|
c565f4cfd0 | ||
|
|
f804b8f0ca | ||
|
|
ef1cf8e4df | ||
|
|
661356e33e | ||
|
|
5842f50b03 | ||
|
|
0f80591f51 | ||
|
|
0622f43a0f | ||
|
|
8f0224feb6 | ||
|
|
781897984e | ||
|
|
340b40c6ce | ||
|
|
58ce899b5d | ||
|
|
ead8335c84 | ||
|
|
84ee81b35b | ||
|
|
03be232f31 | ||
|
|
e568162bff | ||
|
|
e395892b8e | ||
|
|
3483fee766 | ||
|
|
6cba915950 | ||
|
|
046df38be8 | ||
|
|
c7e96b837d | ||
|
|
2f23c89307 | ||
|
|
67d19d88d7 | ||
|
|
b4401db512 | ||
|
|
bc646c974a | ||
|
|
857a950e23 | ||
|
|
888752fa0a | ||
|
|
14427129c7 | ||
|
|
683bfe007a | ||
|
|
263a9099ed | ||
|
|
a78004a1e6 | ||
|
|
9acd30c355 | ||
|
|
441ba1a7b5 | ||
|
|
52b788d9de | ||
|
|
16fdf61903 | ||
|
|
59990573c2 | ||
|
|
acb787e8f6 | ||
|
|
6260b2f7e0 | ||
|
|
95739b8a58 | ||
|
|
c81f5d7d1a | ||
|
|
4961844f82 | ||
|
|
afca923cd9 | ||
|
|
a31436bc6d | ||
|
|
ebaa355bf1 | ||
|
|
46639fc4ec | ||
|
|
2052a86351 | ||
|
|
7a5ff8054b | ||
|
|
a3d6e24741 | ||
|
|
6c5b577b46 | ||
|
|
f4bab98b00 | ||
|
|
733be65148 | ||
|
|
2c26e9fc26 | ||
|
|
2faf921731 | ||
|
|
89f3968eef | ||
|
|
9c7d633b41 | ||
|
|
cfba82e17a | ||
|
|
6811b93d6a | ||
|
|
6916636e8e | ||
|
|
0a4c19527b | ||
|
|
f807d62b18 | ||
|
|
f5c5c5a3b0 | ||
|
|
553bd3993a | ||
|
|
e74bfeb7f9 | ||
|
|
9ab9fe5f2b | ||
|
|
93e7e3edb4 | ||
|
|
49fe020b84 | ||
|
|
6c95372d27 | ||
|
|
cfd46cf63f | ||
|
|
ff1638f653 | ||
|
|
0dff60442e | ||
|
|
d8d6deb675 | ||
|
|
81b2d45440 | ||
|
|
fda4859b5a | ||
|
|
9fa2630dc8 | ||
|
|
b27e9e67dd | ||
|
|
afa7cce46a | ||
|
|
e9c15b2806 | ||
|
|
8ee7a190c6 | ||
|
|
ec3b7a8e6a | ||
|
|
58b422976a | ||
|
|
ee0cf7b3d3 | ||
|
|
ebda5dba93 | ||
|
|
89110aa9f6 | ||
|
|
6f94d765fc | ||
|
|
fd940463b5 | ||
|
|
3f8fd6ac3d | ||
|
|
758c1704b5 | ||
|
|
0e5b6ce91e | ||
|
|
ccf32d3b4f | ||
|
|
0026cca422 | ||
|
|
633833e3c7 | ||
|
|
be64cdffa0 | ||
|
|
9670a6684f | ||
|
|
8447137a3f | ||
|
|
e75bbf9615 | ||
|
|
68af7ec15d | ||
|
|
f08ac5bcce | ||
|
|
ff2d749d61 | ||
|
|
4cc1dec80b | ||
|
|
75993cd021 | ||
|
|
f7ce35ae82 | ||
|
|
36404a6187 | ||
|
|
496f210116 | ||
|
|
b25d53ed6d | ||
|
|
ee7be1a233 | ||
|
|
5644520545 | ||
|
|
5b465216f9 | ||
|
|
d82d70dacf | ||
|
|
23afff13fc | ||
|
|
d7b4fb002f | ||
|
|
85fe39e31b | ||
|
|
690eb7fc9f | ||
|
|
e44f8cd498 | ||
|
|
ceb52c1b9b | ||
|
|
dea1d2eac3 | ||
|
|
f448ab7372 | ||
|
|
fd9c29c87c | ||
|
|
0b62fefb10 | ||
|
|
e13214135a | ||
|
|
c2fdfb235a | ||
|
|
50f8633e90 |
@@ -28,9 +28,9 @@ jobs:
|
||||
shell: bash
|
||||
run: |
|
||||
# install dependencies
|
||||
pip3 install papermill==2.4.0 clr-loader==0.1.6
|
||||
pip3 install papermill==2.4.0 clr-loader==0.2.9
|
||||
# install kernel
|
||||
dotnet tool install --global Microsoft.dotnet-interactive --version 1.0.607001
|
||||
dotnet tool install -g --no-cache --version 1.0.661703 --add-source "https://pkgs.dev.azure.com/dnceng/public/_packaging/dotnet-tools/nuget/v3/index.json" Microsoft.dotnet-interactive
|
||||
# Add dotnet tools to Path
|
||||
export PATH="$HOME/.dotnet/tools:$PATH"
|
||||
# activate kernel for jupyter
|
||||
|
||||
2
.github/workflows/syntax-tests.yml
vendored
2
.github/workflows/syntax-tests.yml
vendored
@@ -28,5 +28,5 @@ jobs:
|
||||
options: --workdir /__w/Lean/Lean -v /home/runner/work:/__w
|
||||
shell: bash
|
||||
run: |
|
||||
pip install --no-cache-dir quantconnect-stubs types-requests==2.32.* mypy==1.15.0 && \
|
||||
pip install --no-cache-dir quantconnect-stubs types-requests==2.32.* types-pytz==2025.2.0.* mypy==1.15.0 && \
|
||||
python run_syntax_check.py
|
||||
|
||||
16
.github/workflows/virtual-environments.yml
vendored
16
.github/workflows/virtual-environments.yml
vendored
@@ -30,11 +30,11 @@ jobs:
|
||||
# Build
|
||||
dotnet build /p:Configuration=Release /v:quiet /p:WarningLevel=1 QuantConnect.Lean.sln && \
|
||||
# Python Virtual Environment System Packages
|
||||
python -m venv /lean-testenv --system-site-packages && . /lean-testenv/bin/activate && pip install --no-cache-dir lean==1.0.185 && deactivate && \
|
||||
python -m venv /lean-testenv --system-site-packages && . /lean-testenv/bin/activate && pip install --no-cache-dir lean==1.0.221 && deactivate && \
|
||||
# Run Virtual Environment Test System Packages
|
||||
dotnet test ./Tests/bin/Release/QuantConnect.Tests.dll --filter "FullyQualifiedName=QuantConnect.Tests.Python.PythonVirtualEnvironmentTests.AssertVirtualEnvironment" && \
|
||||
# Python Virtual Environment
|
||||
rm -rf /lean-testenv && python -m venv /lean-testenv && . /lean-testenv/bin/activate && pip install --no-cache-dir lean==1.0.185 && deactivate && \
|
||||
rm -rf /lean-testenv && python -m venv /lean-testenv && . /lean-testenv/bin/activate && pip install --no-cache-dir lean==1.0.221 && deactivate && \
|
||||
# Run Virtual Environment Test
|
||||
dotnet test ./Tests/bin/Release/QuantConnect.Tests.dll --filter "FullyQualifiedName=QuantConnect.Tests.Python.PythonVirtualEnvironmentTests.AssertVirtualEnvironment" && \
|
||||
# Run Python Package Tests
|
||||
@@ -46,19 +46,21 @@ jobs:
|
||||
# Run TensorlyTest Python Package Test
|
||||
dotnet test ./Tests/bin/Release/QuantConnect.Tests.dll --filter "FullyQualifiedName=QuantConnect.Tests.Python.PythonPackagesTests.TensorlyTest" --blame-hang-timeout 120seconds --blame-crash && \
|
||||
# Run NeuralTangents, Ignite Python Package Test
|
||||
dotnet test ./Tests/bin/Release/QuantConnect.Tests.dll --filter "FullyQualifiedName=QuantConnect.Tests.Python.PythonPackagesTests.NeuralTangentsTest|IgniteTest" --blame-hang-timeout 120seconds --blame-crash && \
|
||||
dotnet test ./Tests/bin/Release/QuantConnect.Tests.dll --filter "FullyQualifiedName=QuantConnect.Tests.Python.PythonPackagesTests.IgniteTest" --blame-hang-timeout 120seconds --blame-crash && \
|
||||
# Run TensorflowTest
|
||||
dotnet test ./Tests/bin/Release/QuantConnect.Tests.dll --filter "FullyQualifiedName=QuantConnect.Tests.Python.PythonPackagesTests.TensorflowTest" --blame-hang-timeout 120seconds --blame-crash && \
|
||||
# Run TensorflowProbability
|
||||
dotnet test ./Tests/bin/Release/QuantConnect.Tests.dll --filter "FullyQualifiedName=QuantConnect.Tests.Python.PythonPackagesTests.TensorflowProbabilityTest" --blame-hang-timeout 120seconds --blame-crash && \
|
||||
# Run Hvplot Python Package Test
|
||||
dotnet test ./Tests/bin/Release/QuantConnect.Tests.dll --filter "FullyQualifiedName=QuantConnect.Tests.Python.PythonPackagesTests.HvplotTest" --blame-hang-timeout 120seconds --blame-crash && \
|
||||
dotnet test ./Tests/bin/Release/QuantConnect.Tests.dll --filter "FullyQualifiedName=QuantConnect.Tests.Python.PythonPackagesTests.RiskparityportfolioTest" --blame-hang-timeout 120seconds --blame-crash && \
|
||||
# Run Transformers
|
||||
dotnet test ./Tests/bin/Release/QuantConnect.Tests.dll --filter "FullyQualifiedName=QuantConnect.Tests.Python.PythonPackagesTests.Transformers" --blame-hang-timeout 120seconds --blame-crash && \
|
||||
dotnet test ./Tests/bin/Release/QuantConnect.Tests.dll --filter "FullyQualifiedName=QuantConnect.Tests.Python.PythonPackagesTests.XTransformers" --blame-hang-timeout 120seconds --blame-crash && \
|
||||
# Run Shap
|
||||
dotnet test ./Tests/bin/Release/QuantConnect.Tests.dll --filter "FullyQualifiedName=QuantConnect.Tests.Python.PythonPackagesTests.ShapTest|KerasTest|PyvinecopulibTest" --blame-hang-timeout 120seconds --blame-crash && \
|
||||
dotnet test ./Tests/bin/Release/QuantConnect.Tests.dll --filter "FullyQualifiedName=QuantConnect.Tests.Python.PythonPackagesTests.Mlforecast" --blame-hang-timeout 120seconds --blame-crash && \
|
||||
dotnet test ./Tests/bin/Release/QuantConnect.Tests.dll --filter "FullyQualifiedName=QuantConnect.Tests.Python.PythonPackagesTests.KerasTest|PyvinecopulibTest" --blame-hang-timeout 120seconds --blame-crash && \
|
||||
dotnet test ./Tests/bin/Release/QuantConnect.Tests.dll --filter "FullyQualifiedName=QuantConnect.Tests.Python.PythonPackagesTests.StatsForecast|Mlforecast" --blame-hang-timeout 120seconds --blame-crash && \
|
||||
dotnet test ./Tests/bin/Release/QuantConnect.Tests.dll --filter "FullyQualifiedName=QuantConnect.Tests.Python.PythonPackagesTests.MlxtendTest|Thinc" --blame-hang-timeout 120seconds --blame-crash && \
|
||||
dotnet test ./Tests/bin/Release/QuantConnect.Tests.dll --filter "FullyQualifiedName=QuantConnect.Tests.Python.PythonPackagesTests.ModuleVersionTestExplicit" --blame-hang-timeout 120seconds --blame-crash && \
|
||||
dotnet test ./Tests/bin/Release/QuantConnect.Tests.dll --filter "FullyQualifiedName=QuantConnect.Tests.Python.PythonPackagesTests.Neuralforecast" --blame-hang-timeout 120seconds --blame-crash
|
||||
dotnet test ./Tests/bin/Release/QuantConnect.Tests.dll --filter "FullyQualifiedName=QuantConnect.Tests.Python.PythonPackagesTests.Neuralforecast" --blame-hang-timeout 120seconds --blame-crash && \
|
||||
dotnet test ./Tests/bin/Release/QuantConnect.Tests.dll --filter "FullyQualifiedName=QuantConnect.Tests.Python.PythonPackagesTests.Tsfel" --blame-hang-timeout 120seconds --blame-crash && \
|
||||
dotnet test ./Tests/bin/Release/QuantConnect.Tests.dll --filter "FullyQualifiedName=QuantConnect.Tests.Python.PythonPackagesTests.ScikitOptimizeTest" --blame-hang-timeout 120seconds --blame-crash
|
||||
|
||||
@@ -87,7 +87,7 @@ namespace QuantConnect.Algorithm.CSharp
|
||||
/// <summary>
|
||||
/// Data Points count of all timeslices of algorithm
|
||||
/// </summary>
|
||||
public long DataPoints => 24;
|
||||
public long DataPoints => 26;
|
||||
|
||||
/// <summary>
|
||||
/// Data Points count of the algorithm history
|
||||
|
||||
@@ -82,7 +82,7 @@ namespace QuantConnect.Algorithm.CSharp
|
||||
/// <summary>
|
||||
/// Data Points count of all timeslices of algorithm
|
||||
/// </summary>
|
||||
public long DataPoints => 24;
|
||||
public long DataPoints => 25;
|
||||
|
||||
/// <summary>
|
||||
/// Data Points count of the algorithm history
|
||||
|
||||
@@ -1,11 +1,11 @@
|
||||
/*
|
||||
* QUANTCONNECT.COM - Democratizing Finance, Empowering Individuals.
|
||||
* Lean Algorithmic Trading Engine v2.0. Copyright 2014 QuantConnect Corporation.
|
||||
*
|
||||
* Licensed under the Apache License, Version 2.0 (the "License");
|
||||
*
|
||||
* 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.
|
||||
@@ -107,7 +107,7 @@ namespace QuantConnect.Algorithm.CSharp
|
||||
/// <summary>
|
||||
/// Data Points count of the algorithm history
|
||||
/// </summary>
|
||||
public int AlgorithmHistoryDataPoints => 77;
|
||||
public int AlgorithmHistoryDataPoints => 26;
|
||||
|
||||
/// <summary>
|
||||
/// Final status of the algorithm
|
||||
@@ -122,18 +122,18 @@ namespace QuantConnect.Algorithm.CSharp
|
||||
{"Total Orders", "436"},
|
||||
{"Average Win", "0.28%"},
|
||||
{"Average Loss", "-0.01%"},
|
||||
{"Compounding Annual Return", "1.926%"},
|
||||
{"Compounding Annual Return", "1.925%"},
|
||||
{"Drawdown", "1.000%"},
|
||||
{"Expectancy", "1.650"},
|
||||
{"Expectancy", "1.649"},
|
||||
{"Start Equity", "10000.00"},
|
||||
{"End Equity", "10411.11"},
|
||||
{"Net Profit", "4.111%"},
|
||||
{"End Equity", "10410.99"},
|
||||
{"Net Profit", "4.110%"},
|
||||
{"Sharpe Ratio", "0.332"},
|
||||
{"Sortino Ratio", "0.313"},
|
||||
{"Probabilistic Sharpe Ratio", "74.084%"},
|
||||
{"Loss Rate", "90%"},
|
||||
{"Win Rate", "10%"},
|
||||
{"Profit-Loss Ratio", "25.26"},
|
||||
{"Profit-Loss Ratio", "25.25"},
|
||||
{"Alpha", "0.003"},
|
||||
{"Beta", "0.001"},
|
||||
{"Annual Standard Deviation", "0.01"},
|
||||
@@ -146,7 +146,7 @@ namespace QuantConnect.Algorithm.CSharp
|
||||
{"Lowest Capacity Asset", "BTCUSD 2XR"},
|
||||
{"Portfolio Turnover", "2.22%"},
|
||||
{"Drawdown Recovery", "139"},
|
||||
{"OrderListHash", "9fce77ef8817cf0159897fc64d01f5e9"}
|
||||
{"OrderListHash", "896ecc92440d51ed26644aac5b8706e4"}
|
||||
};
|
||||
}
|
||||
}
|
||||
|
||||
@@ -132,34 +132,34 @@ namespace QuantConnect.Algorithm.CSharp
|
||||
/// </summary>
|
||||
public Dictionary<string, string> ExpectedStatistics => new Dictionary<string, string>
|
||||
{
|
||||
{"Total Orders", "3"},
|
||||
{"Total Orders", "4"},
|
||||
{"Average Win", "0%"},
|
||||
{"Average Loss", "-0.03%"},
|
||||
{"Compounding Annual Return", "-2.594%"},
|
||||
{"Drawdown", "0.000%"},
|
||||
{"Average Loss", "-0.10%"},
|
||||
{"Compounding Annual Return", "-14.232%"},
|
||||
{"Drawdown", "0.200%"},
|
||||
{"Expectancy", "-1"},
|
||||
{"Start Equity", "100000"},
|
||||
{"End Equity", "99966.4"},
|
||||
{"Net Profit", "-0.034%"},
|
||||
{"Sharpe Ratio", "-10.666"},
|
||||
{"End Equity", "99803.9"},
|
||||
{"Net Profit", "-0.196%"},
|
||||
{"Sharpe Ratio", "-7.95"},
|
||||
{"Sortino Ratio", "0"},
|
||||
{"Probabilistic Sharpe Ratio", "1.216%"},
|
||||
{"Loss Rate", "100%"},
|
||||
{"Win Rate", "0%"},
|
||||
{"Profit-Loss Ratio", "0"},
|
||||
{"Alpha", "-0.029"},
|
||||
{"Beta", "0.004"},
|
||||
{"Annual Standard Deviation", "0.003"},
|
||||
{"Alpha", "-0.128"},
|
||||
{"Beta", "0.026"},
|
||||
{"Annual Standard Deviation", "0.016"},
|
||||
{"Annual Variance", "0"},
|
||||
{"Information Ratio", "-0.768"},
|
||||
{"Tracking Error", "0.241"},
|
||||
{"Treynor Ratio", "-6.368"},
|
||||
{"Information Ratio", "-1.186"},
|
||||
{"Tracking Error", "0.237"},
|
||||
{"Treynor Ratio", "-4.747"},
|
||||
{"Total Fees", "$8.60"},
|
||||
{"Estimated Strategy Capacity", "$5500000.00"},
|
||||
{"Lowest Capacity Asset", "ES VMKLFZIH2MTD"},
|
||||
{"Portfolio Turnover", "66.80%"},
|
||||
{"Estimated Strategy Capacity", "$2000.00"},
|
||||
{"Lowest Capacity Asset", "ES VU1EHIDJYLMP"},
|
||||
{"Portfolio Turnover", "66.50%"},
|
||||
{"Drawdown Recovery", "0"},
|
||||
{"OrderListHash", "39f1e15c27212d8fdd58aeb7fb2b93cc"}
|
||||
{"OrderListHash", "4720516462fcabb4db1aead46051cb4a"}
|
||||
};
|
||||
}
|
||||
}
|
||||
|
||||
@@ -134,10 +134,10 @@ namespace QuantConnect.Algorithm.CSharp
|
||||
{"Treynor Ratio", "68696.045"},
|
||||
{"Total Fees", "$35.70"},
|
||||
{"Estimated Strategy Capacity", "$2600000.00"},
|
||||
{"Lowest Capacity Asset", "ES 31C3JQS9D84PW|ES XCZJLC9NOB29"},
|
||||
{"Lowest Capacity Asset", "ES 31C3JQS9DCF1G|ES XCZJLC9NOB29"},
|
||||
{"Portfolio Turnover", "495.15%"},
|
||||
{"Drawdown Recovery", "0"},
|
||||
{"OrderListHash", "85257286f088992d599c1ad0799a6237"}
|
||||
{"OrderListHash", "af830085995d0b8fa0d33a6e80dd1241"}
|
||||
};
|
||||
}
|
||||
}
|
||||
|
||||
@@ -0,0 +1,145 @@
|
||||
/*
|
||||
* QUANTCONNECT.COM - Democratizing Finance, Empowering Individuals.
|
||||
* Lean Algorithmic Trading Engine v2.0. Copyright 2014 QuantConnect Corporation.
|
||||
*
|
||||
* 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.
|
||||
*/
|
||||
|
||||
using System;
|
||||
using System.Collections.Generic;
|
||||
using System.Linq;
|
||||
using QuantConnect.Data.UniverseSelection;
|
||||
using QuantConnect.Interfaces;
|
||||
using QuantConnect.Securities;
|
||||
using QuantConnect.Securities.Future;
|
||||
using QuantConnect.Securities.Option;
|
||||
|
||||
namespace QuantConnect.Algorithm.CSharp
|
||||
{
|
||||
/// <summary>
|
||||
/// Algorithm asserting AddFutureOptionContract does not throw even when the underlying security configurations are internal
|
||||
/// </summary>
|
||||
public class AddFutureOptionContractWithInternalMappedUnderlyingRegressionAlgorithm : QCAlgorithm, IRegressionAlgorithmDefinition
|
||||
{
|
||||
private Future _continuousContract;
|
||||
private Option _fopContract;
|
||||
|
||||
public override void Initialize()
|
||||
{
|
||||
SetStartDate(2020, 01, 04);
|
||||
SetEndDate(2020, 01 , 06);
|
||||
|
||||
_continuousContract = AddFuture(Futures.Indices.SP500EMini,
|
||||
dataNormalizationMode: DataNormalizationMode.BackwardsRatio,
|
||||
dataMappingMode: DataMappingMode.LastTradingDay,
|
||||
contractDepthOffset: 0);
|
||||
}
|
||||
|
||||
public override void OnSecuritiesChanged(SecurityChanges changes)
|
||||
{
|
||||
if (changes.AddedSecurities.Any(security => security.Symbol == _continuousContract.Symbol))
|
||||
{
|
||||
if (SubscriptionManager.SubscriptionDataConfigService.GetSubscriptionDataConfigs(_continuousContract.Mapped).Count != 0 ||
|
||||
SubscriptionManager.SubscriptionDataConfigService.GetSubscriptionDataConfigs(_continuousContract.Mapped, includeInternalConfigs: true).Count == 0)
|
||||
{
|
||||
throw new RegressionTestException("Continuous future underlying should only have internal subscription configs");
|
||||
}
|
||||
|
||||
var contract = OptionChain(_continuousContract.Mapped).FirstOrDefault()?.Symbol;
|
||||
|
||||
try
|
||||
{
|
||||
_fopContract = AddFutureOptionContract(contract);
|
||||
}
|
||||
catch (Exception e)
|
||||
{
|
||||
throw new RegressionTestException($"Failed to add future option contract {contract}", e);
|
||||
}
|
||||
}
|
||||
else if (_fopContract != null && changes.AddedSecurities.Any(security => security.Symbol == _fopContract.Symbol))
|
||||
{
|
||||
var underlyingSubscriptions = SubscriptionManager.SubscriptionDataConfigService.GetSubscriptionDataConfigs(_fopContract.Symbol.Underlying);
|
||||
if (underlyingSubscriptions.Any(x => x.DataNormalizationMode == DataNormalizationMode.Raw))
|
||||
{
|
||||
throw new RegressionTestException("Future option underlying should not have raw data normalization mode");
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
public override void OnEndOfAlgorithm()
|
||||
{
|
||||
if (_fopContract == null)
|
||||
{
|
||||
throw new RegressionTestException("Failed to add future option contract");
|
||||
}
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// This is used by the regression test system to indicate if the open source Lean repository has the required data to run this algorithm.
|
||||
/// </summary>
|
||||
public bool CanRunLocally { get; } = true;
|
||||
|
||||
/// <summary>
|
||||
/// This is used by the regression test system to indicate which languages this algorithm is written in.
|
||||
/// </summary>
|
||||
public List<Language> Languages { get; } = new() { Language.CSharp };
|
||||
|
||||
/// <summary>
|
||||
/// Data Points count of all timeslices of algorithm
|
||||
/// </summary>
|
||||
public long DataPoints => 3181;
|
||||
|
||||
/// <summary>
|
||||
/// Data Points count of the algorithm history
|
||||
/// </summary>
|
||||
public int AlgorithmHistoryDataPoints => 1;
|
||||
|
||||
/// <summary>
|
||||
/// Final status of the algorithm
|
||||
/// </summary>
|
||||
public AlgorithmStatus AlgorithmStatus => AlgorithmStatus.Completed;
|
||||
|
||||
/// <summary>
|
||||
/// This is used by the regression test system to indicate what the expected statistics are from running the algorithm
|
||||
/// </summary>
|
||||
public Dictionary<string, string> ExpectedStatistics => new Dictionary<string, string>
|
||||
{
|
||||
{"Total Orders", "0"},
|
||||
{"Average Win", "0%"},
|
||||
{"Average Loss", "0%"},
|
||||
{"Compounding Annual Return", "0%"},
|
||||
{"Drawdown", "0%"},
|
||||
{"Expectancy", "0"},
|
||||
{"Start Equity", "100000"},
|
||||
{"End Equity", "100000"},
|
||||
{"Net Profit", "0%"},
|
||||
{"Sharpe Ratio", "0"},
|
||||
{"Sortino Ratio", "0"},
|
||||
{"Probabilistic Sharpe Ratio", "0%"},
|
||||
{"Loss Rate", "0%"},
|
||||
{"Win Rate", "0%"},
|
||||
{"Profit-Loss Ratio", "0"},
|
||||
{"Alpha", "0"},
|
||||
{"Beta", "0"},
|
||||
{"Annual Standard Deviation", "0"},
|
||||
{"Annual Variance", "0"},
|
||||
{"Information Ratio", "-14.395"},
|
||||
{"Tracking Error", "0.043"},
|
||||
{"Treynor Ratio", "0"},
|
||||
{"Total Fees", "$0.00"},
|
||||
{"Estimated Strategy Capacity", "$0"},
|
||||
{"Lowest Capacity Asset", ""},
|
||||
{"Portfolio Turnover", "0%"},
|
||||
{"Drawdown Recovery", "0"},
|
||||
{"OrderListHash", "d41d8cd98f00b204e9800998ecf8427e"}
|
||||
};
|
||||
}
|
||||
}
|
||||
@@ -240,31 +240,31 @@ namespace QuantConnect.Algorithm.CSharp
|
||||
{"Total Orders", "2"},
|
||||
{"Average Win", "0%"},
|
||||
{"Average Loss", "0%"},
|
||||
{"Compounding Annual Return", "309.669%"},
|
||||
{"Drawdown", "0.900%"},
|
||||
{"Compounding Annual Return", "430.834%"},
|
||||
{"Drawdown", "4.200%"},
|
||||
{"Expectancy", "0"},
|
||||
{"Start Equity", "100000"},
|
||||
{"End Equity", "101950.53"},
|
||||
{"Net Profit", "1.951%"},
|
||||
{"Sharpe Ratio", "15.402"},
|
||||
{"End Equity", "102313.03"},
|
||||
{"Net Profit", "2.313%"},
|
||||
{"Sharpe Ratio", "17.721"},
|
||||
{"Sortino Ratio", "0"},
|
||||
{"Probabilistic Sharpe Ratio", "95.977%"},
|
||||
{"Loss Rate", "0%"},
|
||||
{"Win Rate", "0%"},
|
||||
{"Profit-Loss Ratio", "0"},
|
||||
{"Alpha", "1.886"},
|
||||
{"Beta", "1.066"},
|
||||
{"Annual Standard Deviation", "0.155"},
|
||||
{"Annual Variance", "0.024"},
|
||||
{"Information Ratio", "13.528"},
|
||||
{"Tracking Error", "0.142"},
|
||||
{"Treynor Ratio", "2.237"},
|
||||
{"Alpha", "2.663"},
|
||||
{"Beta", "1.264"},
|
||||
{"Annual Standard Deviation", "0.184"},
|
||||
{"Annual Variance", "0.034"},
|
||||
{"Information Ratio", "16.514"},
|
||||
{"Tracking Error", "0.169"},
|
||||
{"Treynor Ratio", "2.574"},
|
||||
{"Total Fees", "$3.57"},
|
||||
{"Estimated Strategy Capacity", "$760000.00"},
|
||||
{"Lowest Capacity Asset", "ES XCZJLDQX2SRO|ES XCZJLC9NOB29"},
|
||||
{"Portfolio Turnover", "32.31%"},
|
||||
{"Estimated Strategy Capacity", "$28000000.00"},
|
||||
{"Lowest Capacity Asset", "ES XCZJLCA62LNO|ES XCZJLC9NOB29"},
|
||||
{"Portfolio Turnover", "33.84%"},
|
||||
{"Drawdown Recovery", "0"},
|
||||
{"OrderListHash", "7a04f66a30d793bf187c2695781ad3ee"}
|
||||
{"OrderListHash", "7c82013ecabca41591e0253a477025dd"}
|
||||
};
|
||||
}
|
||||
}
|
||||
|
||||
@@ -117,7 +117,7 @@ namespace QuantConnect.Algorithm.CSharp
|
||||
/// <summary>
|
||||
/// Data Points count of all timeslices of algorithm
|
||||
/// </summary>
|
||||
public long DataPoints => 37597;
|
||||
public long DataPoints => 37598;
|
||||
|
||||
/// <summary>
|
||||
/// Data Points count of the algorithm history
|
||||
@@ -158,10 +158,10 @@ namespace QuantConnect.Algorithm.CSharp
|
||||
{"Treynor Ratio", "2.01"},
|
||||
{"Total Fees", "$2.00"},
|
||||
{"Estimated Strategy Capacity", "$5700000.00"},
|
||||
{"Lowest Capacity Asset", "AOL VRKS95ENLBYE|AOL R735QTJ8XC9X"},
|
||||
{"Lowest Capacity Asset", "AOL VRKS95ENPM9Y|AOL R735QTJ8XC9X"},
|
||||
{"Portfolio Turnover", "0.55%"},
|
||||
{"Drawdown Recovery", "0"},
|
||||
{"OrderListHash", "fc5ab25181a01ca5ce39212f60eb0ecd"}
|
||||
{"OrderListHash", "d314aef81752b6583fd58f9e49054cd4"}
|
||||
};
|
||||
}
|
||||
}
|
||||
|
||||
@@ -169,7 +169,7 @@ namespace QuantConnect.Algorithm.CSharp
|
||||
/// <summary>
|
||||
/// Data Points count of all timeslices of algorithm
|
||||
/// </summary>
|
||||
public long DataPoints => 5798;
|
||||
public long DataPoints => 5800;
|
||||
|
||||
/// <summary>
|
||||
/// Data Points count of the algorithm history
|
||||
@@ -210,10 +210,10 @@ namespace QuantConnect.Algorithm.CSharp
|
||||
{"Treynor Ratio", "0.335"},
|
||||
{"Total Fees", "$2.00"},
|
||||
{"Estimated Strategy Capacity", "$2800000.00"},
|
||||
{"Lowest Capacity Asset", "AOL VRKS95ENLBYE|AOL R735QTJ8XC9X"},
|
||||
{"Lowest Capacity Asset", "AOL VRKS95ENPM9Y|AOL R735QTJ8XC9X"},
|
||||
{"Portfolio Turnover", "1.14%"},
|
||||
{"Drawdown Recovery", "0"},
|
||||
{"OrderListHash", "90aa4bf345a6ba5ea2b0b14e32d1598f"}
|
||||
{"OrderListHash", "e33b98d8e94ed92d0441fc6fe0d461fb"}
|
||||
};
|
||||
}
|
||||
}
|
||||
|
||||
@@ -116,7 +116,7 @@ namespace QuantConnect.Algorithm.CSharp
|
||||
/// <summary>
|
||||
/// Data Points count of all timeslices of algorithm
|
||||
/// </summary>
|
||||
public long DataPoints => 3814;
|
||||
public long DataPoints => 3818;
|
||||
|
||||
/// <summary>
|
||||
/// Data Points count of the algorithm history
|
||||
@@ -157,10 +157,10 @@ namespace QuantConnect.Algorithm.CSharp
|
||||
{"Treynor Ratio", "0"},
|
||||
{"Total Fees", "$2.00"},
|
||||
{"Estimated Strategy Capacity", "$5000000.00"},
|
||||
{"Lowest Capacity Asset", "AAPL VXBK4R62CXGM|AAPL R735QTJ8XC9X"},
|
||||
{"Lowest Capacity Asset", "AAPL VXBK4R62H7S6|AAPL R735QTJ8XC9X"},
|
||||
{"Portfolio Turnover", "22.70%"},
|
||||
{"Drawdown Recovery", "0"},
|
||||
{"OrderListHash", "29fd1b75f6db05dd823a6db7e8bd90a9"}
|
||||
{"OrderListHash", "71511e4929377cd55fbf5e7e9555c248"}
|
||||
};
|
||||
}
|
||||
}
|
||||
|
||||
@@ -96,7 +96,7 @@ namespace QuantConnect.Algorithm.CSharp
|
||||
/// <summary>
|
||||
/// Data Points count of all timeslices of algorithm
|
||||
/// </summary>
|
||||
public long DataPoints => 1658167;
|
||||
public long DataPoints => 2349547;
|
||||
|
||||
/// <summary>
|
||||
/// Data Points count of the algorithm history
|
||||
|
||||
@@ -246,10 +246,10 @@ namespace QuantConnect.Algorithm.CSharp
|
||||
{"Treynor Ratio", "0"},
|
||||
{"Total Fees", "$6.00"},
|
||||
{"Estimated Strategy Capacity", "$4000.00"},
|
||||
{"Lowest Capacity Asset", "GOOCV 305RBQ2BZBZT2|GOOCV VP83T1ZUHROL"},
|
||||
{"Lowest Capacity Asset", "GOOCV 305RBQ2BZGA4M|GOOCV VP83T1ZUHROL"},
|
||||
{"Portfolio Turnover", "2.58%"},
|
||||
{"Drawdown Recovery", "0"},
|
||||
{"OrderListHash", "12037c87de17d6e62eadd99c70a0685e"}
|
||||
{"OrderListHash", "f418de0673fc166487daf80991dfe3a0"}
|
||||
};
|
||||
}
|
||||
}
|
||||
|
||||
@@ -83,7 +83,7 @@ namespace QuantConnect.Algorithm.CSharp
|
||||
/// <summary>
|
||||
/// Data Points count of all timeslices of algorithm
|
||||
/// </summary>
|
||||
public long DataPoints => 11202;
|
||||
public long DataPoints => 15042;
|
||||
|
||||
/// <summary>
|
||||
/// Data Points count of the algorithm history
|
||||
|
||||
@@ -110,7 +110,7 @@ namespace QuantConnect.Algorithm.CSharp
|
||||
/// <summary>
|
||||
/// Data Points count of all timeslices of algorithm
|
||||
/// </summary>
|
||||
public long DataPoints => 7063;
|
||||
public long DataPoints => 7065;
|
||||
|
||||
/// <summary>
|
||||
/// Data Points count of the algorithm history
|
||||
|
||||
@@ -101,7 +101,7 @@ namespace QuantConnect.Algorithm.CSharp
|
||||
/// <summary>
|
||||
/// Data Points count of all timeslices of algorithm
|
||||
/// </summary>
|
||||
public long DataPoints => 1578;
|
||||
public long DataPoints => 1579;
|
||||
|
||||
/// <summary>
|
||||
/// Data Points count of the algorithm history
|
||||
@@ -142,10 +142,10 @@ namespace QuantConnect.Algorithm.CSharp
|
||||
{"Treynor Ratio", "0"},
|
||||
{"Total Fees", "$2.00"},
|
||||
{"Estimated Strategy Capacity", "$6200000.00"},
|
||||
{"Lowest Capacity Asset", "AAPL VXBK4QA5EM92|AAPL R735QTJ8XC9X"},
|
||||
{"Lowest Capacity Asset", "AAPL VXBK4QA5IWKM|AAPL R735QTJ8XC9X"},
|
||||
{"Portfolio Turnover", "90.27%"},
|
||||
{"Drawdown Recovery", "0"},
|
||||
{"OrderListHash", "a111609c2c64554268539b5798e5b31f"}
|
||||
{"OrderListHash", "a332b93ff5e2dfe89258c450a64c7125"}
|
||||
};
|
||||
}
|
||||
}
|
||||
|
||||
@@ -38,7 +38,7 @@ namespace QuantConnect.Algorithm.CSharp
|
||||
SetEndDate(2013, 10, 10);
|
||||
|
||||
var SP500 = QuantConnect.Symbol.Create(Futures.Indices.SP500EMini, SecurityType.Future, Market.CME);
|
||||
_symbol = FuturesChain(SP500).First();
|
||||
_symbol = FuturesChain(SP500).OrderBy(x => x.Symbol.ID.Date).First();
|
||||
|
||||
// Test case: custom IndicatorBase<QuoteBar> indicator using Future unsubscribed symbol
|
||||
var indicator1 = new CustomIndicator();
|
||||
|
||||
137
Algorithm.CSharp/AutomaticSeedBaseRegressionAlgorithm.cs
Normal file
137
Algorithm.CSharp/AutomaticSeedBaseRegressionAlgorithm.cs
Normal file
@@ -0,0 +1,137 @@
|
||||
/*
|
||||
* QUANTCONNECT.COM - Democratizing Finance, Empowering Individuals.
|
||||
* Lean Algorithmic Trading Engine v2.0. Copyright 2014 QuantConnect Corporation.
|
||||
*
|
||||
* 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.
|
||||
*
|
||||
*/
|
||||
|
||||
using System.Collections.Generic;
|
||||
using System.Linq;
|
||||
using QuantConnect.Interfaces;
|
||||
using QuantConnect.Data.UniverseSelection;
|
||||
using QuantConnect.Data.Market;
|
||||
using QuantConnect.Securities;
|
||||
|
||||
namespace QuantConnect.Algorithm.CSharp
|
||||
{
|
||||
/// <summary>
|
||||
/// Regression algorithm asserting that security are automatically seeded by default
|
||||
/// </summary>
|
||||
public abstract class AutomaticSeedBaseRegressionAlgorithm : QCAlgorithm, IRegressionAlgorithmDefinition
|
||||
{
|
||||
protected virtual bool ShouldHaveTradeData { get; }
|
||||
protected virtual bool ShouldHaveQuoteData { get; }
|
||||
protected virtual bool ShouldHaveOpenInterestData { get; }
|
||||
|
||||
public override void OnSecuritiesChanged(SecurityChanges changes)
|
||||
{
|
||||
var gotTrades = false;
|
||||
var gotQuotes = false;
|
||||
var gotOpenInterest = false;
|
||||
|
||||
foreach (var addedSecurity in changes.AddedSecurities.Where(x => !x.Symbol.IsCanonical() || x.Symbol.SecurityType == SecurityType.Future))
|
||||
{
|
||||
if (addedSecurity.Price == 0)
|
||||
{
|
||||
throw new RegressionTestException("Security was not seeded");
|
||||
}
|
||||
|
||||
if (!addedSecurity.HasData)
|
||||
{
|
||||
throw new RegressionTestException("Security does not have TradeBar or QuoteBar or OpenInterest data");
|
||||
}
|
||||
|
||||
gotTrades |= addedSecurity.Cache.GetData<TradeBar>() != null;
|
||||
gotQuotes |= addedSecurity.Cache.GetData<QuoteBar>() != null;
|
||||
gotOpenInterest |= addedSecurity.Cache.GetData<OpenInterest>() != null;
|
||||
}
|
||||
|
||||
if (changes.AddedSecurities.Count > 0)
|
||||
{
|
||||
if (ShouldHaveTradeData && !gotTrades)
|
||||
{
|
||||
throw new RegressionTestException("No contract had TradeBar data");
|
||||
}
|
||||
|
||||
if (ShouldHaveQuoteData && !gotQuotes)
|
||||
{
|
||||
throw new RegressionTestException("No contract had QuoteBar data");
|
||||
}
|
||||
|
||||
if (ShouldHaveOpenInterestData && !gotOpenInterest)
|
||||
{
|
||||
throw new RegressionTestException("No contract had OpenInterest data");
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// This is used by the regression test system to indicate if the open source Lean repository has the required data to run this algorithm.
|
||||
/// </summary>
|
||||
public bool CanRunLocally { get; } = true;
|
||||
|
||||
/// <summary>
|
||||
/// This is used by the regression test system to indicate which languages this algorithm is written in.
|
||||
/// </summary>
|
||||
public List<Language> Languages { get; } = new() { Language.CSharp };
|
||||
|
||||
/// <summary>
|
||||
/// Data Points count of all timeslices of algorithm
|
||||
/// </summary>
|
||||
public abstract long DataPoints { get; }
|
||||
|
||||
/// <summary>
|
||||
/// Data Points count of the algorithm history
|
||||
/// </summary>
|
||||
public abstract int AlgorithmHistoryDataPoints { get; }
|
||||
|
||||
/// <summary>
|
||||
/// Final status of the algorithm
|
||||
/// </summary>
|
||||
public AlgorithmStatus AlgorithmStatus => AlgorithmStatus.Completed;
|
||||
|
||||
/// <summary>
|
||||
/// This is used by the regression test system to indicate what the expected statistics are from running the algorithm
|
||||
/// </summary>
|
||||
public virtual Dictionary<string, string> ExpectedStatistics => new Dictionary<string, string>
|
||||
{
|
||||
{"Total Orders", "0"},
|
||||
{"Average Win", "0%"},
|
||||
{"Average Loss", "0%"},
|
||||
{"Compounding Annual Return", "0%"},
|
||||
{"Drawdown", "0%"},
|
||||
{"Expectancy", "0"},
|
||||
{"Start Equity", "100000"},
|
||||
{"End Equity", "100000"},
|
||||
{"Net Profit", "0%"},
|
||||
{"Sharpe Ratio", "0"},
|
||||
{"Sortino Ratio", "0"},
|
||||
{"Probabilistic Sharpe Ratio", "0%"},
|
||||
{"Loss Rate", "0%"},
|
||||
{"Win Rate", "0%"},
|
||||
{"Profit-Loss Ratio", "0"},
|
||||
{"Alpha", "0"},
|
||||
{"Beta", "0"},
|
||||
{"Annual Standard Deviation", "0"},
|
||||
{"Annual Variance", "0"},
|
||||
{"Information Ratio", "0"},
|
||||
{"Tracking Error", "0"},
|
||||
{"Treynor Ratio", "0"},
|
||||
{"Total Fees", "$0.00"},
|
||||
{"Estimated Strategy Capacity", "$0"},
|
||||
{"Lowest Capacity Asset", ""},
|
||||
{"Portfolio Turnover", "0%"},
|
||||
{"Drawdown Recovery", "0"},
|
||||
{"OrderListHash", "d41d8cd98f00b204e9800998ecf8427e"}
|
||||
};
|
||||
}
|
||||
}
|
||||
@@ -119,7 +119,7 @@ namespace QuantConnect.Algorithm.CSharp
|
||||
/// <summary>
|
||||
/// Data Points count of all timeslices of algorithm
|
||||
/// </summary>
|
||||
public long DataPoints => 126221;
|
||||
public long DataPoints => 126222;
|
||||
|
||||
/// <summary>
|
||||
/// Data Points count of the algorithm history
|
||||
|
||||
@@ -0,0 +1,156 @@
|
||||
/*
|
||||
* QUANTCONNECT.COM - Democratizing Finance, Empowering Individuals.
|
||||
* Lean Algorithmic Trading Engine v2.0. Copyright 2014 QuantConnect Corporation.
|
||||
*
|
||||
* 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.
|
||||
*/
|
||||
|
||||
using System.Collections.Generic;
|
||||
using QuantConnect.Data;
|
||||
using QuantConnect.Interfaces;
|
||||
using QuantConnect.Orders;
|
||||
|
||||
namespace QuantConnect.Algorithm.CSharp
|
||||
{
|
||||
/// <summary>
|
||||
/// Regression algorithm asserting that in backtesting, orders are submitted in the same time step even when asynchronous
|
||||
/// </summary>
|
||||
public class BacktestingAsynchronousOrdersRegressionAlgorithm : QCAlgorithm, IRegressionAlgorithmDefinition
|
||||
{
|
||||
private Symbol _symbol;
|
||||
|
||||
public override void Initialize()
|
||||
{
|
||||
SetStartDate(2013, 10, 07);
|
||||
SetEndDate(2013, 10, 08);
|
||||
SetCash(100000);
|
||||
|
||||
_symbol = AddEquity("SPY").Symbol;
|
||||
}
|
||||
|
||||
public override void OnData(Slice slice)
|
||||
{
|
||||
if (!Portfolio.Invested)
|
||||
{
|
||||
var marketOrderTicket = MarketOrder(_symbol, 100, asynchronous: false);
|
||||
AssertMarketOrderStatus(marketOrderTicket);
|
||||
|
||||
var asyncMarketOrderTicket = MarketOrder(_symbol, -100, asynchronous: true);
|
||||
AssertMarketOrderStatus(asyncMarketOrderTicket);
|
||||
|
||||
var limitPrice = Securities[_symbol].Price * 0.95m;
|
||||
var limitOrderTicket = LimitOrder(_symbol, 100, limitPrice, asynchronous: false);
|
||||
AssertLimitOrderStatus(limitOrderTicket);
|
||||
|
||||
var asyncLimitOrderTicket = LimitOrder(_symbol, -100, limitPrice, asynchronous: true);
|
||||
AssertLimitOrderStatus(asyncLimitOrderTicket);
|
||||
}
|
||||
}
|
||||
|
||||
private static void AssertMarketOrderStatus(OrderTicket ticket)
|
||||
{
|
||||
// In backtesting the order should be submitted and filled right away.
|
||||
// Note that OrderSet event will not be fired if there is an error when processing the order submission,
|
||||
// but this is a happy case
|
||||
if (!ticket.OrderSet.WaitOne(0))
|
||||
{
|
||||
throw new RegressionTestException("Order was not submitted immediately in backtesting mode");
|
||||
}
|
||||
if (!ticket.OrderClosed.WaitOne(0))
|
||||
{
|
||||
throw new RegressionTestException("Order was not filled immediately in backtesting mode");
|
||||
}
|
||||
if (ticket.Status != OrderStatus.Filled)
|
||||
{
|
||||
throw new RegressionTestException($"Order status is not filled: {ticket.Status}");
|
||||
}
|
||||
}
|
||||
|
||||
private static void AssertLimitOrderStatus(OrderTicket ticket)
|
||||
{
|
||||
// In backtesting the order should be submitted right away but not filled since price hasn't moved even when asynchronous
|
||||
// Note that OrderSet event will not be fired if there is an error when processing the order submission,
|
||||
// but this is a happy case
|
||||
if (!ticket.OrderSet.WaitOne(0))
|
||||
{
|
||||
throw new RegressionTestException("Asynchronous limit order was not submitted immediately in backtesting mode");
|
||||
}
|
||||
if (ticket.OrderClosed.WaitOne(0))
|
||||
{
|
||||
throw new RegressionTestException("Asynchronous limit order was filled immediately in backtesting mode when it shouldn't");
|
||||
}
|
||||
if (ticket.Status != OrderStatus.Submitted)
|
||||
{
|
||||
throw new RegressionTestException($"Order status is not submitted: {ticket.Status}");
|
||||
}
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// This is used by the regression test system to indicate if the open source Lean repository has the required data to run this algorithm.
|
||||
/// </summary>
|
||||
public bool CanRunLocally { get; } = true;
|
||||
|
||||
/// <summary>
|
||||
/// This is used by the regression test system to indicate which languages this algorithm is written in.
|
||||
/// </summary>
|
||||
public List<Language> Languages { get; } = new() { Language.CSharp };
|
||||
|
||||
/// <summary>
|
||||
/// Data Points count of all timeslices of algorithm
|
||||
/// </summary>
|
||||
public long DataPoints => 1582;
|
||||
|
||||
/// <summary>
|
||||
/// Data Points count of the algorithm history
|
||||
/// </summary>
|
||||
public int AlgorithmHistoryDataPoints => 0;
|
||||
|
||||
/// <summary>
|
||||
/// Final status of the algorithm
|
||||
/// </summary>
|
||||
public AlgorithmStatus AlgorithmStatus => AlgorithmStatus.Completed;
|
||||
|
||||
/// <summary>
|
||||
/// This is used by the regression test system to indicate what the expected statistics are from running the algorithm
|
||||
/// </summary>
|
||||
public Dictionary<string, string> ExpectedStatistics => new Dictionary<string, string>
|
||||
{
|
||||
{"Total Orders", "4"},
|
||||
{"Average Win", "0%"},
|
||||
{"Average Loss", "0%"},
|
||||
{"Compounding Annual Return", "0%"},
|
||||
{"Drawdown", "0%"},
|
||||
{"Expectancy", "0"},
|
||||
{"Start Equity", "100000"},
|
||||
{"End Equity", "100168.20"},
|
||||
{"Net Profit", "0%"},
|
||||
{"Sharpe Ratio", "0"},
|
||||
{"Sortino Ratio", "0"},
|
||||
{"Probabilistic Sharpe Ratio", "0%"},
|
||||
{"Loss Rate", "0%"},
|
||||
{"Win Rate", "0%"},
|
||||
{"Profit-Loss Ratio", "0"},
|
||||
{"Alpha", "0"},
|
||||
{"Beta", "0"},
|
||||
{"Annual Standard Deviation", "0"},
|
||||
{"Annual Variance", "0"},
|
||||
{"Information Ratio", "0"},
|
||||
{"Tracking Error", "0"},
|
||||
{"Treynor Ratio", "0"},
|
||||
{"Total Fees", "$3.00"},
|
||||
{"Estimated Strategy Capacity", "$22000000.00"},
|
||||
{"Lowest Capacity Asset", "SPY R735QTJ8XC9X"},
|
||||
{"Portfolio Turnover", "21.72%"},
|
||||
{"Drawdown Recovery", "0"},
|
||||
{"OrderListHash", "65f010e904a929e5383f0920a3c5b797"}
|
||||
};
|
||||
}
|
||||
}
|
||||
@@ -340,7 +340,7 @@ namespace QuantConnect.Algorithm.CSharp
|
||||
{"Lowest Capacity Asset", "GOOCV VP83T1ZUHROL"},
|
||||
{"Portfolio Turnover", "17.02%"},
|
||||
{"Drawdown Recovery", "0"},
|
||||
{"OrderListHash", "a7ce5ff2bbe0fe273cf1631ea5a73fa6"}
|
||||
{"OrderListHash", "1be5073f2cf8802ffa163f7dab7d040e"}
|
||||
};
|
||||
}
|
||||
}
|
||||
|
||||
@@ -77,7 +77,7 @@ namespace QuantConnect.Algorithm.CSharp
|
||||
/// <summary>
|
||||
/// Data Points count of the algorithm history
|
||||
/// </summary>
|
||||
public int AlgorithmHistoryDataPoints => 120;
|
||||
public int AlgorithmHistoryDataPoints => 15;
|
||||
|
||||
/// <summary>
|
||||
/// Final status of the algorithm
|
||||
|
||||
@@ -47,7 +47,7 @@ namespace QuantConnect.Algorithm.CSharp
|
||||
/// <summary>
|
||||
/// Data Points count of the algorithm history
|
||||
/// </summary>
|
||||
public int AlgorithmHistoryDataPoints => 120;
|
||||
public int AlgorithmHistoryDataPoints => 15;
|
||||
|
||||
/// <summary>
|
||||
/// Final status of the algorithm
|
||||
|
||||
@@ -202,7 +202,7 @@ namespace QuantConnect.Algorithm.CSharp
|
||||
/// <summary>
|
||||
/// Data Points count of the algorithm history
|
||||
/// </summary>
|
||||
public int AlgorithmHistoryDataPoints => 240;
|
||||
public int AlgorithmHistoryDataPoints => 35;
|
||||
|
||||
/// <summary>
|
||||
/// Final status of the algorithm
|
||||
@@ -220,7 +220,7 @@ namespace QuantConnect.Algorithm.CSharp
|
||||
{"Compounding Annual Return", "0%"},
|
||||
{"Drawdown", "0%"},
|
||||
{"Expectancy", "0"},
|
||||
{"Start Equity", "31588.24"},
|
||||
{"Start Equity", "31592.84"},
|
||||
{"End Equity", "30866.71"},
|
||||
{"Net Profit", "0%"},
|
||||
{"Sharpe Ratio", "0"},
|
||||
|
||||
@@ -119,9 +119,7 @@ namespace QuantConnect.Algorithm.CSharp
|
||||
{
|
||||
throw new RegressionTestException($"Unexpected holdings cost {btcUsdHoldings.HoldingsCost}");
|
||||
}
|
||||
// margin used is based on the maintenance rate
|
||||
if (Math.Abs(btcUsdHoldings.AbsoluteHoldingsCost * 0.05m - marginUsed) > 1
|
||||
|| _btcUsd.BuyingPowerModel.GetMaintenanceMargin(_btcUsd) != marginUsed)
|
||||
if (_btcUsd.BuyingPowerModel.GetMaintenanceMargin(_btcUsd) != marginUsed)
|
||||
{
|
||||
throw new RegressionTestException($"Unexpected margin used {marginUsed}");
|
||||
}
|
||||
@@ -142,8 +140,7 @@ namespace QuantConnect.Algorithm.CSharp
|
||||
{
|
||||
throw new RegressionTestException($"Unexpected holdings cost {adaUsdtHoldings.HoldingsCost}");
|
||||
}
|
||||
if (Math.Abs(adaUsdtHoldings.AbsoluteHoldingsCost * 0.05m - marginUsed) > 1
|
||||
|| _adaUsdt.BuyingPowerModel.GetMaintenanceMargin(_adaUsdt) != marginUsed)
|
||||
if (_adaUsdt.BuyingPowerModel.GetMaintenanceMargin(_adaUsdt) != marginUsed)
|
||||
{
|
||||
throw new RegressionTestException($"Unexpected margin used {marginUsed}");
|
||||
}
|
||||
@@ -273,7 +270,7 @@ namespace QuantConnect.Algorithm.CSharp
|
||||
{"Tracking Error", "0"},
|
||||
{"Treynor Ratio", "0"},
|
||||
{"Total Fees", "$0.65"},
|
||||
{"Estimated Strategy Capacity", "$500000000.00"},
|
||||
{"Estimated Strategy Capacity", "$620000000.00"},
|
||||
{"Lowest Capacity Asset", "ADAUSDT 18R"},
|
||||
{"Portfolio Turnover", "0.16%"},
|
||||
{"Drawdown Recovery", "0"},
|
||||
|
||||
@@ -93,7 +93,7 @@ namespace QuantConnect.Algorithm.CSharp
|
||||
if (!Portfolio.Invested && Transactions.OrdersCount == 0)
|
||||
{
|
||||
var ticket = Buy(_adaUsdt.Symbol, 100000);
|
||||
if(ticket.Status != OrderStatus.Invalid)
|
||||
if (ticket.Status != OrderStatus.Invalid)
|
||||
{
|
||||
throw new RegressionTestException($"Unexpected valid order {ticket}, should fail due to margin not sufficient");
|
||||
}
|
||||
@@ -114,8 +114,7 @@ namespace QuantConnect.Algorithm.CSharp
|
||||
{
|
||||
throw new RegressionTestException($"Unexpected holdings cost {adaUsdtHoldings.HoldingsCost}");
|
||||
}
|
||||
if (Math.Abs(adaUsdtHoldings.AbsoluteHoldingsCost * 0.05m - marginUsed) > 1
|
||||
|| _adaUsdt.BuyingPowerModel.GetMaintenanceMargin(_adaUsdt) != marginUsed)
|
||||
if (_adaUsdt.BuyingPowerModel.GetMaintenanceMargin(_adaUsdt) != marginUsed)
|
||||
{
|
||||
throw new RegressionTestException($"Unexpected margin used {marginUsed}");
|
||||
}
|
||||
@@ -236,7 +235,7 @@ namespace QuantConnect.Algorithm.CSharp
|
||||
{"Tracking Error", "0"},
|
||||
{"Treynor Ratio", "0"},
|
||||
{"Total Fees", "$0.61"},
|
||||
{"Estimated Strategy Capacity", "$370000000.00"},
|
||||
{"Estimated Strategy Capacity", "$460000000.00"},
|
||||
{"Lowest Capacity Asset", "ADAUSDT 18R"},
|
||||
{"Portfolio Turnover", "0.12%"},
|
||||
{"Drawdown Recovery", "0"},
|
||||
|
||||
@@ -154,7 +154,7 @@ namespace QuantConnect.Algorithm.CSharp
|
||||
/// <summary>
|
||||
/// Data Points count of the algorithm history
|
||||
/// </summary>
|
||||
public int AlgorithmHistoryDataPoints => 340;
|
||||
public int AlgorithmHistoryDataPoints => 354;
|
||||
|
||||
/// <summary>
|
||||
/// Final status of the algorithm
|
||||
|
||||
@@ -127,7 +127,7 @@ namespace QuantConnect.Algorithm.CSharp
|
||||
/// <summary>
|
||||
/// Data Points count of all timeslices of algorithm
|
||||
/// </summary>
|
||||
public virtual long DataPoints => 5861;
|
||||
public virtual long DataPoints => 5867;
|
||||
|
||||
/// <summary>
|
||||
/// Data Points count of the algorithm history
|
||||
@@ -144,34 +144,34 @@ namespace QuantConnect.Algorithm.CSharp
|
||||
/// </summary>
|
||||
public virtual Dictionary<string, string> ExpectedStatistics => new Dictionary<string, string>
|
||||
{
|
||||
{"Total Orders", "34"},
|
||||
{"Total Orders", "38"},
|
||||
{"Average Win", "0.33%"},
|
||||
{"Average Loss", "-0.04%"},
|
||||
{"Compounding Annual Return", "0.106%"},
|
||||
{"Average Loss", "-0.03%"},
|
||||
{"Compounding Annual Return", "0.098%"},
|
||||
{"Drawdown", "0.300%"},
|
||||
{"Expectancy", "0.178"},
|
||||
{"Expectancy", "0.165"},
|
||||
{"Start Equity", "1000000"},
|
||||
{"End Equity", "1001066.2"},
|
||||
{"Net Profit", "0.107%"},
|
||||
{"Sharpe Ratio", "-1.695"},
|
||||
{"Sortino Ratio", "-0.804"},
|
||||
{"Probabilistic Sharpe Ratio", "14.797%"},
|
||||
{"Loss Rate", "88%"},
|
||||
{"Win Rate", "12%"},
|
||||
{"Profit-Loss Ratio", "9.01"},
|
||||
{"End Equity", "1000991.96"},
|
||||
{"Net Profit", "0.099%"},
|
||||
{"Sharpe Ratio", "-1.708"},
|
||||
{"Sortino Ratio", "-0.84"},
|
||||
{"Probabilistic Sharpe Ratio", "14.542%"},
|
||||
{"Loss Rate", "89%"},
|
||||
{"Win Rate", "11%"},
|
||||
{"Profit-Loss Ratio", "10.07"},
|
||||
{"Alpha", "-0.007"},
|
||||
{"Beta", "0.002"},
|
||||
{"Annual Standard Deviation", "0.004"},
|
||||
{"Annual Variance", "0"},
|
||||
{"Information Ratio", "-1.353"},
|
||||
{"Information Ratio", "-1.354"},
|
||||
{"Tracking Error", "0.089"},
|
||||
{"Treynor Ratio", "-4.112"},
|
||||
{"Total Fees", "$76.30"},
|
||||
{"Treynor Ratio", "-4.054"},
|
||||
{"Total Fees", "$85.54"},
|
||||
{"Estimated Strategy Capacity", "$0"},
|
||||
{"Lowest Capacity Asset", "ES VRJST036ZY0X"},
|
||||
{"Portfolio Turnover", "0.92%"},
|
||||
{"Portfolio Turnover", "1.04%"},
|
||||
{"Drawdown Recovery", "69"},
|
||||
{"OrderListHash", "ddaa9dd20647fdbc4811d6e64bb30a40"}
|
||||
{"OrderListHash", "eafc33ea4dcb219f7aacdbdd0973d5bc"}
|
||||
};
|
||||
}
|
||||
}
|
||||
|
||||
@@ -36,7 +36,7 @@ namespace QuantConnect.Algorithm.CSharp
|
||||
/// <summary>
|
||||
/// Data Points count of all timeslices of algorithm
|
||||
/// </summary>
|
||||
public override long DataPoints => 25312;
|
||||
public override long DataPoints => 25339;
|
||||
|
||||
/// <summary>
|
||||
/// This is used by the regression test system to indicate what the expected statistics are from running the algorithm
|
||||
@@ -70,7 +70,7 @@ namespace QuantConnect.Algorithm.CSharp
|
||||
{"Lowest Capacity Asset", "ES VP274HSU1AF5"},
|
||||
{"Portfolio Turnover", "20.14%"},
|
||||
{"Drawdown Recovery", "0"},
|
||||
{"OrderListHash", "f6482c8757f82cb9f4c058e3ed6bc494"}
|
||||
{"OrderListHash", "c301a0a086f8905b1a555f0257087272"}
|
||||
};
|
||||
}
|
||||
}
|
||||
|
||||
@@ -154,7 +154,7 @@ namespace QuantConnect.Algorithm.CSharp
|
||||
/// <summary>
|
||||
/// Data Points count of the algorithm history
|
||||
/// </summary>
|
||||
public int AlgorithmHistoryDataPoints => 340;
|
||||
public int AlgorithmHistoryDataPoints => 354;
|
||||
|
||||
/// <summary>
|
||||
/// Final status of the algorithm
|
||||
|
||||
@@ -36,41 +36,41 @@ namespace QuantConnect.Algorithm.CSharp
|
||||
/// <summary>
|
||||
/// Data Points count of all timeslices of algorithm
|
||||
/// </summary>
|
||||
public override long DataPoints => 5965;
|
||||
public override long DataPoints => 5971;
|
||||
|
||||
/// <summary>
|
||||
/// This is used by the regression test system to indicate what the expected statistics are from running the algorithm
|
||||
/// </summary>
|
||||
public override Dictionary<string, string> ExpectedStatistics => new Dictionary<string, string>
|
||||
{
|
||||
{"Total Orders", "32"},
|
||||
{"Total Orders", "36"},
|
||||
{"Average Win", "0.33%"},
|
||||
{"Average Loss", "-0.04%"},
|
||||
{"Compounding Annual Return", "0.110%"},
|
||||
{"Average Loss", "-0.03%"},
|
||||
{"Compounding Annual Return", "0.103%"},
|
||||
{"Drawdown", "0.300%"},
|
||||
{"Expectancy", "0.184"},
|
||||
{"Expectancy", "0.172"},
|
||||
{"Start Equity", "1000000"},
|
||||
{"End Equity", "1001108"},
|
||||
{"Net Profit", "0.111%"},
|
||||
{"Sharpe Ratio", "-1.688"},
|
||||
{"Sortino Ratio", "-0.772"},
|
||||
{"Probabilistic Sharpe Ratio", "14.944%"},
|
||||
{"Loss Rate", "88%"},
|
||||
{"Win Rate", "12%"},
|
||||
{"Profit-Loss Ratio", "8.47"},
|
||||
{"End Equity", "1001033.76"},
|
||||
{"Net Profit", "0.103%"},
|
||||
{"Sharpe Ratio", "-1.701"},
|
||||
{"Sortino Ratio", "-0.809"},
|
||||
{"Probabilistic Sharpe Ratio", "14.685%"},
|
||||
{"Loss Rate", "89%"},
|
||||
{"Win Rate", "11%"},
|
||||
{"Profit-Loss Ratio", "9.55"},
|
||||
{"Alpha", "-0.007"},
|
||||
{"Beta", "0.002"},
|
||||
{"Annual Standard Deviation", "0.004"},
|
||||
{"Annual Variance", "0"},
|
||||
{"Information Ratio", "-1.353"},
|
||||
{"Tracking Error", "0.089"},
|
||||
{"Treynor Ratio", "-4.099"},
|
||||
{"Total Fees", "$72.00"},
|
||||
{"Treynor Ratio", "-4.042"},
|
||||
{"Total Fees", "$81.24"},
|
||||
{"Estimated Strategy Capacity", "$0"},
|
||||
{"Lowest Capacity Asset", "ES VRJST036ZY0X"},
|
||||
{"Portfolio Turnover", "0.87%"},
|
||||
{"Portfolio Turnover", "0.99%"},
|
||||
{"Drawdown Recovery", "69"},
|
||||
{"OrderListHash", "741a26424d2210171ad849d92fc75d23"}
|
||||
{"OrderListHash", "67120ad5c9a6116001dda6c8061e5353"}
|
||||
};
|
||||
}
|
||||
}
|
||||
|
||||
@@ -41,7 +41,7 @@ namespace QuantConnect.Algorithm.CSharp
|
||||
/// <summary>
|
||||
/// Data Points count of all timeslices of algorithm
|
||||
/// </summary>
|
||||
public override long DataPoints => 67924;
|
||||
public override long DataPoints => 67998;
|
||||
|
||||
/// <summary>
|
||||
/// This is used by the regression test system to indicate what the expected statistics are from running the algorithm
|
||||
|
||||
@@ -168,10 +168,10 @@ namespace QuantConnect.Algorithm.CSharp
|
||||
{"Treynor Ratio", "-1.771"},
|
||||
{"Total Fees", "$0.00"},
|
||||
{"Estimated Strategy Capacity", "$3000.00"},
|
||||
{"Lowest Capacity Asset", "SPX XL80P3GHDZXQ|SPX 31"},
|
||||
{"Lowest Capacity Asset", "SPX XL80P3GHIA9A|SPX 31"},
|
||||
{"Portfolio Turnover", "23.97%"},
|
||||
{"Drawdown Recovery", "9"},
|
||||
{"OrderListHash", "51f1bc2ea080df79748dc66c2520b782"}
|
||||
{"OrderListHash", "4b560d2a8cfae510c3c8dc92603470fc"}
|
||||
};
|
||||
}
|
||||
}
|
||||
|
||||
@@ -147,10 +147,10 @@ namespace QuantConnect.Algorithm.CSharp
|
||||
{"Treynor Ratio", "-6.937"},
|
||||
{"Total Fees", "$0.00"},
|
||||
{"Estimated Strategy Capacity", "$0"},
|
||||
{"Lowest Capacity Asset", "SPX XL80P3GHDZXQ|SPX 31"},
|
||||
{"Lowest Capacity Asset", "SPX XL80P3GHIA9A|SPX 31"},
|
||||
{"Portfolio Turnover", "2.42%"},
|
||||
{"Drawdown Recovery", "0"},
|
||||
{"OrderListHash", "61e8517ac3da6bed414ef23d26736fef"}
|
||||
{"OrderListHash", "ce421d0aeb7bde3bc92a6b87c09c510e"}
|
||||
};
|
||||
}
|
||||
}
|
||||
|
||||
@@ -64,10 +64,10 @@ namespace QuantConnect.Algorithm.CSharp
|
||||
{"Treynor Ratio", "-6.189"},
|
||||
{"Total Fees", "$0.00"},
|
||||
{"Estimated Strategy Capacity", "$300000.00"},
|
||||
{"Lowest Capacity Asset", "SPX XL80P3GHDZXQ|SPX 31"},
|
||||
{"Lowest Capacity Asset", "SPX XL80P3GHIA9A|SPX 31"},
|
||||
{"Portfolio Turnover", "24.63%"},
|
||||
{"Drawdown Recovery", "0"},
|
||||
{"OrderListHash", "5595ab834c2584c1d124ad575e88cc1a"}
|
||||
{"OrderListHash", "7bc05310e971f09b0663bc380fdfee80"}
|
||||
};
|
||||
}
|
||||
}
|
||||
|
||||
@@ -108,10 +108,10 @@ namespace QuantConnect.Algorithm.CSharp
|
||||
{"Treynor Ratio", "-44.954"},
|
||||
{"Total Fees", "$0.00"},
|
||||
{"Estimated Strategy Capacity", "$0"},
|
||||
{"Lowest Capacity Asset", "SPX XL80P59H5E6M|SPX 31"},
|
||||
{"Lowest Capacity Asset", "SPX XL80P59H9OI6|SPX 31"},
|
||||
{"Portfolio Turnover", "0.00%"},
|
||||
{"Drawdown Recovery", "0"},
|
||||
{"OrderListHash", "8340619d603921c1ce261287890b9c1c"}
|
||||
{"OrderListHash", "34d295b82e29b1dbe8f104d3300d9255"}
|
||||
};
|
||||
}
|
||||
}
|
||||
|
||||
@@ -79,10 +79,10 @@ namespace QuantConnect.Algorithm.CSharp
|
||||
{"Treynor Ratio", "116.921"},
|
||||
{"Total Fees", "$0.00"},
|
||||
{"Estimated Strategy Capacity", "$0"},
|
||||
{"Lowest Capacity Asset", "SPX XL80P59H5E6M|SPX 31"},
|
||||
{"Lowest Capacity Asset", "SPX XL80P59H9OI6|SPX 31"},
|
||||
{"Portfolio Turnover", "0.00%"},
|
||||
{"Drawdown Recovery", "0"},
|
||||
{"OrderListHash", "1c5f424cfe62777733ee68a20320bb8d"}
|
||||
{"OrderListHash", "214026660a13ecaecc7074fa97f86ea1"}
|
||||
};
|
||||
}
|
||||
}
|
||||
|
||||
@@ -44,7 +44,7 @@ namespace QuantConnect.Algorithm.CSharp
|
||||
_optionSymbol = option.Symbol;
|
||||
|
||||
// set our strike/expiry filter for this option chain
|
||||
option.SetFilter(u => u.Strikes(-2, +2)
|
||||
option.SetFilter(u => u.StandardsOnly().Strikes(-2, +2)
|
||||
// Expiration method accepts TimeSpan objects or integer for days.
|
||||
// The following statements yield the same filtering criteria
|
||||
.Expiration(0, 180));
|
||||
@@ -73,7 +73,7 @@ namespace QuantConnect.Algorithm.CSharp
|
||||
var higherStrike = callContracts[2].Strike;
|
||||
|
||||
var optionStrategy = OptionStrategies.CallButterfly(_optionSymbol, higherStrike, middleStrike, lowerStrike, expiry);
|
||||
|
||||
|
||||
Order(optionStrategy, 10);
|
||||
}
|
||||
}
|
||||
@@ -143,10 +143,10 @@ namespace QuantConnect.Algorithm.CSharp
|
||||
{"Treynor Ratio", "0"},
|
||||
{"Total Fees", "$26.00"},
|
||||
{"Estimated Strategy Capacity", "$69000.00"},
|
||||
{"Lowest Capacity Asset", "GOOCV W78ZERHAOVVQ|GOOCV VP83T1ZUHROL"},
|
||||
{"Lowest Capacity Asset", "GOOCV W78ZERHAT67A|GOOCV VP83T1ZUHROL"},
|
||||
{"Portfolio Turnover", "61.31%"},
|
||||
{"Drawdown Recovery", "0"},
|
||||
{"OrderListHash", "35d406df401e5b27244e20f5ec57346e"}
|
||||
{"OrderListHash", "ccd6cb1b6244d0c6d30b2760938958f1"}
|
||||
};
|
||||
}
|
||||
}
|
||||
|
||||
@@ -50,8 +50,9 @@ namespace QuantConnect.Algorithm.CSharp
|
||||
// set our strike/expiry filter for this option chain
|
||||
// SetFilter method accepts TimeSpan objects or integer for days.
|
||||
// The following statements yield the same filtering criteria
|
||||
option.SetFilter(-2, +2, 0, 180);
|
||||
// option.SetFilter(-2, +2, TimeSpan.Zero, TimeSpan.FromDays(180));
|
||||
option.SetFilter(u => u.StandardsOnly()
|
||||
.Strikes(-2, +2)
|
||||
.Expiration(0, 180));
|
||||
|
||||
// Adding this to reproduce GH issue #2314
|
||||
SetWarmup(TimeSpan.FromMinutes(1));
|
||||
@@ -83,7 +84,7 @@ namespace QuantConnect.Algorithm.CSharp
|
||||
Liquidate();
|
||||
}
|
||||
|
||||
foreach(var kpv in slice.Bars)
|
||||
foreach (var kpv in slice.Bars)
|
||||
{
|
||||
Log($"---> OnData: {Time}, {kpv.Key.Value}, {kpv.Value.Close:0.00}");
|
||||
}
|
||||
@@ -153,10 +154,10 @@ namespace QuantConnect.Algorithm.CSharp
|
||||
{"Treynor Ratio", "0"},
|
||||
{"Total Fees", "$543.40"},
|
||||
{"Estimated Strategy Capacity", "$4000.00"},
|
||||
{"Lowest Capacity Asset", "GOOCV W78ZFMEBBB2E|GOOCV VP83T1ZUHROL"},
|
||||
{"Lowest Capacity Asset", "GOOCV W78ZFMEBFLDY|GOOCV VP83T1ZUHROL"},
|
||||
{"Portfolio Turnover", "338.60%"},
|
||||
{"Drawdown Recovery", "0"},
|
||||
{"OrderListHash", "301c15063f6e269023d144ca69a765da"}
|
||||
{"OrderListHash", "8229716b93428dc885cf856b4cc9fc35"}
|
||||
};
|
||||
}
|
||||
}
|
||||
|
||||
@@ -48,11 +48,10 @@ namespace QuantConnect.Algorithm.CSharp
|
||||
_optionSymbol = option.Symbol;
|
||||
|
||||
// set our strike/expiry filter for this option chain
|
||||
option.SetFilter(u => u.Strikes(-2, +2)
|
||||
option.SetFilter(u => u.StandardsOnly().Strikes(-2, +2)
|
||||
// Expiration method accepts TimeSpan objects or integer for days.
|
||||
// The following statements yield the same filtering criteria
|
||||
.Expiration(0, 180));
|
||||
// .Expiration(TimeSpan.Zero, TimeSpan.FromDays(180)));
|
||||
.Expiration(0, 180)); // .Expiration(TimeSpan.Zero, TimeSpan.FromDays(180)));
|
||||
|
||||
// use the underlying equity as the benchmark
|
||||
SetBenchmark(equity.Symbol);
|
||||
@@ -150,10 +149,10 @@ namespace QuantConnect.Algorithm.CSharp
|
||||
{"Treynor Ratio", "0"},
|
||||
{"Total Fees", "$2.00"},
|
||||
{"Estimated Strategy Capacity", "$1300000.00"},
|
||||
{"Lowest Capacity Asset", "GOOCV 30AKMEIPOSS1Y|GOOCV VP83T1ZUHROL"},
|
||||
{"Lowest Capacity Asset", "GOOCV 30AKMEIPOX2DI|GOOCV VP83T1ZUHROL"},
|
||||
{"Portfolio Turnover", "10.71%"},
|
||||
{"Drawdown Recovery", "0"},
|
||||
{"OrderListHash", "8a36462ee0349c04d01d464e592dd347"}
|
||||
{"OrderListHash", "19ba1220073493495880581b38df2da9"}
|
||||
};
|
||||
}
|
||||
}
|
||||
|
||||
@@ -163,10 +163,10 @@ namespace QuantConnect.Algorithm.CSharp
|
||||
{"Treynor Ratio", "-3.212"},
|
||||
{"Total Fees", "$1.00"},
|
||||
{"Estimated Strategy Capacity", "$72000.00"},
|
||||
{"Lowest Capacity Asset", "AAPL W78ZEO2985GM|AAPL R735QTJ8XC9X"},
|
||||
{"Lowest Capacity Asset", "AAPL W78ZEO29CFS6|AAPL R735QTJ8XC9X"},
|
||||
{"Portfolio Turnover", "0.02%"},
|
||||
{"Drawdown Recovery", "0"},
|
||||
{"OrderListHash", "5e20fad3461ac9998afe8d76ad43b25c"}
|
||||
{"OrderListHash", "5639c19a7d56ec312f61029b943903b8"}
|
||||
};
|
||||
}
|
||||
}
|
||||
|
||||
@@ -143,7 +143,7 @@ namespace QuantConnect.Algorithm.CSharp
|
||||
{"Lowest Capacity Asset", "GOOCV VP83T1ZUHROL"},
|
||||
{"Portfolio Turnover", "15.08%"},
|
||||
{"Drawdown Recovery", "0"},
|
||||
{"OrderListHash", "f68f6d64a5721ee148bc3c643f8d1b7f"}
|
||||
{"OrderListHash", "c53bc9318676161ed3b7797c945e2113"}
|
||||
};
|
||||
}
|
||||
}
|
||||
|
||||
@@ -139,7 +139,7 @@ namespace QuantConnect.Algorithm.CSharp
|
||||
/// <summary>
|
||||
/// Data Points count of all timeslices of algorithm
|
||||
/// </summary>
|
||||
public long DataPoints => 17486;
|
||||
public long DataPoints => 17487;
|
||||
|
||||
/// <summary>
|
||||
/// Data Points count of the algorithm history
|
||||
@@ -183,7 +183,7 @@ namespace QuantConnect.Algorithm.CSharp
|
||||
{"Lowest Capacity Asset", "AAPL R735QTJ8XC9X"},
|
||||
{"Portfolio Turnover", "13.50%"},
|
||||
{"Drawdown Recovery", "2"},
|
||||
{"OrderListHash", "d40c84371facba5dac8a2c919ea75807"}
|
||||
{"OrderListHash", "2ab4ffc0944a2888a3be0568c2570a79"}
|
||||
};
|
||||
}
|
||||
}
|
||||
|
||||
@@ -48,7 +48,7 @@ namespace QuantConnect.Algorithm.CSharp
|
||||
_optionSymbol = option.Symbol;
|
||||
|
||||
// set our strike/expiry filter for this option chain
|
||||
option.SetFilter(u => u.Strikes(-2, +2)
|
||||
option.SetFilter(u => u.StandardsOnly().Strikes(-2, +2)
|
||||
// Expiration method accepts TimeSpan objects or integer for days.
|
||||
// The following statements yield the same filtering criteria
|
||||
.Expiration(0, 180));
|
||||
@@ -150,10 +150,10 @@ namespace QuantConnect.Algorithm.CSharp
|
||||
{"Treynor Ratio", "1.434"},
|
||||
{"Total Fees", "$4.00"},
|
||||
{"Estimated Strategy Capacity", "$1000.00"},
|
||||
{"Lowest Capacity Asset", "AAPL 2ZTXYMUAHCIAU|AAPL R735QTJ8XC9X"},
|
||||
{"Lowest Capacity Asset", "AAPL 2ZTXYMUAHGSME|AAPL R735QTJ8XC9X"},
|
||||
{"Portfolio Turnover", "2.28%"},
|
||||
{"Drawdown Recovery", "0"},
|
||||
{"OrderListHash", "7804b3dcf20d3096a2265a289fa81cd3"}
|
||||
{"OrderListHash", "70bbc60c969f18e943e8e00cf0f7a0ea"}
|
||||
};
|
||||
}
|
||||
}
|
||||
|
||||
@@ -144,10 +144,10 @@ namespace QuantConnect.Algorithm.CSharp
|
||||
{"Treynor Ratio", "-0.725"},
|
||||
{"Total Fees", "$0.00"},
|
||||
{"Estimated Strategy Capacity", "$580000.00"},
|
||||
{"Lowest Capacity Asset", "SPXW 31K54PVWHUJHQ|SPX 31"},
|
||||
{"Lowest Capacity Asset", "SPXW 31K54PVWHYTTA|SPX 31"},
|
||||
{"Portfolio Turnover", "0.40%"},
|
||||
{"Drawdown Recovery", "0"},
|
||||
{"OrderListHash", "db5e3681c5fa1888262f2370a9b14c11"}
|
||||
{"OrderListHash", "03148bbb5453fc1056a3285bd31ce158"}
|
||||
};
|
||||
}
|
||||
}
|
||||
|
||||
@@ -150,10 +150,10 @@ namespace QuantConnect.Algorithm.CSharp
|
||||
{"Treynor Ratio", "0.589"},
|
||||
{"Total Fees", "$0.00"},
|
||||
{"Estimated Strategy Capacity", "$13000000.00"},
|
||||
{"Lowest Capacity Asset", "SPXW XKX6S2GM9PGU|SPX 31"},
|
||||
{"Lowest Capacity Asset", "SPXW XKX6S2GMDZSE|SPX 31"},
|
||||
{"Portfolio Turnover", "0.28%"},
|
||||
{"Drawdown Recovery", "2"},
|
||||
{"OrderListHash", "17764ae9e216d003b1f3ce68d15b68ef"}
|
||||
{"OrderListHash", "9d03f85003416861df07ccb31a18af9a"}
|
||||
};
|
||||
}
|
||||
}
|
||||
|
||||
@@ -87,10 +87,10 @@ namespace QuantConnect.Algorithm.CSharp
|
||||
{"Treynor Ratio", "-1.771"},
|
||||
{"Total Fees", "$0.00"},
|
||||
{"Estimated Strategy Capacity", "$3000.00"},
|
||||
{"Lowest Capacity Asset", "SPX XL80P3GHDZXQ|SPX 31"},
|
||||
{"Lowest Capacity Asset", "SPX XL80P3GHIA9A|SPX 31"},
|
||||
{"Portfolio Turnover", "24.03%"},
|
||||
{"Drawdown Recovery", "9"},
|
||||
{"OrderListHash", "fcd6fddb0a315e21095c2b35eb633e2b"}
|
||||
{"OrderListHash", "691cf4990024b856a0a70255c9fd2545"}
|
||||
};
|
||||
}
|
||||
}
|
||||
|
||||
34
Algorithm.CSharp/Benchmarks/EmptySPXOptionChainBenchmark.cs
Normal file
34
Algorithm.CSharp/Benchmarks/EmptySPXOptionChainBenchmark.cs
Normal file
@@ -0,0 +1,34 @@
|
||||
/*
|
||||
* QUANTCONNECT.COM - Democratizing Finance, Empowering Individuals.
|
||||
* Lean Algorithmic Trading Engine v2.0. Copyright 2014 QuantConnect Corporation.
|
||||
*
|
||||
* 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.
|
||||
*/
|
||||
|
||||
namespace QuantConnect.Algorithm.CSharp.Benchmarks
|
||||
{
|
||||
/// <summary>
|
||||
/// Benchmark Algorithm that adds SPX option chain but does not trade it.
|
||||
/// This is an interesting benchmark because SPX option chains are large
|
||||
/// </summary>
|
||||
public class EmptySPXOptionChainBenchmark : QCAlgorithm
|
||||
{
|
||||
public override void Initialize()
|
||||
{
|
||||
SetStartDate(2018, 1, 1);
|
||||
SetEndDate(2020, 6, 1);
|
||||
|
||||
var index = AddIndex("SPX");
|
||||
var option = AddOption(index);
|
||||
option.SetFilter(x => x.IncludeWeeklys().Strikes(-30, 30).Expiration(0, 7));
|
||||
}
|
||||
}
|
||||
}
|
||||
@@ -46,7 +46,7 @@ namespace QuantConnect.Algorithm.CSharp
|
||||
/// <summary>
|
||||
/// Data Points count of the algorithm history
|
||||
/// </summary>
|
||||
public override int AlgorithmHistoryDataPoints => 28;
|
||||
public override int AlgorithmHistoryDataPoints => 5;
|
||||
|
||||
/// <summary>
|
||||
/// Final status of the algorithm
|
||||
|
||||
@@ -46,7 +46,7 @@ namespace QuantConnect.Algorithm.CSharp
|
||||
/// <summary>
|
||||
/// Data Points count of the algorithm history
|
||||
/// </summary>
|
||||
public override int AlgorithmHistoryDataPoints => 28;
|
||||
public override int AlgorithmHistoryDataPoints => 5;
|
||||
|
||||
/// <summary>
|
||||
/// Final status of the algorithm
|
||||
|
||||
@@ -45,7 +45,7 @@ namespace QuantConnect.Algorithm.CSharp
|
||||
/// <summary>
|
||||
/// Data Points count of the algorithm history
|
||||
/// </summary>
|
||||
public override int AlgorithmHistoryDataPoints => 28;
|
||||
public override int AlgorithmHistoryDataPoints => 5;
|
||||
|
||||
/// <summary>
|
||||
/// Final status of the algorithm
|
||||
|
||||
@@ -45,7 +45,7 @@ namespace QuantConnect.Algorithm.CSharp
|
||||
/// <summary>
|
||||
/// Data Points count of the algorithm history
|
||||
/// </summary>
|
||||
public override int AlgorithmHistoryDataPoints => 28;
|
||||
public override int AlgorithmHistoryDataPoints => 5;
|
||||
|
||||
/// <summary>
|
||||
/// Final status of the algorithm
|
||||
|
||||
@@ -112,9 +112,7 @@ namespace QuantConnect.Algorithm.CSharp
|
||||
{
|
||||
throw new RegressionTestException($"Unexpected holdings cost {btcUsdHoldings.HoldingsCost}");
|
||||
}
|
||||
// margin used is based on the maintenance rate
|
||||
if (Math.Abs(btcUsdHoldings.AbsoluteHoldingsCost * 0.05m - marginUsed) > 1
|
||||
|| _btcUsd.BuyingPowerModel.GetMaintenanceMargin(_btcUsd) != marginUsed)
|
||||
if (_btcUsd.BuyingPowerModel.GetMaintenanceMargin(_btcUsd) != marginUsed)
|
||||
{
|
||||
throw new RegressionTestException($"Unexpected margin used {marginUsed}");
|
||||
}
|
||||
@@ -135,8 +133,7 @@ namespace QuantConnect.Algorithm.CSharp
|
||||
{
|
||||
throw new RegressionTestException($"Unexpected holdings cost {btcUsdtHoldings.HoldingsCost}");
|
||||
}
|
||||
if (Math.Abs(btcUsdtHoldings.AbsoluteHoldingsCost * 0.05m - marginUsed) > 1
|
||||
|| _btcUsdt.BuyingPowerModel.GetMaintenanceMargin(_btcUsdt) != marginUsed)
|
||||
if (_btcUsdt.BuyingPowerModel.GetMaintenanceMargin(_btcUsdt) != marginUsed)
|
||||
{
|
||||
throw new RegressionTestException($"Unexpected margin used {marginUsed}");
|
||||
}
|
||||
@@ -226,7 +223,7 @@ namespace QuantConnect.Algorithm.CSharp
|
||||
/// <summary>
|
||||
/// Data Points count of the algorithm history
|
||||
/// </summary>
|
||||
public int AlgorithmHistoryDataPoints => 60;
|
||||
public int AlgorithmHistoryDataPoints => 10;
|
||||
|
||||
/// <summary>
|
||||
/// Final status of the algorithm
|
||||
@@ -244,7 +241,7 @@ namespace QuantConnect.Algorithm.CSharp
|
||||
{"Compounding Annual Return", "0%"},
|
||||
{"Drawdown", "0%"},
|
||||
{"Expectancy", "0"},
|
||||
{"Start Equity", "100285.86"},
|
||||
{"Start Equity", "100285.85"},
|
||||
{"End Equity", "100285.26"},
|
||||
{"Net Profit", "0%"},
|
||||
{"Sharpe Ratio", "0"},
|
||||
@@ -261,7 +258,7 @@ namespace QuantConnect.Algorithm.CSharp
|
||||
{"Tracking Error", "0"},
|
||||
{"Treynor Ratio", "0"},
|
||||
{"Total Fees", "$0.60"},
|
||||
{"Estimated Strategy Capacity", "$200000000.00"},
|
||||
{"Estimated Strategy Capacity", "$100000000.00"},
|
||||
{"Lowest Capacity Asset", "BTCUSDT 2V3"},
|
||||
{"Portfolio Turnover", "1.08%"},
|
||||
{"Drawdown Recovery", "0"},
|
||||
|
||||
@@ -135,7 +135,7 @@ namespace QuantConnect.Algorithm.CSharp
|
||||
/// <summary>
|
||||
/// Data Points count of the algorithm history
|
||||
/// </summary>
|
||||
public int AlgorithmHistoryDataPoints => 60;
|
||||
public int AlgorithmHistoryDataPoints => 10;
|
||||
|
||||
/// <summary>
|
||||
/// Final status of the algorithm
|
||||
@@ -153,7 +153,7 @@ namespace QuantConnect.Algorithm.CSharp
|
||||
{"Compounding Annual Return", "0%"},
|
||||
{"Drawdown", "0%"},
|
||||
{"Expectancy", "0"},
|
||||
{"Start Equity", "117171.12"},
|
||||
{"Start Equity", "117170.74"},
|
||||
{"End Equity", "117244.52"},
|
||||
{"Net Profit", "0%"},
|
||||
{"Sharpe Ratio", "0"},
|
||||
|
||||
@@ -147,7 +147,7 @@ namespace QuantConnect.Algorithm.CSharp
|
||||
/// <summary>
|
||||
/// Data Points count of the algorithm history
|
||||
/// </summary>
|
||||
public int AlgorithmHistoryDataPoints => 60;
|
||||
public int AlgorithmHistoryDataPoints => 10;
|
||||
|
||||
/// <summary>
|
||||
/// Final status of the algorithm
|
||||
|
||||
@@ -130,7 +130,7 @@ namespace QuantConnect.Algorithm.CSharp
|
||||
/// <summary>
|
||||
/// Data Points count of the algorithm history
|
||||
/// </summary>
|
||||
public int AlgorithmHistoryDataPoints => 120;
|
||||
public int AlgorithmHistoryDataPoints => 20;
|
||||
|
||||
/// <summary>
|
||||
/// Final status of the algorithm
|
||||
|
||||
@@ -47,6 +47,11 @@ namespace QuantConnect.Algorithm.CSharp
|
||||
_aapl = QuantConnect.Symbol.Create("AAPL", SecurityType.Equity, Market.USA);
|
||||
UniverseSettings.Resolution = Resolution.Minute;
|
||||
|
||||
// Let's disable initial price seeding, the algorithm will wait until both equity
|
||||
// and options are added an have prices to do the tests, we don't want the equity
|
||||
// having prices before the options are added.
|
||||
Settings.SeedInitialPrices = false;
|
||||
|
||||
SetStartDate(2014, 06, 04);
|
||||
// TWX is selected the 4th and 5th and aapl after that.
|
||||
// If the algo ends on the 6th, TWX subscriptions will not be removed before OnEndOfAlgorithm is called:
|
||||
@@ -206,7 +211,7 @@ namespace QuantConnect.Algorithm.CSharp
|
||||
{"Lowest Capacity Asset", "AOL R735QTJ8XC9X"},
|
||||
{"Portfolio Turnover", "17.64%"},
|
||||
{"Drawdown Recovery", "0"},
|
||||
{"OrderListHash", "a8605c1f5a9c67f60f1ddc963ec45542"}
|
||||
{"OrderListHash", "228e694280e05c8aa24246a5866b5a83"}
|
||||
};
|
||||
}
|
||||
}
|
||||
|
||||
@@ -0,0 +1,120 @@
|
||||
/*
|
||||
* QUANTCONNECT.COM - Democratizing Finance, Empowering Individuals.
|
||||
* Lean Algorithmic Trading Engine v2.0. Copyright 2014 QuantConnect Corporation.
|
||||
*
|
||||
* 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.
|
||||
*
|
||||
*/
|
||||
|
||||
using System;
|
||||
using System.Collections.Generic;
|
||||
using System.Linq;
|
||||
using QuantConnect.Data.UniverseSelection;
|
||||
|
||||
namespace QuantConnect.Algorithm.CSharp
|
||||
{
|
||||
/// <summary>
|
||||
/// Regression algorithm asserting that securities added via coarse selection get automatically seeded by default
|
||||
/// </summary>
|
||||
public class CoarseSelectionsAutomaticSeedRegressionAlgorithm : AutomaticSeedBaseRegressionAlgorithm
|
||||
{
|
||||
private readonly Queue<List<Symbol>> _coarseSelections = new(new[] { "AAPL", "GOOG", "AIG", "BAC", "FB", "IBM" }
|
||||
.Select(x => QuantConnect.Symbol.Create(x, SecurityType.Equity, Market.USA))
|
||||
.BatchBy(2));
|
||||
|
||||
private HashSet<Symbol> _addedSecurities = new();
|
||||
|
||||
protected override bool ShouldHaveTradeData => true;
|
||||
// Daily resolution, only trade data is available
|
||||
protected override bool ShouldHaveQuoteData => false;
|
||||
protected override bool ShouldHaveOpenInterestData => false;
|
||||
|
||||
public override void Initialize()
|
||||
{
|
||||
SetStartDate(2015, 01, 01);
|
||||
SetEndDate(2015, 03, 01);
|
||||
SetCash(100000);
|
||||
|
||||
Settings.SeedInitialPrices = true;
|
||||
UniverseSettings.Resolution = Resolution.Daily;
|
||||
|
||||
AddUniverse((coarse) =>
|
||||
{
|
||||
var selection = _coarseSelections.Dequeue();
|
||||
_coarseSelections.Enqueue(selection);
|
||||
return selection;
|
||||
});
|
||||
}
|
||||
|
||||
public override void OnSecuritiesChanged(SecurityChanges changes)
|
||||
{
|
||||
base.OnSecuritiesChanged(changes);
|
||||
|
||||
foreach (var addedSecurity in changes.AddedSecurities.Where(x => !x.Symbol.IsCanonical()))
|
||||
{
|
||||
_addedSecurities.Add(addedSecurity.Symbol);
|
||||
}
|
||||
}
|
||||
|
||||
public override void OnEndOfAlgorithm()
|
||||
{
|
||||
if (!_coarseSelections.SelectMany(x => x).Order().SequenceEqual(_addedSecurities.Order()))
|
||||
{
|
||||
throw new RegressionTestException("Not all securities were added");
|
||||
}
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Data Points count of all timeslices of algorithm
|
||||
/// </summary>
|
||||
public override long DataPoints => 358;
|
||||
|
||||
/// <summary>
|
||||
/// Data Points count of the algorithm history
|
||||
/// </summary>
|
||||
public override int AlgorithmHistoryDataPoints => 390;
|
||||
|
||||
/// <summary>
|
||||
/// This is used by the regression test system to indicate what the expected statistics are from running the algorithm
|
||||
/// </summary>
|
||||
public override Dictionary<string, string> ExpectedStatistics => new Dictionary<string, string>
|
||||
{
|
||||
{"Total Orders", "0"},
|
||||
{"Average Win", "0%"},
|
||||
{"Average Loss", "0%"},
|
||||
{"Compounding Annual Return", "0%"},
|
||||
{"Drawdown", "0%"},
|
||||
{"Expectancy", "0"},
|
||||
{"Start Equity", "100000"},
|
||||
{"End Equity", "100000"},
|
||||
{"Net Profit", "0%"},
|
||||
{"Sharpe Ratio", "0"},
|
||||
{"Sortino Ratio", "0"},
|
||||
{"Probabilistic Sharpe Ratio", "0%"},
|
||||
{"Loss Rate", "0%"},
|
||||
{"Win Rate", "0%"},
|
||||
{"Profit-Loss Ratio", "0"},
|
||||
{"Alpha", "0"},
|
||||
{"Beta", "0"},
|
||||
{"Annual Standard Deviation", "0"},
|
||||
{"Annual Variance", "0"},
|
||||
{"Information Ratio", "-1.066"},
|
||||
{"Tracking Error", "0.116"},
|
||||
{"Treynor Ratio", "0"},
|
||||
{"Total Fees", "$0.00"},
|
||||
{"Estimated Strategy Capacity", "$0"},
|
||||
{"Lowest Capacity Asset", ""},
|
||||
{"Portfolio Turnover", "0%"},
|
||||
{"Drawdown Recovery", "0"},
|
||||
{"OrderListHash", "d41d8cd98f00b204e9800998ecf8427e"}
|
||||
};
|
||||
}
|
||||
}
|
||||
@@ -104,7 +104,7 @@ namespace QuantConnect.Algorithm.CSharp
|
||||
/// <summary>
|
||||
/// Data Points count of the algorithm history
|
||||
/// </summary>
|
||||
public int AlgorithmHistoryDataPoints => 43;
|
||||
public int AlgorithmHistoryDataPoints => 11;
|
||||
|
||||
/// <summary>
|
||||
/// Final status of the algorithm
|
||||
|
||||
@@ -153,7 +153,7 @@ namespace QuantConnect.Algorithm.CSharp
|
||||
/// <summary>
|
||||
/// Data Points count of the algorithm history
|
||||
/// </summary>
|
||||
public int AlgorithmHistoryDataPoints => 11147;
|
||||
public int AlgorithmHistoryDataPoints => 50;
|
||||
|
||||
/// <summary>
|
||||
/// Final status of the algorithm
|
||||
|
||||
@@ -176,7 +176,7 @@ namespace QuantConnect.Algorithm.CSharp
|
||||
/// <summary>
|
||||
/// Data Points count of the algorithm history
|
||||
/// </summary>
|
||||
public int AlgorithmHistoryDataPoints => 11147;
|
||||
public int AlgorithmHistoryDataPoints => 50;
|
||||
|
||||
/// <summary>
|
||||
/// Final status of the algorithm
|
||||
|
||||
@@ -27,6 +27,8 @@ namespace QuantConnect.Algorithm.CSharp
|
||||
{
|
||||
private List<decimal> _originalLimitPrices = new();
|
||||
|
||||
protected virtual bool AsynchronousOrders => false;
|
||||
|
||||
protected override IEnumerable<OrderTicket> PlaceComboOrder(List<Leg> legs, int quantity, decimal? limitPrice = null)
|
||||
{
|
||||
foreach (var leg in legs)
|
||||
@@ -35,7 +37,7 @@ namespace QuantConnect.Algorithm.CSharp
|
||||
leg.OrderPrice *= 2; // Won't fill
|
||||
}
|
||||
|
||||
return ComboLegLimitOrder(legs, quantity);
|
||||
return ComboLegLimitOrder(legs, quantity, asynchronous: AsynchronousOrders);
|
||||
}
|
||||
|
||||
protected override void UpdateComboOrder(List<OrderTicket> tickets)
|
||||
@@ -55,6 +57,14 @@ namespace QuantConnect.Algorithm.CSharp
|
||||
{
|
||||
throw new RegressionTestException($"Limit price expected to be greater that the fill price for each order. Limit prices: {string.Join(",", OrderLegs.Select(x => x.OrderPrice))} Fill prices: {string.Join(",", FillOrderEvents.Select(x => x.FillPrice))}");
|
||||
}
|
||||
|
||||
foreach (var ticket in Transactions.GetOrderTickets())
|
||||
{
|
||||
if (ticket.SubmitRequest.Asynchronous != AsynchronousOrders)
|
||||
{
|
||||
throw new RegressionTestException("Expected all orders to have the same asynchronous flag as the algorithm.");
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
@@ -111,10 +121,10 @@ namespace QuantConnect.Algorithm.CSharp
|
||||
{"Treynor Ratio", "0"},
|
||||
{"Total Fees", "$26.00"},
|
||||
{"Estimated Strategy Capacity", "$58000.00"},
|
||||
{"Lowest Capacity Asset", "GOOCV W78ZERHAOVVQ|GOOCV VP83T1ZUHROL"},
|
||||
{"Lowest Capacity Asset", "GOOCV W78ZERHAT67A|GOOCV VP83T1ZUHROL"},
|
||||
{"Portfolio Turnover", "30.22%"},
|
||||
{"Drawdown Recovery", "0"},
|
||||
{"OrderListHash", "ab6171073cd96df46fd9d7bce62f5594"}
|
||||
{"OrderListHash", "6168ffaa5b9f3c389f5da52e90455889"}
|
||||
};
|
||||
}
|
||||
}
|
||||
|
||||
25
Algorithm.CSharp/ComboLegLimitOrderAsyncAlgorithm.cs
Normal file
25
Algorithm.CSharp/ComboLegLimitOrderAsyncAlgorithm.cs
Normal file
@@ -0,0 +1,25 @@
|
||||
/*
|
||||
* QUANTCONNECT.COM - Democratizing Finance, Empowering Individuals.
|
||||
* Lean Algorithmic Trading Engine v2.0. Copyright 2014 QuantConnect Corporation.
|
||||
*
|
||||
* 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.
|
||||
*/
|
||||
|
||||
namespace QuantConnect.Algorithm.CSharp
|
||||
{
|
||||
/// <summary>
|
||||
/// Regression algorithm to test combo leg limit orders in asynchronous mode
|
||||
/// </summary>
|
||||
public class ComboLegLimitOrderAsyncAlgorithm : ComboLegLimitOrderAlgorithm
|
||||
{
|
||||
protected override bool AsynchronousOrders => true;
|
||||
}
|
||||
}
|
||||
@@ -46,6 +46,8 @@ namespace QuantConnect.Algorithm.CSharp
|
||||
}
|
||||
}
|
||||
|
||||
protected virtual bool AsynchronousOrders => false;
|
||||
|
||||
protected override IEnumerable<OrderTicket> PlaceComboOrder(List<Leg> legs, int quantity, decimal? limitPrice)
|
||||
{
|
||||
_limitPrice = limitPrice.Value;
|
||||
@@ -56,7 +58,7 @@ namespace QuantConnect.Algorithm.CSharp
|
||||
legs.ForEach(x => { x.OrderPrice = null; });
|
||||
|
||||
// First, let's place a limit order that won't fill so we can update it later
|
||||
return ComboLimitOrder(legs, _temporaryComboQuantity, _temporaryLimitPrice);
|
||||
return ComboLimitOrder(legs, _temporaryComboQuantity, _temporaryLimitPrice, asynchronous: AsynchronousOrders);
|
||||
}
|
||||
|
||||
protected override void UpdateComboOrder(List<OrderTicket> tickets)
|
||||
@@ -121,6 +123,14 @@ namespace QuantConnect.Algorithm.CSharp
|
||||
{
|
||||
throw new RegressionTestException("Combo order was not liquidated");
|
||||
}
|
||||
|
||||
foreach (var ticket in Transactions.GetOrderTickets().Where(x => x.OrderType == OrderType.ComboLimit))
|
||||
{
|
||||
if (ticket.SubmitRequest.Asynchronous != AsynchronousOrders)
|
||||
{
|
||||
throw new RegressionTestException("Expected all orders to have the same asynchronous flag as the algorithm.");
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
@@ -177,10 +187,10 @@ namespace QuantConnect.Algorithm.CSharp
|
||||
{"Treynor Ratio", "0"},
|
||||
{"Total Fees", "$52.00"},
|
||||
{"Estimated Strategy Capacity", "$5000.00"},
|
||||
{"Lowest Capacity Asset", "GOOCV W78ZERHAOVVQ|GOOCV VP83T1ZUHROL"},
|
||||
{"Lowest Capacity Asset", "GOOCV W78ZERHAT67A|GOOCV VP83T1ZUHROL"},
|
||||
{"Portfolio Turnover", "60.91%"},
|
||||
{"Drawdown Recovery", "0"},
|
||||
{"OrderListHash", "100742aeee45101940dc60e26fa1aa39"}
|
||||
{"OrderListHash", "7daf3d43bef2b023ab26517085840c0e"}
|
||||
};
|
||||
}
|
||||
}
|
||||
|
||||
25
Algorithm.CSharp/ComboLimitOrderAsyncAlgorithm.cs
Normal file
25
Algorithm.CSharp/ComboLimitOrderAsyncAlgorithm.cs
Normal file
@@ -0,0 +1,25 @@
|
||||
/*
|
||||
* QUANTCONNECT.COM - Democratizing Finance, Empowering Individuals.
|
||||
* Lean Algorithmic Trading Engine v2.0. Copyright 2014 QuantConnect Corporation.
|
||||
*
|
||||
* 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.
|
||||
*/
|
||||
|
||||
namespace QuantConnect.Algorithm.CSharp
|
||||
{
|
||||
/// <summary>
|
||||
/// Regression algorithm to test combo limit orders in asynchronous mode
|
||||
/// </summary>
|
||||
public class ComboLimitOrderAsyncAlgorithm : ComboLimitOrderAlgorithm
|
||||
{
|
||||
protected override bool AsynchronousOrders => true;
|
||||
}
|
||||
}
|
||||
@@ -93,10 +93,10 @@ namespace QuantConnect.Algorithm.CSharp
|
||||
{"Treynor Ratio", "0"},
|
||||
{"Total Fees", "$26.00"},
|
||||
{"Estimated Strategy Capacity", "$69000.00"},
|
||||
{"Lowest Capacity Asset", "GOOCV W78ZERHAOVVQ|GOOCV VP83T1ZUHROL"},
|
||||
{"Lowest Capacity Asset", "GOOCV W78ZERHAT67A|GOOCV VP83T1ZUHROL"},
|
||||
{"Portfolio Turnover", "30.35%"},
|
||||
{"Drawdown Recovery", "0"},
|
||||
{"OrderListHash", "615c795b0c450cb8e4c3cba803ebb180"}
|
||||
{"OrderListHash", "0b9f42bc22c9c7c382bc57a64c99f7e5"}
|
||||
};
|
||||
}
|
||||
}
|
||||
|
||||
@@ -58,7 +58,7 @@ namespace QuantConnect.Algorithm.CSharp
|
||||
var option = AddOption(equity.Symbol, fillForward: true);
|
||||
_optionSymbol = option.Symbol;
|
||||
|
||||
option.SetFilter(u => u.Strikes(-2, +2)
|
||||
option.SetFilter(u => u.StandardsOnly().Strikes(-2, +2)
|
||||
.Expiration(0, 180));
|
||||
}
|
||||
|
||||
|
||||
@@ -47,7 +47,7 @@ namespace QuantConnect.Algorithm.CSharp
|
||||
var option = AddOption(equity.Symbol, fillForward: true);
|
||||
_optionSymbol = option.Symbol;
|
||||
|
||||
option.SetFilter(u => u.Strikes(-2, +2)
|
||||
option.SetFilter(u => u.StandardsOnly().Strikes(-2, +2)
|
||||
.Expiration(0, 180));
|
||||
}
|
||||
|
||||
@@ -243,8 +243,7 @@ namespace QuantConnect.Algorithm.CSharp
|
||||
}
|
||||
if (orderEvent.Quantity != order.Quantity)
|
||||
{
|
||||
throw new RegressionTestException($@"OrderEvent quantity should hold the current order Quantity. Got {orderEvent.Quantity
|
||||
}, expected {order.Quantity}");
|
||||
throw new RegressionTestException($@"OrderEvent quantity should hold the current order Quantity. Got {orderEvent.Quantity}, expected {order.Quantity}");
|
||||
}
|
||||
if (order is ComboLegLimitOrder && orderEvent.LimitPrice == 0)
|
||||
{
|
||||
@@ -303,8 +302,7 @@ namespace QuantConnect.Algorithm.CSharp
|
||||
{
|
||||
throw new RegressionTestException(
|
||||
"There were expected 6 filled market orders, 3 filled combo limit orders and 6 filled combo leg limit orders, " +
|
||||
$@"but there were {filledComboMarketOrders.Count} filled market orders, {filledComboLimitOrders.Count
|
||||
} filled combo limit orders and {filledComboLegLimitOrders.Count} filled combo leg limit orders");
|
||||
$@"but there were {filledComboMarketOrders.Count} filled market orders, {filledComboLimitOrders.Count} filled combo limit orders and {filledComboLegLimitOrders.Count} filled combo leg limit orders");
|
||||
}
|
||||
|
||||
if (openOrders.Count != 0 || openOrderTickets.Count != 0)
|
||||
@@ -372,10 +370,10 @@ namespace QuantConnect.Algorithm.CSharp
|
||||
{"Treynor Ratio", "0"},
|
||||
{"Total Fees", "$26.00"},
|
||||
{"Estimated Strategy Capacity", "$2000.00"},
|
||||
{"Lowest Capacity Asset", "GOOCV W78ZERHAOVVQ|GOOCV VP83T1ZUHROL"},
|
||||
{"Lowest Capacity Asset", "GOOCV W78ZERHAT67A|GOOCV VP83T1ZUHROL"},
|
||||
{"Portfolio Turnover", "58.98%"},
|
||||
{"Drawdown Recovery", "0"},
|
||||
{"OrderListHash", "e69460f62d4c165fe4b4a9bff1f48962"}
|
||||
{"OrderListHash", "bec09c16bbc4d87a4e5122f29dd5a38b"}
|
||||
};
|
||||
}
|
||||
}
|
||||
|
||||
@@ -13,7 +13,6 @@
|
||||
* limitations under the License.
|
||||
*/
|
||||
|
||||
using System;
|
||||
using System.Collections.Generic;
|
||||
using QuantConnect.Data.Market;
|
||||
using QuantConnect.Interfaces;
|
||||
@@ -31,6 +30,8 @@ namespace QuantConnect.Algorithm.CSharp
|
||||
private bool _thereIsAtLeastOneTradeBar;
|
||||
private bool _thereIsAtLeastOneQuoteBar;
|
||||
|
||||
private int _consolidationCount;
|
||||
|
||||
public override void Initialize()
|
||||
{
|
||||
SetStartDate(2013, 10, 06);
|
||||
@@ -56,6 +57,12 @@ namespace QuantConnect.Algorithm.CSharp
|
||||
public void OnQuoteTickMaxCount(QuoteBar quoteBar)
|
||||
{
|
||||
_thereIsAtLeastOneQuoteBar = true;
|
||||
|
||||
// Let's shortcut to reduce regression test duration: algorithms using tick data are too long
|
||||
if (++_consolidationCount >= 1000)
|
||||
{
|
||||
Quit();
|
||||
}
|
||||
}
|
||||
|
||||
public void OnQuoteTick(Tick tick)
|
||||
@@ -112,7 +119,7 @@ namespace QuantConnect.Algorithm.CSharp
|
||||
/// <summary>
|
||||
/// Data Points count of all timeslices of algorithm
|
||||
/// </summary>
|
||||
public long DataPoints => 2857175;
|
||||
public long DataPoints => 12190;
|
||||
|
||||
/// <summary>
|
||||
/// Data Points count of the algorithm history
|
||||
|
||||
@@ -47,7 +47,7 @@ namespace QuantConnect.Algorithm.CSharp
|
||||
SetEndDate(2020, 01, 20);
|
||||
|
||||
var SP500 = QuantConnect.Symbol.Create(Futures.Indices.SP500EMini, SecurityType.Future, Market.CME);
|
||||
var symbol = FuturesChain(SP500).First();
|
||||
var symbol = FuturesChain(SP500).OrderBy(x => x.Symbol.ID.Date).First();
|
||||
_future = AddFutureContract(symbol);
|
||||
|
||||
var tradableDatesCount = QuantConnect.Time.EachTradeableDayInTimeZone(_future.Exchange.Hours,
|
||||
|
||||
143
Algorithm.CSharp/ConsolidatorStartTimeRegressionAlgorithm.cs
Normal file
143
Algorithm.CSharp/ConsolidatorStartTimeRegressionAlgorithm.cs
Normal file
@@ -0,0 +1,143 @@
|
||||
/*
|
||||
* QUANTCONNECT.COM - Democratizing Finance, Empowering Individuals.
|
||||
* Lean Algorithmic Trading Engine v2.0. Copyright 2014 QuantConnect Corporation.
|
||||
*
|
||||
* 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.
|
||||
*/
|
||||
|
||||
using System;
|
||||
using QuantConnect.Data;
|
||||
using QuantConnect.Interfaces;
|
||||
using QuantConnect.Data.Market;
|
||||
using System.Collections.Generic;
|
||||
using QuantConnect.Data.Consolidators;
|
||||
|
||||
namespace QuantConnect.Algorithm.CSharp
|
||||
{
|
||||
/// <summary>
|
||||
/// Regression algorithm show casing and asserting the behavior of creating a consolidator specifying the start time
|
||||
/// </summary>
|
||||
public class ConsolidatorStartTimeRegressionAlgorithm : QCAlgorithm, IRegressionAlgorithmDefinition
|
||||
{
|
||||
private readonly Queue<TimeSpan> _expectedConsolidationTime = new([
|
||||
new TimeSpan(9, 30, 0),
|
||||
new TimeSpan(10, 30, 0),
|
||||
new TimeSpan(11, 30, 0),
|
||||
new TimeSpan(12, 30, 0),
|
||||
new TimeSpan(13, 30, 0),
|
||||
new TimeSpan(14, 30, 0)
|
||||
]);
|
||||
private TradeBarConsolidator consolidator;
|
||||
|
||||
/// <summary>
|
||||
/// Initialise the data and resolution required, as well as the cash and start-end dates for your algorithm. All algorithms must initialized.
|
||||
/// </summary>
|
||||
public override void Initialize()
|
||||
{
|
||||
SetStartDate(2013, 10, 04);
|
||||
SetEndDate(2013, 10, 04);
|
||||
|
||||
AddEquity("SPY", Resolution.Minute);
|
||||
|
||||
consolidator = new TradeBarConsolidator(TimeSpan.FromHours(1), startTime: new TimeSpan(9, 30, 0));
|
||||
consolidator.DataConsolidated += BarHandler;
|
||||
|
||||
SubscriptionManager.AddConsolidator("SPY", consolidator);
|
||||
}
|
||||
|
||||
private void BarHandler(object _, TradeBar bar)
|
||||
{
|
||||
if (Time != bar.EndTime)
|
||||
{
|
||||
throw new RegressionTestException($"Unexpected consolidation time {bar.Time} != {Time}!");
|
||||
}
|
||||
|
||||
var expected = _expectedConsolidationTime.Dequeue();
|
||||
if (bar.Time.TimeOfDay != expected)
|
||||
{
|
||||
throw new RegressionTestException($"Unexpected consolidation time {bar.Time.TimeOfDay} != {expected}!");
|
||||
}
|
||||
|
||||
if (bar.Period != TimeSpan.FromHours(1))
|
||||
{
|
||||
throw new RegressionTestException($"Unexpected consolidation period {bar.Period}!");
|
||||
}
|
||||
}
|
||||
|
||||
public override void OnEndOfAlgorithm()
|
||||
{
|
||||
if (_expectedConsolidationTime.Count > 0)
|
||||
{
|
||||
throw new RegressionTestException("Unexpected consolidation times!");
|
||||
}
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// This is used by the regression test system to indicate if the open source Lean repository has the required data to run this algorithm.
|
||||
/// </summary>
|
||||
public bool CanRunLocally { get; } = true;
|
||||
|
||||
/// <summary>
|
||||
/// This is used by the regression test system to indicate which languages this algorithm is written in.
|
||||
/// </summary>
|
||||
public List<Language> Languages { get; } = new() { Language.CSharp, Language.Python };
|
||||
|
||||
/// <summary>
|
||||
/// Data Points count of all timeslices of algorithm
|
||||
/// </summary>
|
||||
public long DataPoints => 795;
|
||||
|
||||
/// <summary>
|
||||
/// Data Points count of the algorithm history
|
||||
/// </summary>
|
||||
public int AlgorithmHistoryDataPoints => 0;
|
||||
|
||||
/// <summary>
|
||||
/// Final status of the algorithm
|
||||
/// </summary>
|
||||
public AlgorithmStatus AlgorithmStatus => AlgorithmStatus.Completed;
|
||||
|
||||
/// <summary>
|
||||
/// This is used by the regression test system to indicate what the expected statistics are from running the algorithm
|
||||
/// </summary>
|
||||
public Dictionary<string, string> ExpectedStatistics => new Dictionary<string, string>
|
||||
{
|
||||
{"Total Orders", "0"},
|
||||
{"Average Win", "0%"},
|
||||
{"Average Loss", "0%"},
|
||||
{"Compounding Annual Return", "0%"},
|
||||
{"Drawdown", "0%"},
|
||||
{"Expectancy", "0"},
|
||||
{"Start Equity", "100000"},
|
||||
{"End Equity", "100000"},
|
||||
{"Net Profit", "0%"},
|
||||
{"Sharpe Ratio", "0"},
|
||||
{"Sortino Ratio", "0"},
|
||||
{"Probabilistic Sharpe Ratio", "0%"},
|
||||
{"Loss Rate", "0%"},
|
||||
{"Win Rate", "0%"},
|
||||
{"Profit-Loss Ratio", "0"},
|
||||
{"Alpha", "0"},
|
||||
{"Beta", "0"},
|
||||
{"Annual Standard Deviation", "0"},
|
||||
{"Annual Variance", "0"},
|
||||
{"Information Ratio", "0"},
|
||||
{"Tracking Error", "0"},
|
||||
{"Treynor Ratio", "0"},
|
||||
{"Total Fees", "$0.00"},
|
||||
{"Estimated Strategy Capacity", "$0"},
|
||||
{"Lowest Capacity Asset", ""},
|
||||
{"Portfolio Turnover", "0%"},
|
||||
{"Drawdown Recovery", "0"},
|
||||
{"OrderListHash", "d41d8cd98f00b204e9800998ecf8427e"}
|
||||
};
|
||||
}
|
||||
}
|
||||
@@ -26,20 +26,20 @@ namespace QuantConnect.Algorithm.CSharp
|
||||
{
|
||||
/// <summary>
|
||||
/// Regression algorithm asserting that continuous future universe selection happens right away for all futures.
|
||||
/// An example case is ES and Milk futures, which have different time zones. ES is in New York and Milk is in Chicago.
|
||||
/// An example case is ES and HSI futures, which have different time zones. ES is in New York and HSI is in Hong Kong.
|
||||
/// ES selection would happen first just because of this, but all futures should have a mapped contract right away.
|
||||
/// </summary>
|
||||
public class ContinuousFutureImmediateUniverseSelectionRegressionAlgorithm : QCAlgorithm, IRegressionAlgorithmDefinition
|
||||
{
|
||||
private Future _es;
|
||||
private Future _milk;
|
||||
private Future _hsi;
|
||||
|
||||
private bool _dataReceived;
|
||||
|
||||
private DateTime _startDateUtc;
|
||||
|
||||
private DateTime _esSelectionTimeUtc;
|
||||
private DateTime _milkSelectionTimeUtc;
|
||||
private DateTime _hsiSelectionTimeUtc;
|
||||
|
||||
private bool _securitiesChangedEventReceived;
|
||||
|
||||
@@ -57,10 +57,9 @@ namespace QuantConnect.Algorithm.CSharp
|
||||
contractDepthOffset: 0,
|
||||
extendedMarketHours: true);
|
||||
|
||||
// Milk time zone is Chicago, so market open will be after ES
|
||||
_milk = AddFuture(Futures.Dairy.ClassIIIMilk,
|
||||
_hsi = AddFuture(Futures.Indices.HangSeng,
|
||||
dataNormalizationMode: DataNormalizationMode.BackwardsRatio,
|
||||
dataMappingMode: DataMappingMode.OpenInterestAnnual,
|
||||
dataMappingMode: DataMappingMode.FirstDayMonth,
|
||||
contractDepthOffset: 0,
|
||||
extendedMarketHours: true);
|
||||
|
||||
@@ -75,25 +74,22 @@ namespace QuantConnect.Algorithm.CSharp
|
||||
throw new RegressionTestException($"Expected ES universe selection to happen on algorithm start ({_startDateUtc}), " +
|
||||
$"but happened on {_esSelectionTimeUtc}");
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
return universe;
|
||||
});
|
||||
|
||||
_milk.SetFilter(universe =>
|
||||
_hsi.SetFilter(universe =>
|
||||
{
|
||||
if (_milkSelectionTimeUtc == DateTime.MinValue)
|
||||
if (_hsiSelectionTimeUtc == DateTime.MinValue)
|
||||
{
|
||||
_milkSelectionTimeUtc = universe.LocalTime.ConvertToUtc(_milk.Exchange.TimeZone);
|
||||
_hsiSelectionTimeUtc = universe.LocalTime.ConvertToUtc(_hsi.Exchange.TimeZone);
|
||||
|
||||
if (_milkSelectionTimeUtc != _startDateUtc)
|
||||
if (_hsiSelectionTimeUtc != _startDateUtc)
|
||||
{
|
||||
throw new RegressionTestException($"Expected DC universe selection to happen on algorithm start ({_startDateUtc}), " +
|
||||
$"but happened on {_milkSelectionTimeUtc}");
|
||||
throw new RegressionTestException($"Expected HSI universe selection to happen on algorithm start ({_startDateUtc}), " +
|
||||
$"but happened on {_hsiSelectionTimeUtc}");
|
||||
}
|
||||
}
|
||||
|
||||
return universe;
|
||||
});
|
||||
}
|
||||
@@ -107,14 +103,14 @@ namespace QuantConnect.Algorithm.CSharp
|
||||
throw new RegressionTestException("ES mapped contract is null");
|
||||
}
|
||||
|
||||
// This is what we actually want to assert: even though Milk future time zone is 1 hour behind,
|
||||
// This is what we actually want to assert: even though Hong Kong future time zone is different,
|
||||
// we should have a mapped contract right away.
|
||||
if (_milk.Mapped == null)
|
||||
if (_hsi.Mapped == null)
|
||||
{
|
||||
throw new RegressionTestException("DC mapped contract is null");
|
||||
throw new RegressionTestException("HSI mapped contract is null");
|
||||
}
|
||||
|
||||
Log($"{slice.Time} :: ES Mapped Contract: {_es.Mapped}. DC Mapped Contract: {_milk.Mapped}");
|
||||
Log($"{slice.Time} :: ES Mapped Contract: {_es.Mapped}. HSI Mapped Contract: {_hsi.Mapped}");
|
||||
}
|
||||
|
||||
public override void OnSecuritiesChanged(SecurityChanges changes)
|
||||
@@ -134,9 +130,9 @@ namespace QuantConnect.Algorithm.CSharp
|
||||
throw new RegressionTestException("ES universe selection time was not set");
|
||||
}
|
||||
|
||||
if (_milkSelectionTimeUtc == DateTime.MinValue)
|
||||
if (_hsiSelectionTimeUtc == DateTime.MinValue)
|
||||
{
|
||||
throw new RegressionTestException("DC universe selection time was not set");
|
||||
throw new RegressionTestException("HSI universe selection time was not set");
|
||||
}
|
||||
|
||||
if (changes.AddedSecurities.Count == 0 || changes.RemovedSecurities.Count != 0)
|
||||
@@ -150,9 +146,9 @@ namespace QuantConnect.Algorithm.CSharp
|
||||
throw new RegressionTestException($"Expected to find a multiple futures for ES");
|
||||
}
|
||||
|
||||
if (!changes.AddedSecurities.Any(x => !x.Symbol.IsCanonical() && x.Symbol.Canonical == _milk.Symbol))
|
||||
if (!changes.AddedSecurities.Any(x => !x.Symbol.IsCanonical() && x.Symbol.Canonical == _hsi.Symbol))
|
||||
{
|
||||
throw new RegressionTestException($"Expected to find a multiple futures for DC");
|
||||
throw new RegressionTestException($"Expected to find a multiple futures for HSI");
|
||||
}
|
||||
}
|
||||
}
|
||||
@@ -184,7 +180,7 @@ namespace QuantConnect.Algorithm.CSharp
|
||||
/// <summary>
|
||||
/// Data Points count of all timeslices of algorithm
|
||||
/// </summary>
|
||||
public long DataPoints => 445961;
|
||||
public long DataPoints => 129796;
|
||||
|
||||
/// <summary>
|
||||
/// Data Points count of the algorithm history
|
||||
|
||||
@@ -45,17 +45,23 @@ namespace QuantConnect.Algorithm.CSharp
|
||||
|
||||
protected abstract Offset ExchangeToDataTimeZoneOffset { get; }
|
||||
|
||||
protected virtual bool SeedIntialPrices { get; }
|
||||
|
||||
private DateTimeZone DataTimeZone => TimeZones.Utc;
|
||||
|
||||
private DateTimeZone ExchangeTimeZone => DateTimeZone.ForOffset(ExchangeToDataTimeZoneOffset);
|
||||
|
||||
private bool RolloverHappened => _rolloverTime != DateTime.MinValue;
|
||||
|
||||
private BaseData MappedContractSeededData;
|
||||
|
||||
public override void Initialize()
|
||||
{
|
||||
SetStartDate(2013, 10, 8);
|
||||
SetEndDate(2013, 12, 20);
|
||||
|
||||
Settings.SeedInitialPrices = SeedIntialPrices;
|
||||
|
||||
_originalMhdbEntry = MarketHoursDatabase.GetEntry(Market.CME, Ticker, SecurityType.Future);
|
||||
var exchangeHours = new SecurityExchangeHours(ExchangeTimeZone,
|
||||
_originalMhdbEntry.ExchangeHours.Holidays,
|
||||
@@ -115,6 +121,9 @@ namespace QuantConnect.Algorithm.CSharp
|
||||
$"Expected {expectedMappingOldSymbol} -> {expectedMappingNewSymbol} " +
|
||||
$"but was {symbolChangedEvent.OldSymbol} -> {symbolChangedEvent.NewSymbol}");
|
||||
}
|
||||
|
||||
var mappedContract = Securities[_continuousContract.Mapped];
|
||||
MappedContractSeededData = mappedContract.GetLastData();
|
||||
}
|
||||
|
||||
var mappedFuture = Securities[_continuousContract.Mapped];
|
||||
@@ -148,7 +157,10 @@ namespace QuantConnect.Algorithm.CSharp
|
||||
}
|
||||
else if (mappedFuturePrice != 0 || !RolloverHappened)
|
||||
{
|
||||
if (continuousContractPrice != mappedFuturePrice)
|
||||
var mappedFutureData = mappedFuture.GetLastData();
|
||||
// We only do this check is default securities seeding is desabled, else the mapped contract will have historical data
|
||||
if ((!Settings.SeedInitialPrices || !ReferenceEquals(MappedContractSeededData, mappedFutureData)) &&
|
||||
continuousContractPrice != mappedFuturePrice)
|
||||
{
|
||||
var continuousContractLastData = _continuousContract.GetLastData();
|
||||
throw new RegressionTestException($"[{Time}] -- Prices do not match. " +
|
||||
@@ -221,7 +233,7 @@ namespace QuantConnect.Algorithm.CSharp
|
||||
/// <summary>
|
||||
/// Data Points count of the algorithm history
|
||||
/// </summary>
|
||||
public int AlgorithmHistoryDataPoints => 0;
|
||||
public virtual int AlgorithmHistoryDataPoints => 0;
|
||||
|
||||
/// <summary>
|
||||
/// This is used by the regression test system to indicate what the expected statistics are from running the algorithm
|
||||
|
||||
@@ -34,5 +34,10 @@ namespace QuantConnect.Algorithm.CSharp
|
||||
/// Data Points count of all timeslices of algorithm
|
||||
/// </summary>
|
||||
public override long DataPoints => 483;
|
||||
|
||||
/// <summary>
|
||||
/// Data Points count of the algorithm history
|
||||
/// </summary>
|
||||
public override int AlgorithmHistoryDataPoints => 0;
|
||||
}
|
||||
}
|
||||
|
||||
@@ -0,0 +1,33 @@
|
||||
/*
|
||||
* QUANTCONNECT.COM - Democratizing Finance, Empowering Individuals.
|
||||
* Lean Algorithmic Trading Engine v2.0. Copyright 2014 QuantConnect Corporation.
|
||||
*
|
||||
* 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.
|
||||
*
|
||||
*/
|
||||
|
||||
namespace QuantConnect.Algorithm.CSharp
|
||||
{
|
||||
/// <summary>
|
||||
/// Base class for regression algorithms testing that when a continuous future rollover happens,
|
||||
/// the continuous contract is updated correctly with the new contract data.
|
||||
/// The algorithms asserts the behavior for the case when the exchange time zone is ahead of the data time zone.
|
||||
/// </summary>
|
||||
public class ContinuousFutureRolloverDailyExchangeTimeZoneAheadOfDataWithInitialSeedRegressionAlgorithm
|
||||
: ContinuousFutureRolloverDailyExchangeTimeZoneAheadOfDataRegressionAlgorithm
|
||||
{
|
||||
protected override bool SeedIntialPrices => true;
|
||||
/// <summary>
|
||||
/// Data Points count of the algorithm history
|
||||
/// </summary>
|
||||
public override int AlgorithmHistoryDataPoints => 15;
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,34 @@
|
||||
/*
|
||||
* QUANTCONNECT.COM - Democratizing Finance, Empowering Individuals.
|
||||
* Lean Algorithmic Trading Engine v2.0. Copyright 2014 QuantConnect Corporation.
|
||||
*
|
||||
* 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.
|
||||
*
|
||||
*/
|
||||
|
||||
namespace QuantConnect.Algorithm.CSharp
|
||||
{
|
||||
/// <summary>
|
||||
/// Base class for regression algorithms testing that when a continuous future rollover happens,
|
||||
/// the continuous contract is updated correctly with the new contract data.
|
||||
/// The algorithms asserts the behavior for the case when the exchange time zone is behind of the data time zone.
|
||||
/// </summary>
|
||||
public class ContinuousFutureRolloverDailyExchangeTimeZoneBehindOfDataWithInitialSeedRegressionAlgorithm
|
||||
: ContinuousFutureRolloverDailyExchangeTimeZoneBehindOfDataRegressionAlgorithm
|
||||
{
|
||||
protected override bool SeedIntialPrices => true;
|
||||
|
||||
/// <summary>
|
||||
/// Data Points count of the algorithm history
|
||||
/// </summary>
|
||||
public override int AlgorithmHistoryDataPoints => 17;
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,35 @@
|
||||
/*
|
||||
* QUANTCONNECT.COM - Democratizing Finance, Empowering Individuals.
|
||||
* Lean Algorithmic Trading Engine v2.0. Copyright 2014 QuantConnect Corporation.
|
||||
*
|
||||
* 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.
|
||||
*
|
||||
*/
|
||||
|
||||
namespace QuantConnect.Algorithm.CSharp
|
||||
{
|
||||
/// <summary>
|
||||
/// Base class for regression algorithms testing that when a continuous future rollover happens,
|
||||
/// the continuous contract is updated correctly with the new contract data.
|
||||
/// The algorithms asserts the behavior for the case when the data time zone is the same as the exchange time zone.
|
||||
/// </summary>
|
||||
public class ContinuousFutureRolloverDailyExchangeTimeZoneSameAsDataWithInitialSeedRegressionAlgorithm
|
||||
: ContinuousFutureRolloverDailyExchangeTimeZoneSameAsDataRegressionAlgorithm
|
||||
|
||||
{
|
||||
protected override bool SeedIntialPrices => true;
|
||||
|
||||
/// <summary>
|
||||
/// Data Points count of the algorithm history
|
||||
/// </summary>
|
||||
public override int AlgorithmHistoryDataPoints => 17;
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,34 @@
|
||||
/*
|
||||
* QUANTCONNECT.COM - Democratizing Finance, Empowering Individuals.
|
||||
* Lean Algorithmic Trading Engine v2.0. Copyright 2014 QuantConnect Corporation.
|
||||
*
|
||||
* 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.
|
||||
*
|
||||
*/
|
||||
|
||||
namespace QuantConnect.Algorithm.CSharp
|
||||
{
|
||||
/// <summary>
|
||||
/// Base class for regression algorithms testing that when a continuous future rollover happens,
|
||||
/// the continuous contract is updated correctly with the new contract data.
|
||||
/// The algorithms asserts the behavior for the case when the exchange time zone is ahead of the data time zone.
|
||||
/// </summary>
|
||||
public class ContinuousFutureRolloverHourExchangeTimeZoneAheadOfDataWithInitialSeedRegressionAlgorithm
|
||||
: ContinuousFutureRolloverHourExchangeTimeZoneAheadOfDataRegressionAlgorithm
|
||||
{
|
||||
protected override bool SeedIntialPrices => true;
|
||||
|
||||
/// <summary>
|
||||
/// Data Points count of the algorithm history
|
||||
/// </summary>
|
||||
public override int AlgorithmHistoryDataPoints => 65;
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,34 @@
|
||||
/*
|
||||
* QUANTCONNECT.COM - Democratizing Finance, Empowering Individuals.
|
||||
* Lean Algorithmic Trading Engine v2.0. Copyright 2014 QuantConnect Corporation.
|
||||
*
|
||||
* 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.
|
||||
*
|
||||
*/
|
||||
|
||||
namespace QuantConnect.Algorithm.CSharp
|
||||
{
|
||||
/// <summary>
|
||||
/// Base class for regression algorithms testing that when a continuous future rollover happens,
|
||||
/// the continuous contract is updated correctly with the new contract data.
|
||||
/// The algorithms asserts the behavior for the case when the exchange time zone is behind of the data time zone.
|
||||
/// </summary>
|
||||
public class ContinuousFutureRolloverHourExchangeTimeZoneBehindOfDataWithInitialSeedRegressionAlgorithm
|
||||
: ContinuousFutureRolloverHourExchangeTimeZoneBehindOfDataRegressionAlgorithm
|
||||
{
|
||||
protected override bool SeedIntialPrices => true;
|
||||
|
||||
/// <summary>
|
||||
/// Data Points count of the algorithm history
|
||||
/// </summary>
|
||||
public override int AlgorithmHistoryDataPoints => 64;
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,34 @@
|
||||
/*
|
||||
* QUANTCONNECT.COM - Democratizing Finance, Empowering Individuals.
|
||||
* Lean Algorithmic Trading Engine v2.0. Copyright 2014 QuantConnect Corporation.
|
||||
*
|
||||
* 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.
|
||||
*
|
||||
*/
|
||||
|
||||
namespace QuantConnect.Algorithm.CSharp
|
||||
{
|
||||
/// <summary>
|
||||
/// Base class for regression algorithms testing that when a continuous future rollover happens,
|
||||
/// the continuous contract is updated correctly with the new contract data.
|
||||
/// The algorithms asserts the behavior for the case when the data time zone is the same as the exchange time zone.
|
||||
/// </summary>
|
||||
public class ContinuousFutureRolloverHourExchangeTimeZoneSameAsDataWithInitialSeedRegressionAlgorithm
|
||||
: ContinuousFutureRolloverHourExchangeTimeZoneSameAsDataRegressionAlgorithm
|
||||
{
|
||||
protected override bool SeedIntialPrices => true;
|
||||
|
||||
/// <summary>
|
||||
/// Data Points count of the algorithm history
|
||||
/// </summary>
|
||||
public override int AlgorithmHistoryDataPoints => 64;
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,34 @@
|
||||
/*
|
||||
* QUANTCONNECT.COM - Democratizing Finance, Empowering Individuals.
|
||||
* Lean Algorithmic Trading Engine v2.0. Copyright 2014 QuantConnect Corporation.
|
||||
*
|
||||
* 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.
|
||||
*
|
||||
*/
|
||||
|
||||
namespace QuantConnect.Algorithm.CSharp
|
||||
{
|
||||
/// <summary>
|
||||
/// Base class for regression algorithms testing that when a continuous future rollover happens,
|
||||
/// the continuous contract is updated correctly with the new contract data.
|
||||
/// The algorithms asserts the behavior for the case when the exchange time zone is ahead of the data time zone.
|
||||
/// </summary>
|
||||
public class ContinuousFutureRolloverMinuteExchangeTimeZoneAheadOfDataWithInitialSeedRegressionAlgorithm
|
||||
: ContinuousFutureRolloverMinuteExchangeTimeZoneAheadOfDataRegressionAlgorithm
|
||||
{
|
||||
protected override bool SeedIntialPrices => true;
|
||||
|
||||
/// <summary>
|
||||
/// Data Points count of the algorithm history
|
||||
/// </summary>
|
||||
public override int AlgorithmHistoryDataPoints => 1958;
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,34 @@
|
||||
/*
|
||||
* QUANTCONNECT.COM - Democratizing Finance, Empowering Individuals.
|
||||
* Lean Algorithmic Trading Engine v2.0. Copyright 2014 QuantConnect Corporation.
|
||||
*
|
||||
* 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.
|
||||
*
|
||||
*/
|
||||
|
||||
namespace QuantConnect.Algorithm.CSharp
|
||||
{
|
||||
/// <summary>
|
||||
/// Base class for regression algorithms testing that when a continuous future rollover happens,
|
||||
/// the continuous contract is updated correctly with the new contract data.
|
||||
/// The algorithms asserts the behavior for the case when the exchange time zone is behind of the data time zone.
|
||||
/// </summary>
|
||||
public class ContinuousFutureRolloverMinuteExchangeTimeZoneBehindOfDataWithInitialSeedRegressionAlgorithm
|
||||
: ContinuousFutureRolloverMinuteExchangeTimeZoneBehindOfDataRegressionAlgorithm
|
||||
{
|
||||
protected override bool SeedIntialPrices => true;
|
||||
|
||||
/// <summary>
|
||||
/// Data Points count of the algorithm history
|
||||
/// </summary>
|
||||
public override int AlgorithmHistoryDataPoints => 892;
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,34 @@
|
||||
/*
|
||||
* QUANTCONNECT.COM - Democratizing Finance, Empowering Individuals.
|
||||
* Lean Algorithmic Trading Engine v2.0. Copyright 2014 QuantConnect Corporation.
|
||||
*
|
||||
* 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.
|
||||
*
|
||||
*/
|
||||
|
||||
namespace QuantConnect.Algorithm.CSharp
|
||||
{
|
||||
/// <summary>
|
||||
/// Base class for regression algorithms testing that when a continuous future rollover happens,
|
||||
/// the continuous contract is updated correctly with the new contract data.
|
||||
/// The algorithms asserts the behavior for the case when the data time zone is the same as the exchange time zone.
|
||||
/// </summary>
|
||||
public class ContinuousFutureRolloverMinuteExchangeTimeZoneSameAsDataWithInitialSeedRegressionAlgorithm
|
||||
: ContinuousFutureRolloverMinuteExchangeTimeZoneSameAsDataRegressionAlgorithm
|
||||
{
|
||||
protected override bool SeedIntialPrices => true;
|
||||
|
||||
/// <summary>
|
||||
/// Data Points count of the algorithm history
|
||||
/// </summary>
|
||||
public override int AlgorithmHistoryDataPoints => 668;
|
||||
}
|
||||
}
|
||||
@@ -138,10 +138,10 @@ namespace QuantConnect.Algorithm.CSharp
|
||||
{"Treynor Ratio", "0"},
|
||||
{"Total Fees", "$4.60"},
|
||||
{"Estimated Strategy Capacity", "$120000.00"},
|
||||
{"Lowest Capacity Asset", "GOOCV WBGM92QHIYO6|GOOCV VP83T1ZUHROL"},
|
||||
{"Lowest Capacity Asset", "GOOCV WBGM92QHN8ZQ|GOOCV VP83T1ZUHROL"},
|
||||
{"Portfolio Turnover", "32.18%"},
|
||||
{"Drawdown Recovery", "0"},
|
||||
{"OrderListHash", "c0e25967c528ec4b1281f25a7735ed92"}
|
||||
{"OrderListHash", "f8b1dfb65e4795a7929e7f3a3edd0205"}
|
||||
};
|
||||
}
|
||||
}
|
||||
|
||||
@@ -138,10 +138,10 @@ namespace QuantConnect.Algorithm.CSharp
|
||||
{"Treynor Ratio", "0"},
|
||||
{"Total Fees", "$4.60"},
|
||||
{"Estimated Strategy Capacity", "$160000.00"},
|
||||
{"Lowest Capacity Asset", "GOOCV 30AKMEIPOSS1Y|GOOCV VP83T1ZUHROL"},
|
||||
{"Lowest Capacity Asset", "GOOCV 30AKMEIPOX2DI|GOOCV VP83T1ZUHROL"},
|
||||
{"Portfolio Turnover", "32.12%"},
|
||||
{"Drawdown Recovery", "0"},
|
||||
{"OrderListHash", "6a09be0b3b0ec11848f3b2c520234332"}
|
||||
{"OrderListHash", "3f95cba29e9c396bc19c0d47a889dbfb"}
|
||||
};
|
||||
}
|
||||
}
|
||||
|
||||
@@ -43,7 +43,7 @@ namespace QuantConnect.Algorithm.CSharp
|
||||
var option = AddOption(equity.Symbol);
|
||||
_optionSymbol = option.Symbol;
|
||||
|
||||
option.SetFilter(u => u.Strikes(-1, +1).Expiration(0, 30));
|
||||
option.SetFilter(u => u.StandardsOnly().Strikes(-1, +1).Expiration(0, 30));
|
||||
}
|
||||
/// <summary>
|
||||
/// OnData event is the primary entry point for your algorithm. Each new data point will be pumped in here.
|
||||
@@ -70,7 +70,7 @@ namespace QuantConnect.Algorithm.CSharp
|
||||
var legs = new List<Leg> { Leg.Create(atmContract.Symbol, -1), Leg.Create(atmContract.Symbol.Underlying, 100) };
|
||||
|
||||
var comboPrice = underlyingPrice - optionPrice;
|
||||
if(comboPrice < 734m)
|
||||
if (comboPrice < 734m)
|
||||
{
|
||||
// just to make sure the price makes sense
|
||||
throw new RegressionTestException($"Unexpected combo price {comboPrice}");
|
||||
@@ -147,10 +147,10 @@ namespace QuantConnect.Algorithm.CSharp
|
||||
{"Treynor Ratio", "0"},
|
||||
{"Total Fees", "$6.90"},
|
||||
{"Estimated Strategy Capacity", "$8000.00"},
|
||||
{"Lowest Capacity Asset", "GOOCV W78ZFMEBBB2E|GOOCV VP83T1ZUHROL"},
|
||||
{"Lowest Capacity Asset", "GOOCV W78ZFMEBFLDY|GOOCV VP83T1ZUHROL"},
|
||||
{"Portfolio Turnover", "227.27%"},
|
||||
{"Drawdown Recovery", "0"},
|
||||
{"OrderListHash", "94a9ae926f68c23d06d32af2b5a25fea"}
|
||||
{"OrderListHash", "e36c11e174486d80060855efed57a2a9"}
|
||||
};
|
||||
}
|
||||
}
|
||||
|
||||
@@ -63,7 +63,7 @@ namespace QuantConnect.Algorithm.CSharp
|
||||
{"Tracking Error", "0"},
|
||||
{"Treynor Ratio", "0"},
|
||||
{"Total Fees", "$0.15"},
|
||||
{"Estimated Strategy Capacity", "$3400000000.00"},
|
||||
{"Estimated Strategy Capacity", "$4300000000.00"},
|
||||
{"Lowest Capacity Asset", "ADAUSDT 18R"},
|
||||
{"Portfolio Turnover", "0.02%"},
|
||||
{"Drawdown Recovery", "0"},
|
||||
|
||||
@@ -167,7 +167,7 @@ namespace QuantConnect.Algorithm.CSharp
|
||||
{"Tracking Error", "0"},
|
||||
{"Treynor Ratio", "0"},
|
||||
{"Total Fees", "$0.15"},
|
||||
{"Estimated Strategy Capacity", "$330000000.00"},
|
||||
{"Estimated Strategy Capacity", "$410000000.00"},
|
||||
{"Lowest Capacity Asset", "ADAUSDT 18R"},
|
||||
{"Portfolio Turnover", "0.02%"},
|
||||
{"Drawdown Recovery", "0"},
|
||||
|
||||
@@ -0,0 +1,170 @@
|
||||
/*
|
||||
* QUANTCONNECT.COM - Democratizing Finance, Empowering Individuals.
|
||||
* Lean Algorithmic Trading Engine v2.0. Copyright 2014 QuantConnect Corporation.
|
||||
*
|
||||
* 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.
|
||||
*/
|
||||
|
||||
using QuantConnect.Brokerages;
|
||||
using QuantConnect.Data;
|
||||
using QuantConnect.Interfaces;
|
||||
using QuantConnect.Securities.CryptoFuture;
|
||||
using System.Collections.Generic;
|
||||
|
||||
namespace QuantConnect.Algorithm.CSharp
|
||||
{
|
||||
/// <summary>
|
||||
/// Regression algorithm asserting that margin used and margin remaining update correctly when
|
||||
/// changing leverage on a crypto future
|
||||
/// </summary>
|
||||
public class CryptoFutureLeverageBasedMarginRegressionAlgorithm : QCAlgorithm, IRegressionAlgorithmDefinition
|
||||
{
|
||||
private CryptoFuture _cryptoFuture;
|
||||
|
||||
public override void Initialize()
|
||||
{
|
||||
SetStartDate(2022, 12, 13);
|
||||
SetEndDate(2022, 12, 13);
|
||||
|
||||
SetTimeZone(TimeZones.Utc);
|
||||
|
||||
SetAccountCurrency("USDT");
|
||||
SetCash(200);
|
||||
|
||||
SetBrokerageModel(BrokerageName.BinanceFutures, AccountType.Margin);
|
||||
|
||||
_cryptoFuture = AddCryptoFuture("ADAUSDT");
|
||||
_cryptoFuture.SetLeverage(10);
|
||||
}
|
||||
|
||||
public override void OnData(Slice slice)
|
||||
{
|
||||
if (_cryptoFuture.Price == 0)
|
||||
{
|
||||
return;
|
||||
}
|
||||
|
||||
if (!Portfolio.Invested)
|
||||
{
|
||||
SetHoldings(_cryptoFuture.Symbol, 10); // Buy all we can with our margin (leverage is 10)
|
||||
|
||||
var marginUsed = Portfolio.TotalMarginUsed;
|
||||
var marginRemaining = Portfolio.MarginRemaining;
|
||||
|
||||
if (marginRemaining > 0)
|
||||
{
|
||||
throw new RegressionTestException($"Expected no margin remaining after buying with full leverage. " +
|
||||
$"Actual margin remaining is {marginRemaining}");
|
||||
}
|
||||
|
||||
_cryptoFuture.SetLeverage(20);
|
||||
|
||||
var newMarginUsed = Portfolio.TotalMarginUsed;
|
||||
var newMarginRemaining = Portfolio.MarginRemaining;
|
||||
|
||||
if (newMarginUsed >= marginUsed)
|
||||
{
|
||||
throw new RegressionTestException($"Expected margin used to decrease after increasing leverage. " +
|
||||
$"Previous margin used: {marginUsed}, new margin used: {newMarginUsed}");
|
||||
}
|
||||
|
||||
if (newMarginRemaining <= 0 || newMarginRemaining <= marginRemaining)
|
||||
{
|
||||
throw new RegressionTestException($"Expected margin remaining to increase after increasing leverage. " +
|
||||
$"Previous margin remaining: {marginRemaining}, new margin remaining: {newMarginRemaining}");
|
||||
}
|
||||
|
||||
var holdingsQuantity = _cryptoFuture.Holdings.AbsoluteQuantity;
|
||||
|
||||
SetHoldings(_cryptoFuture.Symbol, 20); // Buy all we can with our margin (new leverage is 20)
|
||||
|
||||
var newHoldingsQuantity = _cryptoFuture.Holdings.AbsoluteQuantity;
|
||||
|
||||
if (newHoldingsQuantity <= holdingsQuantity)
|
||||
{
|
||||
throw new RegressionTestException($"Expected holdings quantity to increase after increasing leverage and buying more. " +
|
||||
$"Previous holdings quantity: {holdingsQuantity}, new holdings quantity: {newHoldingsQuantity}");
|
||||
}
|
||||
|
||||
newMarginRemaining = Portfolio.MarginRemaining;
|
||||
|
||||
if (marginRemaining > 0)
|
||||
{
|
||||
throw new RegressionTestException($"Expected no margin remaining after buying with full leverage. " +
|
||||
$"Actual margin remaining is {newMarginRemaining}");
|
||||
}
|
||||
|
||||
// We are done testing, exit the algorithm
|
||||
Quit();
|
||||
}
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// This is used by the regression test system to indicate if the open source Lean repository has the required data to run this algorithm.
|
||||
/// </summary>
|
||||
public bool CanRunLocally { get; } = true;
|
||||
|
||||
/// <summary>
|
||||
/// This is used by the regression test system to indicate which languages this algorithm is written in.
|
||||
/// </summary>
|
||||
public List<Language> Languages { get; } = new() { Language.CSharp };
|
||||
|
||||
/// <summary>
|
||||
/// Data Points count of all timeslices of algorithm
|
||||
/// </summary>
|
||||
public long DataPoints => 4;
|
||||
|
||||
/// <summary>
|
||||
/// Data Points count of the algorithm history
|
||||
/// </summary>
|
||||
public int AlgorithmHistoryDataPoints => 0;
|
||||
|
||||
/// <summary>
|
||||
/// Final status of the algorithm
|
||||
/// </summary>
|
||||
public AlgorithmStatus AlgorithmStatus => AlgorithmStatus.Completed;
|
||||
|
||||
/// <summary>
|
||||
/// This is used by the regression test system to indicate what the expected statistics are from running the algorithm
|
||||
/// </summary>
|
||||
public Dictionary<string, string> ExpectedStatistics => new Dictionary<string, string>
|
||||
{
|
||||
{"Total Orders", "2"},
|
||||
{"Average Win", "0%"},
|
||||
{"Average Loss", "0%"},
|
||||
{"Compounding Annual Return", "0%"},
|
||||
{"Drawdown", "0%"},
|
||||
{"Expectancy", "0"},
|
||||
{"Start Equity", "200"},
|
||||
{"End Equity", "195.58"},
|
||||
{"Net Profit", "0%"},
|
||||
{"Sharpe Ratio", "0"},
|
||||
{"Sortino Ratio", "0"},
|
||||
{"Probabilistic Sharpe Ratio", "0%"},
|
||||
{"Loss Rate", "0%"},
|
||||
{"Win Rate", "0%"},
|
||||
{"Profit-Loss Ratio", "0"},
|
||||
{"Alpha", "0"},
|
||||
{"Beta", "0"},
|
||||
{"Annual Standard Deviation", "0"},
|
||||
{"Annual Variance", "0"},
|
||||
{"Information Ratio", "0"},
|
||||
{"Tracking Error", "0"},
|
||||
{"Treynor Ratio", "0"},
|
||||
{"Total Fees", "₮1.57"},
|
||||
{"Estimated Strategy Capacity", "₮0"},
|
||||
{"Lowest Capacity Asset", "ADAUSDT 18R"},
|
||||
{"Portfolio Turnover", "2009.51%"},
|
||||
{"Drawdown Recovery", "0"},
|
||||
{"OrderListHash", "f92ad762f77fbf4ee13b1e89a78cb1eb"}
|
||||
};
|
||||
}
|
||||
}
|
||||
232
Algorithm.CSharp/CustomDataAutomaticSeedRegressionAlgorithm.cs
Normal file
232
Algorithm.CSharp/CustomDataAutomaticSeedRegressionAlgorithm.cs
Normal file
@@ -0,0 +1,232 @@
|
||||
/*
|
||||
* QUANTCONNECT.COM - Democratizing Finance, Empowering Individuals.
|
||||
* Lean Algorithmic Trading Engine v2.0. Copyright 2014 QuantConnect Corporation.
|
||||
*
|
||||
* 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.
|
||||
*/
|
||||
|
||||
using System;
|
||||
using System.Collections.Generic;
|
||||
using System.Globalization;
|
||||
using Newtonsoft.Json;
|
||||
using QuantConnect.Data;
|
||||
using QuantConnect.Interfaces;
|
||||
|
||||
namespace QuantConnect.Algorithm.CSharp
|
||||
{
|
||||
/// <summary>
|
||||
/// Regression test to assert that custom data is seeded by default
|
||||
/// </summary>
|
||||
public class CustomDataAutomaticSeedRegressionAlgorithm : QCAlgorithm, IRegressionAlgorithmDefinition
|
||||
{
|
||||
public override void Initialize()
|
||||
{
|
||||
SetStartDate(2020, 01, 05);
|
||||
SetEndDate(2020, 01, 10);
|
||||
SetCash(100000);
|
||||
|
||||
Settings.SeedInitialPrices = true;
|
||||
|
||||
var resolution = Resolution.Daily;
|
||||
var customData = AddData<Bitcoin>("BTC", resolution);
|
||||
|
||||
if (!customData.HasData || customData.Price == 0)
|
||||
{
|
||||
throw new RegressionTestException("Custom data was not seeded with data on addition");
|
||||
}
|
||||
|
||||
var seedData = customData.GetLastData();
|
||||
if (seedData is not Bitcoin)
|
||||
{
|
||||
throw new RegressionTestException("Custom data was not seeded with correct data type");
|
||||
}
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// This is used by the regression test system to indicate if the open source Lean repository has the required data to run this algorithm.
|
||||
/// </summary>
|
||||
public bool CanRunLocally { get; } = true;
|
||||
|
||||
/// <summary>
|
||||
/// This is used by the regression test system to indicate which languages this algorithm is written in.
|
||||
/// </summary>
|
||||
public List<Language> Languages { get; } = new() { Language.CSharp };
|
||||
|
||||
/// <summary>
|
||||
/// Data Points count of all timeslices of algorithm
|
||||
/// </summary>
|
||||
public long DataPoints => 50;
|
||||
|
||||
/// <summary>
|
||||
/// Data Points count of the algorithm history
|
||||
/// </summary>
|
||||
public int AlgorithmHistoryDataPoints => 5;
|
||||
|
||||
/// <summary>
|
||||
/// Final status of the algorithm
|
||||
/// </summary>
|
||||
public AlgorithmStatus AlgorithmStatus => AlgorithmStatus.Completed;
|
||||
|
||||
/// <summary>
|
||||
/// This is used by the regression test system to indicate what the expected statistics are from running the algorithm
|
||||
/// </summary>
|
||||
public Dictionary<string, string> ExpectedStatistics => new Dictionary<string, string>
|
||||
{
|
||||
{"Total Orders", "0"},
|
||||
{"Average Win", "0%"},
|
||||
{"Average Loss", "0%"},
|
||||
{"Compounding Annual Return", "0%"},
|
||||
{"Drawdown", "0%"},
|
||||
{"Expectancy", "0"},
|
||||
{"Start Equity", "100000"},
|
||||
{"End Equity", "100000"},
|
||||
{"Net Profit", "0%"},
|
||||
{"Sharpe Ratio", "0"},
|
||||
{"Sortino Ratio", "0"},
|
||||
{"Probabilistic Sharpe Ratio", "0%"},
|
||||
{"Loss Rate", "0%"},
|
||||
{"Win Rate", "0%"},
|
||||
{"Profit-Loss Ratio", "0"},
|
||||
{"Alpha", "0"},
|
||||
{"Beta", "0"},
|
||||
{"Annual Standard Deviation", "0"},
|
||||
{"Annual Variance", "0"},
|
||||
{"Information Ratio", "-9.259"},
|
||||
{"Tracking Error", "0.073"},
|
||||
{"Treynor Ratio", "0"},
|
||||
{"Total Fees", "$0.00"},
|
||||
{"Estimated Strategy Capacity", "$0"},
|
||||
{"Lowest Capacity Asset", ""},
|
||||
{"Portfolio Turnover", "0%"},
|
||||
{"Drawdown Recovery", "0"},
|
||||
{"OrderListHash", "d41d8cd98f00b204e9800998ecf8427e"}
|
||||
};
|
||||
|
||||
/// <summary>
|
||||
/// Custom Data Type: Bitcoin data from Quandl - http://www.quandl.com/help/api-for-bitcoin-data
|
||||
/// </summary>
|
||||
public class Bitcoin : BaseData
|
||||
{
|
||||
[JsonProperty("timestamp")]
|
||||
public int Timestamp { get; set; }
|
||||
[JsonProperty("open")]
|
||||
public decimal Open { get; set; }
|
||||
[JsonProperty("high")]
|
||||
public decimal High { get; set; }
|
||||
[JsonProperty("low")]
|
||||
public decimal Low { get; set; }
|
||||
public decimal Mid { get; set; }
|
||||
|
||||
[JsonProperty("last")]
|
||||
public decimal Close { get; set; }
|
||||
[JsonProperty("bid")]
|
||||
public decimal Bid { get; set; }
|
||||
[JsonProperty("ask")]
|
||||
public decimal Ask { get; set; }
|
||||
[JsonProperty("vwap")]
|
||||
public decimal WeightedPrice { get; set; }
|
||||
[JsonProperty("volume")]
|
||||
public decimal VolumeBTC { get; set; }
|
||||
|
||||
/// <summary>
|
||||
/// The end time of this data. Some data covers spans (trade bars)
|
||||
/// and as such we want to know the entire time span covered
|
||||
/// </summary>
|
||||
/// <remarks>
|
||||
/// This property is overriden to allow different values for Time and EndTime
|
||||
/// if they are set in the Reader. In the base implementation EndTime equals Time
|
||||
/// </remarks>
|
||||
public override DateTime EndTime { get; set; }
|
||||
|
||||
/// <summary>
|
||||
/// 1. DEFAULT CONSTRUCTOR: Custom data types need a default constructor.
|
||||
/// We search for a default constructor so please provide one here. It won't be used for data, just to generate the "Factory".
|
||||
/// </summary>
|
||||
public Bitcoin()
|
||||
{
|
||||
Symbol = "BTC";
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// 2. RETURN THE STRING URL SOURCE LOCATION FOR YOUR DATA:
|
||||
/// This is a powerful and dynamic select source file method. If you have a large dataset, 10+mb we recommend you break it into smaller files. E.g. One zip per year.
|
||||
/// We can accept raw text or ZIP files. We read the file extension to determine if it is a zip file.
|
||||
/// </summary>
|
||||
/// <param name="config">Configuration object</param>
|
||||
/// <param name="date">Date of this source file</param>
|
||||
/// <param name="isLiveMode">true if we're in live mode, false for backtesting mode</param>
|
||||
/// <returns>String URL of source file.</returns>
|
||||
public override SubscriptionDataSource GetSource(SubscriptionDataConfig config, DateTime date, bool isLiveMode)
|
||||
{
|
||||
if (isLiveMode)
|
||||
{
|
||||
return new SubscriptionDataSource("https://www.bitstamp.net/api/ticker/", SubscriptionTransportMedium.Rest);
|
||||
}
|
||||
|
||||
//return "http://my-ftp-server.com/futures-data-" + date.ToString("Ymd") + ".zip";
|
||||
// OR simply return a fixed small data file. Large files will slow down your backtest
|
||||
return new SubscriptionDataSource("https://www.quantconnect.com/api/v2/proxy/nasdaq/api/v3/datatables/QDL/BITFINEX.csv?code=BTCUSD&api_key=qAWKpUfmSVFnU3bRQwKy")
|
||||
{
|
||||
Sort = true
|
||||
};
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// 3. READER METHOD: Read 1 line from data source and convert it into Object.
|
||||
/// Each line of the CSV File is presented in here. The backend downloads your file, loads it into memory and then line by line
|
||||
/// feeds it into your algorithm
|
||||
/// </summary>
|
||||
/// <param name="line">string line from the data source file submitted above</param>
|
||||
/// <param name="config">Subscription data, symbol name, data type</param>
|
||||
/// <param name="date">Current date we're requesting. This allows you to break up the data source into daily files.</param>
|
||||
/// <param name="isLiveMode">true if we're in live mode, false for backtesting mode</param>
|
||||
/// <returns>New Bitcoin Object which extends BaseData.</returns>
|
||||
public override BaseData Reader(SubscriptionDataConfig config, string line, DateTime date, bool isLiveMode)
|
||||
{
|
||||
var coin = new Bitcoin();
|
||||
if (isLiveMode)
|
||||
{
|
||||
//Example Line Format:
|
||||
//{"high": "441.00", "last": "421.86", "timestamp": "1411606877", "bid": "421.96", "vwap": "428.58", "volume": "14120.40683975", "low": "418.83", "ask": "421.99"}
|
||||
try
|
||||
{
|
||||
coin = JsonConvert.DeserializeObject<Bitcoin>(line);
|
||||
coin.EndTime = DateTime.UtcNow.ConvertFromUtc(config.ExchangeTimeZone);
|
||||
coin.Value = coin.Close;
|
||||
}
|
||||
catch { /* Do nothing, possible error in json decoding */ }
|
||||
return coin;
|
||||
}
|
||||
|
||||
//Example Line Format:
|
||||
// code date high low mid last bid ask volume
|
||||
// BTCUSD 2024-10-08 63248.0 61940.0 62246.5 62245.0 62246.0 62247.0 477.91102114
|
||||
try
|
||||
{
|
||||
string[] data = line.Split(',');
|
||||
coin.Time = DateTime.Parse(data[1], CultureInfo.InvariantCulture);
|
||||
coin.EndTime = coin.Time.AddDays(1);
|
||||
coin.High = Convert.ToDecimal(data[2], CultureInfo.InvariantCulture);
|
||||
coin.Low = Convert.ToDecimal(data[3], CultureInfo.InvariantCulture);
|
||||
coin.Mid = Convert.ToDecimal(data[4], CultureInfo.InvariantCulture);
|
||||
coin.Close = Convert.ToDecimal(data[5], CultureInfo.InvariantCulture);
|
||||
coin.Bid = Convert.ToDecimal(data[6], CultureInfo.InvariantCulture);
|
||||
coin.Ask = Convert.ToDecimal(data[7], CultureInfo.InvariantCulture);
|
||||
coin.VolumeBTC = Convert.ToDecimal(data[8], CultureInfo.InvariantCulture);
|
||||
coin.Value = coin.Close;
|
||||
}
|
||||
catch { /* Do nothing, skip first title row */ }
|
||||
|
||||
return coin;
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
@@ -198,7 +198,6 @@ namespace QuantConnect.Algorithm.CSharp
|
||||
/// </summary>
|
||||
public Bitcoin()
|
||||
{
|
||||
Symbol = "BTC";
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
@@ -237,7 +236,7 @@ namespace QuantConnect.Algorithm.CSharp
|
||||
/// <returns>New Bitcoin Object which extends BaseData.</returns>
|
||||
public override BaseData Reader(SubscriptionDataConfig config, string line, DateTime date, bool isLiveMode)
|
||||
{
|
||||
var coin = new Bitcoin();
|
||||
var coin = new Bitcoin() { Symbol = config.Symbol };
|
||||
if (isLiveMode)
|
||||
{
|
||||
//Example Line Format:
|
||||
|
||||
@@ -0,0 +1,121 @@
|
||||
/*
|
||||
* QUANTCONNECT.COM - Democratizing Finance, Empowering Individuals.
|
||||
* Lean Algorithmic Trading Engine v2.0. Copyright 2014 QuantConnect Corporation.
|
||||
*
|
||||
* 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.
|
||||
*/
|
||||
|
||||
using System.Collections.Generic;
|
||||
using System.Linq;
|
||||
using QuantConnect.Data;
|
||||
using QuantConnect.Interfaces;
|
||||
using QuantConnect.Securities;
|
||||
using static QuantConnect.Algorithm.CSharp.CustomDataRegressionAlgorithm;
|
||||
|
||||
|
||||
namespace QuantConnect.Algorithm.CSharp
|
||||
{
|
||||
/// <summary>
|
||||
/// Regression algorithm used to verify that GetData<T> correctly retrieves
|
||||
/// the latest custom data stored in the security cache.
|
||||
/// </summary>
|
||||
public class CustomDataSecurityCacheGetDataRegressionAlgorithm : QCAlgorithm, IRegressionAlgorithmDefinition
|
||||
{
|
||||
public override void Initialize()
|
||||
{
|
||||
SetStartDate(2020, 01, 05);
|
||||
SetEndDate(2020, 01, 10);
|
||||
|
||||
AddData<Bitcoin>("BTC", Resolution.Daily);
|
||||
|
||||
var seeder = new FuncSecuritySeeder(GetLastKnownPrices);
|
||||
SetSecurityInitializer(security => seeder.SeedSecurity(security));
|
||||
}
|
||||
|
||||
public override void OnData(Slice slice)
|
||||
{
|
||||
var bitcoin = Securities["BTC"].Cache.GetData<Bitcoin>();
|
||||
if (bitcoin == null)
|
||||
{
|
||||
throw new RegressionTestException("Expected Bitcoin data in cache, but none was found");
|
||||
}
|
||||
if (bitcoin.Value == 0)
|
||||
{
|
||||
throw new RegressionTestException("Expected Bitcoin value to be non-zero");
|
||||
}
|
||||
var bitcoinFromSlice = slice.Get<Bitcoin>().Values.FirstOrDefault();
|
||||
if (bitcoinFromSlice != bitcoin)
|
||||
{
|
||||
throw new RegressionTestException("Expected cached Bitcoin to match the one from Slice");
|
||||
}
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// This is used by the regression test system to indicate if the open source Lean repository has the required data to run this algorithm.
|
||||
/// </summary>
|
||||
public bool CanRunLocally { get; } = true;
|
||||
|
||||
/// <summary>
|
||||
/// This is used by the regression test system to indicate which languages this algorithm is written in.
|
||||
/// </summary>
|
||||
public List<Language> Languages { get; } = new() { Language.CSharp, Language.Python };
|
||||
|
||||
/// <summary>
|
||||
/// Data Points count of all timeslices of algorithm
|
||||
/// </summary>
|
||||
public long DataPoints => 50;
|
||||
|
||||
/// <summary>
|
||||
/// Data Points count of the algorithm history
|
||||
/// </summary>
|
||||
public int AlgorithmHistoryDataPoints => 0;
|
||||
|
||||
/// <summary>
|
||||
/// Final status of the algorithm
|
||||
/// </summary>
|
||||
public AlgorithmStatus AlgorithmStatus => AlgorithmStatus.Completed;
|
||||
|
||||
/// <summary>
|
||||
/// This is used by the regression test system to indicate what the expected statistics are from running the algorithm
|
||||
/// </summary>
|
||||
public Dictionary<string, string> ExpectedStatistics => new Dictionary<string, string>
|
||||
{
|
||||
{"Total Orders", "0"},
|
||||
{"Average Win", "0%"},
|
||||
{"Average Loss", "0%"},
|
||||
{"Compounding Annual Return", "0%"},
|
||||
{"Drawdown", "0%"},
|
||||
{"Expectancy", "0"},
|
||||
{"Start Equity", "100000"},
|
||||
{"End Equity", "100000"},
|
||||
{"Net Profit", "0%"},
|
||||
{"Sharpe Ratio", "0"},
|
||||
{"Sortino Ratio", "0"},
|
||||
{"Probabilistic Sharpe Ratio", "0%"},
|
||||
{"Loss Rate", "0%"},
|
||||
{"Win Rate", "0%"},
|
||||
{"Profit-Loss Ratio", "0"},
|
||||
{"Alpha", "0"},
|
||||
{"Beta", "0"},
|
||||
{"Annual Standard Deviation", "0"},
|
||||
{"Annual Variance", "0"},
|
||||
{"Information Ratio", "-9.259"},
|
||||
{"Tracking Error", "0.073"},
|
||||
{"Treynor Ratio", "0"},
|
||||
{"Total Fees", "$0.00"},
|
||||
{"Estimated Strategy Capacity", "$0"},
|
||||
{"Lowest Capacity Asset", ""},
|
||||
{"Portfolio Turnover", "0%"},
|
||||
{"Drawdown Recovery", "0"},
|
||||
{"OrderListHash", "d41d8cd98f00b204e9800998ecf8427e"}
|
||||
};
|
||||
}
|
||||
}
|
||||
@@ -83,7 +83,7 @@ namespace QuantConnect.Algorithm.CSharp
|
||||
/// <summary>
|
||||
/// Data Points count of the algorithm history
|
||||
/// </summary>
|
||||
public int AlgorithmHistoryDataPoints => 60;
|
||||
public int AlgorithmHistoryDataPoints => 5;
|
||||
|
||||
/// <summary>
|
||||
/// Final status of the algorithm
|
||||
|
||||
@@ -83,10 +83,10 @@ namespace QuantConnect.Algorithm.CSharp
|
||||
{"Treynor Ratio", "-0.115"},
|
||||
{"Total Fees", "$2.00"},
|
||||
{"Estimated Strategy Capacity", "$4800000.00"},
|
||||
{"Lowest Capacity Asset", "GOOCV 305RBQ20WHPNQ|GOOCV VP83T1ZUHROL"},
|
||||
{"Lowest Capacity Asset", "GOOCV 305RBQ20WLZZA|GOOCV VP83T1ZUHROL"},
|
||||
{"Portfolio Turnover", "26.72%"},
|
||||
{"Drawdown Recovery", "0"},
|
||||
{"OrderListHash", "fb2bef182af109f6441ae739d826f39f"}
|
||||
{"OrderListHash", "20f33e143b62ee896aa56f85dd2aa2e8"}
|
||||
};
|
||||
}
|
||||
}
|
||||
|
||||
@@ -91,10 +91,10 @@ namespace QuantConnect.Algorithm.CSharp
|
||||
{"Treynor Ratio", "-3.295"},
|
||||
{"Total Fees", "$16.00"},
|
||||
{"Estimated Strategy Capacity", "$87000.00"},
|
||||
{"Lowest Capacity Asset", "GOOCV 305RBQ20WHPNQ|GOOCV VP83T1ZUHROL"},
|
||||
{"Lowest Capacity Asset", "GOOCV 305RBQ20WLZZA|GOOCV VP83T1ZUHROL"},
|
||||
{"Portfolio Turnover", "10.93%"},
|
||||
{"Drawdown Recovery", "0"},
|
||||
{"OrderListHash", "8133cb99a1a9f9e9335bc98def3cc624"}
|
||||
{"OrderListHash", "19b8f2a8081c3cfa8f6bc02b5d045765"}
|
||||
};
|
||||
}
|
||||
}
|
||||
|
||||
@@ -1,4 +1,4 @@
|
||||
/*
|
||||
/*
|
||||
* QUANTCONNECT.COM - Democratizing Finance, Empowering Individuals.
|
||||
* Lean Algorithmic Trading Engine v2.0. Copyright 2014 QuantConnect Corporation.
|
||||
*
|
||||
|
||||
128
Algorithm.CSharp/DYDXCryptoFuturesRegressionAlgorithm.cs
Normal file
128
Algorithm.CSharp/DYDXCryptoFuturesRegressionAlgorithm.cs
Normal file
@@ -0,0 +1,128 @@
|
||||
/*
|
||||
* QUANTCONNECT.COM - Democratizing Finance, Empowering Individuals.
|
||||
* Lean Algorithmic Trading Engine v2.0. Copyright 2014 QuantConnect Corporation.
|
||||
*
|
||||
* 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.
|
||||
*/
|
||||
|
||||
using System;
|
||||
using QuantConnect.Data;
|
||||
using QuantConnect.Interfaces;
|
||||
using System.Collections.Generic;
|
||||
using QuantConnect.Securities.CryptoFuture;
|
||||
|
||||
namespace QuantConnect.Algorithm.CSharp
|
||||
{
|
||||
/// <summary>
|
||||
/// Regression algorithm asserting DYDX Crypto Future support
|
||||
/// </summary>
|
||||
public class DYDXCryptoFuturesRegressionAlgorithm : QCAlgorithm, IRegressionAlgorithmDefinition
|
||||
{
|
||||
private CryptoFuture _cryptoFuture;
|
||||
|
||||
/// <summary>
|
||||
/// Initialise the data and resolution required, as well as the cash and start-end dates for your algorithm. All algorithms must initialized.
|
||||
/// </summary>
|
||||
public override void Initialize()
|
||||
{
|
||||
SetStartDate(2026, 1, 1);
|
||||
SetEndDate(2026, 1, 1);
|
||||
|
||||
SetBrokerageModel(Brokerages.BrokerageName.DYDX, AccountType.Margin);
|
||||
_cryptoFuture = AddCryptoFuture("BTCUSD");
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// OnData event is the primary entry point for your algorithm. Each new data point will be pumped in here.
|
||||
/// </summary>
|
||||
/// <param name="data">Slice object keyed by symbol containing the stock data</param>
|
||||
public override void OnData(Slice slice)
|
||||
{
|
||||
if (!Portfolio.Invested)
|
||||
{
|
||||
Buy("BTCUSD", 1);
|
||||
}
|
||||
else
|
||||
{
|
||||
if (Math.Abs(Portfolio.TotalFees - Portfolio.TotalHoldingsValue * 0.0005m) > 1
|
||||
|| Math.Abs(Portfolio.TotalFees - _cryptoFuture.Price * 0.0005m) > 1)
|
||||
{
|
||||
throw new RegressionTestException("Unexpected fees value!");
|
||||
}
|
||||
if (Math.Abs(Portfolio.TotalHoldingsValue - _cryptoFuture.Price) > 1)
|
||||
{
|
||||
throw new RegressionTestException("Unexpected holdings value!");
|
||||
}
|
||||
Quit();
|
||||
}
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// This is used by the regression test system to indicate if the open source Lean repository has the required data to run this algorithm.
|
||||
/// </summary>
|
||||
public bool CanRunLocally { get; } = true;
|
||||
|
||||
/// <summary>
|
||||
/// This is used by the regression test system to indicate which languages this algorithm is written in.
|
||||
/// </summary>
|
||||
public List<Language> Languages { get; } = new() { Language.CSharp };
|
||||
|
||||
/// <summary>
|
||||
/// Data Points count of all timeslices of algorithm
|
||||
/// </summary>
|
||||
public long DataPoints => 5;
|
||||
|
||||
/// <summary>
|
||||
/// Data Points count of the algorithm history
|
||||
/// </summary>
|
||||
public int AlgorithmHistoryDataPoints => 15;
|
||||
|
||||
/// <summary>
|
||||
/// Final status of the algorithm
|
||||
/// </summary>
|
||||
public AlgorithmStatus AlgorithmStatus => AlgorithmStatus.Completed;
|
||||
|
||||
/// <summary>
|
||||
/// This is used by the regression test system to indicate what the expected statistics are from running the algorithm
|
||||
/// </summary>
|
||||
public Dictionary<string, string> ExpectedStatistics => new Dictionary<string, string>
|
||||
{
|
||||
{"Total Orders", "1"},
|
||||
{"Average Win", "0%"},
|
||||
{"Average Loss", "0%"},
|
||||
{"Compounding Annual Return", "0%"},
|
||||
{"Drawdown", "0%"},
|
||||
{"Expectancy", "0"},
|
||||
{"Start Equity", "100000"},
|
||||
{"End Equity", "99929.57"},
|
||||
{"Net Profit", "0%"},
|
||||
{"Sharpe Ratio", "0"},
|
||||
{"Sortino Ratio", "0"},
|
||||
{"Probabilistic Sharpe Ratio", "0%"},
|
||||
{"Loss Rate", "0%"},
|
||||
{"Win Rate", "0%"},
|
||||
{"Profit-Loss Ratio", "0"},
|
||||
{"Alpha", "0"},
|
||||
{"Beta", "0"},
|
||||
{"Annual Standard Deviation", "0"},
|
||||
{"Annual Variance", "0"},
|
||||
{"Information Ratio", "0"},
|
||||
{"Tracking Error", "0"},
|
||||
{"Treynor Ratio", "0"},
|
||||
{"Total Fees", "$43.71"},
|
||||
{"Estimated Strategy Capacity", "$33000.00"},
|
||||
{"Lowest Capacity Asset", "BTCUSD 38Z"},
|
||||
{"Portfolio Turnover", "87.48%"},
|
||||
{"Drawdown Recovery", "0"},
|
||||
{"OrderListHash", "637a937cda83ce88d29a3b279832401d"}
|
||||
};
|
||||
}
|
||||
}
|
||||
@@ -101,7 +101,7 @@ namespace QuantConnect.Algorithm.CSharp
|
||||
/// <summary>
|
||||
/// Data Points count of the algorithm history
|
||||
/// </summary>
|
||||
public int AlgorithmHistoryDataPoints => 564;
|
||||
public int AlgorithmHistoryDataPoints => 458;
|
||||
|
||||
/// <summary>
|
||||
/// Final status of the algorithm
|
||||
|
||||
Some files were not shown because too many files have changed in this diff Show More
Reference in New Issue
Block a user