Please wait. This can take some minutes ...
Many resources are needed to download a project. Please understand that we have to compensate our server costs. Thank you in advance.
Project price only 1 $
You can buy this project and download/modify it how often you want.
scoverage.reporter.ScoverageHtmlWriter.scala Maven / Gradle / Ivy
package scoverage.reporter
import java.io.File
import java.util.Date
import scala.xml.Node
import scoverage.domain.CodeGrid
import scoverage.domain.Coverage
import scoverage.domain.MeasuredClass
import scoverage.domain.MeasuredFile
import scoverage.domain.MeasuredPackage
/** @author Stephen Samuel */
class ScoverageHtmlWriter(
sourceDirectories: Seq[File],
outputDir: File,
sourceEncoding: Option[String]
) extends BaseReportWriter(sourceDirectories, outputDir, sourceEncoding) {
// to be used by gradle-scoverage plugin
def this(
sourceDirectories: Array[File],
outputDir: File,
sourceEncoding: Option[String]
) = {
this(sourceDirectories.toSeq, outputDir, sourceEncoding)
}
// for backward compatibility only
def this(sourceDirectories: Seq[File], outputDir: File) = {
this(sourceDirectories, outputDir, None);
}
// for backward compatibility only
def this(sourceDirectory: File, outputDir: File) = {
this(Seq(sourceDirectory), outputDir)
}
def write(coverage: Coverage): Unit = {
val indexFile = new File(outputDir.getAbsolutePath + "/index.html")
val cssFile = new File(outputDir.getAbsolutePath + "/pure-min.css")
val packageFile = new File(outputDir.getAbsolutePath + "/packages.html")
val overviewFile = new File(outputDir.getAbsolutePath + "/overview.html")
val index = {
val in = getClass.getResourceAsStream("/scoverage/index.html")
try IOUtils.readStreamAsString(in)
finally in.close()
}
val css = {
val in = getClass.getResourceAsStream("/scoverage/pure-min.css")
try IOUtils.readStreamAsString(in)
finally in.close()
}
IOUtils.writeToFile(indexFile, index, sourceEncoding)
IOUtils.writeToFile(cssFile, css, sourceEncoding)
IOUtils.writeToFile(
packageFile,
packageList(coverage).toString(),
sourceEncoding
)
IOUtils.writeToFile(
overviewFile,
overview(coverage).toString(),
sourceEncoding
)
coverage.packages.foreach(writePackage)
}
private def writePackage(pkg: MeasuredPackage): Unit = {
// package overview files are written out using a filename that respects the package name
// that means package com.example declared in a class at src/main/scala/mystuff/MyClass.scala will be written
// to com.example.html
val file = new File(outputDir, packageOverviewRelativePath(pkg))
file.getParentFile.mkdirs()
IOUtils.writeToFile(file, packageOverview(pkg).toString(), sourceEncoding)
pkg.files.foreach(writeFile)
}
private def writeFile(mfile: MeasuredFile): Unit = {
// each highlighted file is written out using the same structure as the original file.
val file = new File(outputDir, relativeSource(mfile.source) + ".html")
file.getParentFile.mkdirs()
IOUtils.writeToFile(file, filePage(mfile).toString(), sourceEncoding)
}
private def packageOverviewRelativePath(pkg: MeasuredPackage) =
pkg.name.replace("", "(empty)") + ".html"
private def filePage(mfile: MeasuredFile): Node = {
val filename = relativeSource(mfile.source) + ".html"
val css =
"table.codegrid { font-family: monospace; font-size: 12px; width: auto!important; }" +
"table.statementlist { width: auto!important; font-size: 13px; } " +
"table.codegrid td { padding: 0!important; border: 0!important } " +
"table td.linenumber { width: 40px!important; } "
{filename}
{plugins}
{xml.Unparsed(new CodeGrid(mfile, sourceEncoding).highlighted)}
{new StatementWriter(mfile).output}
}
def header = {
val css = """.meter {
| height: 14px;
| position: relative;
| background: #BB2020;
|}
|
|.meter span {
| display: block;
| height: 100%;
| background-color: rgb(43,194,83);
| background-image: -webkit-gradient(
| linear,
| left bottom,
| left top,
| color-stop(0, rgb(43,194,83)),
| color-stop(1, rgb(84,240,84))
| );
| background-image: -webkit-linear-gradient(
| center bottom,
| rgb(43,194,83) 37%,
| rgb(84,240,84) 69%
| );
| background-image: -moz-linear-gradient(
| center bottom,
| rgb(43,194,83) 37%,
| rgb(84,240,84) 69%
| );
| background-image: -ms-linear-gradient(
| center bottom,
| rgb(43,194,83) 37%,
| rgb(84,240,84) 69%
| );
| background-image: -o-linear-gradient(
| center bottom,
| rgb(43,194,83) 37%,
| rgb(84,240,84) 69%
| );
| -webkit-box-shadow:
| inset 0 2px 9px rgba(255,255,255,0.3),
| inset 0 -2px 6px rgba(0,0,0,0.4);
| -moz-box-shadow:
| inset 0 2px 9px rgba(255,255,255,0.3),
| inset 0 -2px 6px rgba(0,0,0,0.4);
| position: relative;
| overflow: hidden;
|}""".stripMargin
Scoverage Code Coverage
{plugins}
}
def packageOverview(pack: MeasuredPackage): Node = {
{header}
{classesTable(pack.classes, addPath = false)}
}
def classesTable(classes: Iterable[MeasuredClass], addPath: Boolean): Node = {
Class
Source file
Lines
Methods
Statements
Invoked
Coverage
Branches
Invoked
Coverage
{classes.toSeq.sortBy(_.fullClassName) map classRow}
}
def classRow(klass: MeasuredClass): Node = {
val filename: String = {
val fileRelativeToSource = new File(
relativeSource(klass.source) + ".html"
)
val path = fileRelativeToSource.getParent
val value = fileRelativeToSource.getName
if (path.ne("")) {
// (Normalise the pathSeparator to "/" in case we are running on Windows)
fileRelativeToSource.toString.replace(File.separator, "/")
} else {
value
}
}
val statement0f = Math.round(klass.statementCoveragePercent).toInt.toString
val branch0f = Math.round(klass.branchCoveragePercent).toInt.toString
{klass.displayClassName}
{
klass.statements.headOption
.map(_.source.split(File.separatorChar).last)
.getOrElse("")
}
{klass.loc.toString}
{klass.methodCount.toString}
{klass.statementCount.toString}
{klass.invokedStatementCount.toString}
{klass.statementCoverageFormatted}
%
{klass.branchCount.toString}
{klass.invokedBranchesCount.toString}
{klass.branchCoverageFormatted}
%
}
def packageList(coverage: Coverage): Node = {
Scoverage Code Coverage
{plugins}
All packages
{coverage.statementCoverageFormatted}%
{
coverage.packages.map(arg =>
{
arg.name
}
{arg.statementCoverageFormatted}%
)
}
}
def risks(coverage: Coverage, limit: Int) = {
Class
Lines
Methods
Statements
Statement Rate
Branches
Branch Rate
{
coverage
.risks(limit)
.map(klass =>
{klass.displayClassName}
{klass.loc.toString}
{klass.methodCount.toString}
{klass.statementCount.toString}
{klass.statementCoverageFormatted}
%
{klass.branchCount.toString}
{klass.branchCoverageFormatted}
%
)
}
}
def packages2(coverage: Coverage) = {
val rows = coverage.packages.map(arg => {
{arg.name}
{arg.invokedClasses.toString}
/
{arg.classCount}
(
{arg.classCoverage.toString}
%)
{arg.invokedStatements.toString()}
/
{arg.statementCount}
(
{arg.statementCoverageFormatted}
%)
})
}
def overview(coverage: Coverage): Node = {
{header}
SCoverage
generated at
{new Date().toString}
{stats(coverage)}
{classesTable(coverage.classes, addPath = true)}
}
def stats(coverage: Coverage): Node = {
val statement0f =
Math.round(coverage.statementCoveragePercent).toInt.toString
val branch0f = Math.round(coverage.branchCoveragePercent).toInt.toString
Lines of code:
{coverage.loc.toString}
Files:
{coverage.fileCount.toString}
Classes:
{coverage.classCount.toString}
Methods:
{coverage.methodCount.toString}
Lines per file:
{coverage.linesPerFileFormatted}
Packages:
{coverage.packageCount.toString}
Classes per package:
{coverage.avgClassesPerPackageFormatted}
Methods per class:
{coverage.avgMethodsPerClassFormatted}
Total statements:
{coverage.statementCount.toString}
Invoked statements:
{coverage.invokedStatementCount.toString}
Total branches:
{coverage.branchCount.toString}
Invoked branches:
{coverage.invokedBranchesCount.toString}
Ignored statements:
{coverage.ignoredStatementCount.toString}
Statement coverage:
{coverage.statementCoverageFormatted}
%
Branch coverage:
{coverage.branchCoverageFormatted}
%
}
def plugins = {
}
}