Skip to content

Commit

Permalink
Initial work on the AsciiDoc reporter (#54)
Browse files Browse the repository at this point in the history
  • Loading branch information
Jan Schäfer committed Jan 11, 2015
1 parent 3668136 commit 5e99283
Show file tree
Hide file tree
Showing 38 changed files with 828 additions and 151 deletions.
23 changes: 23 additions & 0 deletions build.gradle
Original file line number Diff line number Diff line change
Expand Up @@ -3,10 +3,12 @@ apply plugin: 'sonar-runner'
buildscript {
repositories {
mavenCentral()
jcenter()
}

dependencies {
classpath 'org.kt3k.gradle.plugin:coveralls-gradle-plugin:2.0.1'
classpath 'org.asciidoctor:asciidoctor-gradle-plugin:1.5.2'
}
}

Expand Down Expand Up @@ -35,6 +37,7 @@ subprojects {
apply plugin: 'java'
apply plugin: 'maven'
apply plugin: 'signing'
apply plugin: 'org.asciidoctor.convert'

description "${rootProject.description} - Module ${project.name}"
sourceCompatibility = targetCompatibility = 1.6
Expand Down Expand Up @@ -149,6 +152,26 @@ subprojects {
classpath = configurations.testCompile
}

task jgivenAsciiDocReport(type: JavaExec) {
main = 'com.tngtech.jgiven.report.ReportGenerator'
args '--sourceDir=build/reports/jgiven/json',
'--targetDir=build/reports/jgiven/asciidoc',
'--format=asciidoc'

classpath = configurations.testCompile
}

asciidoctor.sourceDir= new File('build/reports/jgiven/asciidoc')
asciidoctor.outputDir= new File('build/reports/jgiven/htmladoc')
asciidoctor.attributes toc: ''

task copyAsciiDoc(type: Copy, dependsOn: jgivenAsciiDocReport) {
from 'src/asciidoc'
into 'build/reports/jgiven/asciidoc'
}

copyAsciiDoc.finalizedBy(asciidoctor)

// -- build and publish artifacts -------------------------------------------------------------------------------------

signing {
Expand Down
Original file line number Diff line number Diff line change
@@ -0,0 +1,22 @@
package com.tngtech.jgiven.report;

import java.io.File;

import com.tngtech.jgiven.report.json.JsonModelTraverser;
import com.tngtech.jgiven.report.json.ReportModelFileHandler;

public abstract class AbstractReportGenerator implements ReportModelFileHandler {

/**
* The directory where the resulting report should be stored in.
*/
protected File targetDirectory;

public void generate( File sourceDir, File targetDirectory ) {
this.targetDirectory = targetDirectory;
new JsonModelTraverser().traverseModels( sourceDir, this );
generationFinished( targetDirectory );
}

public abstract void generationFinished( File targetDirectory );
}
Original file line number Diff line number Diff line change
@@ -0,0 +1,179 @@
package com.tngtech.jgiven.report;

import java.util.List;

import com.google.common.collect.Lists;
import com.tngtech.jgiven.report.model.*;

public class AbstractReportModelHandler {

public void handle( ReportModel reportModel, ReportModelHandler handler ) {
reportModel.accept( new ReportModelHandlerVisitor( handler ) );
}

private static class ReportModelHandlerVisitor extends ReportModelVisitor {

private final ReportModelHandler handler;
private boolean isMultiCase;
private boolean hasDataTable;
private ScenarioModel currentScenarioModel;
private boolean skipCase;

public ReportModelHandlerVisitor( ReportModelHandler handler ) {
this.handler = handler;
}

@Override
public void visit( ReportModel reportModel ) {
handler.className( reportModel.getClassName() );
if( reportModel.getDescription() != null ) {
handler.reportDescription( reportModel.getDescription() );
}
}

@Override
public void visit( ScenarioModel scenarioModel ) {
handler.scenarioTitle( scenarioModel.getDescription() );

this.currentScenarioModel = scenarioModel;
this.isMultiCase = scenarioModel.getScenarioCases().size() > 1;
this.hasDataTable = scenarioModel.isCasesAsTable();
}

@Override
public void visitEnd( ScenarioModel scenarioModel ) {
if( hasDataTable ) {
handler.dataTable( new ScenarioDataTableImpl( scenarioModel ) );
}
handler.scenarioEnd();
}

@Override
public void visit( ScenarioCaseModel scenarioCase ) {
if( scenarioCase.getCaseNr() > 1 && hasDataTable ) {
this.skipCase = true;
return;
}
this.skipCase = false;

if( isMultiCase && !hasDataTable ) {
handler.caseHeader( scenarioCase.getCaseNr(),
currentScenarioModel.getExplicitParameters(), scenarioCase.getExplicitArguments() );
}
}

@Override
public void visit( StepModel stepModel ) {
if( skipCase ) {
return;
}

handler.stepStart();

for( Word word : stepModel.getWords() ) {
if( word.isIntroWord() ) {
handler.introWord( word.getValue() );
} else {
if( word.isArg() ) {
if( word.getArgumentInfo().isParameter() ) {
if( hasDataTable ) {
handler.stepArgumentPlaceHolder( word.getArgumentInfo().getParameterName() );
} else {
handler.stepCaseArgument( word.getFormattedValue() );
}
} else {
if( word.getArgumentInfo().isDataTable() ) {
handler.stepDataTableArgument( word.getArgumentInfo().getDataTable() );
} else {
handler.stepArgument( word.getFormattedValue(), word.isDifferent() );
}
}
} else {
handler.stepWord( word.getFormattedValue(), word.isDifferent() );
}
}
}

handler.stepEnd();
}

private static class ScenarioDataTableImpl implements ScenarioDataTable {
private final ScenarioModel scenarioModel;

private ScenarioDataTableImpl( ScenarioModel scenarioModel ) {
this.scenarioModel = scenarioModel;
}

@Override
public List<String> placeHolders() {
return scenarioModel.getDerivedParameters();
}

@Override
public List<Row> rows() {
List<Row> rows = Lists.newArrayList();
for( ScenarioCaseModel caseModel : scenarioModel.getScenarioCases() ) {
rows.add( new RowImpl( caseModel ) );
}
return rows;
}

private static class RowImpl implements Row {

private final ScenarioCaseModel caseModel;

public RowImpl( ScenarioCaseModel caseModel ) {
this.caseModel = caseModel;
}

@Override
public int nr() {
return caseModel.getCaseNr();
}

@Override
public ExecutionStatus status() {
return caseModel.getExecutionStatus();
}

@Override
public List<String> arguments() {
return caseModel.getDerivedArguments();
}
}
}
}

public interface ScenarioDataTable {
/**
* The place holders of the data table
*/
List<String> placeHolders();

/**
* The rows of the table, not including the header
*/
List<Row> rows();

/**
* Represents one case of a scenario
*/
public interface Row {
/**
* The row number starting from 1
*/
int nr();

/**
* The execution status of the case
*/
ExecutionStatus status();

/**
* The argument values of the case
*
*/
List<String> arguments();
}
}
}
Original file line number Diff line number Diff line change
Expand Up @@ -11,6 +11,7 @@
import com.google.common.io.Files;
import com.tngtech.jgiven.exception.JGivenInstallationException;
import com.tngtech.jgiven.exception.JGivenInternalDefectException;
import com.tngtech.jgiven.report.asciidoc.AsciiDocReportGenerator;
import com.tngtech.jgiven.report.html.StaticHtmlReportGenerator;
import com.tngtech.jgiven.report.impl.FileGenerator;
import com.tngtech.jgiven.report.text.PlainTextReportGenerator;
Expand All @@ -22,6 +23,7 @@ public class ReportGenerator {
public enum Format {
HTML( "html" ),
TEXT( "text" ),
ASCIIDOC( "asciidoc" ),
HTML5( "html5" );

private final String text;
Expand All @@ -40,8 +42,8 @@ public static Format fromStringOrNull( String value ) {
}
}

private File sourceDir = new File( "." );
private File toDir = new File( "." );
private File sourceDirectory = new File( "." );
private File targetDirectory = new File( "." );
private File customCssFile = null;
private Format format = HTML;

Expand All @@ -55,10 +57,16 @@ static void parseArgs( ReportGenerator generator, String... args ) {
for( String arg : args ) {
if( arg.equals( "-h" ) || arg.equals( "--help" ) ) {
printUsageAndExit();
} else if( arg.startsWith( "--dir=" ) ) {
generator.setSourceDir( new File( arg.split( "=" )[1] ) );
} else if( arg.startsWith( "--todir=" ) ) {
generator.setToDir( new File( arg.split( "=" )[1] ) );
} else if( arg.startsWith( "--dir=" ) || arg.startsWith( "--sourceDir=" ) ) {
generator.setSourceDirectory( new File( arg.split( "=" )[1] ) );
if( arg.startsWith( "--dir=" ) ) {
System.err.println( "DEPRECATION WARNING: --dir is deprecated, please use --sourceDir instead" );
}
} else if( arg.startsWith( "--todir=" ) || arg.startsWith( "--targetDir=" ) ) {
generator.setTargetDirectory( new File( arg.split( "=" )[1] ) );
if( arg.startsWith( "--todir=" ) ) {
System.err.println( "DEPRECATION WARNING: --todir is deprecated, please use--targetDir instead" );
}
} else if( arg.startsWith( "--customcss=" ) ) {
generator.setCustomCssFile( new File( arg.split( "=" )[1] ) );
} else if( arg.startsWith( "--format=" ) ) {
Expand All @@ -80,8 +88,8 @@ public void setFormat( Format format ) {
}

public void generate() throws Exception {
if( !getToDir().exists() && !getToDir().mkdirs() ) {
log.error( "Could not create target directory " + getToDir() );
if( !getTargetDirectory().exists() && !getTargetDirectory().mkdirs() ) {
log.error( "Could not create target directory " + getTargetDirectory() );
return;
}

Expand All @@ -90,18 +98,20 @@ public void generate() throws Exception {
} else if( format == HTML5 ) {
generateHtml5Report();
} else if( format == TEXT ) {
new PlainTextReportGenerator().generate( getToDir(), getSourceDir() );
new PlainTextReportGenerator().generate( getSourceDirectory(), getTargetDirectory() );
} else if( format == ASCIIDOC ) {
new AsciiDocReportGenerator().generate( getSourceDirectory(), getTargetDirectory() );
}

}

private void generateStaticHtmlReport() throws IOException {
new StaticHtmlReportGenerator().generate( getToDir(), getSourceDir() );
new StaticHtmlReportGenerator().generate( getTargetDirectory(), getSourceDirectory() );
if( getCustomCssFile() != null ) {
if( !getCustomCssFile().canRead() ) {
log.info( "Cannot read customCssFile " + getCustomCssFile() + " skipping" );
} else {
Files.copy( getCustomCssFile(), new File( getToDir(), "custom.css" ) );
Files.copy( getCustomCssFile(), new File( getTargetDirectory(), "custom.css" ) );
}
}
}
Expand All @@ -118,29 +128,29 @@ private void generateHtml5Report() throws IOException {
throw new JGivenInternalDefectException( "The HTML5 Report Generator could not be instantiated.", e );
}

fileGenerator.generate( getToDir(), getSourceDir() );
fileGenerator.generate( getTargetDirectory(), getSourceDirectory() );
}

private static void printUsageAndExit() {
System.err.println( "Options: [--format=<format>] [--dir=<dir>] [--todir=<dir>] [--customcss=<cssfile>]" ); // NOSONAR
System.err.println( "Options: [--format=<format>] [--sourceDir=<dir>] [--targetDir=<dir>] [--customcss=<cssfile>]" ); // NOSONAR
System.err.println( " <format> = html, html5, or text, default is html" );
System.exit( 1 );
}

public File getSourceDir() {
return sourceDir;
public File getSourceDirectory() {
return sourceDirectory;
}

public void setSourceDir( File sourceDir ) {
this.sourceDir = sourceDir;
public void setSourceDirectory( File sourceDirectory ) {
this.sourceDirectory = sourceDirectory;
}

public File getToDir() {
return toDir;
public File getTargetDirectory() {
return targetDirectory;
}

public void setToDir( File toDir ) {
this.toDir = toDir;
public void setTargetDirectory( File targetDirectory ) {
this.targetDirectory = targetDirectory;
}

public File getCustomCssFile() {
Expand Down
Loading

0 comments on commit 5e99283

Please sign in to comment.