Skip to content
This repository was archived by the owner on Dec 5, 2024. It is now read-only.

Commit 12d701c

Browse files
committed
Fix issues, add tests
1 parent 704ac8e commit 12d701c

File tree

9 files changed

+159
-48
lines changed

9 files changed

+159
-48
lines changed

src/GitHub.Api/Metrics/UsageModel.cs

Lines changed: 3 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -85,18 +85,18 @@ public Usage GetCurrentUsage(string appVersion, string unityVersion, string inst
8585

8686
public List<Usage> SelectReports(DateTime beforeDate)
8787
{
88-
return Reports.Where(usage => usage.Dimensions.Date.Date != beforeDate.Date).ToList();
88+
return Reports.Where(usage => usage.Dimensions.Date.Date < beforeDate.Date).ToList();
8989
}
9090

9191
public void RemoveReports(DateTime beforeDate)
9292
{
93-
Reports.RemoveAll(usage => usage.Dimensions.Date.Date != beforeDate.Date);
93+
Reports.RemoveAll(usage => usage.Dimensions.Date.Date < beforeDate.Date);
9494
}
9595
}
9696

9797
class UsageStore
9898
{
99-
public DateTimeOffset LastUpdated { get; set; } = DateTimeOffset.Now;
99+
public DateTimeOffset LastSubmissionDate { get; set; } = DateTimeOffset.Now;
100100
public UsageModel Model { get; set; } = new UsageModel();
101101

102102
public Measures GetCurrentMeasures(string appVersion, string unityVersion, string instanceId)

src/GitHub.Api/Metrics/UsageTracker.cs

Lines changed: 31 additions & 28 deletions
Original file line numberDiff line numberDiff line change
@@ -1,9 +1,7 @@
11
using System;
22
using System.Linq;
33
using System.Text;
4-
using System.Threading.Tasks;
54
using System.Threading;
6-
using Timer = System.Threading.Timer;
75
using GitHub.Logging;
86

97
namespace GitHub.Unity
@@ -60,7 +58,7 @@ public UsageTracker(ISettings userSettings,
6058

6159
private void RunTimer(int seconds)
6260
{
63-
timer = new Timer(_ =>
61+
timer = new System.Threading.Timer(_ =>
6462
{
6563
try
6664
{
@@ -79,45 +77,50 @@ private void SendUsage()
7977
return;
8078
}
8179

82-
var usageStore = usageLoader.Load(userId);
80+
UsageStore usageStore = null;
81+
lock (_lock)
82+
{
83+
usageStore = usageLoader.Load(userId);
84+
}
8385

8486
var currentTimeOffset = DateTimeOffset.UtcNow;
85-
if (usageStore.LastUpdated.Date == currentTimeOffset)
87+
if (usageStore.LastSubmissionDate.Date == currentTimeOffset.Date)
8688
{
8789
return;
8890
}
8991

90-
lock (_lock)
92+
var success = false;
93+
var extractReports = usageStore.Model.SelectReports(currentTimeOffset.Date);
94+
if (!extractReports.Any())
95+
{
96+
Logger.Trace("No items to send");
97+
}
98+
else
9199
{
92-
var success = false;
93-
var extractReports = usageStore.Model.SelectReports(currentTimeOffset.Date);
94-
if (!extractReports.Any())
100+
if (!Enabled)
95101
{
96-
Logger.Trace("No items to send");
102+
Logger.Trace("Metrics disabled");
103+
return;
97104
}
98-
else
99-
{
100-
if (!Enabled)
101-
{
102-
Logger.Trace("Metrics disabled");
103-
return;
104-
}
105105

106-
try
107-
{
108-
MetricsService.PostUsage(extractReports);
109-
success = true;
110-
}
111-
catch (Exception ex)
112-
{
113-
Logger.Warning(@"Error Sending Usage Exception Type:""{0}"" Message:""{1}""", ex.GetType().ToString(), ex.GetExceptionMessageShort());
114-
}
106+
try
107+
{
108+
MetricsService.PostUsage(extractReports);
109+
success = true;
115110
}
111+
catch (Exception ex)
112+
{
113+
Logger.Warning(@"Error Sending Usage Exception Type:""{0}"" Message:""{1}""", ex.GetType().ToString(), ex.GetExceptionMessageShort());
114+
}
115+
}
116116

117-
if (success)
117+
if (success)
118+
{
119+
lock(_lock)
118120
{
121+
usageStore = usageLoader.Load(userId);
122+
usageStore.LastSubmissionDate = currentTimeOffset;
119123
usageStore.Model.RemoveReports(currentTimeOffset.Date);
120-
usageStore.LastUpdated = currentTimeOffset;
121124
usageLoader.Save(usageStore);
122125
}
123126
}

src/tests/CommandLine/Program.cs

Lines changed: 59 additions & 5 deletions
Original file line numberDiff line numberDiff line change
@@ -6,6 +6,8 @@
66
using GitHub.Unity;
77
using GitHub;
88
using GitHub.Logging;
9+
using System.Net;
10+
using System.Text;
911

1012
namespace TestApp
1113
{
@@ -39,6 +41,18 @@ static void RunWebServer(NPath path, int port)
3941
server.Stop();
4042
}
4143

44+
static TestWebServer.HttpServer RunWebServer(int port)
45+
{
46+
var path = typeof(Program).Assembly.Location.ToNPath().Parent.Combine("files");
47+
var server = new TestWebServer.HttpServer(path, port);
48+
var thread = new Thread(() =>
49+
{
50+
server.Start();
51+
});
52+
thread.Start();
53+
return server;
54+
}
55+
4256
static int Main(string[] args)
4357
{
4458
LogHelper.LogAdapter = new ConsoleLogAdapter();
@@ -61,30 +75,70 @@ static int Main(string[] args)
6175
string url = null;
6276
string readVersion = null;
6377
string msg = null;
78+
string host = null;
79+
bool runUsage = false;
6480

81+
var arguments = new List<string>(args);
82+
if (arguments.Contains("usage"))
83+
{
84+
runUsage = true;
85+
arguments.RemoveRange(0, 2);
86+
}
6587

6688
p = p
6789
.Add("r=", (int v) => retCode = v)
6890
.Add("d=|data=", v => data = v)
6991
.Add("e=|error=", v => error = v)
7092
.Add("f=|file=", v => data = File.ReadAllText(v))
7193
.Add("ef=|errorFile=", v => error = File.ReadAllText(v))
72-
.Add("s=|sleep=", (int v) => sleepms = v)
94+
.Add("sleep=", (int v) => sleepms = v)
7395
.Add("i|input", v => readInputToEof = true)
7496
.Add("w|web", v => runWebServer = true)
75-
.Add("port=", (int v) => webServerPort = v)
97+
.Add("p|port=", "Port", (int v) => webServerPort = v)
7698
.Add("g|generateVersion", v => generateVersion = true)
7799
.Add("v=|version=", v => version = v)
78-
.Add("p|gen-package", "Pass --version --url --path --md5 --rn --msg to generate a package", v => generatePackage = true)
100+
.Add("gen-package", "Pass --version --url --path --md5 --rn --msg to generate a package", v => generatePackage = true)
79101
.Add("u=|url=", v => url = v)
80102
.Add("path=", v => path = v.ToNPath())
81103
.Add("rn=", "Path to file with release notes", v => releaseNotes = v.ReadAllTextIfFileExists())
82104
.Add("msg=", "Path to file with message for package", v => msg = v.ReadAllTextIfFileExists())
83105
.Add("readVersion=", v => readVersion = v)
84106
.Add("o=|outfile=", v => outfile = v.ToNPath().MakeAbsolute())
85-
.Add("h|help", v => p.WriteOptionDescriptions(Console.Out));
107+
.Add("h=", "Host", v => host = v)
108+
.Add("help", v => p.WriteOptionDescriptions(Console.Out));
86109

87-
p.Parse(args);
110+
var extra = p.Parse(arguments);
111+
if (runUsage)
112+
{
113+
extra.Remove("usage");
114+
p.Parse(extra);
115+
116+
path = extra[extra.Count - 1].ToNPath();
117+
var server = RunWebServer(webServerPort);
118+
var webRequest = (HttpWebRequest)WebRequest.Create(new UriString("http://localhost:" + webServerPort + "/api/usage/unity"));
119+
webRequest.Method = "POST";
120+
using (var sw = new StreamWriter(webRequest.GetRequestStream()))
121+
{
122+
foreach (var line in path.ReadAllLines())
123+
{
124+
sw.WriteLine(line);
125+
}
126+
}
127+
using (var webResponse = (HttpWebResponse)webRequest.GetResponseWithoutException())
128+
{
129+
MemoryStream ms = new MemoryStream();
130+
var responseLength = webResponse.ContentLength;
131+
using (var sr = new StreamWriter(ms))
132+
using (var responseStream = webResponse.GetResponseStream())
133+
{
134+
Utils.Copy(responseStream, ms, responseLength);
135+
}
136+
Console.WriteLine(Encoding.ASCII.GetString(ms.ToArray()));
137+
}
138+
139+
server.Stop();
140+
return 0;
141+
}
88142

89143
if (generatePackage)
90144
{

src/tests/IntegrationTests/BaseIntegrationTest.cs

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -15,6 +15,7 @@ namespace IntegrationTests
1515
[Isolated]
1616
class BaseIntegrationTest
1717
{
18+
protected NPath TestApp => System.Reflection.Assembly.GetExecutingAssembly().Location.ToNPath().Parent.Combine("CommandLine.exe");
1819
public IRepositoryManager RepositoryManager { get; set; }
1920
protected IApplicationManager ApplicationManager { get; set; }
2021
protected ILogging Logger { get; set; }

src/tests/IntegrationTests/IntegrationTests.csproj

Lines changed: 4 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -95,6 +95,10 @@
9595
<Project>{bb6a8eda-15d8-471b-a6ed-ee551e0b3ba0}</Project>
9696
<Name>GitHub.Logging</Name>
9797
</ProjectReference>
98+
<ProjectReference Include="..\CommandLine\CommandLine.csproj">
99+
<Project>{08b87d2a-8cf1-4211-b7aa-5209f00f72f8}</Project>
100+
<Name>CommandLine</Name>
101+
</ProjectReference>
98102
<ProjectReference Include="..\TestUtils\TestUtils.csproj">
99103
<Project>{66a1d219-f61d-4ae4-9bd7-aaeb97276fff}</Project>
100104
<Name>TestUtils</Name>

src/tests/IntegrationTests/Metrics/MetricsTests.cs

Lines changed: 39 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -78,5 +78,44 @@ public void LoadingWorks()
7878
var savedStore = json.FromJson<UsageStore>(lowerCase: true);
7979
Assert.AreEqual(2, savedStore.GetCurrentMeasures(appVersion, unityVersion, instanceId).NumberOfStartups);
8080
}
81+
82+
[Test]
83+
public void SubmissionWorks()
84+
{
85+
InitializeEnvironment(TestBasePath, false, false);
86+
InitializePlatform(TestBasePath, false, "SubmissionWorks");
87+
var userId = Guid.NewGuid().ToString();
88+
var appVersion = ApplicationInfo.Version;
89+
var unityVersion = "2017.3f1";
90+
var instanceId = Guid.NewGuid().ToString();
91+
var usageStore = new UsageStore();
92+
usageStore.Model.Guid = userId;
93+
var storePath = Environment.UserCachePath.Combine(Constants.UsageFile);
94+
var usageLoader = new UsageLoader(storePath);
95+
96+
var settings = Substitute.For<ISettings>();
97+
settings.Exists(Arg.Is<string>(Constants.GuidKey)).Returns(true);
98+
settings.Get(Arg.Is<string>(Constants.GuidKey)).Returns(userId);
99+
var usageTracker = new UsageTracker(settings, usageLoader, unityVersion, instanceId);
100+
101+
usageTracker.IncrementNumberOfStartups();
102+
usageTracker.IncrementNumberOfStartups();
103+
104+
var json = storePath.ReadAllText(Encoding.UTF8);
105+
var savedStore = json.FromJson<UsageStore>(lowerCase: true);
106+
var current = savedStore.Model.GetCurrentUsage(appVersion, unityVersion, instanceId);
107+
var yesterday = DateTimeOffset.UtcNow.AddDays(-1);
108+
current.Dimensions.Date = yesterday;
109+
savedStore.LastSubmissionDate = yesterday;
110+
storePath.WriteAllText(savedStore.ToJson(lowerCase: true));
111+
settings.Get(Arg.Is<string>(Constants.MetricsKey), Arg.Any<bool>()).Returns(true);
112+
113+
var metricsService = new MetricsService(ProcessManager, TaskManager, Environment.FileSystem, TestApp, TestApp);
114+
usageTracker.MetricsService = metricsService;
115+
var method = usageTracker.GetType().GetMethod("SendUsage", System.Reflection.BindingFlags.NonPublic | System.Reflection.BindingFlags.Instance);
116+
method.Invoke(usageTracker, null);
117+
json = storePath.ReadAllText(Encoding.UTF8);
118+
savedStore = json.FromJson<UsageStore>(lowerCase: true);
119+
}
81120
}
82121
}

src/tests/TaskSystemIntegrationTests/Tests.cs

Lines changed: 6 additions & 6 deletions
Original file line numberDiff line numberDiff line change
@@ -30,7 +30,7 @@ public BaseTest()
3030
protected IProcessManager ProcessManager { get; set; }
3131
protected NPath TestBasePath { get; private set; }
3232
protected CancellationToken Token => TaskManager.Token;
33-
protected NPath TestApp => System.Reflection.Assembly.GetExecutingAssembly().Location.ToNPath().Combine("CommandLine.exe");
33+
protected NPath TestApp => System.Reflection.Assembly.GetExecutingAssembly().Location.ToNPath().Parent.Combine("CommandLine.exe");
3434

3535
[TestFixtureSetUp]
3636
public void OneTimeSetup()
@@ -115,7 +115,7 @@ public async Task ProcessReadsFromStandardInput()
115115

116116
var expectedOutput = "Hello";
117117

118-
var procTask = new FirstNonNullLineProcessTask(Token, TestApp, @"-s 100 -i")
118+
var procTask = new FirstNonNullLineProcessTask(Token, TestApp, @"--sleep 100 -i")
119119
.Configure(ProcessManager, true);
120120

121121
procTask.OnStartProcess += proc =>
@@ -142,13 +142,13 @@ public async Task ProcessOnStartOnEndTaskOrder()
142142
string process1Value = null;
143143
string process2Value = null;
144144

145-
var process1Task = new FirstNonNullLineProcessTask(Token, TestApp, @"-s 100 -d process1")
145+
var process1Task = new FirstNonNullLineProcessTask(Token, TestApp, @"--sleep 100 -d process1")
146146
.Configure(ProcessManager, true).Then((b, s) => {
147147
process1Value = s;
148148
values.Add(s);
149149
});
150150

151-
var process2Task = new FirstNonNullLineProcessTask(Token, TestApp, @"-s 100 -d process2")
151+
var process2Task = new FirstNonNullLineProcessTask(Token, TestApp, @"---sleep 100 -d process2")
152152
.Configure(ProcessManager, true).Then((b, s) => {
153153
process2Value = s;
154154
values.Add(s);
@@ -181,7 +181,7 @@ public async Task ProcessReturningErrorThrowsException()
181181
var output = new List<string>();
182182
var expectedOutput = new List<string> { "one name" };
183183

184-
var task = new FirstNonNullLineProcessTask(Token, TestApp, @"-s 100 -d ""one name""").Configure(ProcessManager)
184+
var task = new FirstNonNullLineProcessTask(Token, TestApp, @"--sleep 100 -d ""one name""").Configure(ProcessManager)
185185
.Catch(ex => thrown = ex)
186186
.Then((s, d) => output.Add(d))
187187
.Then(new FirstNonNullLineProcessTask(Token, TestApp, @"-e kaboom -r -1").Configure(ProcessManager))
@@ -207,7 +207,7 @@ public async Task NestedProcessShouldChainCorrectly()
207207
await new ActionTask(Token, _ => {
208208
results.Add("BeforeProcess");
209209
})
210-
.Then(new FirstNonNullLineProcessTask(Token, TestApp, @"-s 1000 -d ""ok""")
210+
.Then(new FirstNonNullLineProcessTask(Token, TestApp, @"--sleep 1000 -d ""ok""")
211211
.Configure(ProcessManager)
212212
.Then(new FuncTask<int>(Token, (b, i) => {
213213
results.Add("ProcessOutput");

src/tests/TestWebServer/HttpServer.cs

Lines changed: 12 additions & 6 deletions
Original file line numberDiff line numberDiff line change
@@ -1,10 +1,12 @@
11
using GitHub.Logging;
2+
using GitHub.Unity;
23
using System;
34
using System.Collections.Generic;
45
using System.Diagnostics;
56
using System.IO;
67
using System.Net;
78
using System.Net.Sockets;
9+
using System.Text;
810
using System.Threading;
911

1012
namespace TestWebServer
@@ -19,7 +21,8 @@ public class HttpServer
1921
{ ".png", "image/png" },
2022
{ ".txt", "text/plain" },
2123
{ ".md5", "text/plain" },
22-
{ ".zip", "application/zip" }
24+
{ ".zip", "application/zip" },
25+
{ ".json", "application/json" },
2326
};
2427
private readonly HttpListener listener;
2528
private readonly string rootDirectory;
@@ -81,7 +84,6 @@ public void Start()
8184
}
8285
catch (Exception ex)
8386
{
84-
Logger.Error(ex);
8587
break;
8688
}
8789
}
@@ -104,12 +106,16 @@ private void Process(HttpListenerContext context)
104106

105107
if (context.Request.Url.AbsolutePath == "/api/usage/unity")
106108
{
109+
var json = new { result = "Cool unity usage" }.ToJson();
107110
context.Response.StatusCode = (int)HttpStatusCode.OK;
108-
109-
var streamWriter = new StreamWriter(context.Response.OutputStream);
110-
streamWriter.Write("Cool Unity usage bro!");
111-
streamWriter.Flush();
111+
context.Response.ContentLength64 = json.Length;
112112

113+
string mime;
114+
context.Response.ContentType = mimeTypeMappings.TryGetValue(".json", out mime)
115+
? mime
116+
: "application/octet-stream";
117+
Utils.Copy(new MemoryStream(Encoding.UTF8.GetBytes(json)), context.Response.OutputStream, json.Length);
118+
context.Response.OutputStream.Flush();
113119
context.Response.Close();
114120
return;
115121
}

src/tests/TestWebServer/TestWebServer.csproj

Lines changed: 4 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -83,6 +83,10 @@
8383
</None>
8484
</ItemGroup>
8585
<ItemGroup>
86+
<ProjectReference Include="..\..\GitHub.Api\GitHub.Api.csproj">
87+
<Project>{B389ADAF-62CC-486E-85B4-2D8B078DF763}</Project>
88+
<Name>GitHub.Api</Name>
89+
</ProjectReference>
8690
<ProjectReference Include="..\..\GitHub.Logging\GitHub.Logging.csproj">
8791
<Project>{bb6a8eda-15d8-471b-a6ed-ee551e0b3ba0}</Project>
8892
<Name>GitHub.Logging</Name>

0 commit comments

Comments
 (0)