From ba73d4770f7154a3f03ae6956adcf09db97570db Mon Sep 17 00:00:00 2001 From: Inga Lovinde <52715130+inga-lovinde@users.noreply.github.com> Date: Thu, 24 Sep 2015 14:13:21 +0300 Subject: [PATCH] Refactoring; fixed race conditions --- DotNetBuilder/Compiler.cs | 19 ++++---- DotNetBuilder/Message.cs | 37 ++++++++++++++++ DotNetBuilder/Messages.cs | 44 +++++++++++++++++++ .../MicroBuildServer.DotNetBuilder.csproj | 2 + DotNetBuilder/NUnitTester.cs | 33 +++++++------- DotNetBuilder/NuGetter.cs | 18 ++++---- DotNetBuilder/Program.cs | 4 +- DotNetBuilder/Response.cs | 43 ++++++++---------- 8 files changed, 139 insertions(+), 61 deletions(-) create mode 100644 DotNetBuilder/Message.cs create mode 100644 DotNetBuilder/Messages.cs diff --git a/DotNetBuilder/Compiler.cs b/DotNetBuilder/Compiler.cs index d487a01..dc78e45 100644 --- a/DotNetBuilder/Compiler.cs +++ b/DotNetBuilder/Compiler.cs @@ -15,7 +15,7 @@ namespace MicroBuildServer.DotNetBuilder { private class CompilerLogger : Logger { - public readonly IList Messages = new List(); + public readonly Messages Messages = new Messages(); private int indent = 0; @@ -34,30 +34,30 @@ namespace MicroBuildServer.DotNetBuilder private void OnProjectStarted(object sender, ProjectStartedEventArgs e) { - Messages.Add(Response.Message.CreateInfo(GetLine("Started {0}", e.ProjectFile))); + Messages.Add(Message.CreateInfo(GetLine("Started {0}", e.ProjectFile))); indent++; } private void OnProjectFinished(object sender, ProjectFinishedEventArgs e) { indent--; - Messages.Add(Response.Message.CreateInfo(GetLine("Finished {0}", e.ProjectFile))); + Messages.Add(Message.CreateInfo(GetLine("Finished {0}", e.ProjectFile))); } private void OnError(object sender, BuildErrorEventArgs e) { - Messages.Add(Response.Message.CreateError(GetLine("{0} (#{1}, {2}:{3},{4})", e.Message, e.Code, e.File, e.LineNumber, e.ColumnNumber))); + Messages.Add(Message.CreateError(GetLine("{0} (#{1}, {2}:{3},{4})", e.Message, e.Code, e.File, e.LineNumber, e.ColumnNumber))); } private void OnWarning(object sender, BuildWarningEventArgs e) { - Messages.Add(Response.Message.CreateWarn(GetLine("{0} (#{1}, {2}:{3},{4})", e.Message, e.Code, e.File, e.LineNumber, e.ColumnNumber))); + Messages.Add(Message.CreateWarn(GetLine("{0} (#{1}, {2}:{3},{4})", e.Message, e.Code, e.File, e.LineNumber, e.ColumnNumber))); } private void OnMessage(object sender, BuildMessageEventArgs e) { //if (e.Importance != MessageImportance.High) return; - Messages.Add(Response.Message.CreateInfo(GetLine("{0}: {1}", e.Importance, e.Message))); + Messages.Add(Message.CreateInfo(GetLine("{0}: {1}", e.Importance, e.Message))); } private string GetLine(string format, params object[] args) @@ -105,13 +105,10 @@ namespace MicroBuildServer.DotNetBuilder var buildResult = BuildManager.DefaultBuildManager.Build(parameters, buildRequest); if (buildResult.OverallResult == BuildResultCode.Failure) { - logger.Messages.Add(Response.Message.CreateError("BuildResult is false")); + logger.Messages.Add(Message.CreateError("BuildResult is false")); } - return new Response - { - Messages = logger.Messages.ToArray(), - }; + return new Response(logger.Messages); } } } diff --git a/DotNetBuilder/Message.cs b/DotNetBuilder/Message.cs new file mode 100644 index 0000000..9b65e83 --- /dev/null +++ b/DotNetBuilder/Message.cs @@ -0,0 +1,37 @@ +using Newtonsoft.Json; + +namespace MicroBuildServer.DotNetBuilder +{ + public class Message + { + public readonly string Type; + + public readonly string Body; + + private Message(string type, string body) + { + Type = type; + Body = body; + } + + public static Message CreateInfo(string body) + { + return new Message("info", body); + } + + public static Message CreateWarn(string body) + { + return new Message("warn", body); + } + + public static Message CreateError(string body) + { + return new Message("error", body); + } + + public override string ToString() + { + return string.Format("{0}: {1}", Type, Body); + } + } +} diff --git a/DotNetBuilder/Messages.cs b/DotNetBuilder/Messages.cs new file mode 100644 index 0000000..3c6653e --- /dev/null +++ b/DotNetBuilder/Messages.cs @@ -0,0 +1,44 @@ +using System; +using System.Collections.Generic; +using System.Linq; +using System.Text; +using System.Threading.Tasks; + +namespace MicroBuildServer.DotNetBuilder +{ + internal class Messages + { + private readonly object syncRoot = new object(); + + private readonly List storage = new List(); + + public void Add(Message message) + { + if (message == null) + { + throw new ArgumentNullException(nameof(message)); + } + + lock(syncRoot) + { + storage.Add(message); + } + } + + public TResult[] ToArray(Func selector) + { + lock(syncRoot) + { + return storage.Select(selector).ToArray(); + } + } + + public bool Any() + { + lock(syncRoot) + { + return storage.Any(); + } + } + } +} diff --git a/DotNetBuilder/MicroBuildServer.DotNetBuilder.csproj b/DotNetBuilder/MicroBuildServer.DotNetBuilder.csproj index fa4c936..4692610 100644 --- a/DotNetBuilder/MicroBuildServer.DotNetBuilder.csproj +++ b/DotNetBuilder/MicroBuildServer.DotNetBuilder.csproj @@ -97,6 +97,8 @@ + + diff --git a/DotNetBuilder/NUnitTester.cs b/DotNetBuilder/NUnitTester.cs index 9b966e3..7a46866 100644 --- a/DotNetBuilder/NUnitTester.cs +++ b/DotNetBuilder/NUnitTester.cs @@ -13,7 +13,7 @@ namespace MicroBuildServer.DotNetBuilder private class Listener : EventListener { - public readonly List Messages = new List(); + public readonly Messages Messages = new Messages(); private bool runFail; private bool suiteFail; @@ -56,7 +56,7 @@ namespace MicroBuildServer.DotNetBuilder public void RunFinished(Exception exception) { - Messages.Add(Response.Message.CreateError("Run finished: " + exception)); + Messages.Add(Message.CreateError("Run finished: " + exception)); runFail = true; } @@ -66,17 +66,17 @@ namespace MicroBuildServer.DotNetBuilder if (!IsSuccess(result) && !runFail) { - Messages.Add(Response.Message.CreateError(message)); + Messages.Add(Message.CreateError(message)); } else { - Messages.Add(Response.Message.CreateInfo(message)); + Messages.Add(Message.CreateInfo(message)); } } public void RunStarted(string name, int testCount) { - Messages.Add(Response.Message.CreateInfo("Run started: " + name)); + Messages.Add(Message.CreateInfo("Run started: " + name)); runFail = false; } @@ -86,11 +86,11 @@ namespace MicroBuildServer.DotNetBuilder if (!IsSuccess(result) && !suiteFail) { - Messages.Add(Response.Message.CreateError(message)); + Messages.Add(Message.CreateError(message)); } else { - Messages.Add(Response.Message.CreateInfo(message)); + Messages.Add(Message.CreateInfo(message)); } if (!result.IsSuccess) @@ -101,7 +101,7 @@ namespace MicroBuildServer.DotNetBuilder public void SuiteStarted(TestName testName) { - Messages.Add(Response.Message.CreateInfo("Suite started: " + testName.Name)); + Messages.Add(Message.CreateInfo("Suite started: " + testName.Name)); suiteFail = false; } @@ -111,28 +111,28 @@ namespace MicroBuildServer.DotNetBuilder if (!IsSuccess(result)) { - Messages.Add(Response.Message.CreateError(message)); + Messages.Add(Message.CreateError(message)); } else { - Messages.Add(Response.Message.CreateInfo(message)); + Messages.Add(Message.CreateInfo(message)); } suiteFail = true; } public void TestOutput(TestOutput testOutput) { - Messages.Add(Response.Message.CreateInfo("Test output: " + testOutput.Text)); + Messages.Add(Message.CreateInfo("Test output: " + testOutput.Text)); } public void TestStarted(TestName testName) { - Messages.Add(Response.Message.CreateInfo("Test started: " + testName.Name)); + Messages.Add(Message.CreateInfo("Test started: " + testName.Name)); } public void UnhandledException(Exception exception) { - Messages.Add(Response.Message.CreateError("Unhandled exception: " + exception)); + Messages.Add(Message.CreateError("Unhandled exception: " + exception)); suiteFail = true; runFail = true; } @@ -162,9 +162,12 @@ namespace MicroBuildServer.DotNetBuilder } //DebugTestResult(Console.Out, result); - var messages = listener.Messages.Any() ? listener.Messages.ToArray() : new[] {Response.Message.CreateError("No messages from listener")}; + if (!listener.Messages.Any()) + { + listener.Messages.Add(Message.CreateError("No messages from listener")); + } - AppDomain.CurrentDomain.SetData(DATA_TEST_RESULTS_KEY, new Response { Messages = messages }); + AppDomain.CurrentDomain.SetData(DATA_TEST_RESULTS_KEY, new Response(listener.Messages)); } } diff --git a/DotNetBuilder/NuGetter.cs b/DotNetBuilder/NuGetter.cs index 6abfad4..2bbf7f5 100644 --- a/DotNetBuilder/NuGetter.cs +++ b/DotNetBuilder/NuGetter.cs @@ -11,7 +11,7 @@ namespace MicroBuildServer.DotNetBuilder { private class Console : IConsole { - public readonly IList Messages = new List(); + public readonly Messages Messages = new Messages(); public bool Confirm(string description) { @@ -74,7 +74,7 @@ namespace MicroBuildServer.DotNetBuilder public void Write(string value) { - Messages.Add(Response.Message.CreateInfo(value)); + Messages.Add(Message.CreateInfo(value)); } public void Write(object value) @@ -89,7 +89,7 @@ namespace MicroBuildServer.DotNetBuilder public void WriteError(string value) { - Messages.Add(Response.Message.CreateError(value)); + Messages.Add(Message.CreateError(value)); } public void WriteError(object value) @@ -123,7 +123,7 @@ namespace MicroBuildServer.DotNetBuilder public void WriteWarning(bool prependWarningText, string value, params object[] args) { - throw new NotImplementedException(); + WriteWarning(value, args); } public void WriteWarning(string value, params object[] args) @@ -133,12 +133,12 @@ namespace MicroBuildServer.DotNetBuilder public void WriteWarning(bool prependWarningText, string value) { - throw new NotImplementedException(); + WriteWarning(value); } public void WriteWarning(string value) { - Messages.Add(Response.Message.CreateWarn(value)); + Messages.Add(Message.CreateWarn(value)); } public void Log(MessageLevel level, string message, params object[] args) @@ -187,7 +187,7 @@ namespace MicroBuildServer.DotNetBuilder console.WriteError(e); } - return new Response { Messages = console.Messages.ToArray() }; + return new Response(console.Messages); } public static Response Push(NuGetPushRequest request) @@ -211,7 +211,7 @@ namespace MicroBuildServer.DotNetBuilder console.WriteError(e); } - return new Response {Messages = console.Messages.ToArray()}; + return new Response(console.Messages); } public static Response Restore(NuGetRestoreRequest request) @@ -235,7 +235,7 @@ namespace MicroBuildServer.DotNetBuilder console.WriteError(e); } - return new Response { Messages = console.Messages.ToArray() }; + return new Response(console.Messages); } } } diff --git a/DotNetBuilder/Program.cs b/DotNetBuilder/Program.cs index 944b35f..68559e7 100644 --- a/DotNetBuilder/Program.cs +++ b/DotNetBuilder/Program.cs @@ -30,7 +30,9 @@ namespace MicroBuildServer.DotNetBuilder } catch (Exception e) { - return new Response { Messages = new[] { Response.Message.CreateError(e.ToString()) } }; + var messages = new Messages(); + messages.Add(Message.CreateError(e.ToString())); + return new Response(messages); } } diff --git a/DotNetBuilder/Response.cs b/DotNetBuilder/Response.cs index e344192..b8477c2 100644 --- a/DotNetBuilder/Response.cs +++ b/DotNetBuilder/Response.cs @@ -1,40 +1,33 @@ -using System; -using System.Collections.Generic; -using System.Linq; -using System.Text; +using Newtonsoft.Json; +using System; namespace MicroBuildServer.DotNetBuilder { + [JsonObject(MemberSerialization = MemberSerialization.OptIn)] [Serializable] class Response { + [JsonObject(MemberSerialization = MemberSerialization.OptIn)] [Serializable] - public class Message + private class ResponseMessage { - public string Type { get; private set; } - public string Body { get; private set; } + [JsonProperty(Required = Required.Always)] + public string Type { get; set; } - public static Message CreateInfo(string body) - { - return new Message { Type = "info", Body = body }; - } + [JsonProperty(Required = Required.Always)] + public string Body { get; set; } + } - public static Message CreateWarn(string body) - { - return new Message { Type = "warn", Body = body }; - } + [JsonProperty(Required = Required.Always, PropertyName = "Messages")] + private ResponseMessage[] Messages { get; set; } - public static Message CreateError(string body) - { - return new Message { Type = "error", Body = body }; - } - - public override string ToString() + public Response(Messages messages) + { + Messages = messages.ToArray(message => new ResponseMessage { - return string.Format("{0}: {1}", Type, Body); - } + Type = message.Type, + Body = message.Body, + }); } - - public Message[] Messages { get; set; } } }