Coverage Report - org.jbehave.core.embedder.Embedder
 
Classes in this File Line Coverage Branch Coverage Complexity
Embedder
89%
222/249
78%
74/94
1.983
Embedder$AnnotatedEmbedderRunFailed
100%
2/2
N/A
1.983
Embedder$EmbedderFailureStrategy
N/A
N/A
1.983
Embedder$RunningEmbeddablesFailed
100%
4/4
N/A
1.983
Embedder$RunningStoriesFailed
100%
4/4
N/A
1.983
Embedder$ThrowingRunningStoriesFailed
100%
3/3
N/A
1.983
Embedder$ViewGenerationFailed
50%
2/4
N/A
1.983
 
 1  
 package org.jbehave.core.embedder;
 2  
 
 3  
 import java.io.File;
 4  
 import java.util.ArrayList;
 5  
 import java.util.List;
 6  
 import java.util.Properties;
 7  
 import java.util.concurrent.ExecutorService;
 8  
 import java.util.concurrent.ThreadPoolExecutor;
 9  
 
 10  
 import org.apache.commons.lang.StringUtils;
 11  
 import org.apache.commons.lang.builder.ToStringBuilder;
 12  
 import org.apache.commons.lang.builder.ToStringStyle;
 13  
 import org.jbehave.core.ConfigurableEmbedder;
 14  
 import org.jbehave.core.Embeddable;
 15  
 import org.jbehave.core.configuration.Configuration;
 16  
 import org.jbehave.core.configuration.MostUsefulConfiguration;
 17  
 import org.jbehave.core.embedder.executors.FixedThreadExecutors;
 18  
 import org.jbehave.core.failures.BatchFailures;
 19  
 import org.jbehave.core.failures.FailingUponPendingStep;
 20  
 import org.jbehave.core.junit.AnnotatedEmbedderRunner;
 21  
 import org.jbehave.core.junit.AnnotatedEmbedderUtils;
 22  
 import org.jbehave.core.model.Story;
 23  
 import org.jbehave.core.model.StoryMaps;
 24  
 import org.jbehave.core.reporters.ReportsCount;
 25  
 import org.jbehave.core.reporters.StepdocReporter;
 26  
 import org.jbehave.core.reporters.StoryReporterBuilder;
 27  
 import org.jbehave.core.reporters.ViewGenerator;
 28  
 import org.jbehave.core.steps.CandidateSteps;
 29  
 import org.jbehave.core.steps.InjectableStepsFactory;
 30  
 import org.jbehave.core.steps.ProvidedStepsFactory;
 31  
 import org.jbehave.core.steps.StepFinder;
 32  
 import org.jbehave.core.steps.Stepdoc;
 33  
 
 34  
 /**
 35  
  * The Embedder is a facade allowing all functionality to be embedded into other
 36  
  * run contexts, such as IDEs (e.g. via JUnit support) or CLIs (via Ant or
 37  
  * Maven).
 38  
  */
 39  
 public class Embedder {
 40  
 
 41  
     private StoryMapper storyMapper;
 42  
     private StoryRunner storyRunner;
 43  
     private EmbedderMonitor embedderMonitor;
 44  
     private EmbedderClassLoader classLoader;
 45  
     private EmbedderControls embedderControls;
 46  
     private EmbedderFailureStrategy embedderFailureStrategy;
 47  
     private Configuration configuration;
 48  
     private List<CandidateSteps> candidateSteps;
 49  
     private InjectableStepsFactory stepsFactory;
 50  
     private List<String> metaFilters;
 51  
     private Properties systemProperties;
 52  
     private ExecutorService executorService;
 53  
     private boolean executorServiceCreated;
 54  
     private StoryManager storyManager;
 55  
 
 56  
     public Embedder() {
 57  45
         this(new StoryMapper(), new StoryRunner(), new PrintStreamEmbedderMonitor());
 58  45
     }
 59  
 
 60  78
     public Embedder(StoryMapper storyMapper, StoryRunner storyRunner, EmbedderMonitor embedderMonitor) {
 61  78
         this.storyMapper = storyMapper;
 62  78
         this.storyRunner = storyRunner;
 63  78
         this.embedderMonitor = embedderMonitor;
 64  78
     }
 65  
 
 66  
     public void mapStoriesAsPaths(List<String> storyPaths) {
 67  1
         EmbedderControls embedderControls = embedderControls();
 68  1
         embedderMonitor.usingControls(embedderControls);
 69  
 
 70  1
         if (embedderControls.skip()) {
 71  0
             embedderMonitor.storiesSkipped(storyPaths);
 72  0
             return;
 73  
         }
 74  
 
 75  1
         processSystemProperties();
 76  
 
 77  1
         StoryManager storyManager = storyManager();
 78  1
         for (String storyPath : storyPaths) {
 79  2
             Story story = storyManager.storyOfPath(storyPath);
 80  2
             embedderMonitor.mappingStory(storyPath, metaFilters());
 81  2
             storyMapper.map(story, new MetaFilter(""));
 82  2
             for (String filter : metaFilters) {
 83  0
                 storyMapper.map(story, new MetaFilter(filter));
 84  0
             }
 85  2
         }
 86  
 
 87  1
         generateMapsView(storyMapper.getStoryMaps());
 88  
 
 89  1
     }
 90  
 
 91  
     private void generateMapsView(StoryMaps storyMaps) {
 92  1
         Configuration configuration = configuration();
 93  1
         StoryReporterBuilder builder = configuration.storyReporterBuilder();
 94  1
         File outputDirectory = builder.outputDirectory();
 95  1
         Properties viewResources = builder.viewResources();
 96  1
         ViewGenerator viewGenerator = configuration.viewGenerator();
 97  
         try {
 98  1
             embedderMonitor.generatingMapsView(outputDirectory, storyMaps, viewResources);
 99  1
             viewGenerator.generateMapsView(outputDirectory, storyMaps, viewResources);
 100  0
         } catch (RuntimeException e) {
 101  0
             embedderMonitor.mapsViewGenerationFailed(outputDirectory, storyMaps, viewResources, e);
 102  0
             throw new ViewGenerationFailed(outputDirectory, storyMaps, viewResources, e);
 103  1
         }
 104  1
     }
 105  
 
 106  
     public void runAsEmbeddables(List<String> classNames) {
 107  13
         EmbedderControls embedderControls = embedderControls();
 108  13
         embedderMonitor.usingControls(embedderControls);
 109  
 
 110  13
         if (embedderControls.skip()) {
 111  1
             embedderMonitor.embeddablesSkipped(classNames);
 112  1
             return;
 113  
         }
 114  
 
 115  12
         BatchFailures failures = new BatchFailures(embedderControls.verboseFailures());
 116  12
         for (Embeddable embeddable : embeddables(classNames, classLoader())) {
 117  18
             String name = embeddable.getClass().getName();
 118  
             try {
 119  18
                 embedderMonitor.runningEmbeddable(name);
 120  18
                 embeddable.useEmbedder(this);
 121  18
                 embeddable.run();
 122  7
             } catch (Throwable e) {
 123  7
                 if (embedderControls.batch()) {
 124  
                     // collect and postpone decision to throw exception
 125  2
                     failures.put(name, e);
 126  
                 } else {
 127  5
                     if (ignoreFailure(embedderControls)) {
 128  1
                         embedderMonitor.embeddableFailed(name, e);
 129  
                     } else {
 130  4
                         throw new RunningEmbeddablesFailed(name, e);
 131  
                     }
 132  
                 }
 133  11
             }
 134  14
         }
 135  
 
 136  8
         if (embedderControls.batch() && failures.size() > 0) {
 137  2
             if (ignoreFailure(embedderControls)) {
 138  1
                 embedderMonitor.batchFailed(failures);
 139  
             } else {
 140  1
                 throw new RunningEmbeddablesFailed(failures);
 141  
             }
 142  
         }
 143  
 
 144  7
     }
 145  
 
 146  
     private boolean ignoreFailure(EmbedderControls embedderControls) {
 147  7
         boolean ignore = embedderControls.ignoreFailureInStories();
 148  7
         if (embedderControls.generateViewAfterStories()) {
 149  7
             ignore = ignore && embedderControls.ignoreFailureInView();
 150  
         }
 151  7
         return ignore;
 152  
     }
 153  
 
 154  
     private List<Embeddable> embeddables(List<String> classNames, EmbedderClassLoader classLoader) {
 155  12
         List<Embeddable> embeddables = new ArrayList<Embeddable>();
 156  12
         for (String className : classNames) {
 157  20
             if (!classLoader.isAbstract(className)) {
 158  19
                 embeddables.add(classLoader.newInstance(Embeddable.class, className));
 159  
             }
 160  20
         }
 161  12
         return embeddables;
 162  
     }
 163  
 
 164  
     public void runStoriesWithAnnotatedEmbedderRunner(List<String> classNames) {
 165  4
         EmbedderClassLoader classLoader = classLoader();
 166  4
         for (String className : classNames) {
 167  4
             embedderMonitor.runningWithAnnotatedEmbedderRunner(className);
 168  4
             AnnotatedEmbedderRunner runner = AnnotatedEmbedderUtils.annotatedEmbedderRunner(className, classLoader);
 169  
             try {
 170  3
                 Object annotatedInstance = runner.createTest();
 171  3
                 if (annotatedInstance instanceof Embeddable) {
 172  2
                     ((Embeddable) annotatedInstance).run();
 173  
                 } else {
 174  1
                     embedderMonitor.annotatedInstanceNotOfType(annotatedInstance, Embeddable.class);
 175  
                 }
 176  1
             } catch (Throwable e) {
 177  1
                 throw new AnnotatedEmbedderRunFailed(runner, e);
 178  2
             }
 179  2
         }
 180  2
     }
 181  
 
 182  
     public void runStoriesAsPaths(List<String> storyPaths) {
 183  
 
 184  14
         processSystemProperties();
 185  
 
 186  14
         EmbedderControls embedderControls = embedderControls();
 187  
 
 188  14
         embedderMonitor.usingControls(embedderControls);
 189  
 
 190  14
         if (embedderControls.skip()) {
 191  1
             embedderMonitor.storiesSkipped(storyPaths);
 192  1
             return;
 193  
         }
 194  
 
 195  
         try {
 196  
 
 197  
             // set up run context
 198  13
             StoryManager storyManager = createStoryManager();
 199  13
             MetaFilter filter = metaFilter();
 200  13
             BatchFailures failures = new BatchFailures(embedderControls.verboseFailures());
 201  
 
 202  
             // run stories
 203  13
             storyManager.runStories(storyPaths, filter, failures);
 204  
 
 205  
             // handle any failures
 206  12
             handleFailures(failures);
 207  
 
 208  
         } finally {
 209  
             // generate reports view regardless of failures in running stories
 210  
             // (if configured to do so)
 211  7
             try {
 212  13
                 if (embedderControls.generateViewAfterStories()) {
 213  12
                     generateReportsView();
 214  
                 }
 215  
             } finally {
 216  
                 // shutdown regardless of failures in reports view
 217  13
                 shutdownExecutorService();
 218  13
             }
 219  
 
 220  6
         }
 221  6
     }
 222  
 
 223  
     private void handleFailures(BatchFailures failures) {
 224  12
         if (failures.size() > 0) {
 225  6
             if (embedderControls().ignoreFailureInStories()) {
 226  0
                 embedderMonitor.batchFailed(failures);
 227  
             } else {
 228  6
                 embedderFailureStrategy().handleFailures(failures);
 229  
             }
 230  
         }
 231  6
     }
 232  
 
 233  
     public void generateReportsView() {
 234  12
         StoryReporterBuilder builder = configuration().storyReporterBuilder();
 235  12
         File outputDirectory = builder.outputDirectory();
 236  12
         List<String> formatNames = builder.formatNames(true);
 237  12
         generateReportsView(outputDirectory, formatNames, builder.viewResources());
 238  12
     }
 239  
 
 240  
     public void generateReportsView(File outputDirectory, List<String> formats, Properties viewResources) {
 241  
 
 242  21
         if (embedderControls().skip()) {
 243  1
             embedderMonitor.reportsViewNotGenerated();
 244  1
             return;
 245  
         }
 246  20
         ViewGenerator viewGenerator = configuration().viewGenerator();
 247  
         try {
 248  20
             embedderMonitor.generatingReportsView(outputDirectory, formats, viewResources);
 249  20
             viewGenerator.generateReportsView(outputDirectory, formats, viewResources);
 250  1
         } catch (RuntimeException e) {
 251  1
             embedderMonitor.reportsViewGenerationFailed(outputDirectory, formats, viewResources, e);
 252  1
             throw new ViewGenerationFailed(outputDirectory, formats, viewResources, e);
 253  19
         }
 254  19
         ReportsCount count = viewGenerator.getReportsCount();
 255  19
         embedderMonitor.reportsViewGenerated(count);
 256  19
         handleFailures(count);
 257  
 
 258  15
     }
 259  
 
 260  
     private void handleFailures(ReportsCount count) {
 261  19
         boolean failed = count.failed();
 262  19
         if (configuration().pendingStepStrategy() instanceof FailingUponPendingStep) {
 263  1
             failed = failed || count.pending();
 264  
         }
 265  19
         if (failed) {
 266  6
             if (embedderControls().ignoreFailureInView()) {
 267  1
                 embedderMonitor.reportsViewFailures(count);
 268  
             } else {
 269  5
                 embedderFailureStrategy().handleFailures(count);
 270  
             }
 271  
         }
 272  15
     }
 273  
 
 274  
     public void generateCrossReference() {
 275  4
         StoryReporterBuilder builder = configuration().storyReporterBuilder();
 276  4
         if (builder.hasCrossReference()) {
 277  1
             builder.crossReference().outputToFiles(builder);
 278  
         }
 279  4
     }
 280  
 
 281  
     public void reportStepdocs() {
 282  1
         reportStepdocs(configuration(), candidateSteps());
 283  1
     }
 284  
 
 285  
     public void reportStepdocsAsEmbeddables(List<String> classNames) {
 286  0
         EmbedderControls embedderControls = embedderControls();
 287  0
         if (embedderControls.skip()) {
 288  0
             embedderMonitor.embeddablesSkipped(classNames);
 289  0
             return;
 290  
         }
 291  
 
 292  0
         for (Embeddable embeddable : embeddables(classNames, classLoader())) {
 293  0
             if (embeddable instanceof ConfigurableEmbedder) {
 294  0
                 ConfigurableEmbedder configurableEmbedder = (ConfigurableEmbedder) embeddable;
 295  0
                                 Embedder configuredEmbedder = configurableEmbedder.configuredEmbedder();
 296  0
                                 List<CandidateSteps> steps = configuredEmbedder.candidateSteps();
 297  0
                 if (steps.isEmpty()) {
 298  0
                     steps = configuredEmbedder.stepsFactory().createCandidateSteps();
 299  
                 }
 300  0
                 reportStepdocs(configuredEmbedder.configuration(), steps);
 301  0
             } else {
 302  0
                 embedderMonitor.embeddableNotConfigurable(embeddable.getClass().getName());
 303  
             }
 304  0
         }
 305  0
     }
 306  
 
 307  
     public void reportStepdocs(Configuration configuration, List<CandidateSteps> candidateSteps) {
 308  1
         StepFinder finder = configuration.stepFinder();
 309  1
         StepdocReporter reporter = configuration.stepdocReporter();
 310  1
         List<Object> stepsInstances = finder.stepsInstances(candidateSteps);
 311  1
         reporter.stepdocs(finder.stepdocs(candidateSteps), stepsInstances);
 312  1
     }
 313  
 
 314  
     public void reportMatchingStepdocs(String stepAsString) {
 315  3
         Configuration configuration = configuration();
 316  3
         List<CandidateSteps> candidateSteps = candidateSteps();
 317  3
         StepFinder finder = configuration.stepFinder();
 318  3
         StepdocReporter reporter = configuration.stepdocReporter();
 319  3
         List<Stepdoc> matching = finder.findMatching(stepAsString, candidateSteps);
 320  3
         List<Object> stepsInstances = finder.stepsInstances(candidateSteps);
 321  3
         reporter.stepdocsMatching(stepAsString, matching, stepsInstances);
 322  3
     }
 323  
 
 324  
     public void processSystemProperties() {
 325  17
         Properties properties = systemProperties();
 326  17
         embedderMonitor.processingSystemProperties(properties);
 327  17
         if (!properties.isEmpty()) {
 328  1
             for (Object key : properties.keySet()) {
 329  2
                 String name = (String) key;
 330  2
                 String value = properties.getProperty(name);
 331  2
                 System.setProperty(name, value);
 332  2
                 embedderMonitor.systemPropertySet(name, value);
 333  2
             }
 334  
         }
 335  17
     }
 336  
 
 337  
     public EmbedderClassLoader classLoader() {
 338  16
         if (classLoader == null) {
 339  3
             this.classLoader = new EmbedderClassLoader(this.getClass().getClassLoader());
 340  
         }
 341  16
         return classLoader;
 342  
     }
 343  
 
 344  
     public Configuration configuration() {
 345  115
         if (configuration == null) {
 346  26
             this.configuration = new MostUsefulConfiguration();
 347  
         }
 348  115
         configureThreads(configuration, embedderControls().threads());
 349  115
         return configuration;
 350  
     }
 351  
 
 352  
     public List<CandidateSteps> candidateSteps() {
 353  27
         if (candidateSteps == null) {
 354  13
             candidateSteps = new ArrayList<CandidateSteps>();
 355  
         }
 356  27
         return candidateSteps;
 357  
     }
 358  
 
 359  
     public InjectableStepsFactory stepsFactory() {
 360  25
         if (stepsFactory == null) {
 361  12
             stepsFactory = new ProvidedStepsFactory(candidateSteps());
 362  
         }
 363  25
         return stepsFactory;
 364  
     }
 365  
 
 366  
     public EmbedderControls embedderControls() {
 367  220
         if (embedderControls == null) {
 368  20
             embedderControls = new EmbedderControls();
 369  
         }
 370  220
         return embedderControls;
 371  
     }
 372  
 
 373  
     public EmbedderMonitor embedderMonitor() {
 374  16
         return embedderMonitor;
 375  
     }
 376  
 
 377  
     public EmbedderFailureStrategy embedderFailureStrategy() {
 378  11
         if (embedderFailureStrategy == null) {
 379  10
             this.embedderFailureStrategy = new ThrowingRunningStoriesFailed();
 380  
         }
 381  11
         return embedderFailureStrategy;
 382  
     }
 383  
 
 384  
     public boolean hasExecutorService() {
 385  1
         return executorService != null;
 386  
     }
 387  
 
 388  
     public ExecutorService executorService() {
 389  14
         if (executorService == null) {
 390  14
             executorService = createExecutorService();
 391  14
             executorServiceCreated = true;
 392  
         }
 393  14
         return executorService;
 394  
     }
 395  
 
 396  
     /**
 397  
      * Creates a {@link ThreadPoolExecutor} using the number of threads defined
 398  
      * in the {@link EmbedderControls#threads()}
 399  
      * 
 400  
      * @return An ExecutorService
 401  
      */
 402  
     private ExecutorService createExecutorService() {
 403  14
         return new FixedThreadExecutors().create(embedderControls());
 404  
     }
 405  
 
 406  
     /**
 407  
      * Shuts down executor service, if it was created by Embedder.
 408  
      * ExecutorServices provided by the
 409  
      * {@link #useExecutorService(ExecutorService)} need to be managed by the
 410  
      * provider.
 411  
      */
 412  
     protected void shutdownExecutorService() {
 413  13
         if (executorServiceCreated) {
 414  13
             executorService.shutdownNow();
 415  13
             executorService = null;
 416  13
             executorServiceCreated = false;
 417  
         }
 418  13
     }
 419  
 
 420  
     public StoryManager storyManager() {
 421  1
         if (storyManager == null) {
 422  1
             storyManager = createStoryManager();
 423  
         }
 424  1
         return storyManager;
 425  
     }
 426  
 
 427  
     private StoryManager createStoryManager() {
 428  14
         return new StoryManager(configuration(), embedderControls(), embedderMonitor(), executorService(),
 429  
                 stepsFactory(), storyRunner());
 430  
     }
 431  
 
 432  
     private void configureThreads(Configuration configuration, int threads) {
 433  115
         StoryReporterBuilder reporterBuilder = configuration.storyReporterBuilder();
 434  115
         reporterBuilder.withMultiThreading(threads > 1);
 435  115
         configuration.useStoryReporterBuilder(reporterBuilder);
 436  115
     }
 437  
 
 438  
     public List<String> metaFilters() {
 439  19
         if (metaFilters == null) {
 440  14
             metaFilters = new ArrayList<String>();
 441  
         }
 442  19
         return metaFilters;
 443  
     }
 444  
 
 445  
     public MetaFilter metaFilter() {
 446  13
         return new MetaFilter(StringUtils.join(metaFilters(), " "), embedderMonitor);
 447  
     }
 448  
 
 449  
     public StoryRunner storyRunner() {
 450  16
         return storyRunner;
 451  
     }
 452  
 
 453  
     public Properties systemProperties() {
 454  20
         if (systemProperties == null) {
 455  16
             systemProperties = new Properties();
 456  
         }
 457  20
         return systemProperties;
 458  
     }
 459  
 
 460  
     public void useClassLoader(EmbedderClassLoader classLoader) {
 461  14
         this.classLoader = classLoader;
 462  14
     }
 463  
 
 464  
     public void useConfiguration(Configuration configuration) {
 465  21
         this.configuration = configuration;
 466  21
     }
 467  
 
 468  
     public void useCandidateSteps(List<CandidateSteps> candidateSteps) {
 469  14
         this.candidateSteps = candidateSteps;
 470  14
     }
 471  
 
 472  
     public void useStepsFactory(InjectableStepsFactory stepsFactory) {
 473  14
                 this.stepsFactory = stepsFactory;
 474  14
     }
 475  
 
 476  
     public void useEmbedderControls(EmbedderControls embedderControls) {
 477  33
         this.embedderControls = embedderControls;
 478  33
     }
 479  
 
 480  
     public void useEmbedderFailureStrategy(EmbedderFailureStrategy failureStategy) {
 481  1
         this.embedderFailureStrategy = failureStategy;
 482  1
     }
 483  
 
 484  
     public void useEmbedderMonitor(EmbedderMonitor embedderMonitor) {
 485  1
         this.embedderMonitor = embedderMonitor;
 486  1
     }
 487  
 
 488  
     public void useExecutorService(ExecutorService executorService) {
 489  0
         this.executorService = executorService;
 490  0
         embedderMonitor.usingExecutorService(executorService);
 491  0
     }
 492  
 
 493  
     public void useMetaFilters(List<String> metaFilters) {
 494  4
         this.metaFilters = metaFilters;
 495  4
     }
 496  
 
 497  
     public void useStoryRunner(StoryRunner storyRunner) {
 498  1
         this.storyRunner = storyRunner;
 499  1
     }
 500  
 
 501  
     public void useSystemProperties(Properties systemProperties) {
 502  2
         this.systemProperties = systemProperties;
 503  2
     }
 504  
 
 505  
     @Override
 506  
     public String toString() {
 507  1
         return ToStringBuilder.reflectionToString(this, ToStringStyle.SHORT_PREFIX_STYLE);
 508  
     }
 509  
 
 510  
     public static interface EmbedderFailureStrategy {
 511  
 
 512  
         void handleFailures(BatchFailures failures);
 513  
 
 514  
         void handleFailures(ReportsCount count);
 515  
 
 516  
     }
 517  
 
 518  10
     public static class ThrowingRunningStoriesFailed implements EmbedderFailureStrategy {
 519  
 
 520  
         public void handleFailures(BatchFailures failures) {
 521  6
             throw new RunningStoriesFailed(failures);
 522  
         }
 523  
 
 524  
         public void handleFailures(ReportsCount count) {
 525  4
             throw new RunningStoriesFailed(count);
 526  
         }
 527  
 
 528  
     }
 529  
 
 530  
     @SuppressWarnings("serial")
 531  
     public static class AnnotatedEmbedderRunFailed extends RuntimeException {
 532  
 
 533  
         public AnnotatedEmbedderRunFailed(AnnotatedEmbedderRunner runner, Throwable cause) {
 534  1
             super("Annotated embedder run failed with runner " + runner.toString(), cause);
 535  1
         }
 536  
 
 537  
     }
 538  
 
 539  
     @SuppressWarnings("serial")
 540  
     public static class RunningEmbeddablesFailed extends RuntimeException {
 541  
 
 542  
         public RunningEmbeddablesFailed(String name, Throwable failure) {
 543  4
             super("Failure in running embeddable: " + name, failure);
 544  4
         }
 545  
 
 546  
         public RunningEmbeddablesFailed(BatchFailures failures) {
 547  1
             super("Failures in running embeddables: " + failures);
 548  1
         }
 549  
 
 550  
     }
 551  
 
 552  
     @SuppressWarnings("serial")
 553  
     public static class RunningStoriesFailed extends RuntimeException {
 554  
 
 555  
         public RunningStoriesFailed(ReportsCount reportsCount) {
 556  4
             super("Failures in running stories: " + reportsCount);
 557  4
         }
 558  
 
 559  
         public RunningStoriesFailed(BatchFailures failures) {
 560  6
             super("Failures in running stories: " + failures);
 561  6
         }
 562  
 
 563  
     }
 564  
 
 565  
     @SuppressWarnings("serial")
 566  
     public static class ViewGenerationFailed extends RuntimeException {
 567  
         public ViewGenerationFailed(File outputDirectory, List<String> formats, Properties viewResources,
 568  
                 RuntimeException cause) {
 569  1
             super("View generation failed to " + outputDirectory + " for formats " + formats + " and resources "
 570  
                     + viewResources, cause);
 571  1
         }
 572  
 
 573  
         public ViewGenerationFailed(File outputDirectory, StoryMaps storyMaps, Properties viewResources,
 574  
                 RuntimeException cause) {
 575  0
             super("View generation failed to " + outputDirectory + " for story maps " + storyMaps + " for resources "
 576  
                     + viewResources, cause);
 577  0
         }
 578  
     }
 579  
 
 580  
 }