-
Notifications
You must be signed in to change notification settings - Fork 388
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
Add support for merging results #123
Conversation
Here is a more detail explanation of the changes: The results are merged To merge the coverage results, I have public class Branches : SortedDictionary<int, List<BranchInfo>> { } into public class Branches : SortedDictionary<(int Number, int Offset, int EndOffset, int Path, uint Ordinal), HitInfo> { } I found that a tuple of Unfortunately, the JSON serializer (Jil) does not support keys other than strings or integers. And since it also doesn't support converters, I could not rewrite this without converting the The story doesn't stop here, as Newtonsoft.Json would serialize tuples as strings (e.g. ...
"System.Boolean CoverletTest.Application::DoSomething(System.Boolean)": {
"Lines": [
{
"Key": {
"Line": 21
},
"Value": {
"Hits": 2
}
}
],
"Branches": [
{
"Key": {
"Number": 11,
"Offset": 4,
"EndOffset": 22,
"Path": 1,
"Ordinal": 1
},
"Value": {
"Hits": 1
}
}
]
}
... There are still a few things that I haven't fixed (properly). One of them is the way how the results are stored per assembly. If you take the test project I created, you'll end up with
I solved this (for now) by just taking the file name and stripping the full path. A better solution would be preferred, but this will change the resulting JSON again (similar to the branches above). |
@basilfx All this work is awesome! I really want this to happen. Just a few things that came up when thinking this problem though that i wanted to put out there. I'm not familiar with the code base at all, so please excuse me for being so naive. One question i would ask is why are we bothering to output the intermediate results to a file in the first place? I would think the most efficient and straight forward way to make this happen is to have an in memory collection of all tests ran and keep adding the results until all I would think this would eliminate your serialization issues and knowing all the test projects before hand will allow you to merge all the assemblies As i said originally, this is probably very naive since I have not taken the time to look though how the code currently works. Just wanted to put it out there |
@sjk07 Thanks for the feedback. The reason why I use a intermediate results file is because they are used across multiple processes, so you cannot keep it in memory. From a coverlet point of view, it is not aware if a particular run is the first or the last, so you would need an additional step to process the results (doable, but increases complexity). I also don’t know the tests on beforehand. I could use a wildcard to run all tests, or run dotnet test on the solution. My approach is easy. It doesn’t require scripting (e.g. to discover the test) so it runs very easily in environments such as VSTS. |
@basilfx thanks for taking the time out to look into this. Will take a look once I get the chance. Don't worry about the Travis failure for now, the .NET Core runtime installed on it doesn't support assembly signing. Will move to Appveyor Linux build agents |
Hey @basilfx, please rebase master so that the CI build can kick in. I've transitioned the Linux tests over to Appveyor which already runs all Windows tests |
A branch point now uses a (named) tuple as a key, to uniquely identify its location. As a downside, JIL cannot be used, since it doesn't support keys other than strings, integers or enums.
This commits adds the option `IntermediateResult`, which will write the raw coverage result to an intermediate file, and merge the result of the next run with that file. This is useful in multi-project solutions. Eventually, the last coverage run will produce a report with the combined results of all the runs.
118866d
to
71f95f5
Compare
@tonerdo Rebased. It seems to work :-) |
Hey @basilfx, I've taken a look through your code and I do appreciate the effort. I have a couple of questions as well as thoughts on how to make this implementation much simpler.
In summary, I think it'll be simpler and a lot cleaner to just accept a Let me know your thoughts |
Thanks @tonerdo for looking at the code. Here are my thoughts:
No, the I think that this should be changed, apart from merging the coverage results. That's why I added it as a separate commit. I guess it should be easy to convert this tuple into a object, e.g.
Since
I fully agree, but the point is that Coverlet support multiple output formats. I think it is therefore more confusing for the end-user that it doesn't work whenever JSON format is not selected, so have you any idea's about that?
Agreed. This was, however, the easiest for me to implement :-)
Here is the code. One test project covers the if-part, the other the else-part. I don't have much time coming period to work on this. so I am fine with considering this a first attempt, and start from scratch. Especially since you have an idea on how to merge properly :-) |
Great to see this is being worked on! |
Just like OpenCover which has it's primary format, Coverlet also has it's own JSON format. The support for other formats is entirely for compatibility reasons and to make it easy to integrate Coverlet with existing tools.
Ah ok. That's fine then
I'm not very sold on the new format you came up with. It feels a bit counter-intuitive to have |
Point is that whenever someone doesn't output Coverlet JSON, they cannot merge results. So IMHO it is more confusing to the end-user, as opposed to having a
It should be very easy to output the old format by changing the serializer. I just wanted to demonstrate that the |
Apologies for the edit on your last comment. Didn't realize I was not editing my post, didn't even know I could do that! |
I totally get your point. If a user defaults to opencover as their format of choice they still have to output and extra file to support merging with results from another project. I'd much prefer that extra file to be the primary json coverage result also I don't want to introduce any new properties if I can help it |
Guys when this feature will be merged to master? any schedule? |
I currently have no time/intention to work on this. I'll close it for now. |
This PR adds support for merging results of multiple projects. It is similar to how OpenCover supports this.
It is as simple as adding
/p:CoverletIntermediateResult=intermediate.json
to the arguments. Just ensure that this file doesn't exist when you would record the test results of multiple projects.I have created this test project (you have to fix reference to Coverlet package), which demonstrates how two projects that both cover 50% will yield 100% when merging the intermediate results. I have also verified that the report generated by ReportGenerator looks as expected.
References:
#36