public FileResult CreateChart(string itemName, string leagueName) { ItemsDataContext itemsDB = new ItemsDataContext(DATA_CONNECTION_STRING); var result = from item in itemsDB.Items where item.Name == itemName && item.League == leagueName orderby item.Timestamp ascending select item; Chart chart = new Chart(); chart.Width = 900; chart.Height = 600; chart.BackColor = Color.LightGray; chart.BorderlineDashStyle = ChartDashStyle.Solid; chart.BorderlineWidth = 1; chart.Palette = ChartColorPalette.BrightPastel; chart.BorderlineColor = Color.Black; chart.RenderType = RenderType.BinaryStreaming; chart.BorderSkin.SkinStyle = BorderSkinStyle.Emboss; chart.AntiAliasing = AntiAliasingStyles.All; chart.TextAntiAliasingQuality = TextAntiAliasingQuality.Normal; chart.Titles.Add(CreateTitle(string.Format("{0} in {1} league", itemName, leagueName))); chart.Legends.Add(new Legend()); chart.Series.Add(CreateSeries("Items listed", result, x => (float)x.MaxPrice, Color.Blue)); chart.Series.Add(CreateSeries("Median Price", result, x => (float)x.MedianPrice, Color.Green)); chart.Series.Add(CreateSeries("Mean Price", result, x => (float)x.MeanPrice, Color.Orange)); chart.Series.Add(CreateSeries("Min Price", result, x => (float)x.MinPrice, Color.Violet)); chart.Series.Add(CreateSeries("Max Price", result, x => (float)x.MaxPrice, Color.Red)); chart.ChartAreas.Add(CreateChartArea("Items listed", "Number of listings")); chart.ChartAreas.Add(CreateChartArea("Median Price")); chart.ChartAreas.Add(CreateChartArea("Mean Price")); chart.ChartAreas.Add(CreateChartArea("Min Price")); chart.ChartAreas.Add(CreateChartArea("Max Price")); MemoryStream ms = new MemoryStream(); chart.SaveImage(ms); return File(ms.GetBuffer(), @"image/png"); }
static void Main(string[] args) { var uri = new Uri(URI_STRING); var settings = new ConnectionConfiguration(uri) .PrettyJson(true) .UsePrettyResponses(true); var client = new ElasticsearchClient(settings); ItemNamesDataContext itemNamesDB = new ItemNamesDataContext(DATA_CONNETION_STRING); ItemsDataContext itemsDB = new ItemsDataContext(DATA_CONNETION_STRING); while (true) { // Ordering so we prioritize items that haven't been updated in a while (or ever - so null = yesterday) foreach (ItemName itemName in itemNamesDB.ItemNames.OrderBy(row => row.LastChecked ?? DateTime.Now.AddDays(-1))) { string[] leagues = { "Standard", "Hardcore", "Warbands", "Tempest" }; foreach (string league in leagues) { int amountOfItems; int scanned = 0; List<float> prices = new List<float>(); do { Response response; try { response = GetItemsByName(itemName.Name, league, scanned, 200, client); amountOfItems = response.hits.total; scanned += response.hits.hits.Count(); foreach (Hit hit in response.hits.hits) { prices.Add(hit._source.shop.chaosEquiv); } } catch (System.InvalidOperationException e) { // Deserializer found null value -> query resulted empty response amountOfItems = 0; } // Just to monitor status Console.WriteLine(string.Format("{0} / {1}", scanned, amountOfItems)); // Let's try to not get banned System.Threading.Thread.Sleep(2000); } while (scanned < amountOfItems); prices.Sort(); var entry = new Item { Name = itemName.Name, Amount = amountOfItems, League = league, MaxPrice = prices.Any() ? prices.Last() : 0, MinPrice = prices.Any() ? prices.First() : 0, MeanPrice = prices.Any() ? prices.Average() : 0, MedianPrice = prices.Any() ? prices[prices.Count() / 2] : 0, Timestamp = DateTime.Now }; itemsDB.Items.InsertOnSubmit(entry); Console.WriteLine(string.Format("min_price: {0}, max_price: {1}, median: {2}, mean: {3}, item: {4}", entry.MinPrice, entry.MaxPrice, entry.MedianPrice, entry.MeanPrice, itemName.Name)); } itemName.LastChecked = DateTime.Now; try { itemNamesDB.SubmitChanges(); itemsDB.SubmitChanges(); } catch (Exception e) { // DB might be busy, or being accessed by someone else and submitting may fail // It happens only every few hundred submits so I decided to just keep ignore it and continue continue; } } } }