A few weeks ago I blogged about a problem concerning coverage of unexecuted code in PartCover. The problem was that the report generated by PartCover does not contain any coverage information about uncovered methods. That implicated, that my tool ReportGenerator calculated a wrong coverage quota, since the lines of unexecuted method were considered to be 'not visitable'.
I claimed that it would not be easy to create a workaround for the problem, but actually it isn't that difficult, if you use the right tools.
The problem
The report generated by PartCover contains only one utilizable piece of information: The signature of the method (e.g. 'void (int, long)'). Based on the signature we have to search the method within the source files and determine its start and end line number. As explained in my previous post this can not be accomplished on a source code level.
The solution
One of my readers pointed me to the NRefactory library, which is part of SharpDevelop.
With the following snippet you can get an AST of a code file:
INode ast; using (var parser = ICSharpCode.NRefactory.ParserFactory.CreateParser(filename)) { parser.Parse(); ast = parser.CompilationUnit.CurrentBock; }
Now you can recursively search the syntax tree for a method matching the signature extracted from the PartCover report. You have to perform some mappings between type names, since the type names used in the signature are not named consistently (e.g. string for System.String).
Once you found the correct element within the AST, you obtain the line numbers very easily:
MethodDeclaration methodDeclaration = node as MethodDeclaration; if (methodDeclaration != null) { int startLine = methodDeclaration.Body.StartLocation.Line; int endLine = methodDeclaration.Body.EndLocation.Line; }
Conclusion
The latest version of ReportGenerator already uses the NRefactory library to get coverage information for unexecuted methods and constructors.