public void ImportPeriodicDataWhenCurrencyCodesAreEmpty() { ICurrencyImporter importer = new JsonCurrencyImporter(); ICurrencyProvider currencyProvider = new NationalBankCurrencyProvider(importer); ICachingProcessor cachingProcessor = new ApiDatabaseCachingProcessor(currencyProvider, new MsSqlExplorerRepository(new CurrencyDataContext())); ChartTimePeriod timePeriod = new ChartTimePeriod(DateTime.Now.Subtract(TimeSpan.FromDays(10)), DateTime.Now); var data = cachingProcessor.RequestPeriodData(timePeriod, new CurrencyCodeEntry[] { }); Assert.Equal(0, data.Count); }
public void ImportPeriodicDataWhenCurrencyCodesArrayIsNull() { ICurrencyImporter importer = new JsonCurrencyImporter(); ICurrencyProvider currencyProvider = new NationalBankCurrencyProvider(importer); ICachingProcessor cachingProcessor = new ApiDatabaseCachingProcessor(currencyProvider, new MsSqlExplorerRepository(new CurrencyDataContext())); ChartTimePeriod timePeriod = new ChartTimePeriod(DateTime.Now.Subtract(TimeSpan.FromDays(10)), DateTime.Now); Action action = () => { cachingProcessor.RequestPeriodData(timePeriod, null); }; Assert.ThrowsAny <NullReferenceException>(action); }
public LastStatsTimeSpan GetLastStatsTimeSpan(ChartTimePeriod timePeriod) { switch (timePeriod) { case ChartTimePeriod.Weekly: return(LastStatsTimeSpan.Week); case ChartTimePeriod.Monthly: return(LastStatsTimeSpan.Month); case ChartTimePeriod.Yearly: return(LastStatsTimeSpan.Year); case ChartTimePeriod.AllTime: return(LastStatsTimeSpan.Overall); default: return(LastStatsTimeSpan.Week); } }
public async Task ChangeGuildSettingAsync(IGuild guild, ChartTimePeriod chartTimePeriod, ChartType chartType) { var existingGuild = await this.db.Guilds.FirstOrDefaultAsync(f => f.DiscordGuildId == guild.Id); if (existingGuild == null) { var newGuild = new Guild { DiscordGuildId = guild.Id, ChartTimePeriod = chartTimePeriod, ChartType = chartType, Name = guild.Name, TitlesEnabled = true }; this.db.Guilds.Add(newGuild); await this.db.SaveChangesAsync(); } }
public async Task ChangeGuildSettingAsync(IGuild guild, ChartTimePeriod chartTimePeriod, ChartType chartType) { string guildId = guild.Id.ToString(); Guild existingGuild = await db.Guilds.FirstOrDefaultAsync(f => f.DiscordGuildID == guildId).ConfigureAwait(false); if (existingGuild == null) { Guild newGuild = new Guild { DiscordGuildID = guildId, ChartTimePeriod = chartTimePeriod, ChartType = chartType, Name = guild.Name, TitlesEnabled = true, }; db.Guilds.Add(newGuild); await db.SaveChangesAsync().ConfigureAwait(false); } }
private UserSettings LoadDefaultSettings() { UserSettings defaultUserSettings = new UserSettings(); defaultUserSettings.Language = (CurrencyExplorerLanguage)Enum.Parse(typeof(CurrencyExplorerLanguage), ""); // Process default period. ChartTimePeriod timePeriod = new ChartTimePeriod(); string configPeriodInDays = "";//Configuration["ExplorerSettings:Defaults:ChartPeriodInDays"]; double periodInDays = 10; if (double.TryParse(configPeriodInDays, out periodInDays) == false) { Debug.WriteLine($"Incorrect ChartPeriodInDays value from configuration file. Default valye is set."); } timePeriod.Begin = DateTime.Now.Subtract(TimeSpan.FromDays(periodInDays)); timePeriod.End = DateTime.Now; defaultUserSettings.TimePeriod = timePeriod; // Get currencies list to be displayed. var codesList = Utils.GetListFromConfiguration(Configuration, "ExplorerSettings:Defaults:CurrenciesList"); List <CurrencyCodeEntry> defaultCodes = new List <CurrencyCodeEntry>(); var allCodes = CachingProcessor.RequestAllCurrencyCodes().Distinct().ToList(); defaultCodes.AddRange(allCodes.Where(x => codesList.Contains(x.Alias))); defaultUserSettings.Currencies = defaultCodes.Select(x => new CurrencyDataEntry() { DbCurrencyCodeEntry = x }); return(defaultUserSettings); }
public async Task ChangeGuildSettingAsync(IGuild guild, ChartTimePeriod chartTimePeriod, FmEmbedType fmEmbedType) { await using var db = new FMBotDbContext(ConfigData.Data.Database.ConnectionString); var existingGuild = await db.Guilds .AsQueryable() .FirstOrDefaultAsync(f => f.DiscordGuildId == guild.Id); if (existingGuild == null) { var newGuild = new Guild { DiscordGuildId = guild.Id, ChartTimePeriod = chartTimePeriod, FmEmbedType = fmEmbedType, Name = guild.Name, TitlesEnabled = true }; db.Guilds.Add(newGuild); await db.SaveChangesAsync(); } }
public IQueryable <CurrencyDataEntry> GetDataEntries(ChartTimePeriod timePeriod) { throw new System.NotImplementedException(); }
public static TimeSettingsModel GetTimePeriod( string[] extraOptions, LastStatsTimeSpan defaultLastStatsTimeSpan = LastStatsTimeSpan.Week, ChartTimePeriod defaultChartTimePeriod = ChartTimePeriod.Weekly, string defaultUrlParameter = "LAST_7_DAYS", string defaultApiParameter = "7day", string defaultDescription = "Weekly") { var settingsModel = new TimeSettingsModel(); // time period if (extraOptions.Contains("weekly") || extraOptions.Contains("week") || extraOptions.Contains("w")) { settingsModel.LastStatsTimeSpan = LastStatsTimeSpan.Week; settingsModel.ChartTimePeriod = ChartTimePeriod.Weekly; settingsModel.Description = "Weekly"; settingsModel.UrlParameter = "date_preset=LAST_7_DAYS"; settingsModel.ApiParameter = "7day"; } else if (extraOptions.Contains("monthly") || extraOptions.Contains("month") || extraOptions.Contains("m")) { settingsModel.LastStatsTimeSpan = LastStatsTimeSpan.Month; settingsModel.ChartTimePeriod = ChartTimePeriod.Monthly; settingsModel.Description = "Monthly"; settingsModel.UrlParameter = "date_preset=LAST_30_DAYS"; settingsModel.ApiParameter = "1month"; } else if (extraOptions.Contains("quarterly") || extraOptions.Contains("quarter") || extraOptions.Contains("q")) { settingsModel.LastStatsTimeSpan = LastStatsTimeSpan.Quarter; settingsModel.ChartTimePeriod = ChartTimePeriod.Quarterly; settingsModel.Description = "Quarterly"; settingsModel.UrlParameter = "date_preset=LAST_90_DAYS"; settingsModel.ApiParameter = "3month"; } else if (extraOptions.Contains("halfyearly") || extraOptions.Contains("half") || extraOptions.Contains("h")) { settingsModel.LastStatsTimeSpan = LastStatsTimeSpan.Half; settingsModel.ChartTimePeriod = ChartTimePeriod.Half; settingsModel.Description = "Half-yearly"; settingsModel.UrlParameter = "date_preset=LAST_180_DAYS"; settingsModel.ApiParameter = "6month"; } else if (extraOptions.Contains("yearly") || extraOptions.Contains("year") || extraOptions.Contains("y")) { settingsModel.LastStatsTimeSpan = LastStatsTimeSpan.Year; settingsModel.ChartTimePeriod = ChartTimePeriod.Yearly; settingsModel.Description = "Yearly"; settingsModel.UrlParameter = "date_preset=LAST_365_DAYS"; settingsModel.ApiParameter = "12month"; } else if (extraOptions.Contains("overall") || extraOptions.Contains("alltime") || extraOptions.Contains("o") || extraOptions.Contains("at") || extraOptions.Contains("a")) { settingsModel.LastStatsTimeSpan = LastStatsTimeSpan.Overall; settingsModel.ChartTimePeriod = ChartTimePeriod.AllTime; settingsModel.Description = "Overall"; settingsModel.UrlParameter = "date_preset=ALL"; settingsModel.ApiParameter = "overall"; } else if (extraOptions.Contains("6day") || extraOptions.Contains("6-day") || extraOptions.Contains("day6") || extraOptions.Contains("6d")) { var dateString = DateTime.Today.AddDays(-6).ToString("yyyy-M-dd"); settingsModel.Description = "6-day"; settingsModel.UrlParameter = $"from={dateString}"; settingsModel.UsePlays = true; settingsModel.PlayDays = 6; } else if (extraOptions.Contains("5day") || extraOptions.Contains("5-day") || extraOptions.Contains("day5") || extraOptions.Contains("5d")) { var dateString = DateTime.Today.AddDays(-5).ToString("yyyy-M-dd"); settingsModel.Description = "5-day"; settingsModel.UrlParameter = $"from={dateString}"; settingsModel.UsePlays = true; settingsModel.PlayDays = 5; } else if (extraOptions.Contains("4day") || extraOptions.Contains("4-day") || extraOptions.Contains("day4") || extraOptions.Contains("4d")) { var dateString = DateTime.Today.AddDays(-4).ToString("yyyy-M-dd"); settingsModel.Description = "4-day"; settingsModel.UrlParameter = $"from={dateString}"; settingsModel.UsePlays = true; settingsModel.PlayDays = 4; } else if (extraOptions.Contains("3day") || extraOptions.Contains("3-day") || extraOptions.Contains("day3") || extraOptions.Contains("3d")) { var dateString = DateTime.Today.AddDays(-3).ToString("yyyy-M-dd"); settingsModel.Description = "3-day"; settingsModel.UrlParameter = $"from={dateString}"; settingsModel.UsePlays = true; settingsModel.PlayDays = 3; } else if (extraOptions.Contains("2day") || extraOptions.Contains("2-day") || extraOptions.Contains("day2") || extraOptions.Contains("2d")) { var dateString = DateTime.Today.AddDays(-2).ToString("yyyy-M-dd"); settingsModel.Description = "2-day"; settingsModel.UrlParameter = $"from={dateString}"; settingsModel.UsePlays = true; settingsModel.PlayDays = 2; } else if (extraOptions.Contains("1day") || extraOptions.Contains("1-day") || extraOptions.Contains("day1") || extraOptions.Contains("1d") || extraOptions.Contains("today")) { var dateString = DateTime.Today.AddDays(-1).ToString("yyyy-M-dd"); settingsModel.Description = "1-day"; settingsModel.UrlParameter = $"from={dateString}"; settingsModel.UsePlays = true; settingsModel.PlayDays = 1; } else if (extraOptions.Contains("overall") || extraOptions.Contains("alltime") || extraOptions.Contains("o") || extraOptions.Contains("at") || extraOptions.Contains("a")) { settingsModel.LastStatsTimeSpan = LastStatsTimeSpan.Overall; settingsModel.ChartTimePeriod = ChartTimePeriod.AllTime; settingsModel.Description = "Overall"; settingsModel.UrlParameter = "date_preset=ALL"; settingsModel.ApiParameter = "overall"; } else { settingsModel.LastStatsTimeSpan = defaultLastStatsTimeSpan; settingsModel.ChartTimePeriod = defaultChartTimePeriod; settingsModel.Description = defaultDescription; settingsModel.UrlParameter = defaultUrlParameter; settingsModel.ApiParameter = defaultApiParameter; settingsModel.UsePlays = false; } return(settingsModel); }
public IDictionary <CurrencyCodeEntry, List <CurrencyDataEntry> > RequestPeriodCurrencyData(ChartTimePeriod period) { throw new NotImplementedException(); }
public IDictionary <CurrencyCodeEntry, List <CurrencyDataEntry> > RequestPeriodData(ChartTimePeriod timePeriod, ICollection <CurrencyCodeEntry> codes) { IDictionary <CurrencyCodeEntry, List <CurrencyDataEntry> > periodCurrencyData = new Dictionary <CurrencyCodeEntry, List <CurrencyDataEntry> >(); DateTime beginTime = SelectWorkingDate(timePeriod.Begin, DateSelection.BeforeWeekends); DateTime endTime = SelectWorkingDate(timePeriod.End, DateSelection.AfterWeekends); foreach (CurrencyCodeEntry code in codes) { // Try get from database. var dbEntries = TryGetPeriodDatabaseData(beginTime, endTime, code); List <CurrencyDataEntry> correctedEntries = null; if (dbEntries == null) { correctedEntries = new List <CurrencyDataEntry>(); } else { correctedEntries = dbEntries.ToList(); } CurrencyDataEntry lastSingleData = null; CurrencyDataEntry tempSingleData = null; // Check currency data per date. for (DateTime iterator = beginTime; iterator < endTime; iterator = iterator.AddDays(1)) { tempSingleData = correctedEntries.FirstOrDefault(x => x.ActualDate.Date == iterator.Date); if ( !correctedEntries.Exists( p => p.ActualDate.Date == iterator.Date && p.DbCurrencyCodeEntry.Equals(code))) { if (_weekends.Contains(iterator.DayOfWeek)) { if (lastSingleData != null) { CurrencyDataEntry newCurrencyData = lastSingleData.Clone(); newCurrencyData.ActualDate = iterator; correctedEntries.Add(newCurrencyData); } continue; } // If database doesn't have record for this date. var downloadedData = RequestSingleData(iterator, new CurrencyCodeEntry[] { code }, false); if (tempSingleData == null) { tempSingleData = lastSingleData; } if (downloadedData != null) { correctedEntries.Add(downloadedData[code]); } } lastSingleData = tempSingleData; } correctedEntries.Sort( (d1, d2) => d1.ActualDate > d2.ActualDate ? 1 : (d1.ActualDate == d2.ActualDate ? 0 : -1)); if (!periodCurrencyData.ContainsKey(code)) { periodCurrencyData.Add(code, new List <CurrencyDataEntry>()); } periodCurrencyData[code].AddRange(correctedEntries); } return(periodCurrencyData); /* * //var mData = TryGetPeriodDatabaseData(beginTime, endTime, codes.ElementAt(0)).ToList(); * * // Format the keys of data structure to be returned. * foreach (CurrencyCode code in codes) * { * periodCurrencyData.Add(code, new List<CurrencyData>()); * } * * IDictionary<CurrencyCode, CurrencyData> lastSingleData = null; * IDictionary<CurrencyCode, CurrencyData> tempSingleData = null; * * // TODO: fix iterator to make possible to change the step of selection so that select less data in large queries. * for (DateTime iterator = beginTime; iterator < endTime; iterator = iterator.AddDays(1)) * { * // TODO: select using one query instead of query per day. * * tempSingleData = this.RequestSingleData(iterator, codes); * * if (tempSingleData == null) * { * tempSingleData = lastSingleData; * } * * if (tempSingleData != null) * { * foreach (var pair in tempSingleData) * { * periodCurrencyData[pair.Key].Add(pair.Value); * } * } * else * { * throw new Exception("Unhandled NULL reference exception. The previous data does not"); * } * * * lastSingleData = tempSingleData; * } * * return periodCurrencyData;*/ }
// Top artists for 2 users public async Task <string> GetTableTasteAsync(PageResponse <LastArtist> leftUserArtists, PageResponse <LastArtist> rightUserArtists, int amount, ChartTimePeriod timePeriod, string mainUser, string userToCompare) { var artistsToShow = ArtistsToShow(leftUserArtists, rightUserArtists); var artists = artistsToShow.Select(s => { return(new TasteTwoUserModel { Artist = !string.IsNullOrWhiteSpace(s.Name) && s.Name.Length > AllowedCharacterCount(s.Name) ? $"{s.Name.Substring(0, AllowedCharacterCount(s.Name) - 2)}…" : s.Name, OwnPlaycount = s.PlayCount.Value, OtherPlaycount = rightUserArtists.Content.First(f => f.Name.Equals(s.Name)).PlayCount.Value });
// Top artists for 2 users public async Task <TasteModels> GetEmbedTasteAsync(PageResponse <LastArtist> leftUserArtists, PageResponse <LastArtist> rightUserArtists, int amount, ChartTimePeriod timePeriod) { var matchedArtists = ArtistsToShow(leftUserArtists, rightUserArtists); var left = ""; var right = ""; foreach (var artist in matchedArtists.Take(amount)) { var name = artist.Name; if (!string.IsNullOrWhiteSpace(name) && name.Length > 24) { left += $"**{name.Substring(0, 24)}..**\n"; } else { left += $"**{name}**\n"; } var ownPlaycount = artist.PlayCount.Value; var otherPlaycount = rightUserArtists.Content.First(f => f.Name.Equals(name)).PlayCount.Value; if (ownPlaycount > otherPlaycount) { right += $"**{ownPlaycount}**"; } else { right += $"{ownPlaycount}"; } right += " • "; if (otherPlaycount > ownPlaycount) { right += $"**{otherPlaycount}**"; } else { right += $"{otherPlaycount}"; } right += $"\n"; } var description = Description(leftUserArtists, timePeriod, matchedArtists); return(new TasteModels { Description = description, LeftDescription = left, RightDescription = right }); }
public IDictionary <CurrencyCodeEntry, ICollection <ChartCurrencyDataPoint <CurrencyDataEntry> > > GetChartData(DateTime begin, DateTime end, ICollection <CurrencyCodeEntry> chartCurrencyCodes) { ChartTimePeriod timePeriod = new ChartTimePeriod(begin, end); return(GetChartData(timePeriod, chartCurrencyCodes));; }
public void RemoveDataEntries(CurrencyCodeEntry entryToRemove, ChartTimePeriod timePeriod) { throw new System.NotImplementedException(); }
public void RemoveDataEntries(ChartTimePeriod timePeriod) { throw new System.NotImplementedException(); }
public IDictionary <CurrencyCodeEntry, List <CurrencyDataEntry> > RequestPeriodData(ChartTimePeriod timePeriod, ICollection <CurrencyCodeEntry> codes) { IDictionary <CurrencyCodeEntry, List <CurrencyDataEntry> > periodCurrencyData = new Dictionary <CurrencyCodeEntry, List <CurrencyDataEntry> >(); DateTime beginTime = SelectWorkingDate(timePeriod.Begin, DateSelection.BeforeWeekends); DateTime endTime = SelectWorkingDate(timePeriod.End, DateSelection.AfterWeekends); foreach (CurrencyCodeEntry code in codes) { // Try get from database. var dbEntries = TryGetPeriodDatabaseData(beginTime, endTime, code); List <CurrencyDataEntry> correctedEntries = null; if (dbEntries == null) { correctedEntries = new List <CurrencyDataEntry>(); } else { correctedEntries = dbEntries.ToList(); } CurrencyDataEntry lastSingleData = null; CurrencyDataEntry tempSingleData = null; // Check currency data per date. for (DateTime iterator = beginTime; iterator < endTime; iterator = iterator.AddDays(1)) { tempSingleData = correctedEntries.FirstOrDefault(x => x.ActualDate.Date == iterator.Date); if ( !correctedEntries.Exists( p => p.ActualDate.Date == iterator.Date && p.DbCurrencyCodeEntry.Equals(code))) { if (_weekends.Contains(iterator.DayOfWeek)) { if (lastSingleData != null) { CurrencyDataEntry newCurrencyData = lastSingleData.Clone(); newCurrencyData.ActualDate = iterator; correctedEntries.Add(newCurrencyData); } continue; } // If database doesn't have record for this date. var downloadedData = RequestSingleData(iterator, new CurrencyCodeEntry[] { code }, false); if (tempSingleData == null) { tempSingleData = lastSingleData; } if (downloadedData != null) { correctedEntries.Add(downloadedData[code]); } } lastSingleData = tempSingleData; } correctedEntries.Sort( (d1, d2) => d1.ActualDate > d2.ActualDate ? 1 : (d1.ActualDate == d2.ActualDate ? 0 : -1)); if (!periodCurrencyData.ContainsKey(code)) { periodCurrencyData.Add(code, new List <CurrencyDataEntry>()); } periodCurrencyData[code].AddRange(correctedEntries); } return(periodCurrencyData); }
public ChartTimePeriodChangedEventArgs(ChartTimePeriod period_) { Period = period_; }
public static SettingsModel StringOptionsToSettings( string[] extraOptions, LastStatsTimeSpan defaultLastStatsTimeSpan = LastStatsTimeSpan.Week, ChartTimePeriod defaultChartTimePeriod = ChartTimePeriod.Weekly, string defaultUrlParameter = "LAST_7_DAYS", string defaultApiParameter = "7day") { var settingsModel = new SettingsModel(); // time period if (extraOptions.Contains("weekly") || extraOptions.Contains("week") || extraOptions.Contains("w")) { settingsModel.LastStatsTimeSpan = LastStatsTimeSpan.Week; settingsModel.ChartTimePeriod = ChartTimePeriod.Weekly; settingsModel.Description = "Weekly"; settingsModel.UrlParameter = "LAST_7_DAYS"; settingsModel.ApiParameter = "7day"; } else if (extraOptions.Contains("monthly") || extraOptions.Contains("month") || extraOptions.Contains("m")) { settingsModel.LastStatsTimeSpan = LastStatsTimeSpan.Month; settingsModel.ChartTimePeriod = ChartTimePeriod.Monthly; settingsModel.Description = "Monthly"; settingsModel.UrlParameter = "LAST_30_DAYS"; settingsModel.ApiParameter = "1month"; } else if (extraOptions.Contains("quarterly") || extraOptions.Contains("quarter") || extraOptions.Contains("q")) { settingsModel.LastStatsTimeSpan = LastStatsTimeSpan.Quarter; settingsModel.ChartTimePeriod = ChartTimePeriod.Quarterly; settingsModel.Description = "Quarterly"; settingsModel.UrlParameter = "LAST_90_DAYS"; settingsModel.ApiParameter = "3month"; } else if (extraOptions.Contains("halfyearly") || extraOptions.Contains("half") || extraOptions.Contains("h")) { settingsModel.LastStatsTimeSpan = LastStatsTimeSpan.Half; settingsModel.ChartTimePeriod = ChartTimePeriod.Half; settingsModel.Description = "Half-yearly"; settingsModel.UrlParameter = "LAST_180_DAYS"; settingsModel.ApiParameter = "6month"; } else if (extraOptions.Contains("yearly") || extraOptions.Contains("year") || extraOptions.Contains("y")) { settingsModel.LastStatsTimeSpan = LastStatsTimeSpan.Year; settingsModel.ChartTimePeriod = ChartTimePeriod.Yearly; settingsModel.Description = "Yearly"; settingsModel.UrlParameter = "LAST_365_DAYS"; settingsModel.ApiParameter = "12month"; } else if (extraOptions.Contains("overall") || extraOptions.Contains("alltime") || extraOptions.Contains("o") || extraOptions.Contains("at") || extraOptions.Contains("a")) { settingsModel.LastStatsTimeSpan = LastStatsTimeSpan.Overall; settingsModel.ChartTimePeriod = ChartTimePeriod.AllTime; settingsModel.Description = "Overall"; settingsModel.UrlParameter = "ALL"; settingsModel.ApiParameter = "overall"; } else { settingsModel.LastStatsTimeSpan = defaultLastStatsTimeSpan; settingsModel.ChartTimePeriod = defaultChartTimePeriod; settingsModel.Description = ""; settingsModel.UrlParameter = defaultUrlParameter; settingsModel.ApiParameter = defaultApiParameter; } settingsModel.Amount = 10; foreach (var extraOption in extraOptions) { if (int.TryParse(extraOption, out var result)) { if (result > 0 && result <= 50) { if (result > 16) { result = 16; } settingsModel.Amount = result; } } if (extraOption.Contains("<@") || extraOption.Length == 18) { var id = extraOption.Trim('@', '!', '<', '>'); if (ulong.TryParse(id, out var discordUserId)) { settingsModel.OtherDiscordUserId = discordUserId; } } } return(settingsModel); }
/// <summary> /// Requests currency data for the chart within specified time period for specified currency codes. /// </summary> /// <param name="chartTimePeriod">The time period which the currency data should be returned for.</param> /// <param name="chartCurrencyCodes">The list of currency codes which currency data should be returned for.</param> /// <returns>The dictionary of currency code as key and the list of chart data points as value.</returns> public IDictionary <CurrencyCodeEntry, ICollection <ChartCurrencyDataPoint <CurrencyDataEntry> > > GetChartData(ChartTimePeriod chartTimePeriod, ICollection <CurrencyCodeEntry> chartCurrencyCodes) { // Request datat from caching processor. var currencyData = _iCachingProcessor.RequestPeriodData(chartTimePeriod, chartCurrencyCodes); var currencyDataPoints = new Dictionary <CurrencyCodeEntry, ICollection <ChartCurrencyDataPoint <CurrencyDataEntry> > >(); // Format the structure of data representation. foreach (KeyValuePair <CurrencyCodeEntry, List <CurrencyDataEntry> > pair in currencyData) { List <ChartCurrencyDataPoint <CurrencyDataEntry> > dataPoints = new List <ChartCurrencyDataPoint <CurrencyDataEntry> >(); foreach (CurrencyDataEntry data in pair.Value) { dataPoints.Add(new ChartCurrencyDataPoint <CurrencyDataEntry>() { DataObject = data }); } currencyDataPoints.Add(pair.Key, dataPoints); } return(currencyDataPoints); }