Skip to content

* use producer consumer pattern for parsing and merging #262

New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Merged
merged 19 commits into from
Sep 25, 2019
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension


Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
7 changes: 7 additions & 0 deletions src/ReportGenerator.Console.NetCore/App.config
Original file line number Diff line number Diff line change
@@ -0,0 +1,7 @@
<?xml version="1.0" encoding="utf-8" ?>
<configuration>
<runtime>
<gcConcurrent enabled="true"/>
<gcServer enabled="true"/>
</runtime>
</configuration>
10 changes: 7 additions & 3 deletions src/ReportGenerator.Console/app.config
Original file line number Diff line number Diff line change
@@ -1,6 +1,10 @@
<?xml version="1.0" encoding="utf-8" ?>
<configuration>
<startup>
<supportedRuntime version="v4.0" sku=".NETFramework,Version=v4.7" />
</startup>
<startup>
<supportedRuntime version="v4.0" sku=".NETFramework,Version=v4.7" />
</startup>
<runtime>
<gcConcurrent enabled="true"/>
<gcServer enabled="true"/>
</runtime>
</configuration>
46 changes: 23 additions & 23 deletions src/ReportGenerator.Core.Test/Parser/CoverageReportParserTest.cs
Original file line number Diff line number Diff line change
Expand Up @@ -28,10 +28,10 @@ public CoverageReportParserTest()
public void ParseFiles_SingleReportFileWithSingleReport_PartCoverNotSupported()
{
string filePath = Path.Combine(FileManager.GetCSharpReportDirectory(), "Partcover2.3.xml");
Assert.Throws<UnsupportedParserException>(() => new CoverageReportParser(1, new string[0], this.filterMock.Object, this.filterMock.Object, this.filterMock.Object).ParseFiles(new string[] { filePath }));
Assert.Throws<UnsupportedParserException>(() => new CoverageReportParser(1, 1, new string[0], this.filterMock.Object, this.filterMock.Object, this.filterMock.Object).ParseFiles(new string[] { filePath }));

filePath = Path.Combine(FileManager.GetCSharpReportDirectory(), "Partcover2.2.xml");
Assert.Throws<UnsupportedParserException>(() => new CoverageReportParser(1, new string[0], this.filterMock.Object, this.filterMock.Object, this.filterMock.Object).ParseFiles(new string[] { filePath }));
Assert.Throws<UnsupportedParserException>(() => new CoverageReportParser(1, 1, new string[0], this.filterMock.Object, this.filterMock.Object, this.filterMock.Object).ParseFiles(new string[] { filePath }));
}

/// <summary>
Expand All @@ -41,60 +41,60 @@ public void ParseFiles_SingleReportFileWithSingleReport_PartCoverNotSupported()
public void ParseFiles_SingleReportFileWithSingleReport_CorrectParserIsReturned()
{
string filePath = Path.Combine(FileManager.GetCSharpReportDirectory(), "NCover1.5.8.xml");
var parserResult = new CoverageReportParser(1, new string[] { "C:\\somedirectory" }, this.filterMock.Object, this.filterMock.Object, this.filterMock.Object).ParseFiles(new string[] { filePath });
var parserResult = new CoverageReportParser(1, 1, new string[] { "C:\\somedirectory" }, this.filterMock.Object, this.filterMock.Object, this.filterMock.Object).ParseFiles(new string[] { filePath });
Assert.Equal("NCoverParser", parserResult.ParserName);
Assert.Equal(0, parserResult.SourceDirectories.Count);

filePath = Path.Combine(FileManager.GetCSharpReportDirectory(), "OpenCover.xml");
parserResult = new CoverageReportParser(1, new string[] { "C:\\somedirectory" }, this.filterMock.Object, this.filterMock.Object, this.filterMock.Object).ParseFiles(new string[] { filePath });
parserResult = new CoverageReportParser(1, 1, new string[] { "C:\\somedirectory" }, this.filterMock.Object, this.filterMock.Object, this.filterMock.Object).ParseFiles(new string[] { filePath });
Assert.Equal("OpenCoverParser", parserResult.ParserName);
Assert.Equal(0, parserResult.SourceDirectories.Count);

filePath = Path.Combine(FileManager.GetCSharpReportDirectory(), "dotCover.xml");
parserResult = new CoverageReportParser(1, new string[] { "C:\\somedirectory" }, this.filterMock.Object, this.filterMock.Object, this.filterMock.Object).ParseFiles(new string[] { filePath });
parserResult = new CoverageReportParser(1, 1, new string[] { "C:\\somedirectory" }, this.filterMock.Object, this.filterMock.Object, this.filterMock.Object).ParseFiles(new string[] { filePath });
Assert.Equal("DotCoverParser", parserResult.ParserName);
Assert.Equal(0, parserResult.SourceDirectories.Count);

filePath = Path.Combine(FileManager.GetCSharpReportDirectory(), "VisualStudio2010.coveragexml");
parserResult = new CoverageReportParser(1, new string[] { "C:\\somedirectory" }, this.filterMock.Object, this.filterMock.Object, this.filterMock.Object).ParseFiles(new string[] { filePath });
parserResult = new CoverageReportParser(1, 1, new string[] { "C:\\somedirectory" }, this.filterMock.Object, this.filterMock.Object, this.filterMock.Object).ParseFiles(new string[] { filePath });
Assert.Equal("VisualStudioParser", parserResult.ParserName);
Assert.Equal(0, parserResult.SourceDirectories.Count);

filePath = Path.Combine(FileManager.GetCSharpReportDirectory(), "DynamicCodeCoverage.xml");
parserResult = new CoverageReportParser(1, new string[] { "C:\\somedirectory" }, this.filterMock.Object, this.filterMock.Object, this.filterMock.Object).ParseFiles(new string[] { filePath });
parserResult = new CoverageReportParser(1, 1, new string[] { "C:\\somedirectory" }, this.filterMock.Object, this.filterMock.Object, this.filterMock.Object).ParseFiles(new string[] { filePath });
Assert.Equal("DynamicCodeCoverageParser", parserResult.ParserName);
Assert.Equal(0, parserResult.SourceDirectories.Count);

filePath = Path.Combine(FileManager.GetCSharpReportDirectory(), "mprof-report.xml");
parserResult = new CoverageReportParser(1, new string[] { "C:\\somedirectory" }, this.filterMock.Object, this.filterMock.Object, this.filterMock.Object).ParseFiles(new string[] { filePath });
parserResult = new CoverageReportParser(1, 1, new string[] { "C:\\somedirectory" }, this.filterMock.Object, this.filterMock.Object, this.filterMock.Object).ParseFiles(new string[] { filePath });
Assert.Equal("MProfParser", parserResult.ParserName);
Assert.Equal(0, parserResult.SourceDirectories.Count);

filePath = Path.Combine(FileManager.GetJavaReportDirectory(), "Cobertura2.1.1.xml");
parserResult = new CoverageReportParser(1, new string[] { "C:\\somedirectory" }, this.filterMock.Object, this.filterMock.Object, this.filterMock.Object).ParseFiles(new string[] { filePath });
parserResult = new CoverageReportParser(1, 1, new string[] { "C:\\somedirectory" }, this.filterMock.Object, this.filterMock.Object, this.filterMock.Object).ParseFiles(new string[] { filePath });
Assert.Equal("CoberturaParser", parserResult.ParserName);
Assert.Equal(1, parserResult.SourceDirectories.Count);
Assert.Equal("C:/temp", parserResult.SourceDirectories.First());

filePath = Path.Combine(FileManager.GetJavaReportDirectory(), "JaCoCo0.8.3.xml");
parserResult = new CoverageReportParser(1, new string[] { "C:\\somedirectory" }, this.filterMock.Object, this.filterMock.Object, this.filterMock.Object).ParseFiles(new string[] { filePath });
parserResult = new CoverageReportParser(1, 1, new string[] { "C:\\somedirectory" }, this.filterMock.Object, this.filterMock.Object, this.filterMock.Object).ParseFiles(new string[] { filePath });
Assert.Equal("JaCoCoParser", parserResult.ParserName);
Assert.Equal(1, parserResult.SourceDirectories.Count);
Assert.Equal("C:\\somedirectory", parserResult.SourceDirectories.First());

filePath = Path.Combine(FileManager.GetJavaReportDirectory(), "Clover_OpenClover4.3.1.xml");
parserResult = new CoverageReportParser(1, new string[] { "C:\\somedirectory" }, this.filterMock.Object, this.filterMock.Object, this.filterMock.Object).ParseFiles(new string[] { filePath });
parserResult = new CoverageReportParser(1, 1, new string[] { "C:\\somedirectory" }, this.filterMock.Object, this.filterMock.Object, this.filterMock.Object).ParseFiles(new string[] { filePath });
Assert.Equal("CloverParser", parserResult.ParserName);
Assert.Equal(1, parserResult.SourceDirectories.Count);
Assert.Equal("C:\\somedirectory", parserResult.SourceDirectories.First());

filePath = Path.Combine(FileManager.GetCSharpReportDirectory(), "lcov.info");
parserResult = new CoverageReportParser(1, new string[] { "C:\\somedirectory" }, this.filterMock.Object, this.filterMock.Object, this.filterMock.Object).ParseFiles(new string[] { filePath });
parserResult = new CoverageReportParser(1, 1, new string[] { "C:\\somedirectory" }, this.filterMock.Object, this.filterMock.Object, this.filterMock.Object).ParseFiles(new string[] { filePath });
Assert.Equal("LCovParser", parserResult.ParserName);
Assert.Equal(0, parserResult.SourceDirectories.Count);

filePath = Path.Combine(FileManager.GetCPlusPlusReportDirectory(), "gcov", "basic", "main.cpp.gcov");
parserResult = new CoverageReportParser(1, new string[] { "C:\\somedirectory" }, this.filterMock.Object, this.filterMock.Object, this.filterMock.Object).ParseFiles(new string[] { filePath });
parserResult = new CoverageReportParser(1, 1, new string[] { "C:\\somedirectory" }, this.filterMock.Object, this.filterMock.Object, this.filterMock.Object).ParseFiles(new string[] { filePath });
Assert.Equal("GCovParser", parserResult.ParserName);
Assert.Equal(1, parserResult.SourceDirectories.Count);
Assert.Equal("C:\\somedirectory", parserResult.SourceDirectories.First());
Expand All @@ -107,10 +107,10 @@ public void ParseFiles_SingleReportFileWithSingleReport_CorrectParserIsReturned(
public void ParseFiles_SingleReportFileWithSeveralReports_PartCoverNotSupported()
{
string filePath = Path.Combine(FileManager.GetCSharpReportDirectory(), "MultiPartcover2.3.xml");
Assert.Throws<UnsupportedParserException>(() => new CoverageReportParser(1, new string[0], this.filterMock.Object, this.filterMock.Object, this.filterMock.Object).ParseFiles(new string[] { filePath }));
Assert.Throws<UnsupportedParserException>(() => new CoverageReportParser(1, 1, new string[0], this.filterMock.Object, this.filterMock.Object, this.filterMock.Object).ParseFiles(new string[] { filePath }));

filePath = Path.Combine(FileManager.GetCSharpReportDirectory(), "MultiPartcover2.2.xml");
Assert.Throws<UnsupportedParserException>(() => new CoverageReportParser(1, new string[0], this.filterMock.Object, this.filterMock.Object, this.filterMock.Object).ParseFiles(new string[] { filePath }));
Assert.Throws<UnsupportedParserException>(() => new CoverageReportParser(1, 1, new string[0], this.filterMock.Object, this.filterMock.Object, this.filterMock.Object).ParseFiles(new string[] { filePath }));
}

/// <summary>
Expand All @@ -120,23 +120,23 @@ public void ParseFiles_SingleReportFileWithSeveralReports_PartCoverNotSupported(
public void ParseFiles_SingleReportFileWithSeveralReports_CorrectParserIsReturned()
{
string filePath = Path.Combine(FileManager.GetCSharpReportDirectory(), "MultiNCover1.5.8.xml");
string parserName = new CoverageReportParser(1, new string[0], this.filterMock.Object, this.filterMock.Object, this.filterMock.Object).ParseFiles(new string[] { filePath }).ParserName;
string parserName = new CoverageReportParser(1, 1, new string[0], this.filterMock.Object, this.filterMock.Object, this.filterMock.Object).ParseFiles(new string[] { filePath }).ParserName;
Assert.Equal("MultiReportParser (2x NCoverParser)", parserName);

filePath = Path.Combine(FileManager.GetCSharpReportDirectory(), "MultiOpenCover.xml");
parserName = new CoverageReportParser(1, new string[0], this.filterMock.Object, this.filterMock.Object, this.filterMock.Object).ParseFiles(new string[] { filePath }).ParserName;
parserName = new CoverageReportParser(1, 1, new string[0], this.filterMock.Object, this.filterMock.Object, this.filterMock.Object).ParseFiles(new string[] { filePath }).ParserName;
Assert.Equal("MultiReportParser (2x OpenCoverParser)", parserName);

filePath = Path.Combine(FileManager.GetCSharpReportDirectory(), "MultidotCover.xml");
parserName = new CoverageReportParser(1, new string[0], this.filterMock.Object, this.filterMock.Object, this.filterMock.Object).ParseFiles(new string[] { filePath }).ParserName;
parserName = new CoverageReportParser(1, 1, new string[0], this.filterMock.Object, this.filterMock.Object, this.filterMock.Object).ParseFiles(new string[] { filePath }).ParserName;
Assert.Equal("MultiReportParser (2x DotCoverParser)", parserName);

filePath = Path.Combine(FileManager.GetCSharpReportDirectory(), "MultiVisualStudio2010.coveragexml");
parserName = new CoverageReportParser(1, new string[0], this.filterMock.Object, this.filterMock.Object, this.filterMock.Object).ParseFiles(new string[] { filePath }).ParserName;
parserName = new CoverageReportParser(1, 1, new string[0], this.filterMock.Object, this.filterMock.Object, this.filterMock.Object).ParseFiles(new string[] { filePath }).ParserName;
Assert.Equal("MultiReportParser (2x VisualStudioParser)", parserName);

filePath = Path.Combine(FileManager.GetCSharpReportDirectory(), "MultiDynamicCodeCoverage.xml");
parserName = new CoverageReportParser(1, new string[0], this.filterMock.Object, this.filterMock.Object, this.filterMock.Object).ParseFiles(new string[] { filePath }).ParserName;
parserName = new CoverageReportParser(1, 1, new string[0], this.filterMock.Object, this.filterMock.Object, this.filterMock.Object).ParseFiles(new string[] { filePath }).ParserName;
Assert.Equal("MultiReportParser (2x DynamicCodeCoverageParser)", parserName);
}

Expand All @@ -148,7 +148,7 @@ public void ParseFiles_SeveralReportFilesWithSingleReport_CorrectParserIsReturne
{
string filePath = Path.Combine(FileManager.GetCSharpReportDirectory(), "OpenCover.xml");
string filePath2 = Path.Combine(FileManager.GetCSharpReportDirectory(), "NCover1.5.8.xml");
string parserName = new CoverageReportParser(1, new string[0], this.filterMock.Object, this.filterMock.Object, this.filterMock.Object).ParseFiles(new string[] { filePath, filePath2 }).ParserName;
string parserName = new CoverageReportParser(1, 1, new string[0], this.filterMock.Object, this.filterMock.Object, this.filterMock.Object).ParseFiles(new string[] { filePath, filePath2 }).ParserName;
Assert.Equal("MultiReportParser (1x NCoverParser, 1x OpenCoverParser)", parserName);
}

Expand All @@ -160,7 +160,7 @@ public void ParseFiles_SeveralReportFilesWithSeveralReports_CorrectParserIsRetur
{
string filePath = Path.Combine(FileManager.GetCSharpReportDirectory(), "NCover1.5.8.xml");
string filePath2 = Path.Combine(FileManager.GetCSharpReportDirectory(), "MultiOpenCover.xml");
string parserName = new CoverageReportParser(1, new string[0], this.filterMock.Object, this.filterMock.Object, this.filterMock.Object).ParseFiles(new string[] { filePath, filePath2 }).ParserName;
string parserName = new CoverageReportParser(1, 1, new string[0], this.filterMock.Object, this.filterMock.Object, this.filterMock.Object).ParseFiles(new string[] { filePath, filePath2 }).ParserName;
Assert.Equal("MultiReportParser (1x NCoverParser, 2x OpenCoverParser)", parserName);
}

Expand All @@ -170,7 +170,7 @@ public void ParseFiles_SeveralReportFilesWithSeveralReports_CorrectParserIsRetur
[Fact]
public void ParseFiles_NoReports_CorrectParserIsReturned()
{
string parserName = new CoverageReportParser(1, new string[0], this.filterMock.Object, this.filterMock.Object, this.filterMock.Object).ParseFiles(new string[] { string.Empty }).ParserName;
string parserName = new CoverageReportParser(1, 1, new string[0], this.filterMock.Object, this.filterMock.Object, this.filterMock.Object).ParseFiles(new string[] { string.Empty }).ParserName;
Assert.Equal(string.Empty, parserName);
}
}
Expand Down
4 changes: 2 additions & 2 deletions src/ReportGenerator.Core.Test/Parser/ParserResultTest.cs
Original file line number Diff line number Diff line change
Expand Up @@ -240,7 +240,7 @@ public void OpenCoverMethodMetricsTest()
filterMock.Setup(f => f.IsElementIncludedInReport(It.IsAny<string>())).Returns(true);

string filePath = Path.Combine(FileManager.GetCSharpReportDirectory(), "MultiOpenCover.xml");
var parserResult = new CoverageReportParser(1, new string[0], filterMock.Object, filterMock.Object, filterMock.Object).ParseFiles(new string[] { filePath });
var parserResult = new CoverageReportParser(1, 1, new string[0], filterMock.Object, filterMock.Object, filterMock.Object).ParseFiles(new string[] { filePath });

var metrics = parserResult.Assemblies
.Single(a => a.Name == "Test").Classes
Expand Down Expand Up @@ -270,7 +270,7 @@ public void OpenCoverBranchesTest()
filterMock.Setup(f => f.IsElementIncludedInReport(It.IsAny<string>())).Returns(true);

string filePath = Path.Combine(FileManager.GetCSharpReportDirectory(), "MultiOpenCover.xml");
var parserResult = new CoverageReportParser(1, new string[0], filterMock.Object, filterMock.Object, filterMock.Object).ParseFiles(new string[] { filePath });
var parserResult = new CoverageReportParser(1, 1, new string[0], filterMock.Object, filterMock.Object, filterMock.Object).ParseFiles(new string[] { filePath });

var fileAnalysis = GetFileAnalysis(parserResult.Assemblies, "Test.TestClass2", "C:\\temp\\TestClass2.cs");

Expand Down
7 changes: 7 additions & 0 deletions src/ReportGenerator.Core/App.config
Original file line number Diff line number Diff line change
@@ -0,0 +1,7 @@
<?xml version="1.0" encoding="utf-8" ?>
<configuration>
<runtime>
<gcConcurrent enabled="true"/>
<gcServer enabled="true"/>
</runtime>
</configuration>
14 changes: 8 additions & 6 deletions src/ReportGenerator.Core/Generator.cs
Original file line number Diff line number Diff line change
@@ -1,7 +1,4 @@
using System;
using System.Collections.Generic;
using System.IO;
using Microsoft.Extensions.Configuration;
using Microsoft.Extensions.Configuration;
using Palmmedia.ReportGenerator.Core.CodeAnalysis;
using Palmmedia.ReportGenerator.Core.Common;
using Palmmedia.ReportGenerator.Core.Logging;
Expand All @@ -12,6 +9,9 @@
using Palmmedia.ReportGenerator.Core.Properties;
using Palmmedia.ReportGenerator.Core.Reporting;
using Palmmedia.ReportGenerator.Core.Reporting.History;
using System;
using System.Collections.Generic;
using System.IO;

namespace Palmmedia.ReportGenerator.Core
{
Expand Down Expand Up @@ -114,9 +114,11 @@ public bool GenerateReport(

var stopWatch = new System.Diagnostics.Stopwatch();
stopWatch.Start();

Logger.Info($"{nameof(settings.NumberOfReportsParsedInParallel)}={settings.NumberOfReportsParsedInParallel}");
Logger.Info($"{nameof(settings.NumberOfReportsMergedInParallel)}={settings.NumberOfReportsMergedInParallel}");
var parserResult = new CoverageReportParser(
settings.NumberOfReportsParsedInParallel,
settings.NumberOfReportsMergedInParallel,
reportConfiguration.SourceDirectories,
new DefaultFilter(reportConfiguration.AssemblyFilters),
new DefaultFilter(reportConfiguration.ClassFilters),
Expand Down Expand Up @@ -228,7 +230,7 @@ public void GenerateReport(

if (historyStorage != null)
{
new HistoryParser(historyStorage, settings.MaximumNumberOfHistoricCoverageFiles)
new HistoryParser(historyStorage, settings.MaximumNumberOfHistoricCoverageFiles, settings.NumberOfReportsParsedInParallel)
.ApplyHistoricCoverage(parserResult.Assemblies, overallHistoricCoverages);

reportContext.OverallHistoricCoverages = overallHistoricCoverages;
Expand Down
Loading