// Path: core/src/main/java/me/gregorias/dfuntest/util/FileUtils.java
// public interface FileUtils {
//   /**
//    * {@link org.apache.commons.io.FileUtils#copyDirectoryToDirectory(java.io.File, java.io.File)}
//    *
//    * @param from Source path
//    * @param to Target directory path
//    */
//   void copyDirectoryToDirectory(File from, File to) throws IOException;
// 
//   /**
//    * {@link org.apache.commons.io.FileUtils#copyFileToDirectory(java.io.File, java.io.File)}
//    *
//    * @param from Source path
//    * @param to Target directory path
//    */
//   void copyFileToDirectory(File from, File to) throws IOException;
// 
//   /**
//    * {@link java.nio.file.Files#createDirectories(java.nio.file.Path,
//    *   java.nio.file.attribute.FileAttribute[])}
//    *
//    * @param path Path to create
//    */
//   void createDirectories(Path path) throws IOException;
// 
//   /**
//    * {@link java.nio.file.Files#createTempDirectory(
//    * String, java.nio.file.attribute.FileAttribute[])}
//    *
//    * @param dirPrefix prefix of temporary directory
//    * @return Path to created directory
//    */
//   Path createTempDirectory(String dirPrefix) throws IOException;
// 
//   /**
//    * {@link org.apache.commons.io.FileUtils#deleteQuietly(java.io.File)}
//    *
//    * @param file File to delete
//    * @return true iff directory was deleted
//    */
//   boolean deleteQuietly(File file);
// 
//   /**
//    * {@link java.nio.file.Files#exists(java.nio.file.Path, java.nio.file.LinkOption...)}
//    *
//    * @param path path to check
//    * @return true iff exists
//    */
//   boolean exists(Path path);
// 
//   /**
//    * {@link java.nio.file.Files#isDirectory(java.nio.file.Path, java.nio.file.LinkOption...)}
//    *
//    * @param path path to check
//    * @return true iff path is a directory
//    */
//   boolean isDirectory(Path path);
// 
//   /**
//    * {@link java.lang.ProcessBuilder}
//    *
//    * @param command command to run
//    * @param pwdFile working directory of the process
//    * @return process running the command
//    */
//   Process runCommand(List<String> command, File pwdFile) throws IOException;
// 
//   /**
//    * {@link java.nio.file.Files#write(java.nio.file.Path, Iterable, java.nio.charset.Charset,
//    * java.nio.file.OpenOption...)}
//    *
//    * @param path Path of file to write to.
//    * @param content String to be written to file.
//    */
//   void write(Path path, String content) throws IOException;
// }


import com.google.inject.Inject;
import me.gregorias.dfuntest.util.FileUtils;
import org.apache.commons.lang.StringUtils;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
import javax.inject.Named;
import java.io.IOException;
import java.nio.file.Path;
import java.util.ArrayList;
import java.util.Collection;
import java.util.Set;
package me.gregorias.dfuntest;



/**
 * <p>
 * Basic implementation of TestRunner which runs sequentially multiple test script on given
 * environments and apps.
 * </p>
 *
 * <p>
 * It prepares the environment for the first time iff shouldPrepareEnvironments flag is set.
 * Otherwise it always restores them.
 *
 * If both shouldPrepareEnvironments and shouldCleanEnvironments are set then environments are
 * prepared and cleaned before and after every test. If shouldCleanEnvironments is set to false then
 * only cleanOutput is called and environments are restored subsequently before next test.
 *
 * After all tests, environments are destroyed iff shouldCleanEnvironments flag is set to true.
 * </p>
 *
 * @author Grzegorz Milka
 *
 * @param <EnvironmentT>
 * @param <AppT>
 */
public class MultiTestRunner<EnvironmentT extends Environment, AppT extends App<EnvironmentT>>
    implements TestRunner {
  public static final String REPORT_FILENAME = "report.txt";
  public static final String SCRIPTS_ARGUMENT_NAME = "MultiTestRunner.scripts";
  public static final String SHOULD_PREPARE_ARGUMENT_NAME =
      "MultiTestRunner.shouldPrepareEnvironments";
  public static final String SHOULD_CLEAN_ARGUMENT_NAME =
      "MultiTestRunner.shouldCleanEnvironments";
  public static final String REPORT_PATH_ARGUMENT_NAME =
      "MultiTestRunner.reportPath";
  private static final Logger LOGGER = LoggerFactory.getLogger(MultiTestRunner.class);
  private final Collection<TestScript<AppT>> mScripts;
  private final EnvironmentFactory<EnvironmentT> mEnvironmentFactory;
  private final EnvironmentPreparator<EnvironmentT> mEnvironmentPreparator;
  private final ApplicationFactory<EnvironmentT, AppT> mApplicationFactory;
  private final boolean mShouldPrepareEnvironments;
  private final boolean mShouldCleanEnvironments;
  private final Path mReportPath;
// Path: core/src/main/java/me/gregorias/dfuntest/util/FileUtils.java
// public interface FileUtils {
//   /**
//    * {@link org.apache.commons.io.FileUtils#copyDirectoryToDirectory(java.io.File, java.io.File)}
//    *
//    * @param from Source path
//    * @param to Target directory path
//    */
//   void copyDirectoryToDirectory(File from, File to) throws IOException;
// 
//   /**
//    * {@link org.apache.commons.io.FileUtils#copyFileToDirectory(java.io.File, java.io.File)}
//    *
//    * @param from Source path
//    * @param to Target directory path
//    */
//   void copyFileToDirectory(File from, File to) throws IOException;
// 
//   /**
//    * {@link java.nio.file.Files#createDirectories(java.nio.file.Path,
//    *   java.nio.file.attribute.FileAttribute[])}
//    *
//    * @param path Path to create
//    */
//   void createDirectories(Path path) throws IOException;
// 
//   /**
//    * {@link java.nio.file.Files#createTempDirectory(
//    * String, java.nio.file.attribute.FileAttribute[])}
//    *
//    * @param dirPrefix prefix of temporary directory
//    * @return Path to created directory
//    */
//   Path createTempDirectory(String dirPrefix) throws IOException;
// 
//   /**
//    * {@link org.apache.commons.io.FileUtils#deleteQuietly(java.io.File)}
//    *
//    * @param file File to delete
//    * @return true iff directory was deleted
//    */
//   boolean deleteQuietly(File file);
// 
//   /**
//    * {@link java.nio.file.Files#exists(java.nio.file.Path, java.nio.file.LinkOption...)}
//    *
//    * @param path path to check
//    * @return true iff exists
//    */
//   boolean exists(Path path);
// 
//   /**
//    * {@link java.nio.file.Files#isDirectory(java.nio.file.Path, java.nio.file.LinkOption...)}
//    *
//    * @param path path to check
//    * @return true iff path is a directory
//    */
//   boolean isDirectory(Path path);
// 
//   /**
//    * {@link java.lang.ProcessBuilder}
//    *
//    * @param command command to run
//    * @param pwdFile working directory of the process
//    * @return process running the command
//    */
//   Process runCommand(List<String> command, File pwdFile) throws IOException;
// 
//   /**
//    * {@link java.nio.file.Files#write(java.nio.file.Path, Iterable, java.nio.charset.Charset,
//    * java.nio.file.OpenOption...)}
//    *
//    * @param path Path of file to write to.
//    * @param content String to be written to file.
//    */
//   void write(Path path, String content) throws IOException;
// }


// Path: core/src/main/java/me/gregorias/dfuntest/MultiTestRunner.java
import com.google.inject.Inject;
import me.gregorias.dfuntest.util.FileUtils;
import org.apache.commons.lang.StringUtils;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
import javax.inject.Named;
import java.io.IOException;
import java.nio.file.Path;
import java.util.ArrayList;
import java.util.Collection;
import java.util.Set;

package me.gregorias.dfuntest;



/**
 * <p>
 * Basic implementation of TestRunner which runs sequentially multiple test script on given
 * environments and apps.
 * </p>
 *
 * <p>
 * It prepares the environment for the first time iff shouldPrepareEnvironments flag is set.
 * Otherwise it always restores them.
 *
 * If both shouldPrepareEnvironments and shouldCleanEnvironments are set then environments are
 * prepared and cleaned before and after every test. If shouldCleanEnvironments is set to false then
 * only cleanOutput is called and environments are restored subsequently before next test.
 *
 * After all tests, environments are destroyed iff shouldCleanEnvironments flag is set to true.
 * </p>
 *
 * @author Grzegorz Milka
 *
 * @param <EnvironmentT>
 * @param <AppT>
 */
public class MultiTestRunner<EnvironmentT extends Environment, AppT extends App<EnvironmentT>>
    implements TestRunner {
  public static final String REPORT_FILENAME = "report.txt";
  public static final String SCRIPTS_ARGUMENT_NAME = "MultiTestRunner.scripts";
  public static final String SHOULD_PREPARE_ARGUMENT_NAME =
      "MultiTestRunner.shouldPrepareEnvironments";
  public static final String SHOULD_CLEAN_ARGUMENT_NAME =
      "MultiTestRunner.shouldCleanEnvironments";
  public static final String REPORT_PATH_ARGUMENT_NAME =
      "MultiTestRunner.reportPath";
  private static final Logger LOGGER = LoggerFactory.getLogger(MultiTestRunner.class);
  private final Collection<TestScript<AppT>> mScripts;
  private final EnvironmentFactory<EnvironmentT> mEnvironmentFactory;
  private final EnvironmentPreparator<EnvironmentT> mEnvironmentPreparator;
  private final ApplicationFactory<EnvironmentT, AppT> mApplicationFactory;
  private final boolean mShouldPrepareEnvironments;
  private final boolean mShouldCleanEnvironments;
  private final Path mReportPath;
  private final FileUtils mFileUtils;