Compare commits
2 Commits
2b9254f217
...
ab4375489a
Author | SHA1 | Date |
---|---|---|
|
ab4375489a | |
|
69660230c2 |
|
@ -1,4 +1,5 @@
|
||||||
using System;
|
using KLHZ.Trader.Core.Contracts.Declisions.Dtos;
|
||||||
|
using System;
|
||||||
using System.Collections.Generic;
|
using System.Collections.Generic;
|
||||||
using System.Linq;
|
using System.Linq;
|
||||||
using System.Text;
|
using System.Text;
|
||||||
|
@ -8,6 +9,12 @@ namespace KLHZ.Trader.Core.Math.Declisions.Utils
|
||||||
{
|
{
|
||||||
public static class Statistics
|
public static class Statistics
|
||||||
{
|
{
|
||||||
|
|
||||||
|
public static decimal Mean(this CachedValue[] values)
|
||||||
|
{
|
||||||
|
return values.Sum(x => x.Value)/ values.Length;
|
||||||
|
}
|
||||||
|
|
||||||
private static (decimal mean, decimal std) CaclSigma(decimal[] values)
|
private static (decimal mean, decimal std) CaclSigma(decimal[] values)
|
||||||
{
|
{
|
||||||
var mean = values.Sum() / values.Length;
|
var mean = values.Sum() / values.Length;
|
||||||
|
|
|
@ -227,7 +227,8 @@ namespace KLHZ.Trader.Core.Exchange.Services
|
||||||
AsksCount = asks.Length,
|
AsksCount = asks.Length,
|
||||||
BidsCount = asks.Length,
|
BidsCount = asks.Length,
|
||||||
};
|
};
|
||||||
await _tradeDataProvider.AddOrderbook(message);
|
|
||||||
|
await _eventBus.Broadcast(message);
|
||||||
}
|
}
|
||||||
|
|
||||||
if (orderbookItemsBuffer.Count + pricesBuffer.Count > 100 || (DateTime.UtcNow - lastWrite).TotalSeconds > 5)
|
if (orderbookItemsBuffer.Count + pricesBuffer.Count > 100 || (DateTime.UtcNow - lastWrite).TotalSeconds > 5)
|
||||||
|
|
|
@ -38,6 +38,7 @@ namespace KLHZ.Trader.Core.Exchange.Services
|
||||||
|
|
||||||
private readonly ConcurrentDictionary<string, TradingEvent> LastTradingEvents = new();
|
private readonly ConcurrentDictionary<string, TradingEvent> LastTradingEvents = new();
|
||||||
private readonly ConcurrentDictionary<string, TradingMode> TradingModes = new();
|
private readonly ConcurrentDictionary<string, TradingMode> TradingModes = new();
|
||||||
|
private readonly ConcurrentDictionary<string, IOrderbook> OrderBooks = new();
|
||||||
|
|
||||||
private readonly ConcurrentDictionary<string, DateTime> LongOpeningStops = new();
|
private readonly ConcurrentDictionary<string, DateTime> LongOpeningStops = new();
|
||||||
private readonly ConcurrentDictionary<string, DateTime> ShortOpeningStops = new();
|
private readonly ConcurrentDictionary<string, DateTime> ShortOpeningStops = new();
|
||||||
|
@ -55,6 +56,7 @@ namespace KLHZ.Trader.Core.Exchange.Services
|
||||||
|
|
||||||
private readonly Channel<INewPrice> _pricesChannel = Channel.CreateUnbounded<INewPrice>();
|
private readonly Channel<INewPrice> _pricesChannel = Channel.CreateUnbounded<INewPrice>();
|
||||||
private readonly Channel<ITradeCommand> _commands = Channel.CreateUnbounded<ITradeCommand>();
|
private readonly Channel<ITradeCommand> _commands = Channel.CreateUnbounded<ITradeCommand>();
|
||||||
|
private readonly Channel<IOrderbook> _orderbooks = Channel.CreateUnbounded<IOrderbook>();
|
||||||
public Trader(
|
public Trader(
|
||||||
ILogger<Trader> logger,
|
ILogger<Trader> logger,
|
||||||
IOptions<ExchangeConfig> options,
|
IOptions<ExchangeConfig> options,
|
||||||
|
@ -86,9 +88,10 @@ namespace KLHZ.Trader.Core.Exchange.Services
|
||||||
public Task StartAsync(CancellationToken cancellationToken)
|
public Task StartAsync(CancellationToken cancellationToken)
|
||||||
{
|
{
|
||||||
_dataBus.AddChannel(nameof(Trader), _pricesChannel);
|
_dataBus.AddChannel(nameof(Trader), _pricesChannel);
|
||||||
//_dataBus.AddChannel(nameof(Trader), _ordersbookChannel);
|
_dataBus.AddChannel(nameof(Trader), _orderbooks);
|
||||||
_dataBus.AddChannel(nameof(Trader), _commands);
|
_dataBus.AddChannel(nameof(Trader), _commands);
|
||||||
_ = ProcessPrices();
|
_ = ProcessPrices();
|
||||||
|
_ = ProcessOrderbooks();
|
||||||
_ = ProcessCommands();
|
_ = ProcessCommands();
|
||||||
return Task.CompletedTask;
|
return Task.CompletedTask;
|
||||||
}
|
}
|
||||||
|
@ -246,6 +249,43 @@ namespace KLHZ.Trader.Core.Exchange.Services
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
private async Task ProcessOrderbooks()
|
||||||
|
{
|
||||||
|
while (await _orderbooks.Reader.WaitToReadAsync())
|
||||||
|
{
|
||||||
|
var message = await _orderbooks.Reader.ReadAsync();
|
||||||
|
await _tradeDataProvider.AddOrderbook(message);
|
||||||
|
|
||||||
|
//if (OrderBooks.TryGetValue(message.Figi, out var oldMessage))
|
||||||
|
//{
|
||||||
|
// if (message.Bids.Length > 0 && oldMessage.Bids.Length>0)
|
||||||
|
// {
|
||||||
|
// var val = message.Bids[0].Count - oldMessage.Bids[0].Count;
|
||||||
|
// await _tradeDataProvider.AddDataTo20SecondsWindowCache(message.Figi, "dbids0", new Contracts.Declisions.Dtos.CachedValue()
|
||||||
|
// {
|
||||||
|
// Time = message.Time,
|
||||||
|
// Value = val
|
||||||
|
// });
|
||||||
|
// if (val!=0)
|
||||||
|
// await LogPrice(message.Figi, message.Ticker, message.Time, val, "bids0");
|
||||||
|
// }
|
||||||
|
// if (message.Asks.Length > 0 && oldMessage.Asks.Length > 0)
|
||||||
|
// {
|
||||||
|
// var val = message.Asks[0].Count - oldMessage.Asks[0].Count;
|
||||||
|
// await _tradeDataProvider.AddDataTo20SecondsWindowCache(message.Figi, "dasks0", new Contracts.Declisions.Dtos.CachedValue()
|
||||||
|
// {
|
||||||
|
// Time = message.Time,
|
||||||
|
// Value = val
|
||||||
|
// });
|
||||||
|
// if (val != 0)
|
||||||
|
// await LogPrice(message.Figi, message.Ticker, message.Time, val, "asks0");
|
||||||
|
// }
|
||||||
|
|
||||||
|
//}
|
||||||
|
OrderBooks[message.Figi] = message;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
private async Task ProcessPrices()
|
private async Task ProcessPrices()
|
||||||
{
|
{
|
||||||
var pricesCache1 = new Dictionary<string, List<INewPrice>>();
|
var pricesCache1 = new Dictionary<string, List<INewPrice>>();
|
||||||
|
@ -600,9 +640,16 @@ namespace KLHZ.Trader.Core.Exchange.Services
|
||||||
if (changemodes.Length > 1)
|
if (changemodes.Length > 1)
|
||||||
{
|
{
|
||||||
|
|
||||||
await LogPrice(message, "changemode", changemodes[changemodes.Length - 1].Value - changemodes[changemodes.Length - 2].Value);
|
await LogPrice(message, "changemode", changeModIndicator);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
//var sells20 = await _tradeDataProvider.GetDataFrom20SecondsWindowCache(message.Figi, "2");
|
||||||
|
//var buys20 = await _tradeDataProvider.GetDataFrom20SecondsWindowCache(message.Figi, "1");
|
||||||
|
|
||||||
|
//if (sells20.Length>0)
|
||||||
|
// await LogPrice(message.Figi, message.Ticker, message.Time, sells20.Sum(v => v.Value), "sells20");
|
||||||
|
//if (buys20.Length > 0)
|
||||||
|
// await LogPrice(message.Figi, message.Ticker, message.Time, buys20.Sum(v => v.Value), "buys20");
|
||||||
//if (changemodes[changemodes.Length-1].Time - changemodes[0].Time > TimeSpan.FromMinutes(10))
|
//if (changemodes[changemodes.Length-1].Time - changemodes[0].Time > TimeSpan.FromMinutes(10))
|
||||||
//{
|
//{
|
||||||
// var diffs = SignalProcessing.CalcDiffs(changemodes.Select(c => c.Value).ToArray());
|
// var diffs = SignalProcessing.CalcDiffs(changemodes.Select(c => c.Value).ToArray());
|
||||||
|
@ -851,7 +898,7 @@ INewPrice message, int windowMaxSize, decimal? uptrendStartingDetectionMeanfullS
|
||||||
// result = MergeResultsMax(result, getLocalTrendsModsTask.Result);
|
// result = MergeResultsMax(result, getLocalTrendsModsTask.Result);
|
||||||
//result = MergeResultsMult(result, getFFTModsTask.Result);
|
//result = MergeResultsMult(result, getFFTModsTask.Result);
|
||||||
//result = MergeResultsMult(result, getSellsDiffsModsTask.Result);
|
//result = MergeResultsMult(result, getSellsDiffsModsTask.Result);
|
||||||
//result = MergeResultsMult(result, getTradingModeModsTask.Result);
|
result = MergeResultsMult(result, getTradingModeModsTask.Result);
|
||||||
result = MergeResultsMult(result, getSpeedResultantModsTask.Result);
|
result = MergeResultsMult(result, getSpeedResultantModsTask.Result);
|
||||||
|
|
||||||
if (result[TradingEvent.UptrendStart] >= Constants.UppingCoefficient
|
if (result[TradingEvent.UptrendStart] >= Constants.UppingCoefficient
|
||||||
|
@ -970,6 +1017,18 @@ INewPrice message, int windowMaxSize, decimal? uptrendStartingDetectionMeanfullS
|
||||||
}, false);
|
}, false);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
private async Task LogPrice(string figi, string ticker,DateTime time, decimal value, string processor)
|
||||||
|
{
|
||||||
|
await _tradeDataProvider.LogPrice(new ProcessedPrice()
|
||||||
|
{
|
||||||
|
Figi = figi,
|
||||||
|
Ticker = ticker,
|
||||||
|
Processor = processor,
|
||||||
|
Time = time,
|
||||||
|
Value = value,
|
||||||
|
}, false);
|
||||||
|
}
|
||||||
|
|
||||||
private async Task LogDeclision(DeclisionTradeAction action, INewPrice message, decimal? profit = null)
|
private async Task LogDeclision(DeclisionTradeAction action, INewPrice message, decimal? profit = null)
|
||||||
{
|
{
|
||||||
await _tradeDataProvider.LogDeclision(new Declision()
|
await _tradeDataProvider.LogDeclision(new Declision()
|
||||||
|
@ -1110,23 +1169,23 @@ INewPrice message, int windowMaxSize, decimal? uptrendStartingDetectionMeanfullS
|
||||||
{
|
{
|
||||||
case TradingMode.Stable:
|
case TradingMode.Stable:
|
||||||
{
|
{
|
||||||
return (0.5m, -0.5m);
|
return (-0.5m, 0.5m);
|
||||||
}
|
}
|
||||||
case TradingMode.Dropping:
|
case TradingMode.Dropping:
|
||||||
{
|
{
|
||||||
return (-1.5m, null); ;
|
return (-1.5m, 0.5m); ;
|
||||||
}
|
}
|
||||||
case TradingMode.SlowDropping:
|
case TradingMode.SlowDropping:
|
||||||
{
|
{
|
||||||
return (-0.5m, null);
|
return (-1m, 0.5m);
|
||||||
}
|
}
|
||||||
case TradingMode.SlowGrowing:
|
case TradingMode.SlowGrowing:
|
||||||
{
|
{
|
||||||
return (null, 0.5m);
|
return (-0.5m, 1m);
|
||||||
}
|
}
|
||||||
case TradingMode.Growing:
|
case TradingMode.Growing:
|
||||||
{
|
{
|
||||||
return (null, 1.5m);
|
return (-0.5m, 1.5m);
|
||||||
}
|
}
|
||||||
default:
|
default:
|
||||||
{
|
{
|
||||||
|
@ -1138,26 +1197,26 @@ INewPrice message, int windowMaxSize, decimal? uptrendStartingDetectionMeanfullS
|
||||||
private (decimal stopLoss, decimal takeProfit) GetStops(INewPrice message, PositionType type)
|
private (decimal stopLoss, decimal takeProfit) GetStops(INewPrice message, PositionType type)
|
||||||
{
|
{
|
||||||
var mode = TradingModes[message.Figi];
|
var mode = TradingModes[message.Figi];
|
||||||
decimal stopLossShift = 15;
|
decimal stopLossShift = 1.5m;
|
||||||
decimal takeProfitShift = 6;
|
decimal takeProfitShift = 6;
|
||||||
if (mode == TradingMode.Growing && type == PositionType.Long)
|
if (mode == TradingMode.Growing && type == PositionType.Long)
|
||||||
{
|
{
|
||||||
takeProfitShift = 15;
|
takeProfitShift = 15;
|
||||||
stopLossShift = 2;
|
//stopLossShift = 2;
|
||||||
}
|
}
|
||||||
if (mode == TradingMode.Growing && type == PositionType.Short)
|
if (mode == TradingMode.Growing && type == PositionType.Short)
|
||||||
{
|
{
|
||||||
stopLossShift = 2;
|
//stopLossShift = 2;
|
||||||
takeProfitShift = 2;
|
takeProfitShift = 3m;
|
||||||
}
|
}
|
||||||
if (mode == TradingMode.Stable && type == PositionType.Long)
|
if (mode == TradingMode.Stable && type == PositionType.Long)
|
||||||
{
|
{
|
||||||
takeProfitShift = 2.5m;
|
takeProfitShift = 3m;
|
||||||
}
|
}
|
||||||
if (mode == TradingMode.Stable && type == PositionType.Short)
|
if (mode == TradingMode.Stable && type == PositionType.Short)
|
||||||
{
|
{
|
||||||
takeProfitShift = 2.5m;
|
takeProfitShift = 3m;
|
||||||
stopLossShift = 10;
|
//stopLossShift = 10;
|
||||||
}
|
}
|
||||||
if (mode == TradingMode.SlowDropping && type == PositionType.Short)
|
if (mode == TradingMode.SlowDropping && type == PositionType.Short)
|
||||||
{
|
{
|
||||||
|
@ -1166,12 +1225,12 @@ INewPrice message, int windowMaxSize, decimal? uptrendStartingDetectionMeanfullS
|
||||||
if (mode == TradingMode.SlowDropping && type == PositionType.Long)
|
if (mode == TradingMode.SlowDropping && type == PositionType.Long)
|
||||||
{
|
{
|
||||||
takeProfitShift = 1.5m;
|
takeProfitShift = 1.5m;
|
||||||
stopLossShift = 10;
|
//stopLossShift = 10;
|
||||||
}
|
}
|
||||||
if (mode == TradingMode.SlowGrowing && type == PositionType.Short)
|
if (mode == TradingMode.SlowGrowing && type == PositionType.Short)
|
||||||
{
|
{
|
||||||
takeProfitShift = 1.5m;
|
//takeProfitShift = 2.5m;
|
||||||
stopLossShift = 10;
|
//stopLossShift = 10;
|
||||||
}
|
}
|
||||||
if (mode == TradingMode.SlowGrowing && type == PositionType.Long)
|
if (mode == TradingMode.SlowGrowing && type == PositionType.Long)
|
||||||
{
|
{
|
||||||
|
@ -1179,12 +1238,12 @@ INewPrice message, int windowMaxSize, decimal? uptrendStartingDetectionMeanfullS
|
||||||
if (mode == TradingMode.Dropping && type == PositionType.Short)
|
if (mode == TradingMode.Dropping && type == PositionType.Short)
|
||||||
{
|
{
|
||||||
takeProfitShift = 15;
|
takeProfitShift = 15;
|
||||||
stopLossShift = 2;
|
//stopLossShift = 2;
|
||||||
}
|
}
|
||||||
if (mode == TradingMode.Dropping && type == PositionType.Long)
|
if (mode == TradingMode.Dropping && type == PositionType.Long)
|
||||||
{
|
{
|
||||||
stopLossShift = 2;
|
//stopLossShift = 2;
|
||||||
takeProfitShift = 1.5m;
|
takeProfitShift = 3m;
|
||||||
}
|
}
|
||||||
return (stopLossShift, takeProfitShift);
|
return (stopLossShift, takeProfitShift);
|
||||||
}
|
}
|
||||||
|
|
|
@ -42,7 +42,7 @@ namespace KLHZ.Trader.Service.Controllers
|
||||||
context1.ChangeTracker.QueryTrackingBehavior = QueryTrackingBehavior.NoTracking;
|
context1.ChangeTracker.QueryTrackingBehavior = QueryTrackingBehavior.NoTracking;
|
||||||
|
|
||||||
|
|
||||||
while (time1 < DateTime.UtcNow.Date)
|
while (time1 < DateTime.UtcNow)
|
||||||
{
|
{
|
||||||
var data = new List<TimeSeriesData>();
|
var data = new List<TimeSeriesData>();
|
||||||
var data2 = new List<TimeSeriesData>();
|
var data2 = new List<TimeSeriesData>();
|
||||||
|
@ -197,13 +197,27 @@ namespace KLHZ.Trader.Service.Controllers
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
else
|
||||||
|
{
|
||||||
|
var ob = data[i].Orderbook;
|
||||||
|
if (ob != null)
|
||||||
|
{
|
||||||
|
var d = new TimeSeriesData()
|
||||||
|
{
|
||||||
|
Figi = ob.Figi,
|
||||||
|
Orderbook = ob,
|
||||||
|
Time = ob.Time,
|
||||||
|
};
|
||||||
|
data2.Add(d);
|
||||||
|
}
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
foreach (var mess in data2)
|
foreach (var mess in data2)
|
||||||
{
|
{
|
||||||
if (mess.Orderbook != null)
|
if (mess.Orderbook != null)
|
||||||
{
|
{
|
||||||
await _traderDataProvider.AddOrderbook(mess.Orderbook);
|
await _dataBus.Broadcast(mess.Orderbook);
|
||||||
}
|
}
|
||||||
if (mess.NewPrice != null)
|
if (mess.NewPrice != null)
|
||||||
{
|
{
|
||||||
|
|
Loading…
Reference in New Issue