Dashboard Bottom

This commit is contained in:
HojouFotytu 2024-01-08 06:53:49 +09:00
parent bde9b98f11
commit 28c12e6d5a
12 changed files with 521 additions and 372 deletions

View File

@ -1,11 +1,9 @@
using System; using System;
using System.Collections.Generic; using System.Collections.Generic;
using System.ComponentModel; using System.ComponentModel;
using System.Text;
namespace Core.Main.DataObjects.PTMagicData namespace Core.Main.DataObjects.PTMagicData
{ {
#region Settings Objects
public class GeneralSettingsWrapper public class GeneralSettingsWrapper
{ {
public GeneralSettings GeneralSettings { get; set; } public GeneralSettings GeneralSettings { get; set; }
@ -21,7 +19,7 @@ namespace Core.Main.DataObjects.PTMagicData
public SecureSettings SecureSettings { get; set; } public SecureSettings SecureSettings { get; set; }
} }
#region GeneralSettings
public class GeneralSettings public class GeneralSettings
{ {
public Application Application { get; set; } public Application Application { get; set; }
@ -43,7 +41,7 @@ namespace Core.Main.DataObjects.PTMagicData
public string ProfitTrailerDefaultSettingName { get; set; } = "default"; public string ProfitTrailerDefaultSettingName { get; set; } = "default";
public int FloodProtectionMinutes { get; set; } = 15; public int FloodProtectionMinutes { get; set; } = 15;
public string Exchange { get; set; } public string Exchange { get; set; }
public double StartBalance { get; set; } = 0; //public double StartBalance { get; set; } = 0;
public string InstanceName { get; set; } = "PT Magic"; public string InstanceName { get; set; } = "PT Magic";
public string TimezoneOffset { get; set; } = "+0:00"; public string TimezoneOffset { get; set; } = "+0:00";
public string MainFiatCurrency { get; set; } = "USD"; public string MainFiatCurrency { get; set; } = "USD";
@ -106,9 +104,7 @@ namespace Core.Main.DataObjects.PTMagicData
public Int64 ChatId { get; set; } public Int64 ChatId { get; set; }
public bool SilentMode { get; set; } = false; public bool SilentMode { get; set; } = false;
} }
#endregion
#region AnalyzerSettings
public class AnalyzerSettings public class AnalyzerSettings
{ {
public MarketAnalyzer MarketAnalyzer { get; set; } public MarketAnalyzer MarketAnalyzer { get; set; }
@ -244,18 +240,12 @@ namespace Core.Main.DataObjects.PTMagicData
[DefaultValue(0)] [DefaultValue(0)]
public int HoursSinceTriggered { get; set; } = 0; public int HoursSinceTriggered { get; set; } = 0;
} }
#endregion
#region SecureSettings
public class SecureSettings public class SecureSettings
{ {
public string MonitorPassword { get; set; } = ""; public string MonitorPassword { get; set; } = "";
} }
#endregion
#endregion
#region Market Analyzer Objects
public class Market public class Market
{ {
public int Position; public int Position;
@ -291,9 +281,7 @@ namespace Core.Main.DataObjects.PTMagicData
public DateTime FirstSeen = Constants.confMinDate; public DateTime FirstSeen = Constants.confMinDate;
public DateTime LastSeen = Constants.confMaxDate; public DateTime LastSeen = Constants.confMaxDate;
} }
#endregion
#region Summary Objects
public class Summary public class Summary
{ {
public string Version { get; set; } = ""; public string Version { get; set; } = "";
@ -324,13 +312,25 @@ namespace Core.Main.DataObjects.PTMagicData
public string SellStrategy { get; set; } = ""; public string SellStrategy { get; set; } = "";
public string MainMarket { get; set; } = ""; public string MainMarket { get; set; } = "";
public double MainMarketPrice { get; set; } = 0; public double MainMarketPrice { get; set; } = 0;
public string MainFiatCurrency { get; set; } = "USD"; private PropertiesData _propertiesData = new PropertiesData();
public double MainFiatCurrencyExchangeRate { get; set; } = 1; public string MainFiatCurrency => _propertiesData.Currency;
private SummaryData _summaryData = new SummaryData();
public double MainFiatCurrencyExchangeRate => _summaryData.FiatConversionRate;
public List<StrategySummary> BuyStrategies { get; set; } = new List<StrategySummary>(); public List<StrategySummary> BuyStrategies { get; set; } = new List<StrategySummary>();
public List<StrategySummary> SellStrategies { get; set; } = new List<StrategySummary>(); public List<StrategySummary> SellStrategies { get; set; } = new List<StrategySummary>();
public List<StrategySummary> DCABuyStrategies { get; set; } = new List<StrategySummary>(); public List<StrategySummary> DCABuyStrategies { get; set; } = new List<StrategySummary>();
public List<StrategySummary> DCASellStrategies { get; set; } = new List<StrategySummary>(); public List<StrategySummary> DCASellStrategies { get; set; } = new List<StrategySummary>();
} }
public class PropertiesData
{
public string Currency { get; set; } = "";
public bool Shorting { get; set; } = false;
public bool Margin { get; set; } = false;
public string UpTime { get; set; } = "";
public int Port { get; set; } = 0;
public bool IsLeverageExchange { get; set; } = false;
public string BaseUrl { get; set; } = "";
}
public class StrategySummary public class StrategySummary
{ {
@ -364,22 +364,7 @@ namespace Core.Main.DataObjects.PTMagicData
public List<StrategySummary> DCABuyStrategies { get; set; } = new List<StrategySummary>(); public List<StrategySummary> DCABuyStrategies { get; set; } = new List<StrategySummary>();
public List<StrategySummary> DCASellStrategies { get; set; } = new List<StrategySummary>(); public List<StrategySummary> DCASellStrategies { get; set; } = new List<StrategySummary>();
} }
#endregion
#region Properties Objects
public class Properties
{
public string Currency { get; set; } = "";
public bool Shorting { get; set; } = false;
public bool Margin { get; set; } = false;
public string UpTime { get; set; } = "";
public int Port { get; set; } = 0;
public bool IsLeverageExchange { get; set; } = false;
public string BaseUrl { get; set; } = "";
}
#endregion
#region Transaction Objects
public class Transaction public class Transaction
{ {
public string GUID { get; set; } = ""; public string GUID { get; set; } = "";
@ -397,9 +382,7 @@ namespace Core.Main.DataObjects.PTMagicData
return result.DateTime; return result.DateTime;
} }
} }
#endregion
#region SingleMarketSettingSummary Objects
public class SingleMarketSettingSummary public class SingleMarketSettingSummary
{ {
public string Market { get; set; } = ""; public string Market { get; set; } = "";
@ -415,9 +398,6 @@ namespace Core.Main.DataObjects.PTMagicData
public double LastPrice { get; set; } = 0; public double LastPrice { get; set; } = 0;
public double Last24hVolume { get; set; } = 0; public double Last24hVolume { get; set; } = 0;
} }
#endregion
#region Profit Trailer JSON Objects
public class SellLogData public class SellLogData
{ {
@ -445,19 +425,39 @@ namespace Core.Main.DataObjects.PTMagicData
public double SalesWeek { get; set; } public double SalesWeek { get; set; }
public double ProfitWeek { get; set; } public double ProfitWeek { get; set; }
public double ProfitPercWeek { get; set; } public double ProfitPercWeek { get; set; }
public double SalesMonth { get; set; } public double SalesThisMonth { get; set; }
public double ProfitMonth { get; set; } public double ProfitThisMonth { get; set; }
public double ProfitPercMonth { get; set; } public double ProfitPercThisMonth { get; set; }
public double SalesLastMonth { get; set; }
public double ProfitLastMonth { get; set; }
public double ProfitPercLastMonth { get; set; }
public double TotalProfit { get; set; } public double TotalProfit { get; set; }
public double TotalSales { get; set; } public double TotalSales { get; set; }
public double TotalProfitPerc { get; set; } public double TotalProfitPerc { get; set; }
public double FundingToday { get; set; } public double FundingToday { get; set; }
public double FundingYesterday { get; set; } public double FundingYesterday { get; set; }
public double FundingWeek { get; set; } public double FundingWeek { get; set; }
public double FundingMonth { get; set; } public double FundingThisMonth { get; set; }
public double FundingLastMonth { get; set; }
public double FundingTotal { get; set; } public double FundingTotal { get; set; }
} }
public class DailyStatsData
{
public string Date { get; set; }
public double TotalSales { get; set; }
public double TotalBuys { get; set; }
public double TotalProfitCurrency { get; set; }
public int Order { get; set; }
}
public class DailyPNLData
{
public string Date { get; set; }
public double CumulativeProfitCurrency { get; set; }
public double Order { get; set; }
}
public class PTStrategy public class PTStrategy
{ {
public string type { get; set; } public string type { get; set; }
@ -534,15 +534,13 @@ namespace Core.Main.DataObjects.PTMagicData
} }
public class SummaryData public class SummaryData
{ { public double Balance { get; set; }
public double Balance { get; set; }
public double StartBalance { get; set; } public double StartBalance { get; set; }
public double FiatConversionRate { get; set; }
public double PairsValue { get; set; } public double PairsValue { get; set; }
public double DCAValue { get; set; } public double DCAValue { get; set; }
public double PendingValue { get; set; } public double PendingValue { get; set; }
public double DustValue { get; set; } public double DustValue { get; set; }
public string Market { get; set; } public string Market { get; set; }
} }
#endregion
} }

View File

@ -15,18 +15,32 @@ namespace Core.Main.DataObjects
public class ProfitTrailerData public class ProfitTrailerData
{ {
private SummaryData _summary = null; private SummaryData _summary = null;
private Properties _properties = null; private PropertiesData _properties = null;
private List<StatsData> _stats = null; private StatsData _stats = null;
private List<DailyStatsData> _dailyStats = new List<DailyStatsData>();
private List<DailyPNLData> _dailyPNL = new List<DailyPNLData>();
private List<SellLogData> _sellLog = new List<SellLogData>(); private List<SellLogData> _sellLog = new List<SellLogData>();
private List<DCALogData> _dcaLog = new List<DCALogData>(); private List<DCALogData> _dcaLog = new List<DCALogData>();
private List<BuyLogData> _buyLog = new List<BuyLogData>(); private List<BuyLogData> _buyLog = new List<BuyLogData>();
private string _ptmBasePath = ""; private string _ptmBasePath = "";
private PTMagicConfiguration _systemConfiguration = null; private PTMagicConfiguration _systemConfiguration = null;
private TransactionData _transactionData = null; private TransactionData _transactionData = null;
private DateTime _statsRefresh = DateTime.UtcNow,_buyLogRefresh = DateTime.UtcNow, _sellLogRefresh = DateTime.UtcNow, _dcaLogRefresh = DateTime.UtcNow, _summaryRefresh = DateTime.UtcNow, _propertiesRefresh = DateTime.UtcNow; private DateTime _dailyStatsRefresh = DateTime.UtcNow;
private volatile object _statsLock = new object(),_buyLock = new object(), _sellLock = new object(), _dcaLock = new object(), _summaryLock = new object(), _propertiesLock = new object(); private DateTime _dailyPNLRefresh = DateTime.UtcNow;
private TimeSpan? _offsetTimeSpan = null; private DateTime _statsRefresh = DateTime.UtcNow;
private DateTime _buyLogRefresh = DateTime.UtcNow;
private DateTime _sellLogRefresh = DateTime.UtcNow;
private DateTime _dcaLogRefresh = DateTime.UtcNow;
private DateTime _summaryRefresh = DateTime.UtcNow;
private DateTime _propertiesRefresh = DateTime.UtcNow;
private volatile object _dailyStatsLock = new object();
private volatile object _dailyPNLLock = new object();
private volatile object _statsLock = new object();
private volatile object _buyLock = new object();
private volatile object _sellLock = new object();
private volatile object _dcaLock = new object();
private volatile object _summaryLock = new object();
private volatile object _propertiesLock = new object(); private TimeSpan? _offsetTimeSpan = null;
public void DoLog(string message) public void DoLog(string message)
{ {
// Implement your logging logic here // Implement your logging logic here
@ -82,7 +96,21 @@ namespace Core.Main.DataObjects
return _summary; return _summary;
} }
} }
public Properties Properties private SummaryData BuildSummaryData(dynamic PTData)
{
return new SummaryData()
{
Market = PTData.market,
FiatConversionRate = PTData.priceDataFiatConversionRate,
Balance = PTData.realBalance,
PairsValue = PTData.totalPairsCurrentValue,
DCAValue = PTData.totalDCACurrentValue,
PendingValue = PTData.totalPendingCurrentValue,
DustValue = PTData.totalDustCurrentValue,
StartBalance = PTData.startBalance,
};
}
public PropertiesData Properties
{ {
get get
{ {
@ -102,8 +130,20 @@ namespace Core.Main.DataObjects
return _properties; return _properties;
} }
} }
private PropertiesData BuildProptertiesData(dynamic PTProperties)
public List<StatsData> Stats {
return new PropertiesData()
{
Currency = PTProperties.currency,
Shorting = PTProperties.shorting,
Margin = PTProperties.margin,
UpTime = PTProperties.upTime,
Port = PTProperties.port,
IsLeverageExchange = PTProperties.isLeverageExchange,
BaseUrl = PTProperties.baseUrl
};
}
public StatsData Stats
{ {
get get
{ {
@ -116,7 +156,7 @@ namespace Core.Main.DataObjects
dynamic statsDataJson = GetDataFromProfitTrailer("/api/v2/data/stats"); dynamic statsDataJson = GetDataFromProfitTrailer("/api/v2/data/stats");
JObject statsDataJObject = statsDataJson as JObject; JObject statsDataJObject = statsDataJson as JObject;
JObject basicSection = (JObject)statsDataJObject["basic"]; JObject basicSection = (JObject)statsDataJObject["basic"];
_stats = new List<StatsData> { BuildStatsData(basicSection) }; _stats = BuildStatsData(basicSection);
_statsRefresh = DateTime.UtcNow.AddSeconds(_systemConfiguration.GeneralSettings.Monitor.RefreshSeconds - 1); _statsRefresh = DateTime.UtcNow.AddSeconds(_systemConfiguration.GeneralSettings.Monitor.RefreshSeconds - 1);
} }
} }
@ -124,8 +164,98 @@ namespace Core.Main.DataObjects
return _stats; return _stats;
} }
} }
private StatsData BuildStatsData(dynamic statsDataJson)
{
return new StatsData()
{
SalesToday = statsDataJson["totalSalesToday"],
ProfitToday = statsDataJson["totalProfitToday"],
ProfitPercToday = statsDataJson["totalProfitPercToday"],
SalesYesterday = statsDataJson["totalSalesYesterday"],
ProfitYesterday = statsDataJson["totalProfitYesterday"],
ProfitPercYesterday = statsDataJson["totalProfitPercYesterday"],
SalesWeek = statsDataJson["totalSalesWeek"],
ProfitWeek = statsDataJson["totalProfitWeek"],
ProfitPercWeek = statsDataJson["totalProfitPercWeek"],
SalesThisMonth = statsDataJson["totalSalesThisMonth"],
ProfitThisMonth = statsDataJson["totalProfitThisMonth"],
ProfitPercThisMonth = statsDataJson["totalProfitPercThisMonth"],
SalesLastMonth = statsDataJson["totalSalesLastMonth"],
ProfitLastMonth = statsDataJson["totalProfitLastMonth"],
ProfitPercLastMonth = statsDataJson["totalProfitPercLastMonth"],
TotalProfit = statsDataJson["totalProfit"],
TotalSales = statsDataJson["totalSales"],
TotalProfitPerc = statsDataJson["totalProfitPerc"],
FundingToday = statsDataJson["totalFundingToday"],
FundingYesterday = statsDataJson["totalFundingYesterday"],
FundingWeek = statsDataJson["totalFundingWeek"],
FundingThisMonth = statsDataJson["totalFundingThisMonth"],
FundingLastMonth = statsDataJson["totalFundingLastMonth"],
FundingTotal = statsDataJson["totalFunding"]
};
}
public List<DailyStatsData> DailyStats
{
get
{
if (_dailyStats == null || DateTime.UtcNow > _dailyStatsRefresh)
{
lock (_dailyStatsLock)
{
if (_dailyStats == null || DateTime.UtcNow > _dailyStatsRefresh)
{
dynamic dailyStatsDataJson = GetDataFromProfitTrailer("/api/v2/data/stats");
JObject dailyStatsDataJObject = dailyStatsDataJson as JObject;
JArray dailyStatsSection = (JArray)dailyStatsDataJObject["extra"]["dailyStats"];
_dailyStats = dailyStatsSection.Select(j => BuildDailyStatsData(j as JObject)).ToList();
_dailyStatsRefresh = DateTime.UtcNow.AddSeconds(_systemConfiguration.GeneralSettings.Monitor.RefreshSeconds - 1);
}
}
}
return _dailyStats;
}
}
private DailyStatsData BuildDailyStatsData(dynamic dailyStatsDataJson)
{
return new DailyStatsData()
{
Date = dailyStatsDataJson["date"],
TotalSales = dailyStatsDataJson["totalSales"],
TotalBuys = dailyStatsDataJson["totalBuys"],
TotalProfitCurrency = dailyStatsDataJson["totalProfitCurrency"],
Order = dailyStatsDataJson["order"],
};
}
public List<DailyPNLData> DailyPNL
{
get
{
if (_dailyPNL == null || DateTime.UtcNow > _dailyPNLRefresh)
{
lock (_dailyPNLLock)
{
if (_dailyPNL == null || DateTime.UtcNow > _dailyPNLRefresh)
{
dynamic dailyPNLDataJson = GetDataFromProfitTrailer("/api/v2/data/stats");
JObject dailyPNLDataJObject = dailyPNLDataJson as JObject;
JArray dailyPNLSection = (JArray)dailyPNLDataJObject["extra"]["dailyPNLStats"];
_dailyPNL = dailyPNLSection.Select(j => BuildDailyPNLData(j as JObject)).ToList();
_dailyPNLRefresh = DateTime.UtcNow.AddSeconds(_systemConfiguration.GeneralSettings.Monitor.RefreshSeconds - 1);
}
}
}
return _dailyPNL;
}
}
private DailyPNLData BuildDailyPNLData(dynamic dailyPNLDataJson)
{
return new DailyPNLData()
{
Date = dailyPNLDataJson["date"],
CumulativeProfitCurrency = dailyPNLDataJson["cumulativeProfitCurrency"],
Order = dailyPNLDataJson["order"],
};
}
public List<SellLogData> SellLog public List<SellLogData> SellLog
{ {
get get
@ -203,7 +333,6 @@ namespace Core.Main.DataObjects
() => () =>
{ {
pendingData = GetDataFromProfitTrailer("/api/v2/data/pending", true); pendingData = GetDataFromProfitTrailer("/api/v2/data/pending", true);
}, },
() => () =>
{ {
@ -277,9 +406,10 @@ namespace Core.Main.DataObjects
(this.Summary.DustValue); (this.Summary.DustValue);
} }
public double GetSnapshotBalance(DateTime snapshotDateTime) public double GetSnapshotBalance(DateTime snapshotDateTime)
{ {
double result = _systemConfiguration.GeneralSettings.Application.StartBalance; double result = _summary.StartBalance;
result += this.SellLog.FindAll(sl => sl.SoldDate.Date < snapshotDateTime.Date).Sum(sl => sl.Profit); result += this.SellLog.FindAll(sl => sl.SoldDate.Date < snapshotDateTime.Date).Sum(sl => sl.Profit);
result += this.TransactionData.Transactions.FindAll(t => t.UTCDateTime < snapshotDateTime).Sum(t => t.Amount); result += this.TransactionData.Transactions.FindAll(t => t.UTCDateTime < snapshotDateTime).Sum(t => t.Amount);
@ -324,62 +454,9 @@ namespace Core.Main.DataObjects
{ {
return JArray.Parse(rawBody); return JArray.Parse(rawBody);
} }
} }
private SummaryData BuildSummaryData(dynamic PTData)
{
return new SummaryData()
{
Market = PTData.market,
Balance = PTData.realBalance,
PairsValue = PTData.totalPairsCurrentValue,
DCAValue = PTData.totalDCACurrentValue,
PendingValue = PTData.totalPendingCurrentValue,
DustValue = PTData.totalDustCurrentValue
};
}
private Properties BuildProptertiesData(dynamic PTProperties)
{
return new Properties()
{
Currency = PTProperties.currency,
Shorting = PTProperties.shorting,
Margin = PTProperties.margin,
UpTime = PTProperties.upTime,
Port = PTProperties.port,
IsLeverageExchange = PTProperties.isLeverageExchange,
BaseUrl = PTProperties.baseUrl
};
}
private StatsData BuildStatsData(dynamic statsDataJson)
{
return new StatsData()
{
SalesToday = statsDataJson["totalSalesToday"],
ProfitToday = statsDataJson["totalProfitToday"],
ProfitPercToday = statsDataJson["totalProfitPercToday"],
SalesYesterday = statsDataJson["totalSalesYesterday"],
ProfitYesterday = statsDataJson["totalProfitYesterday"],
ProfitPercYesterday = statsDataJson["totalProfitPercYesterday"],
SalesWeek = statsDataJson["totalSalesWeek"],
ProfitWeek = statsDataJson["totalProfitWeek"],
ProfitPercWeek = statsDataJson["totalProfitPercWeek"],
SalesMonth = statsDataJson["totalSalesThisMonth"],
ProfitMonth = statsDataJson["totalProfitThisMonth"],
ProfitPercMonth = statsDataJson["totalProfitPercThisMonth"],
TotalProfit = statsDataJson["totalProfit"],
TotalSales = statsDataJson["totalSales"],
TotalProfitPerc = statsDataJson["totalProfitPerc"],
FundingToday = statsDataJson["totalFundingToday"],
FundingYesterday = statsDataJson["totalFundingYesterday"],
FundingWeek = statsDataJson["totalFundingWeek"],
FundingMonth = statsDataJson["totalFundingThisMonth"],
FundingTotal = statsDataJson["totalFunding"]
};
}
private void BuildSellLogData(dynamic rawSellLogData) private void BuildSellLogData(dynamic rawSellLogData)
{ {
foreach (var rsld in rawSellLogData.data) foreach (var rsld in rawSellLogData.data)
@ -399,10 +476,13 @@ namespace Core.Main.DataObjects
System.DateTime dtDateTime = new DateTime(1970, 1, 1, 0, 0, 0, System.DateTimeKind.Utc); System.DateTime dtDateTime = new DateTime(1970, 1, 1, 0, 0, 0, System.DateTimeKind.Utc);
dtDateTime = dtDateTime.AddSeconds((double)rsld.soldDate).ToUniversalTime(); dtDateTime = dtDateTime.AddSeconds((double)rsld.soldDate).ToUniversalTime();
// Profit Trailer sales are saved in UTC // Profit Trailer sales are saved in UTC
DateTimeOffset ptSoldDate = DateTimeOffset.Parse(dtDateTime.Year.ToString() + "-" + dtDateTime.Month.ToString("00") + "-" + dtDateTime.Day.ToString("00") + "T" + dtDateTime.Hour.ToString("00") + ":" + dtDateTime.Minute.ToString("00") + ":" + dtDateTime.Second.ToString("00"), CultureInfo.InvariantCulture, DateTimeStyles.AssumeUniversal); DateTimeOffset ptSoldDate = DateTimeOffset.Parse(dtDateTime.Year.ToString() + "-" + dtDateTime.Month.ToString("00") + "-" + dtDateTime.Day.ToString("00") + "T" + dtDateTime.Hour.ToString("00") + ":" + dtDateTime.Minute.ToString("00") + ":" + dtDateTime.Second.ToString("00"), CultureInfo.InvariantCulture, DateTimeStyles.AssumeUniversal);
// Convert UTC sales time to local offset time // Convert UTC sales time to local offset time
ptSoldDate = ptSoldDate.ToOffset(OffsetTimeSpan); ptSoldDate = ptSoldDate.ToOffset(OffsetTimeSpan);
sellLogData.SoldDate = ptSoldDate.DateTime; sellLogData.SoldDate = ptSoldDate.DateTime;
@ -424,7 +504,6 @@ namespace Core.Main.DataObjects
// Parse watch only pairs data // Parse watch only pairs data
_dcaLog.AddRange(ParsePairsData(rawWatchModeLogData, false)); _dcaLog.AddRange(ParsePairsData(rawWatchModeLogData, false));
} }
// Parse the pairs data from PT to our own common data structure. // Parse the pairs data from PT to our own common data structure.

View File

@ -872,7 +872,7 @@ namespace Core.Main
this.CheckLatestGitHubVersion(this.LastRuntimeSummary.Version); this.CheckLatestGitHubVersion(this.LastRuntimeSummary.Version);
// Get latest main fiat currency exchange rate // Get latest main fiat currency exchange rate
this.GetMainFiatCurrencyDetails(); // this.GetMainFiatCurrencyDetails();
// Load current PT files // Load current PT files
this.LoadCurrentProfitTrailerProperties(); this.LoadCurrentProfitTrailerProperties();
@ -1127,10 +1127,10 @@ namespace Core.Main
} }
} }
private void GetMainFiatCurrencyDetails() //private void GetMainFiatCurrencyDetails()
{ //{
this.LastRuntimeSummary.MainFiatCurrency = this.LastMainFiatCurrency; //this.LastRuntimeSummary.MainFiatCurrency = this.PropertiesData.Currency;
this.LastRuntimeSummary.MainFiatCurrencyExchangeRate = this.LastMainFiatCurrencyExchangeRate; //this.LastRuntimeSummary.MainFiatCurrencyExchangeRate = this.LastMainFiatCurrencyExchangeRate;
// if (this.LastFiatCurrencyCheck < DateTime.UtcNow.AddHours(-12) && !this.PTMagicConfiguration.GeneralSettings.Application.MainFiatCurrency.Equals("USD", StringComparison.InvariantCultureIgnoreCase)) // if (this.LastFiatCurrencyCheck < DateTime.UtcNow.AddHours(-12) && !this.PTMagicConfiguration.GeneralSettings.Application.MainFiatCurrency.Equals("USD", StringComparison.InvariantCultureIgnoreCase))
// { // {
@ -1154,7 +1154,7 @@ namespace Core.Main
// this.LastMainFiatCurrencyExchangeRate = 1; // this.LastMainFiatCurrencyExchangeRate = 1;
// } // }
// } // }
} //}
// Get current PT properties // Get current PT properties
private void LoadCurrentProfitTrailerProperties() private void LoadCurrentProfitTrailerProperties()

View File

@ -33,6 +33,11 @@
$("#baglist-refresh-icon").html('<i class="fa fa-circle-o-notch fa-spin fa-fw" data-toggle="tooltip" data-placement="top" title="Loading fresh data..."></i>'); $("#baglist-refresh-icon").html('<i class="fa fa-circle-o-notch fa-spin fa-fw" data-toggle="tooltip" data-placement="top" title="Loading fresh data..."></i>');
$("#buylist-refresh-icon").html('<i class="fa fa-circle-o-notch fa-spin fa-fw" data-toggle="tooltip" data-placement="top" title="Loading fresh data..."></i>'); $("#buylist-refresh-icon").html('<i class="fa fa-circle-o-notch fa-spin fa-fw" data-toggle="tooltip" data-placement="top" title="Loading fresh data..."></i>');
// Add the page refresh code here
setTimeout(function(){
location.reload();
}, 60 * 60 * 1000); // 60 minutes
// Clear exisitng interval to stop multiple attempts to load at the same time. // Clear exisitng interval to stop multiple attempts to load at the same time.
if (intervalDashboardTop != null) if (intervalDashboardTop != null)
{ {
@ -64,13 +69,13 @@
var loadDashboardBottom = function () { var loadDashboardBottom = function () {
//destroy all d3 svg graph to avoid memory leak //destroy all d3 svg graph to avoid memory leak
$(".nvtooltip").remove(); //$(".nvtooltip").remove();
$("svg > *").remove(); //$("svg > *").remove();
$("svg").remove(); //$("svg").remove();
nv.charts = {}; //nv.charts = {};
nv.graphs = []; //nv.graphs = [];
nv.logs = {}; //nv.logs = {};
nv.tooltip = {}; //nv.tooltip = {};
// Clear exisitng interval to stop multiple attempts to load at the same time. // Clear exisitng interval to stop multiple attempts to load at the same time.
if (intervalDashboardBottom != null) if (intervalDashboardBottom != null)

View File

@ -26,7 +26,7 @@
} }
} }
<th class="m-t-0 header-title text-left">Total Current Value: &nbsp; <text class="text-autocolor"> @totalCurrentValueString @Model.Summary.MainMarket </text> <small> <i class="fa fa-info-circle text-muted" data-toggle="tooltip" data-placement="top" title="This is based on the TCV reported by Profit Trailer."></i></small></th> <th class="m-t-0 header-title text-left">Total Current Value: &nbsp; <text class="text-autocolor"> @totalCurrentValueString @Model.Summary.MainMarket </text> <small> <i class="fa fa-info-circle text-muted" data-toggle="tooltip" data-placement="top" title="This is based on the TCV reported by Profit Trailer."></i></small></th>
<th class="text-right">Starting Value: &nbsp; <text class="text-autocolor"> @Model.PTMagicConfiguration.GeneralSettings.Application.StartBalance &nbsp; @Model.Summary.MainMarket </text> <small> <i class="fa fa-info-circle text-muted" data-toggle="tooltip" data-placement="top" title="This is the starting value found in your settings file"></i></small></th> <th class="text-right">Starting Value: &nbsp; <text class="text-autocolor"> @Model.SummaryData.StartBalance &nbsp; @Model.Summary.MainMarket </text> <small> <i class="fa fa-info-circle text-muted" data-toggle="tooltip" data-placement="top" title="This is the starting value found in your settings file"></i></small></th>
</tr> </tr>
</thead> </thead>
</table> </table>
@ -64,7 +64,7 @@
double totalProfit = 0; double totalProfit = 0;
totalProfit = Model.PTData.SellLog.Sum(s => s.Profit); totalProfit = Model.PTData.SellLog.Sum(s => s.Profit);
double totalProfitFiat = Math.Round(totalProfit * Model.Summary.MainMarketPrice, 2); double totalProfitFiat = Math.Round(totalProfit * Model.Summary.MainMarketPrice, 2);
double percentGain = Math.Round(totalProfit / Model.PTMagicConfiguration.GeneralSettings.Application.StartBalance * 100, 2); double percentGain = Math.Round(totalProfit / Model.SummaryData.StartBalance * 100, 2);
double avgDailyGain = Model.DailyGains.Values.Average(dg => dg); double avgDailyGain = Model.DailyGains.Values.Average(dg => dg);
double avgMonthlyGain = Model.MonthlyGains.Values.Average(dg => dg); double avgMonthlyGain = Model.MonthlyGains.Values.Average(dg => dg);
string percentGainText = percentGain.ToString("#,#0.00", new System.Globalization.CultureInfo("en-US")) + "%"; string percentGainText = percentGain.ToString("#,#0.00", new System.Globalization.CultureInfo("en-US")) + "%";

View File

@ -12,6 +12,7 @@ namespace Monitor.Pages
public class SalesAnalyzer : _Internal.BasePageModelSecure public class SalesAnalyzer : _Internal.BasePageModelSecure
{ {
public ProfitTrailerData PTData = null; public ProfitTrailerData PTData = null;
public SummaryData SummaryData { get; set; }
public string TradesChartDataJSON = ""; public string TradesChartDataJSON = "";
public string ProfitChartDataJSON = ""; public string ProfitChartDataJSON = "";
public string BalanceChartDataJSON = ""; public string BalanceChartDataJSON = "";
@ -31,6 +32,7 @@ namespace Monitor.Pages
private void BindData() private void BindData()
{ {
PTData = this.PtDataObject; PTData = this.PtDataObject;
SummaryData = this.PTData.Summary;
// Convert local offset time to UTC // Convert local offset time to UTC
TimeSpan offsetTimeSpan = TimeSpan.Parse(PTMagicConfiguration.GeneralSettings.Application.TimezoneOffset.Replace("+", "")); TimeSpan offsetTimeSpan = TimeSpan.Parse(PTMagicConfiguration.GeneralSettings.Application.TimezoneOffset.Replace("+", ""));

View File

@ -131,12 +131,12 @@
</div> </div>
</div> *@ </div> *@
<div class="form-group row"> @* <div class="form-group row">
<label class="col-md-4 col-form-label">Starting Balance <i class="fa fa-info-circle text-muted" data-toggle="tooltip" data-placement="top" title="PTM will use this to calculate total profits to date, and projected profits."></i></label> <label class="col-md-4 col-form-label">Starting Balance <i class="fa fa-info-circle text-muted" data-toggle="tooltip" data-placement="top" title="PTM will use this to calculate total profits to date, and projected profits."></i></label>
<div class="col-md-8"> <div class="col-md-8">
<input type="text" class="form-control" name="Application_StartBalance" value="@Model.PTMagicConfiguration.GeneralSettings.Application.StartBalance"> <input type="text" class="form-control" name="Application_StartBalance" value="@Model.SummaryData.StartBalance">
</div>
</div> </div>
</div> *@
<div class="form-group row"> <div class="form-group row">
<label class="col-md-4 col-form-label">CoinMarketCap API Key <i class="fa fa-info-circle text-muted" data-toggle="tooltip" data-placement="top" title="The API Key that will be used to get Coin Data from CoinMarketCap (optional)."></i></label> <label class="col-md-4 col-form-label">CoinMarketCap API Key <i class="fa fa-info-circle text-muted" data-toggle="tooltip" data-placement="top" title="The API Key that will be used to get Coin Data from CoinMarketCap (optional)."></i></label>

View File

@ -1,16 +1,19 @@
using System; using System;
using System.Collections.Generic; using System.Collections.Generic;
using System.Linq;
using Microsoft.AspNetCore.Http; using Microsoft.AspNetCore.Http;
using Core.Main; using Core.Main;
using Core.Helper; using Core.Helper;
using Core.Main.DataObjects;
using Core.Main.DataObjects.PTMagicData; using Core.Main.DataObjects.PTMagicData;
namespace Monitor.Pages namespace Monitor.Pages
{ {
public class SettingsGeneralModel : _Internal.BasePageModelSecure public class SettingsGeneralModel : _Internal.BasePageModelSecure
{ {
public string ValidationMessage = ""; public string ValidationMessage = "";
public ProfitTrailerData PTData = null;
public SummaryData SummaryData { get; set; }
private string GetTimezoneOffsetString(TimeZoneInfo tzi) private string GetTimezoneOffsetString(TimeZoneInfo tzi)
{ {
@ -51,6 +54,8 @@ namespace Monitor.Pages
public void OnGet() public void OnGet()
{ {
base.Init(); base.Init();
PTData = this.PtDataObject;
SummaryData = this.PTData.Summary;
string notification = GetStringParameter("n", ""); string notification = GetStringParameter("n", "");
if (notification.Equals("BackupRestored")) if (notification.Equals("BackupRestored"))
@ -68,7 +73,7 @@ namespace Monitor.Pages
// Read the new settings // Read the new settings
PTMagicConfiguration.GeneralSettings.Application.IsEnabled = HttpContext.Request.Form["Application_IsEnabled"].Equals("on"); PTMagicConfiguration.GeneralSettings.Application.IsEnabled = HttpContext.Request.Form["Application_IsEnabled"].Equals("on");
PTMagicConfiguration.GeneralSettings.Application.TestMode = HttpContext.Request.Form["Application_TestMode"].Equals("on"); PTMagicConfiguration.GeneralSettings.Application.TestMode = HttpContext.Request.Form["Application_TestMode"].Equals("on");
PTMagicConfiguration.GeneralSettings.Application.StartBalance = SystemHelper.TextToDouble(HttpContext.Request.Form["Application_StartBalance"], PTMagicConfiguration.GeneralSettings.Application.StartBalance, "en-US"); //PTMagicConfiguration.GeneralSettings.Application.StartBalance = SystemHelper.TextToDouble(HttpContext.Request.Form["Application_StartBalance"], PTMagicConfiguration.GeneralSettings.Application.StartBalance, "en-US");
PTMagicConfiguration.GeneralSettings.Application.ProfitTrailerDefaultSettingName = HttpContext.Request.Form["Application_ProfitTrailerDefaultSettingName"]; PTMagicConfiguration.GeneralSettings.Application.ProfitTrailerDefaultSettingName = HttpContext.Request.Form["Application_ProfitTrailerDefaultSettingName"];
PTMagicConfiguration.GeneralSettings.Application.Exchange = HttpContext.Request.Form["Application_Exchange"]; PTMagicConfiguration.GeneralSettings.Application.Exchange = HttpContext.Request.Form["Application_Exchange"];
PTMagicConfiguration.GeneralSettings.Application.ProfitTrailerMonitorURL = HttpContext.Request.Form["Application_ProfitTrailerMonitorURL"]; PTMagicConfiguration.GeneralSettings.Application.ProfitTrailerMonitorURL = HttpContext.Request.Form["Application_ProfitTrailerMonitorURL"];

View File

@ -24,7 +24,7 @@
</div> </div>
<div class="col-md-3 px-1"> <div class="col-md-3 px-1">
<div class="card-box px-3" style="height:305px;"> <div class="card-box px-3" style="height:305px;">
<div class="cdev" data-percent="100" data-duration="@Html.Raw(@Model.PTMagicConfiguration.GeneralSettings.Monitor.RefreshSeconds * 1000)" data-color="#aaa,#414d59"></div> @*<div class="cdev" data-percent="100" data-duration="@Html.Raw(@Model.PTMagicConfiguration.GeneralSettings.Monitor.RefreshSeconds * 1000)" data-color="#aaa,#414d59"></div>*@
@{ @{
string totalCurrentValueString = Model.totalCurrentValue.ToString("#,#0.00000000", new System.Globalization.CultureInfo("en-US")); string totalCurrentValueString = Model.totalCurrentValue.ToString("#,#0.00000000", new System.Globalization.CultureInfo("en-US"));
if (Model.totalCurrentValue > 100) { if (Model.totalCurrentValue > 100) {
@ -34,8 +34,8 @@
<div id="AssetDistribution" class="container"> <div id="AssetDistribution" class="container">
<div class="text-center"> <div class="text-center">
<small> <small>
<span data-toggle="tooltip" data-placement="top" title="Starting balance from PTM settings">Start: &nbsp; <text class="text-autocolor"> @Model.PTMagicConfiguration.GeneralSettings.Application.StartBalance @Model.Summary.MainMarket </text></span> <span data-toggle="tooltip" data-placement="top" title="Starting balance from PTM settings">Start: &nbsp; <text class="text-autocolor"> @Model.SummaryData.StartBalance @Model.Summary.MainMarket </text></span>
<span data-toggle="tooltip" data-placement="top" title="TCV gain on starting balance"> &emsp; &emsp; Gain:&nbsp;<text class="text-autocolor">@Math.Round(((Model.totalCurrentValue - Model.PTMagicConfiguration.GeneralSettings.Application.StartBalance) / Model.PTMagicConfiguration.GeneralSettings.Application.StartBalance) * 100, 2)%</text></span> <span data-toggle="tooltip" data-placement="top" title="TCV gain on starting balance"> &emsp; &emsp; Gain:&nbsp;<text class="text-autocolor">@Math.Round(((Model.totalCurrentValue - Model.SummaryData.StartBalance) / Model.SummaryData.StartBalance) * 100, 2)%</text></span>
</small> </small>
</div> </div>
<div class="text-center"> <div class="text-center">
@ -49,7 +49,7 @@
</div> </div>
<div class="col-md-4 px-1"> <div class="col-md-4 px-1">
<div class="cdev" data-percent="100" data-duration="@Html.Raw(@Model.PTMagicConfiguration.GeneralSettings.Monitor.RefreshSeconds * 1000)" data-color="#aaa,#414d59"></div> @*<div class="cdev" data-percent="100" data-duration="@Html.Raw(@Model.PTMagicConfiguration.GeneralSettings.Monitor.RefreshSeconds * 1000)" data-color="#aaa,#414d59"></div>*@
<div class="card-box px-2" style="height:305px;"> <div class="card-box px-2" style="height:305px;">
@if (!Model.ProfitChartDataJSON.Equals("")) { @if (!Model.ProfitChartDataJSON.Equals("")) {
<div class="profit-chart"> <div class="profit-chart">
@ -61,6 +61,7 @@
</div> </div>
</div> </div>
</div> </div>
<div class="row"> <div class="row">
<div class="col-md-5 px-1"> <div class="col-md-5 px-1">
<div class="card-box px-2"> <div class="card-box px-2">
@ -115,53 +116,58 @@
<div class="col-md-7 px-1"> <div class="col-md-7 px-1">
<div class="card-box px-2"> <div class="card-box px-2">
<div class="cdev" data-percent="100" data-duration="@Html.Raw(@Model.PTMagicConfiguration.GeneralSettings.Monitor.RefreshSeconds * 1000)" data-color="#aaa,#414d59"></div> @*<div class="cdev" data-percent="100" data-duration="@Html.Raw(@Model.PTMagicConfiguration.GeneralSettings.Monitor.RefreshSeconds * 1000)" data-color="#aaa,#414d59"></div>
<br> <br>*@
<h4 class="m-t-0 m-b-20 header-title"><b>Sales Overview</b><small class="pull-right"><a href="@Html.Raw(Model.PTMagicConfiguration.GeneralSettings.Monitor.RootUrl)SalesAnalyzer">more</a></small></h4> <h4 class="m-t-0 m-b-20 header-title"><b>Sales Overview</b><small class="pull-right"><a href="@Html.Raw(Model.PTMagicConfiguration.GeneralSettings.Monitor.RootUrl)SalesAnalyzer">more</a></small></h4>
@{ @{
var overviewStats = Model.StatsData.FirstOrDefault(); // todaysStats is a new variable var overviewStats = Model.StatsData; // todaysStats is a new variable
var todaysSales = overviewStats.SalesToday; var todaysSales = overviewStats.SalesToday;
var todaysProfit = overviewStats.ProfitToday; var todaysProfit = overviewStats.ProfitToday;
var todaysFunding = overviewStats.FundingToday; var todaysFunding = overviewStats.FundingToday;
var todaysPercentGain = overviewStats.ProfitPercToday; var todaysPercentGain = overviewStats.ProfitPercToday;
var todaysFundingGain = todaysPercentGain * ((todaysProfit - todaysFunding) / todaysProfit); //var todaysFundingGain = todaysPercentGain * ((todaysProfit - todaysFunding) / todaysProfit);
var yesterdaysSales = overviewStats.SalesYesterday; var yesterdaysSales = overviewStats.SalesYesterday;
var yesterdaysProfit = overviewStats.ProfitYesterday; var yesterdaysProfit = overviewStats.ProfitYesterday;
var yesterdaysFunding = overviewStats.FundingYesterday; var yesterdaysFunding = overviewStats.FundingYesterday;
var yesterdaysPercentGain = overviewStats.ProfitPercYesterday; var yesterdaysPercentGain = overviewStats.ProfitPercYesterday;
var yesterdaysFundingGain = yesterdaysPercentGain * ((yesterdaysProfit + yesterdaysFunding) / yesterdaysProfit); //var yesterdaysFundingGain = yesterdaysPercentGain * ((yesterdaysProfit + yesterdaysFunding) / yesterdaysProfit);
var last7DaysSales = overviewStats.SalesWeek; var last7DaysSales = overviewStats.SalesWeek;
var last7DaysProfit = overviewStats.ProfitWeek; var last7DaysProfit = overviewStats.ProfitWeek;
var last7DaysFunding = overviewStats.FundingWeek; var last7DaysFunding = overviewStats.FundingWeek;
var last7DaysPercentGain = overviewStats.ProfitPercWeek; var last7DaysPercentGain = overviewStats.ProfitPercWeek;
var last7DaysFundingGain = last7DaysPercentGain * ((last7DaysProfit + last7DaysFunding) / last7DaysProfit); //var last7DaysFundingGain = last7DaysPercentGain * ((last7DaysProfit + last7DaysFunding) / last7DaysProfit);
var last30DaysSales = overviewStats.SalesMonth; var thisMonthSales = overviewStats.SalesThisMonth;
var last30DaysProfit = overviewStats.ProfitMonth; var thisMonthProfit = overviewStats.ProfitThisMonth;
var last30DaysFunding = overviewStats.FundingMonth; var thisMonthFunding = overviewStats.FundingThisMonth;
var last30DaysPercentGain = overviewStats.ProfitPercMonth; var thisMonthPercentGain = overviewStats.ProfitPercThisMonth;
var last30DaysFundingGain = last30DaysPercentGain * ((last30DaysProfit + last30DaysFunding) / last30DaysProfit); //var thisMonthFundingGain = thisMonthPercentGain * ((thisMonthProfit + thisMonthFunding) / thisMonthProfit);
var lastMonthSales = overviewStats.SalesLastMonth;
var lastMonthProfit = overviewStats.ProfitLastMonth;
var lastMonthFunding = overviewStats.FundingLastMonth;
var lastMonthPercentGain = overviewStats.ProfitPercLastMonth;
//var lastMonthFundingGain = lastMonthPercentGain * ((lastMonthProfit + lastMonthFunding) / lastMonthProfit);
var totalSales = overviewStats.TotalSales; var totalSales = overviewStats.TotalSales;
var totalProfit = overviewStats.TotalProfit; var totalProfit = overviewStats.TotalProfit;
var totalFunding = overviewStats.FundingTotal; var totalFunding = overviewStats.FundingTotal;
var totalProfitPercent = overviewStats.TotalProfitPerc; var totalProfitPercent = overviewStats.TotalProfitPerc;
var totalFundingGain = totalProfitPercent * ((totalProfit + totalFunding) / totalProfit); //var totalFundingGain = totalProfitPercent * ((totalProfit + totalFunding) / totalProfit);
double todaysProfitFiat = Math.Round((todaysProfit + todaysFunding) * Model.Summary.MainMarketPrice, 2);
double yesterdaysProfitFiat = Math.Round((yesterdaysProfit + yesterdaysFunding) * Model.Summary.MainMarketPrice, 2);
double last7DaysProfitFiat = Math.Round((last7DaysProfit + last7DaysFunding) * Model.Summary.MainMarketPrice, 2);
double last30DaysProfitFiat = Math.Round((last30DaysProfit + last30DaysFunding) * Model.Summary.MainMarketPrice, 2);
double totalProfitFiat = Math.Round((totalProfit + totalFunding) * Model.Summary.MainMarketPrice, 2);
double todaysProfitFiat = Math.Round((todaysProfit + todaysFunding) * Model.PTData.Summary.FiatConversionRate, 2);
double yesterdaysProfitFiat = Math.Round((yesterdaysProfit + yesterdaysFunding) * Model.PTData.Summary.FiatConversionRate, 2);
double last7DaysProfitFiat = Math.Round((last7DaysProfit + last7DaysFunding) * Model.PTData.Summary.FiatConversionRate, 2);
double thisMonthProfitFiat = Math.Round((thisMonthProfit + thisMonthFunding) * Model.PTData.Summary.FiatConversionRate, 2);
double lastMonthProfitFiat = Math.Round((lastMonthProfit + lastMonthFunding) * Model.PTData.Summary.FiatConversionRate, 2);
double totalProfitFiat = Math.Round((totalProfit + totalFunding) * Model.PTData.Summary.FiatConversionRate, 2);
bool futuresFunding = Model.PropertiesData.IsLeverageExchange;
} }
<table class="table table-sm"> <table class="table table-sm">
@ -169,10 +175,13 @@
<tr> <tr>
<th></th> <th></th>
<th class="text-right">Sales</th> <th class="text-right">Sales</th>
<th class="text-right">Profit @Model.Summary.MainMarket</th> <th class="text-right">Profit @Model.PTData.Summary.Market</th>
<th class="text-right">Funding</th>
<th class="text-right">@Model.Summary.MainFiatCurrency</th>
<th class="text-right">Gain</th> <th class="text-right">Gain</th>
@if (futuresFunding)
{
<th class="text-right">Funding</th>
}
<th class="text-right">@Model.PTData.Properties.Currency</th>
</tr> </tr>
</thead> </thead>
<tbody> <tbody>
@ -180,41 +189,67 @@
<th>Today</th> <th>Today</th>
<td class="text-right">@overviewStats.SalesToday</td> <td class="text-right">@overviewStats.SalesToday</td>
<td class="text-right text-autocolor">@todaysProfit.ToString("#,#0.00000000", new System.Globalization.CultureInfo("en-US"))</td> <td class="text-right text-autocolor">@todaysProfit.ToString("#,#0.00000000", new System.Globalization.CultureInfo("en-US"))</td>
<td class="text-right text-autocolor">@todaysPercentGain.ToString("#,#0.00", new System.Globalization.CultureInfo("en-US"))%</td>
@if (futuresFunding)
{
<td class="text-right text-autocolor">@todaysFunding.ToString("#,#0.00000000", new System.Globalization.CultureInfo("en-US"))</td> <td class="text-right text-autocolor">@todaysFunding.ToString("#,#0.00000000", new System.Globalization.CultureInfo("en-US"))</td>
}
<td class="text-right text-autocolor">@Html.Raw(todaysProfitFiat.ToString("#,#0.00", new System.Globalization.CultureInfo("en-US")))</td> <td class="text-right text-autocolor">@Html.Raw(todaysProfitFiat.ToString("#,#0.00", new System.Globalization.CultureInfo("en-US")))</td>
<td class="text-right text-autocolor">@todaysFundingGain.ToString("#,#0.00", new System.Globalization.CultureInfo("en-US"))%</td>
</tr> </tr>
<tr> <tr>
<th>Yesterday</th> <th>Yesterday</th>
<td class="text-right">@yesterdaysSales</td> <td class="text-right">@yesterdaysSales</td>
<td class="text-right text-autocolor">@yesterdaysProfit.ToString("#,#0.00000000", new System.Globalization.CultureInfo("en-US"))</td> <td class="text-right text-autocolor">@yesterdaysProfit.ToString("#,#0.00000000", new System.Globalization.CultureInfo("en-US"))</td>
<td class="text-right text-autocolor">@yesterdaysPercentGain.ToString("#,#0.00", new System.Globalization.CultureInfo("en-US"))%</td>
@if (futuresFunding)
{
<td class="text-right text-autocolor">@yesterdaysFunding.ToString("#,#0.00000000", new System.Globalization.CultureInfo("en-US"))</td> <td class="text-right text-autocolor">@yesterdaysFunding.ToString("#,#0.00000000", new System.Globalization.CultureInfo("en-US"))</td>
}
<td class="text-right text-autocolor">@Html.Raw(yesterdaysProfitFiat.ToString("#,#0.00", new System.Globalization.CultureInfo("en-US")))</td> <td class="text-right text-autocolor">@Html.Raw(yesterdaysProfitFiat.ToString("#,#0.00", new System.Globalization.CultureInfo("en-US")))</td>
<td class="text-right text-autocolor">@yesterdaysFundingGain.ToString("#,#0.00", new System.Globalization.CultureInfo("en-US"))%</td>
</tr> </tr>
<tr> <tr>
<th>Last 7 Days</th> <th>Last 7 Days</th>
<td class="text-right">@last7DaysSales</td> <td class="text-right">@last7DaysSales</td>
<td class="text-right text-autocolor">@last7DaysProfit.ToString("#,#0.00000000", new System.Globalization.CultureInfo("en-US"))</td> <td class="text-right text-autocolor">@last7DaysProfit.ToString("#,#0.00000000", new System.Globalization.CultureInfo("en-US"))</td>
<td class="text-right text-autocolor">@last7DaysPercentGain.ToString("#,#0.00", new System.Globalization.CultureInfo("en-US"))%</td>
@if (futuresFunding)
{
<td class="text-right text-autocolor">@last7DaysFunding.ToString("#,#0.00000000", new System.Globalization.CultureInfo("en-US"))</td> <td class="text-right text-autocolor">@last7DaysFunding.ToString("#,#0.00000000", new System.Globalization.CultureInfo("en-US"))</td>
}
<td class="text-right text-autocolor">@Html.Raw(last7DaysProfitFiat.ToString("#,#0.00", new System.Globalization.CultureInfo("en-US")))</td> <td class="text-right text-autocolor">@Html.Raw(last7DaysProfitFiat.ToString("#,#0.00", new System.Globalization.CultureInfo("en-US")))</td>
<td class="text-right text-autocolor">@last7DaysFundingGain.ToString("#,#0.00", new System.Globalization.CultureInfo("en-US"))%</td>
</tr> </tr>
<tr> <tr>
<th>Last 30 Days</th> <th>This Month</th>
<td class="text-right">@last30DaysSales</td> <td class="text-right">@thisMonthSales</td>
<td class="text-right text-autocolor">@last30DaysProfit.ToString("#,#0.00000000", new System.Globalization.CultureInfo("en-US"))</td> <td class="text-right text-autocolor">@thisMonthProfit.ToString("#,#0.00000000", new System.Globalization.CultureInfo("en-US"))</td>
<td class="text-right text-autocolor">@last30DaysFunding.ToString("#,#0.00000000", new System.Globalization.CultureInfo("en-US"))</td> <td class="text-right text-autocolor">@thisMonthPercentGain.ToString("#,#0.00", new System.Globalization.CultureInfo("en-US"))%</td>
<td class="text-right text-autocolor">@Html.Raw(last30DaysProfitFiat.ToString("#,#0.00", new System.Globalization.CultureInfo("en-US")))</td> @if (futuresFunding)
<td class="text-right text-autocolor">@last30DaysFundingGain.ToString("#,#0.00", new System.Globalization.CultureInfo("en-US"))%</td> {
<td class="text-right text-autocolor">@thisMonthFunding.ToString("#,#0.00000000", new System.Globalization.CultureInfo("en-US"))</td>
}
<td class="text-right text-autocolor">@Html.Raw(thisMonthProfitFiat.ToString("#,#0.00", new System.Globalization.CultureInfo("en-US")))</td>
</tr>
<tr>
<th>Last Month</th>
<td class="text-right">@lastMonthSales</td>
<td class="text-right text-autocolor">@lastMonthProfit.ToString("#,#0.00000000", new System.Globalization.CultureInfo("en-US"))</td>
<td class="text-right text-autocolor">@lastMonthPercentGain.ToString("#,#0.00", new System.Globalization.CultureInfo("en-US"))%</td>
@if (futuresFunding)
{
<td class="text-right text-autocolor">@lastMonthFunding.ToString("#,#0.00000000", new System.Globalization.CultureInfo("en-US"))</td>
}
<td class="text-right text-autocolor">@Html.Raw(lastMonthProfitFiat.ToString("#,#0.00", new System.Globalization.CultureInfo("en-US")))</td>
</tr> </tr>
<tr> <tr>
<th>Total</th> <th>Total</th>
<td class="text-right">@totalSales</td> <td class="text-right">@totalSales</td>
<td class="text-right text-autocolor">@totalProfit.ToString("#,#0.00000000", new System.Globalization.CultureInfo("en-US"))</td> <td class="text-right text-autocolor">@totalProfit.ToString("#,#0.00000000", new System.Globalization.CultureInfo("en-US"))</td>
<td class="text-right text-autocolor">@totalProfitPercent.ToString("#,#0.00", new System.Globalization.CultureInfo("en-US"))%</td>
@if (futuresFunding)
{
<td class="text-right text-autocolor">@totalFunding.ToString("#,#0.00000000", new System.Globalization.CultureInfo("en-US"))</td> <td class="text-right text-autocolor">@totalFunding.ToString("#,#0.00000000", new System.Globalization.CultureInfo("en-US"))</td>
}
<td class="text-right text-autocolor">@Html.Raw(totalProfitFiat.ToString("#,#0.00", new System.Globalization.CultureInfo("en-US")))</td> <td class="text-right text-autocolor">@Html.Raw(totalProfitFiat.ToString("#,#0.00", new System.Globalization.CultureInfo("en-US")))</td>
<td class="text-right text-autocolor">@totalFundingGain.ToString("#,#0.00", new System.Globalization.CultureInfo("en-US"))%</td>
</tr> </tr>
</tbody> </tbody>
</table> </table>
@ -226,72 +261,99 @@
<script src="@Html.Raw(Model.PTMagicConfiguration.GeneralSettings.Monitor.RootUrl)assets/plugins/nvd3/nv.d3.min.js"></script> <script src="@Html.Raw(Model.PTMagicConfiguration.GeneralSettings.Monitor.RootUrl)assets/plugins/nvd3/nv.d3.min.js"></script>
<script src="@Html.Raw(Model.PTMagicConfiguration.GeneralSettings.Monitor.RootUrl)assets/plugins/tablesaw/js/tablesaw.js"></script> <script src="@Html.Raw(Model.PTMagicConfiguration.GeneralSettings.Monitor.RootUrl)assets/plugins/tablesaw/js/tablesaw.js"></script>
<script src="@Html.Raw(Model.PTMagicConfiguration.GeneralSettings.Monitor.RootUrl)assets/plugins/tablesaw/js/tablesaw-init.js"></script> <script src="@Html.Raw(Model.PTMagicConfiguration.GeneralSettings.Monitor.RootUrl)assets/plugins/tablesaw/js/tablesaw-init.js"></script>
<script type="text/javascript"> <script type="text/javascript">
$(document).ready(function () { $(document).ready(function () {
$(".cdev").circlos(); $(".cdev").circlos();
$('[data-toggle="tooltip"]').tooltip(); $('[data-toggle="tooltip"]').tooltip();
$('.text-autocolor').autocolor(false); $('.text-autocolor').autocolor(false);
var assetDistributionChart; // Keep a reference to the chart
var assetDistributionData; // Keep a reference to the data
@if (!Model.AssetDistributionData.Equals("")) { @if (!Model.AssetDistributionData.Equals("")) {
<text> <text>
nv.addGraph(function() { nv.addGraph(function() {
var chart = nv.models.pieChart() assetDistributionChart = nv.models.pieChart()
.x(function(d) { return d.label }) .x(function(d) { return d.label })
.y(function(d) { return d.value }) .y(function(d) { return d.value })
.showLabels(true) //Display pie labels .showLabels(true)
.labelThreshold(.1) //Configure the minimum slice size for labels to show up .labelThreshold(.1)
.labelType("percent") //Configure what type of data to show in the label. Can be "key", "value" or "percent" .labelType("percent")
.donut(true) //Turn on Donut mode. Makes pie chart look tasty! .donut(true)
.donutRatio(0.3) //Configure how big you want the donut hole size to be. .donutRatio(0.3);
;
assetDistributionData = @Html.Raw(Model.AssetDistributionData);
d3.select("#AssetDistribution svg") d3.select("#AssetDistribution svg")
.datum(@Html.Raw(Model.AssetDistributionData)) .datum(assetDistributionData)
.transition().duration(350) .transition().duration(0)
.call(chart); .call(assetDistributionChart);
return chart; return assetDistributionChart;
}); });
</text> </text>
} }
}); });
</script>
<script type="text/javascript">
(function ($) { (function ($) {
'use strict'; 'use strict';
$('[role="tooltip"]').remove(); $('[role="tooltip"]').remove();
$('[data-toggle="tooltip"]').tooltip(); $('[data-toggle="tooltip"]').tooltip();
$('.text-autocolor').autocolor(false); $('.text-autocolor').autocolor(false);
@if (!Model.Summary.CurrentGlobalSetting.SettingName.Equals(Model.LastGlobalSetting)) { var trendChart; // Keep a reference to the chart
<text> var trendData; // Keep a reference to the data
$.Notification.notify('success', 'top left', '@Core.Helper.SystemHelper.SplitCamelCase(Model.Summary.CurrentGlobalSetting.SettingName) now active!', 'PTMagic switched Profit Trailer settings to "@Core.Helper.SystemHelper.SplitCamelCase(Model.Summary.CurrentGlobalSetting.SettingName)".');
</text>
}
@if (!Model.TrendChartDataJSON.Equals("")) { @if (!Model.TrendChartDataJSON.Equals("")) {
<text> <text>
nv.addGraph(function () { nv.addGraph(function () {
var lineChart = nv.models.lineChart(); trendChart = nv.models.lineChart();
var height = 300; var height = 300;
var chartData = @Html.Raw(Model.TrendChartDataJSON); trendChart.useInteractiveGuideline(true);
lineChart.useInteractiveGuideline(true); trendChart.xAxis.tickFormat(function (d) { return d3.time.format('%H:%M')(new Date(d)); });
lineChart.xAxis.tickFormat(function (d) { return d3.time.format('%H:%M')(new Date(d)); }); trendChart.yAxis.axisLabel('Trend %').tickFormat(d3.format(',.2f'));
lineChart.yAxis.axisLabel('Trend %').tickFormat(d3.format(',.2f'));
d3.select('.trend-chart svg').attr('perserveAspectRatio', 'xMinYMid').datum(chartData).transition().duration(500).call(lineChart); trendData = @Html.Raw(Model.TrendChartDataJSON);
//nv.utils.windowResize(lineChart.update); v1.3.0 => Removed this line to prevent memory leak
return lineChart; d3.select('.trend-chart svg')
}); .datum(trendData)
</text> .transition().duration(0)
} .call(trendChart);
@if (!Model.ProfitChartDataJSON.Equals("")) { return trendChart;
<text> });
nv.addGraph(function () { </text>
var lineChart = nv.models.lineChart(); }
var height = 300; })(jQuery);
var chartData = @Html.Raw(Model.ProfitChartDataJSON); </script>
lineChart.useInteractiveGuideline(true);
lineChart.xAxis.tickFormat(function (d) { return d3.time.format('%Y/%m/%d')(new Date(d)); }); <script type="text/javascript">
lineChart.yAxis.axisLabel('Daily Profit').tickFormat(d3.format(',.2f')); (function ($) {
d3.select('.profit-chart svg').attr('perserveAspectRatio', 'xMinYMid').datum(chartData).transition().duration(500).call(lineChart); 'use strict';
//nv.utils.windowResize(lineChart.update); v1.3.0 => Removed this line to prevent memory leak $('[role="tooltip"]').remove();
return lineChart; $('[data-toggle="tooltip"]').tooltip();
$('.text-autocolor').autocolor(false);
var profitChart; // Keep a reference to the chart
var profitData; // Keep a reference to the data
@if (!Model.ProfitChartDataJSON.Equals("")) {
<text>
nv.addGraph(function () {
profitChart = nv.models.lineChart();
var height = 300;
profitChart.useInteractiveGuideline(true);
profitChart.xAxis.tickFormat(function (d) { return d3.time.format('%Y/%m/%d')(new Date(d)); });
profitChart.yAxis.axisLabel('Daily Profit').tickFormat(d3.format(',.2f'));
profitData = @Html.Raw(Model.ProfitChartDataJSON);
d3.select('.profit-chart svg')
.datum(profitData)
.transition().duration(0)
.call(profitChart);
return profitChart;
}); });
</text> </text>
} }

View File

@ -6,14 +6,19 @@ using Core.Main;
using Core.Helper; using Core.Helper;
using Core.Main.DataObjects; using Core.Main.DataObjects;
using Core.Main.DataObjects.PTMagicData; using Core.Main.DataObjects.PTMagicData;
using Core.MarketAnalyzer; using System.Globalization;
using System.Text;
namespace Monitor.Pages namespace Monitor.Pages
{ {
public class DashboardBottomModel : _Internal.BasePageModelSecureAJAX public class DashboardBottomModel : _Internal.BasePageModelSecureAJAX
{ {
public ProfitTrailerData PTData = null; public ProfitTrailerData PTData = null;
public List<StatsData> StatsData { get; set; } public StatsData StatsData { get; set; }
public PropertiesData PropertiesData { get; set; }
public SummaryData SummaryData { get; set; }
public List<DailyStatsData> DailyStats { get; set; } = new List<DailyStatsData>();
public List<DailyPNLData> DailyPNL { get; set; } = new List<DailyPNLData>();
public List<MarketTrend> MarketTrends { get; set; } = new List<MarketTrend>(); public List<MarketTrend> MarketTrends { get; set; } = new List<MarketTrend>();
public string TrendChartDataJSON = ""; public string TrendChartDataJSON = "";
public string ProfitChartDataJSON = ""; public string ProfitChartDataJSON = "";
@ -35,6 +40,10 @@ namespace Monitor.Pages
{ {
PTData = this.PtDataObject; PTData = this.PtDataObject;
StatsData = this.PTData.Stats; StatsData = this.PTData.Stats;
PropertiesData = this.PTData.Properties;
SummaryData = this.PTData.Summary;
List<DailyStatsData> dailyStatsData = this.PTData.DailyStats;
List<DailyPNLData> dailyPNLData = this.PTData.DailyPNL;
// Cleanup temp files // Cleanup temp files
FileHelper.CleanupFilesMinutes(PTMagicMonitorBasePath + "wwwroot" + System.IO.Path.DirectorySeparatorChar + "assets" + System.IO.Path.DirectorySeparatorChar + "tmp" + System.IO.Path.DirectorySeparatorChar, 5); FileHelper.CleanupFilesMinutes(PTMagicMonitorBasePath + "wwwroot" + System.IO.Path.DirectorySeparatorChar + "assets" + System.IO.Path.DirectorySeparatorChar + "tmp" + System.IO.Path.DirectorySeparatorChar, 5);
@ -57,10 +66,11 @@ namespace Monitor.Pages
BuildProfitChartData(); BuildProfitChartData();
} }
private void BuildMarketTrendChartData() private void BuildMarketTrendChartData()
{ {
StringBuilder trendChartDataJSON = new StringBuilder();
if (MarketTrends.Count > 0) if (MarketTrends.Count > 0)
{ {
TrendChartDataJSON = "["; trendChartDataJSON.Append("[");
int mtIndex = 0; int mtIndex = 0;
foreach (MarketTrend mt in MarketTrends) foreach (MarketTrend mt in MarketTrends)
{ {
@ -82,12 +92,12 @@ namespace Monitor.Pages
if (marketTrendChangeSummaries.Count > 0) if (marketTrendChangeSummaries.Count > 0)
{ {
if (!TrendChartDataJSON.Equals("[")) TrendChartDataJSON += ","; if (!trendChartDataJSON.ToString().Equals("[")) trendChartDataJSON.Append(",");
TrendChartDataJSON += "{"; trendChartDataJSON.Append("{");
TrendChartDataJSON += "key: '" + SystemHelper.SplitCamelCase(mt.Name) + "',"; trendChartDataJSON.Append("key: '" + SystemHelper.SplitCamelCase(mt.Name) + "',");
TrendChartDataJSON += "color: '" + lineColor + "',"; trendChartDataJSON.Append("color: '" + lineColor + "',");
TrendChartDataJSON += "values: ["; trendChartDataJSON.Append("values: [");
// Get trend ticks for chart // Get trend ticks for chart
DateTime currentDateTime = new DateTime(DateTime.UtcNow.Year, DateTime.UtcNow.Month, DateTime.UtcNow.Day, DateTime.UtcNow.Hour, 0, 0); DateTime currentDateTime = new DateTime(DateTime.UtcNow.Year, DateTime.UtcNow.Month, DateTime.UtcNow.Day, DateTime.UtcNow.Hour, 0, 0);
@ -100,10 +110,10 @@ namespace Monitor.Pages
if (tickRange.Count > 0) if (tickRange.Count > 0)
{ {
MarketTrendChange mtc = tickRange.First(); MarketTrendChange mtc = tickRange.First();
if (tickTime != startDateTime) TrendChartDataJSON += ",\n"; if (tickTime != startDateTime) trendChartDataJSON.Append(",\n");
if (Double.IsInfinity(mtc.TrendChange)) mtc.TrendChange = 0; if (Double.IsInfinity(mtc.TrendChange)) mtc.TrendChange = 0;
TrendChartDataJSON += "{ x: new Date('" + tickTime.ToString("yyyy-MM-ddTHH:mm:ss").Replace(".", ":") + "'), y: " + mtc.TrendChange.ToString("0.00", new System.Globalization.CultureInfo("en-US")) + "}"; trendChartDataJSON.Append("{ x: new Date('" + tickTime.ToString("yyyy-MM-ddTHH:mm:ss").Replace(".", ":") + "'), y: " + mtc.TrendChange.ToString("0.00", new System.Globalization.CultureInfo("en-US")) + "}");
trendChartTicks++; trendChartTicks++;
} }
} }
@ -112,55 +122,45 @@ namespace Monitor.Pages
if (latestTickRange.Count > 0) if (latestTickRange.Count > 0)
{ {
MarketTrendChange mtc = latestTickRange.First(); MarketTrendChange mtc = latestTickRange.First();
if (trendChartTicks > 0) TrendChartDataJSON += ",\n"; if (trendChartTicks > 0) trendChartDataJSON.Append(",\n");
if (Double.IsInfinity(mtc.TrendChange)) mtc.TrendChange = 0; if (Double.IsInfinity(mtc.TrendChange)) mtc.TrendChange = 0;
TrendChartDataJSON += "{ x: new Date('" + mtc.TrendDateTime.ToString("yyyy-MM-ddTHH:mm:ss").Replace(".", ":") + "'), y: " + mtc.TrendChange.ToString("0.00", new System.Globalization.CultureInfo("en-US")) + "}"; trendChartDataJSON.Append("{ x: new Date('" + mtc.TrendDateTime.ToString("yyyy-MM-ddTHH:mm:ss").Replace(".", ":") + "'), y: " + mtc.TrendChange.ToString("0.00", new System.Globalization.CultureInfo("en-US")) + "}");
} }
TrendChartDataJSON += "]"; trendChartDataJSON.Append("]");
TrendChartDataJSON += "}"; trendChartDataJSON.Append("}");
mtIndex++; mtIndex++;
} }
} }
} }
} }
TrendChartDataJSON += "]"; trendChartDataJSON.Append("]");
}
} }
TrendChartDataJSON = trendChartDataJSON.ToString();
}
private void BuildProfitChartData() private void BuildProfitChartData()
{ {
int tradeDayIndex = 0; StringBuilder profitPerDayJSON = new StringBuilder();
string profitPerDayJSON = "";
if (PTData.SellLog.Count > 0) if (PTData.DailyStats.Count > 0)
{ {
DateTime minSellLogDate = PTData.SellLog.OrderBy(sl => sl.SoldDate).First().SoldDate.Date; DateTime endDate = DateTime.UtcNow.Date;
DateTime graphStartDate = DateTime.UtcNow.Date.AddDays(-30); DateTime startDate = endDate.AddDays(-30);
if (minSellLogDate > graphStartDate)
for (DateTime date = startDate; date <= endDate; date = date.AddDays(1))
{ {
graphStartDate = minSellLogDate; if (profitPerDayJSON.Length > 0)
}
for (DateTime salesDate = graphStartDate; salesDate <= DateTime.UtcNow.Date; salesDate = salesDate.AddDays(1))
{ {
if (tradeDayIndex > 0) profitPerDayJSON.Append(",\n");
{
profitPerDayJSON += ",\n";
} }
int trades = PTData.SellLog.FindAll(t => t.SoldDate.Date == salesDate).Count; DailyStatsData dailyStats = PTData.DailyStats.Find(ds => DateTime.ParseExact(ds.Date, "d-M-yyyy", CultureInfo.InvariantCulture) == date);
double profit = PTData.SellLog.FindAll(t => t.SoldDate.Date == salesDate).Sum(t => t.Profit); double profitFiat = dailyStats != null ? Math.Round(dailyStats.TotalProfitCurrency,2) : 0;
double profitFiat = Math.Round(profit * Summary.MainMarketPrice, 2); profitPerDayJSON.Append("{x: new Date('" + date.ToString("yyyy-MM-dd") + "'), y: " + profitFiat.ToString("0.00", new System.Globalization.CultureInfo("en-US")) + "}");
profitPerDayJSON += "{x: new Date('" + salesDate.ToString("yyyy-MM-dd") + "'), y: " + profitFiat.ToString("0.00", new System.Globalization.CultureInfo("en-US")) + "}";
tradeDayIndex++;
} }
ProfitChartDataJSON = "["; ProfitChartDataJSON = "[{key: 'Profit in " + PTData.Properties.Currency + "',color: '" + Constants.ChartLineColors[1] + "',values: [" + profitPerDayJSON.ToString() + "]}]";
ProfitChartDataJSON += "{";
ProfitChartDataJSON += "key: 'Profit in " + Summary.MainFiatCurrency + "',";
ProfitChartDataJSON += "color: '" + Constants.ChartLineColors[1] + "',";
ProfitChartDataJSON += "values: [" + profitPerDayJSON + "]";
ProfitChartDataJSON += "}";
ProfitChartDataJSON += "]";
} }
} }
private void BuildAssetDistributionData() private void BuildAssetDistributionData()
{ {
// the per PT-Eelroy, the PT API doesn't provide these values when using leverage, so they are calculated here to cover either case. // the per PT-Eelroy, the PT API doesn't provide these values when using leverage, so they are calculated here to cover either case.

View File

@ -10,7 +10,6 @@
"ProfitTrailerMonitorURLXtra": "", // URLs for additional bots you want PTM to update (optional - comma separated list) "ProfitTrailerMonitorURLXtra": "", // URLs for additional bots you want PTM to update (optional - comma separated list)
"ProfitTrailerDefaultSettingName": "default", // Your Profit Trailer default setting name (needed to change your settings) "ProfitTrailerDefaultSettingName": "default", // Your Profit Trailer default setting name (needed to change your settings)
"Exchange": "Bittrex", // The exchange your are running Profit Trailer on "Exchange": "Bittrex", // The exchange your are running Profit Trailer on
"StartBalance": 0, // The balance you had in your wallet when you started working with Profit Trailer
"TimezoneOffset": "+0:00", // Your timezone offset from UTC time "TimezoneOffset": "+0:00", // Your timezone offset from UTC time
//"MainFiatCurrency": "USD", // Your main fiat currency that will be used in the monitor //"MainFiatCurrency": "USD", // Your main fiat currency that will be used in the monitor
"FloodProtectionMinutes": 0, // If a price trend is just zig-zagging around its trigger, you may want to protect your settings from getting switched back and forth every minute "FloodProtectionMinutes": 0, // If a price trend is just zig-zagging around its trigger, you may want to protect your settings from getting switched back and forth every minute

View File

@ -10,7 +10,6 @@
"ProfitTrailerMonitorURLXtra": "", // URLs for additional bots you want PTM to update (optional - comma separated list) "ProfitTrailerMonitorURLXtra": "", // URLs for additional bots you want PTM to update (optional - comma separated list)
"ProfitTrailerDefaultSettingName": "default", // Your Profit Trailer default setting name (needed to change your settings) "ProfitTrailerDefaultSettingName": "default", // Your Profit Trailer default setting name (needed to change your settings)
"Exchange": "Bittrex", // The exchange your are running Profit Trailer on "Exchange": "Bittrex", // The exchange your are running Profit Trailer on
"StartBalance": 0, // The balance you had in your wallet when you started working with Profit Trailer
"TimezoneOffset": "+0:00", // Your timezone offset from UTC time "TimezoneOffset": "+0:00", // Your timezone offset from UTC time
//"MainFiatCurrency": "USD", // Your main fiat currency that will be used in the monitor //"MainFiatCurrency": "USD", // Your main fiat currency that will be used in the monitor
"FloodProtectionMinutes": 0, // If a price trend is just zig-zagging around its trigger, you may want to protect your settings from getting switched back and forth every minute "FloodProtectionMinutes": 0, // If a price trend is just zig-zagging around its trigger, you may want to protect your settings from getting switched back and forth every minute