Skip to content

Commit 764d80d

Browse files
committed
Gas Runner pulling info
1 parent 0e608fb commit 764d80d

29 files changed

+905
-15
lines changed
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,55 @@
1+
using System;
2+
using System.Collections.Generic;
3+
using GasPrice.Data.Interfaces;
4+
using GasPrice.Data.Models;
5+
using Microsoft.WindowsAzure.Storage;
6+
using Microsoft.WindowsAzure.Storage.Blob;
7+
using Newtonsoft.Json;
8+
9+
namespace GasPrice.Data.AzureStorage
10+
{
11+
public class GasAzurePersistor : IGasPersistor
12+
{
13+
private readonly CloudBlobContainer _container;
14+
15+
public GasAzurePersistor(string connstr)
16+
{
17+
var storageAccount = CloudStorageAccount.Parse(connstr);
18+
19+
var blobClient = storageAccount.CreateCloudBlobClient();
20+
_container = blobClient.GetContainerReference(nameof(GasMeasurement).ToLowerInvariant());
21+
_container.CreateIfNotExistsAsync();
22+
}
23+
24+
private static string GetBlobName(DateTime d)
25+
{
26+
return $"{d.ToUniversalTime():yyyyMMdd}.log";
27+
}
28+
29+
private CloudBlockBlob GetBlob(DateTime d)
30+
{
31+
return _container.GetBlockBlobReference(GetBlobName(d));
32+
}
33+
34+
35+
public List<GasMeasurement> Get(DateTime? date)
36+
{
37+
if (!date.HasValue) date = DateTime.UtcNow;
38+
39+
var b = GetBlob(date.Value);
40+
if (!b.ExistsAsync().Result) return new List<GasMeasurement>();
41+
42+
var s = b.DownloadTextAsync().Result;
43+
return JsonConvert.DeserializeObject<List<GasMeasurement>>(s);
44+
}
45+
46+
public void Save(GasMeasurement gas)
47+
{
48+
var l = Get(gas.Moment);
49+
l.Add(gas);
50+
51+
GetBlob(gas.Moment)
52+
.UploadTextAsync(JsonConvert.SerializeObject(l));
53+
}
54+
}
55+
}

GasPrice.Data/GasPrice.Data.csproj

+69
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,69 @@
1+
<?xml version="1.0" encoding="utf-8"?>
2+
<Project ToolsVersion="15.0" xmlns="http://schemas.microsoft.com/developer/msbuild/2003">
3+
<Import Project="$(MSBuildExtensionsPath)\$(MSBuildToolsVersion)\Microsoft.Common.props" Condition="Exists('$(MSBuildExtensionsPath)\$(MSBuildToolsVersion)\Microsoft.Common.props')" />
4+
<PropertyGroup>
5+
<Configuration Condition=" '$(Configuration)' == '' ">Debug</Configuration>
6+
<Platform Condition=" '$(Platform)' == '' ">AnyCPU</Platform>
7+
<ProjectGuid>{E23FFD84-A1FC-4461-A160-2ED889664BEE}</ProjectGuid>
8+
<OutputType>Library</OutputType>
9+
<AppDesignerFolder>Properties</AppDesignerFolder>
10+
<RootNamespace>GasPrice.Data</RootNamespace>
11+
<AssemblyName>GasPrice.Data</AssemblyName>
12+
<TargetFrameworkVersion>v4.6.1</TargetFrameworkVersion>
13+
<FileAlignment>512</FileAlignment>
14+
</PropertyGroup>
15+
<PropertyGroup Condition=" '$(Configuration)|$(Platform)' == 'Debug|AnyCPU' ">
16+
<DebugSymbols>true</DebugSymbols>
17+
<DebugType>full</DebugType>
18+
<Optimize>false</Optimize>
19+
<OutputPath>bin\Debug\</OutputPath>
20+
<DefineConstants>DEBUG;TRACE</DefineConstants>
21+
<ErrorReport>prompt</ErrorReport>
22+
<WarningLevel>4</WarningLevel>
23+
</PropertyGroup>
24+
<PropertyGroup Condition=" '$(Configuration)|$(Platform)' == 'Release|AnyCPU' ">
25+
<DebugType>pdbonly</DebugType>
26+
<Optimize>true</Optimize>
27+
<OutputPath>bin\Release\</OutputPath>
28+
<DefineConstants>TRACE</DefineConstants>
29+
<ErrorReport>prompt</ErrorReport>
30+
<WarningLevel>4</WarningLevel>
31+
</PropertyGroup>
32+
<ItemGroup>
33+
<Reference Include="HtmlAgilityPack, Version=1.4.9.0, Culture=neutral, PublicKeyToken=bd319b19eaf3b43a, processorArchitecture=MSIL">
34+
<HintPath>..\packages\HtmlAgilityPack.CssSelectors.1.0.2\lib\net45\HtmlAgilityPack.dll</HintPath>
35+
</Reference>
36+
<Reference Include="HtmlAgilityPack.CssSelectors, Version=1.0.0.0, Culture=neutral, processorArchitecture=MSIL">
37+
<HintPath>..\packages\HtmlAgilityPack.CssSelectors.1.0.2\lib\net45\HtmlAgilityPack.CssSelectors.dll</HintPath>
38+
</Reference>
39+
<Reference Include="Microsoft.WindowsAzure.Storage, Version=4.3.0.0, Culture=neutral, PublicKeyToken=31bf3856ad364e35, processorArchitecture=MSIL" />
40+
<Reference Include="Newtonsoft.Json, Version=6.0.0.0, Culture=neutral, PublicKeyToken=30ad4fe6b2a6aeed, processorArchitecture=MSIL">
41+
<HintPath>..\packages\Newtonsoft.Json.6.0.8\lib\net45\Newtonsoft.Json.dll</HintPath>
42+
</Reference>
43+
<Reference Include="System" />
44+
<Reference Include="System.Core" />
45+
<Reference Include="System.Web" />
46+
<Reference Include="System.Xml.Linq" />
47+
<Reference Include="System.Data.DataSetExtensions" />
48+
<Reference Include="Microsoft.CSharp" />
49+
<Reference Include="System.Data" />
50+
<Reference Include="System.Net.Http" />
51+
<Reference Include="System.Xml" />
52+
</ItemGroup>
53+
<ItemGroup>
54+
<Compile Include="AzureStorage\GasAzurePersistor.cs" />
55+
<Compile Include="Interfaces\IGasPersistor.cs" />
56+
<Compile Include="Models\CoinMarketCapDTOModels.cs" />
57+
<Compile Include="Models\GasMeasurement.cs" />
58+
<Compile Include="Models\RskJsonRpcModels.cs" />
59+
<Compile Include="Properties\AssemblyInfo.cs" />
60+
<Compile Include="Scraper.cs" />
61+
<Compile Include="Services\CryptoPriceService.cs" />
62+
<Compile Include="Services\GasPriceService.cs" />
63+
</ItemGroup>
64+
<ItemGroup>
65+
<None Include="app.config" />
66+
<None Include="packages.config" />
67+
</ItemGroup>
68+
<Import Project="$(MSBuildToolsPath)\Microsoft.CSharp.targets" />
69+
</Project>
+13
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,13 @@
1+
using System;
2+
using System.Collections.Generic;
3+
using GasPrice.Data.Models;
4+
5+
namespace GasPrice.Data.Interfaces
6+
{
7+
public interface IGasPersistor
8+
{
9+
List<GasMeasurement> Get(DateTime? date);
10+
11+
void Save(GasMeasurement gas);
12+
}
13+
}
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,43 @@
1+
namespace GasPrice.Data.Models
2+
{
3+
public class USD
4+
{
5+
public decimal price { get; set; }
6+
public double volume_24h { get; set; }
7+
public double market_cap { get; set; }
8+
public double percent_change_1h { get; set; }
9+
public double percent_change_24h { get; set; }
10+
public double percent_change_7d { get; set; }
11+
}
12+
13+
public class Quotes
14+
{
15+
public USD USD { get; set; }
16+
}
17+
18+
public class Data
19+
{
20+
public int id { get; set; }
21+
public string name { get; set; }
22+
public string symbol { get; set; }
23+
public string website_slug { get; set; }
24+
public int rank { get; set; }
25+
public double circulating_supply { get; set; }
26+
public double total_supply { get; set; }
27+
public double? max_supply { get; set; }
28+
public Quotes quotes { get; set; }
29+
public int last_updated { get; set; }
30+
}
31+
32+
public class Metadata
33+
{
34+
public int timestamp { get; set; }
35+
public object error { get; set; }
36+
}
37+
38+
public class CoinMarketCapResult
39+
{
40+
public Data data { get; set; }
41+
public Metadata metadata { get; set; }
42+
}
43+
}
+42
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,42 @@
1+
using System;
2+
3+
namespace GasPrice.Data.Models
4+
{
5+
public class GasMeasurement
6+
{
7+
public GasMeasurement()
8+
{
9+
Moment = DateTime.UtcNow;
10+
}
11+
12+
public DateTime Moment { get; set; }
13+
14+
public decimal RSKMinGasPrice { get; set; }
15+
16+
public decimal EthGasPriceLow { get; set; }
17+
18+
public decimal EthGasPriceStandard { get; set; }
19+
20+
public decimal EthGasPriceFast { get; set; }
21+
22+
public decimal EthVsUsd { get; set; }
23+
24+
public decimal BtcVsUsd { get; set; }
25+
26+
27+
public decimal RskGasPriceInUsd()
28+
{
29+
var rskInBtc = RSKMinGasPrice / 1000000000;
30+
31+
return rskInBtc * BtcVsUsd * 21000;
32+
}
33+
34+
public decimal EthGasPriceInUsd()
35+
{
36+
var ethInBtc = EthGasPriceStandard / 1000000000;
37+
38+
return ethInBtc * EthVsUsd * 21000;
39+
}
40+
41+
}
42+
}
+34
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,34 @@
1+
using System.Collections.Generic;
2+
3+
namespace GasPrice.Data.Models
4+
{
5+
public class RskJsonRpcResultModel
6+
{
7+
public string number { get; set; }
8+
public string hash { get; set; }
9+
public string parentHash { get; set; }
10+
public string sha3Uncles { get; set; }
11+
public string logsBloom { get; set; }
12+
public string transactionsRoot { get; set; }
13+
public string stateRoot { get; set; }
14+
public string receiptsRoot { get; set; }
15+
public string miner { get; set; }
16+
public string difficulty { get; set; }
17+
public string totalDifficulty { get; set; }
18+
public string extraData { get; set; }
19+
public string size { get; set; }
20+
public string gasLimit { get; set; }
21+
public string gasUsed { get; set; }
22+
public string timestamp { get; set; }
23+
public List<string> transactions { get; set; }
24+
public List<string> uncles { get; set; }
25+
public string minimumGasPrice { get; set; }
26+
}
27+
28+
public class RskJsonRpcModel
29+
{
30+
public string jsonrpc { get; set; }
31+
public int id { get; set; }
32+
public RskJsonRpcResultModel result { get; set; }
33+
}
34+
}
+36
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,36 @@
1+
using System.Reflection;
2+
using System.Runtime.CompilerServices;
3+
using System.Runtime.InteropServices;
4+
5+
// General Information about an assembly is controlled through the following
6+
// set of attributes. Change these attribute values to modify the information
7+
// associated with an assembly.
8+
[assembly: AssemblyTitle("GasPrice.Data")]
9+
[assembly: AssemblyDescription("")]
10+
[assembly: AssemblyConfiguration("")]
11+
[assembly: AssemblyCompany("")]
12+
[assembly: AssemblyProduct("GasPrice.Data")]
13+
[assembly: AssemblyCopyright("Copyright © 2018")]
14+
[assembly: AssemblyTrademark("")]
15+
[assembly: AssemblyCulture("")]
16+
17+
// Setting ComVisible to false makes the types in this assembly not visible
18+
// to COM components. If you need to access a type in this assembly from
19+
// COM, set the ComVisible attribute to true on that type.
20+
[assembly: ComVisible(false)]
21+
22+
// The following GUID is for the ID of the typelib if this project is exposed to COM
23+
[assembly: Guid("e23ffd84-a1fc-4461-a160-2ed889664bee")]
24+
25+
// Version information for an assembly consists of the following four values:
26+
//
27+
// Major Version
28+
// Minor Version
29+
// Build Number
30+
// Revision
31+
//
32+
// You can specify all the values or you can default the Build and Revision Numbers
33+
// by using the '*' as shown below:
34+
// [assembly: AssemblyVersion("1.0.*")]
35+
[assembly: AssemblyVersion("1.0.0.0")]
36+
[assembly: AssemblyFileVersion("1.0.0.0")]

GasPrice.Data/Scraper.cs

+90
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,90 @@
1+
using System;
2+
using System.Collections.Generic;
3+
using System.IO;
4+
using System.Net;
5+
using System.Net.Http;
6+
using System.Text;
7+
using System.Web;
8+
using HtmlAgilityPack;
9+
10+
namespace GasPrice.Data
11+
{
12+
/// <summary>
13+
/// This class opens a website and scraps the contents
14+
/// </summary>
15+
public class Scraper
16+
{
17+
private readonly Encoding _encoding;
18+
private readonly string _referer;
19+
20+
public HttpWebRequest Request { get; set; }
21+
22+
public Scraper(Uri url)
23+
{
24+
Request = (HttpWebRequest)WebRequest.Create(url);
25+
}
26+
27+
public Scraper(Uri url, Encoding encoding)
28+
{
29+
Request = (HttpWebRequest)WebRequest.Create(url);
30+
_encoding = encoding;
31+
}
32+
33+
public Scraper(Uri url, Encoding encoding, string referer)
34+
{
35+
Request = (HttpWebRequest)WebRequest.Create(url);
36+
_encoding = encoding;
37+
_referer = referer;
38+
}
39+
40+
public HtmlNode GetNodes()
41+
{
42+
return GetNodes(HttpMethod.Get, null);
43+
}
44+
45+
public HtmlNode GetNodes(HttpMethod method, Dictionary<string, object> postParameters)
46+
{
47+
// Create the WebRequest for the URL we are using
48+
Request.Method = method.Method;
49+
50+
if (HttpMethod.Post.Equals(method))
51+
{
52+
if (postParameters != null)
53+
{
54+
var postData = new StringBuilder();
55+
foreach (var postParameter in postParameters)
56+
{
57+
postData.Append($"{postParameter.Key}={HttpUtility.UrlEncode(postParameter.Value.ToString())}&");
58+
}
59+
60+
byte[] postBytes = _encoding.GetBytes(postData.ToString());
61+
62+
Request.ContentType = "application/x-www-form-urlencoded";
63+
Request.ContentLength = postBytes.Length;
64+
65+
var postStream = Request.GetRequestStream();
66+
postStream.Write(postBytes, 0, postBytes.Length);
67+
postStream.Flush();
68+
postStream.Close();
69+
}
70+
}
71+
72+
if (!string.IsNullOrWhiteSpace(_referer))
73+
{
74+
Request.Referer = _referer;
75+
}
76+
77+
// Get the stream from the returned web response
78+
var stream = _encoding != null ? new StreamReader(
79+
Request.GetResponse().GetResponseStream() ??
80+
throw new InvalidOperationException(), _encoding) :
81+
new StreamReader(
82+
Request.GetResponse().GetResponseStream() ??
83+
throw new InvalidOperationException());
84+
85+
var htmlDocument = new HtmlDocument();
86+
htmlDocument.Load(stream);
87+
return htmlDocument.DocumentNode;
88+
}
89+
}
90+
}

0 commit comments

Comments
 (0)