Example #1
0
  @Test
  public void testIsTestRunRequiredForTestBuiltFromCacheIfHasTestResultFiles()
      throws IOException, ExecutionException, InterruptedException {
    ExecutionContext executionContext = createMock(ExecutionContext.class);
    expect(executionContext.isDebugEnabled()).andReturn(false);

    FakeTestRule testRule =
        new FakeTestRule(
            ImmutableSet.<Label>of(Label.of("windows")),
            BuildTargetFactory.newInstance("//:lulz"),
            new SourcePathResolver(new BuildRuleResolver()),
            ImmutableSortedSet.<BuildRule>of());

    CachingBuildEngine cachingBuildEngine = createMock(CachingBuildEngine.class);
    BuildResult result = new BuildResult(testRule, FETCHED_FROM_CACHE, CacheResult.hit("dir"));
    expect(cachingBuildEngine.getBuildRuleResult(BuildTargetFactory.newInstance("//:lulz")))
        .andReturn(result);
    replay(executionContext, cachingBuildEngine);

    assertTrue(
        "A cache hit updates the build artifact but not the test results. "
            + "Therefore, the test should be re-run to ensure the test results are up to date.",
        TestRunning.isTestRunRequiredForTest(
            testRule,
            cachingBuildEngine,
            executionContext,
            createMock(TestRuleKeyFileHelper.class),
            /* results cache enabled */ true,
            /* running with test selectors */ false));

    verify(executionContext, cachingBuildEngine);
  }
Example #2
0
  @Test
  public void testIsTestRunRequiredForTestBuiltLocally()
      throws IOException, ExecutionException, InterruptedException {
    ExecutionContext executionContext = createMock(ExecutionContext.class);
    expect(executionContext.isDebugEnabled()).andReturn(false);

    FakeTestRule testRule =
        new FakeTestRule(
            ImmutableSet.<Label>of(Label.of("windows")),
            BuildTargetFactory.newInstance("//:lulz"),
            new SourcePathResolver(new BuildRuleResolver()),
            ImmutableSortedSet.<BuildRule>of());

    CachingBuildEngine cachingBuildEngine = createMock(CachingBuildEngine.class);
    BuildResult result = new BuildResult(testRule, BUILT_LOCALLY, CacheResult.skip());
    expect(cachingBuildEngine.getBuildRuleResult(BuildTargetFactory.newInstance("//:lulz")))
        .andReturn(result);
    replay(executionContext, cachingBuildEngine);

    assertTrue(
        "A test built locally should always run regardless of any cached result. ",
        TestRunning.isTestRunRequiredForTest(
            testRule,
            cachingBuildEngine,
            executionContext,
            createMock(TestRuleKeyFileHelper.class),
            /* results cache enabled */ true,
            /* running with test selectors */ false));

    verify(executionContext, cachingBuildEngine);
  }
Example #3
0
  /**
   * If the source paths specified contains one source path to a non-generated file then we should
   * return the correct source tmp corresponding to that non-generated source path. Especially when
   * the generated file comes first in the ordered set.
   */
  @Test
  public void testMixedSourceFile() {
    Path pathToGenFile = GEN_PATH.resolve("com/facebook/GeneratedFile.java");
    Path pathToNonGenFile1 = Paths.get("package/src/SourceFile1.java");
    Path pathToNonGenFile2 = Paths.get("package/src-gen/SourceFile2.java");

    ImmutableSortedSet<Path> javaSrcs =
        ImmutableSortedSet.of(pathToGenFile, pathToNonGenFile1, pathToNonGenFile2);

    DefaultJavaPackageFinder defaultJavaPackageFinder = createMock(DefaultJavaPackageFinder.class);
    expect(defaultJavaPackageFinder.getPathsFromRoot()).andReturn(pathsFromRoot).times(2);
    expect(defaultJavaPackageFinder.getPathElements()).andReturn(pathElements).times(2);

    JavaLibrary javaLibrary =
        new FakeJavaLibrary(
                BuildTarget.builder("//foo", "bar").build(),
                new SourcePathResolver(new BuildRuleResolver()))
            .setJavaSrcs(javaSrcs);

    replay(defaultJavaPackageFinder);

    ImmutableSet<String> result =
        TestRunning.getPathToSourceFolders(
            javaLibrary, Optional.of(defaultJavaPackageFinder), new FakeProjectFilesystem());

    assertEquals(
        "The non-generated source files are under two different source folders.",
        ImmutableSet.of("./package/src-gen/", "./package/src/"),
        result);

    verify(defaultJavaPackageFinder);
  }
Example #4
0
  /**
   * If the source paths specified are from the new unified source tmp then we should return the
   * correct source tmp corresponding to the unified source path.
   */
  @Test
  public void testUnifiedSourceFile() {
    Path pathToNonGenFile = Paths.get("java/package/SourceFile1.java");
    assertFalse(MorePaths.isGeneratedFile(pathToNonGenFile));

    ImmutableSortedSet<Path> javaSrcs = ImmutableSortedSet.of(pathToNonGenFile);
    JavaLibrary javaLibrary =
        new FakeJavaLibrary(
                BuildTarget.builder("//foo", "bar").build(),
                new SourcePathResolver(new BuildRuleResolver()))
            .setJavaSrcs(javaSrcs);

    DefaultJavaPackageFinder defaultJavaPackageFinder = createMock(DefaultJavaPackageFinder.class);
    expect(defaultJavaPackageFinder.getPathsFromRoot()).andReturn(pathsFromRoot);

    Object[] mocks = new Object[] {defaultJavaPackageFinder};
    replay(mocks);

    ImmutableSet<String> result =
        TestRunning.getPathToSourceFolders(
            javaLibrary, Optional.of(defaultJavaPackageFinder), new FakeProjectFilesystem());

    assertEquals(
        "All non-generated source files are under one source tmp.",
        ImmutableSet.of("java/"),
        result);

    verify(mocks);
  }
Example #5
0
  /**
   * If the source paths specified are all generated files, then our path to source tmp should be
   * absent.
   */
  @Test
  public void testGeneratedSourceFile() {
    Path pathToGenFile = GEN_PATH.resolve("GeneratedFile.java");
    assertTrue(MorePaths.isGeneratedFile(pathToGenFile));

    ImmutableSortedSet<Path> javaSrcs = ImmutableSortedSet.of(pathToGenFile);
    JavaLibrary javaLibrary =
        new FakeJavaLibrary(
                BuildTarget.builder("//foo", "bar").build(),
                new SourcePathResolver(new BuildRuleResolver()))
            .setJavaSrcs(javaSrcs);

    DefaultJavaPackageFinder defaultJavaPackageFinder = createMock(DefaultJavaPackageFinder.class);

    Object[] mocks = new Object[] {defaultJavaPackageFinder};
    replay(mocks);

    ImmutableSet<String> result =
        TestRunning.getPathToSourceFolders(
            javaLibrary, Optional.of(defaultJavaPackageFinder), new FakeProjectFilesystem());

    assertTrue(
        "No path should be returned if the library contains only generated files.",
        result.isEmpty());

    verify(mocks);
  }
Example #6
0
  @Test
  public void whenSeparateTestFailsThenBuildFails() throws Exception {
    CommandRunnerParams commandRunnerParams = CommandRunnerParamsForTesting.builder().build();
    final TestResults failingTestResults =
        new TestResults(
            ImmutableList.of(
                new TestCaseSummary(
                    "TestCase",
                    ImmutableList.of(
                        new TestResultSummary(
                            "TestCaseResult",
                            "failTest",
                            ResultType.FAILURE,
                            5000,
                            null,
                            null,
                            null,
                            null)))));
    BuildTarget failingTestTarget = BuildTargetFactory.newInstance("//:failingtest");
    FakeTestRule failingTest =
        new FakeTestRule(
            BuildRuleParamsFactory.createTrivialBuildRuleParams(failingTestTarget),
            new SourcePathResolver(new BuildRuleResolver()),
            ImmutableSet.<Label>of(),
            Optional.of(Paths.get("failingTestStep1OutputDir")),
            true, // runTestSeparately
            ImmutableList.<Step>of(),
            new Callable<TestResults>() {
              @Override
              public TestResults call() {
                return failingTestResults;
              }
            });

    ListeningExecutorService service =
        MoreExecutors.listeningDecorator(Executors.newFixedThreadPool(3));
    FakeBuildEngine fakeBuildEngine =
        new FakeBuildEngine(
            ImmutableMap.of(
                failingTestTarget, new BuildResult(failingTest, BUILT_LOCALLY, CacheResult.skip())),
            ImmutableMap.of(failingTestTarget, new RuleKey("00")));
    ExecutionContext fakeExecutionContext =
        TestExecutionContext.newBuilder().setProjectFilesystem(new FakeProjectFilesystem()).build();
    DefaultStepRunner stepRunner = new DefaultStepRunner(fakeExecutionContext);
    int ret =
        TestRunning.runTests(
            commandRunnerParams,
            ImmutableList.<TestRule>of(failingTest),
            FakeBuildContext.NOOP_CONTEXT,
            fakeExecutionContext,
            DEFAULT_OPTIONS,
            service,
            fakeBuildEngine,
            stepRunner);

    assertThat(ret, equalTo(TestRunning.TEST_FAILURES_EXIT_CODE));
  }
Example #7
0
  @Test
  public void testIsTestRunRequiredIfRuleKeyNotPresent()
      throws IOException, ExecutionException, InterruptedException {
    ExecutionContext executionContext = createMock(ExecutionContext.class);
    expect(executionContext.isDebugEnabled()).andReturn(false);

    FakeTestRule testRule =
        new FakeTestRule(
            ImmutableSet.<Label>of(Label.of("windows")),
            BuildTargetFactory.newInstance("//:lulz"),
            new SourcePathResolver(new BuildRuleResolver()),
            ImmutableSortedSet.<BuildRule>of()) {

          @Override
          public boolean hasTestResultFiles(ExecutionContext context) {
            return true;
          }
        };

    TestRuleKeyFileHelper testRuleKeyFileHelper = createNiceMock(TestRuleKeyFileHelper.class);
    expect(testRuleKeyFileHelper.isRuleKeyInDir(testRule)).andReturn(false);

    CachingBuildEngine cachingBuildEngine = createMock(CachingBuildEngine.class);
    BuildResult result = new BuildResult(testRule, MATCHING_RULE_KEY, CacheResult.skip());
    expect(cachingBuildEngine.getBuildRuleResult(BuildTargetFactory.newInstance("//:lulz")))
        .andReturn(result);
    replay(executionContext, cachingBuildEngine, testRuleKeyFileHelper);

    assertTrue(
        "A cached build should run the tests if the test output directory\'s rule key is not "
            + "present or does not matche the rule key for the test.",
        TestRunning.isTestRunRequiredForTest(
            testRule,
            cachingBuildEngine,
            executionContext,
            testRuleKeyFileHelper,
            /* results cache enabled */ true,
            /* running with test selectors */ false));

    verify(executionContext, cachingBuildEngine, testRuleKeyFileHelper);
  }
Example #8
0
  @Test
  public void testIsTestRunRequiredForTestInDebugMode()
      throws IOException, ExecutionException, InterruptedException {
    ExecutionContext executionContext = createMock(ExecutionContext.class);
    expect(executionContext.isDebugEnabled()).andReturn(true);

    replay(executionContext);

    assertTrue(
        "In debug mode, test should always run regardless of any cached results since "
            + "the user is expecting to hook up a debugger.",
        TestRunning.isTestRunRequiredForTest(
            createMock(TestRule.class),
            createMock(CachingBuildEngine.class),
            executionContext,
            createMock(TestRuleKeyFileHelper.class),
            true,
            false));

    verify(executionContext);
  }
Example #9
0
  private int runTestsInternal(
      CommandRunnerParams params,
      BuildEngine buildEngine,
      Build build,
      Iterable<TestRule> testRules)
      throws InterruptedException, IOException {

    if (!withDashArguments.isEmpty()) {
      params
          .getBuckEventBus()
          .post(
              ConsoleEvent.severe("Unexpected arguments after \"--\" when using internal runner"));
      return 1;
    }

    ConcurrencyLimit concurrencyLimit =
        new ConcurrencyLimit(
            getNumTestThreads(params.getBuckConfig()), params.getBuckConfig().getLoadLimit());
    try (CommandThreadManager testPool =
        new CommandThreadManager(
            "Test-Run", params.getBuckConfig().getWorkQueueExecutionOrder(), concurrencyLimit)) {
      return TestRunning.runTests(
          params,
          testRules,
          Preconditions.checkNotNull(build.getBuildContext()),
          build.getExecutionContext(),
          getTestRunningOptions(params),
          testPool.getExecutor(),
          buildEngine,
          new DefaultStepRunner(build.getExecutionContext()));
    } catch (ExecutionException e) {
      params
          .getBuckEventBus()
          .post(ConsoleEvent.severe(MoreExceptions.getHumanReadableOrLocalizedMessage(e)));
      return 1;
    }
  }
Example #10
0
  @Test
  public void whenSomeTestsAreSeparateThenSeparateTestsRunAtEnd() throws Exception {
    CommandRunnerParams commandRunnerParams = CommandRunnerParamsForTesting.builder().build();

    AtomicInteger atomicExecutionOrder = new AtomicInteger(0);
    ExecutionOrderAwareFakeStep separateTestStep1 =
        new ExecutionOrderAwareFakeStep("teststep1", "teststep1", 0, atomicExecutionOrder);
    final TestResults fakeTestResults =
        new TestResults(
            ImmutableList.of(
                new TestCaseSummary(
                    "TestCase",
                    ImmutableList.of(
                        new TestResultSummary(
                            "TestCaseResult",
                            "passTest",
                            ResultType.SUCCESS,
                            5000,
                            null,
                            null,
                            null,
                            null)))));

    BuildTarget separateTest1Target = BuildTargetFactory.newInstance("//:test1");
    FakeTestRule separateTest1 =
        new FakeTestRule(
            BuildRuleParamsFactory.createTrivialBuildRuleParams(separateTest1Target),
            new SourcePathResolver(new BuildRuleResolver()),
            ImmutableSet.<Label>of(),
            Optional.of(Paths.get("separateTestStep1OutputDir")),
            true, // runTestSeparately
            ImmutableList.<Step>of(separateTestStep1),
            new Callable<TestResults>() {
              @Override
              public TestResults call() {
                return fakeTestResults;
              }
            });

    ExecutionOrderAwareFakeStep separateTestStep2 =
        new ExecutionOrderAwareFakeStep("teststep2", "teststep2", 0, atomicExecutionOrder);
    BuildTarget separateTest2Target = BuildTargetFactory.newInstance("//:test2");
    FakeTestRule separateTest2 =
        new FakeTestRule(
            BuildRuleParamsFactory.createTrivialBuildRuleParams(separateTest2Target),
            new SourcePathResolver(new BuildRuleResolver()),
            ImmutableSet.<Label>of(),
            Optional.of(Paths.get("separateTestStep2OutputDir")),
            true, // runTestSeparately
            ImmutableList.<Step>of(separateTestStep2),
            new Callable<TestResults>() {
              @Override
              public TestResults call() {
                return fakeTestResults;
              }
            });

    ExecutionOrderAwareFakeStep separateTestStep3 =
        new ExecutionOrderAwareFakeStep("teststep3", "teststep3", 0, atomicExecutionOrder);
    BuildTarget separateTest3Target = BuildTargetFactory.newInstance("//:test3");
    FakeTestRule separateTest3 =
        new FakeTestRule(
            BuildRuleParamsFactory.createTrivialBuildRuleParams(separateTest3Target),
            new SourcePathResolver(new BuildRuleResolver()),
            ImmutableSet.<Label>of(),
            Optional.of(Paths.get("separateTestStep3OutputDir")),
            true, // runTestSeparately
            ImmutableList.<Step>of(separateTestStep3),
            new Callable<TestResults>() {
              @Override
              public TestResults call() {
                return fakeTestResults;
              }
            });

    ExecutionOrderAwareFakeStep parallelTestStep1 =
        new ExecutionOrderAwareFakeStep(
            "parallelteststep1", "parallelteststep1", 0, atomicExecutionOrder);
    BuildTarget parallelTest1Target = BuildTargetFactory.newInstance("//:paralleltest1");
    FakeTestRule parallelTest1 =
        new FakeTestRule(
            BuildRuleParamsFactory.createTrivialBuildRuleParams(parallelTest1Target),
            new SourcePathResolver(new BuildRuleResolver()),
            ImmutableSet.<Label>of(),
            Optional.of(Paths.get("parallelTestStep1OutputDir")),
            false, // runTestSeparately
            ImmutableList.<Step>of(parallelTestStep1),
            new Callable<TestResults>() {
              @Override
              public TestResults call() {
                return fakeTestResults;
              }
            });

    ExecutionOrderAwareFakeStep parallelTestStep2 =
        new ExecutionOrderAwareFakeStep(
            "parallelteststep2", "parallelteststep2", 0, atomicExecutionOrder);
    BuildTarget parallelTest2Target = BuildTargetFactory.newInstance("//:paralleltest2");
    FakeTestRule parallelTest2 =
        new FakeTestRule(
            BuildRuleParamsFactory.createTrivialBuildRuleParams(parallelTest2Target),
            new SourcePathResolver(new BuildRuleResolver()),
            ImmutableSet.<Label>of(),
            Optional.of(Paths.get("parallelTestStep2OutputDir")),
            false, // runTestSeparately
            ImmutableList.<Step>of(parallelTestStep2),
            new Callable<TestResults>() {
              @Override
              public TestResults call() {
                return fakeTestResults;
              }
            });

    ExecutionOrderAwareFakeStep parallelTestStep3 =
        new ExecutionOrderAwareFakeStep(
            "parallelteststep3", "parallelteststep3", 0, atomicExecutionOrder);
    BuildTarget parallelTest3Target = BuildTargetFactory.newInstance("//:paralleltest3");
    FakeTestRule parallelTest3 =
        new FakeTestRule(
            BuildRuleParamsFactory.createTrivialBuildRuleParams(parallelTest3Target),
            new SourcePathResolver(new BuildRuleResolver()),
            ImmutableSet.<Label>of(),
            Optional.of(Paths.get("parallelTestStep3OutputDir")),
            false, // runTestSeparately
            ImmutableList.<Step>of(parallelTestStep3),
            new Callable<TestResults>() {
              @Override
              public TestResults call() {
                return fakeTestResults;
              }
            });

    // We explicitly use an actual thread pool here; the logic should ensure the
    // separate tests are run in the correct order.
    ListeningExecutorService service =
        MoreExecutors.listeningDecorator(Executors.newFixedThreadPool(3));
    FakeBuildEngine fakeBuildEngine =
        new FakeBuildEngine(
            ImmutableMap.<BuildTarget, BuildResult>builder()
                .put(
                    separateTest1Target,
                    new BuildResult(separateTest1, BUILT_LOCALLY, CacheResult.skip()))
                .put(
                    separateTest2Target,
                    new BuildResult(separateTest2, BUILT_LOCALLY, CacheResult.skip()))
                .put(
                    separateTest3Target,
                    new BuildResult(separateTest3, BUILT_LOCALLY, CacheResult.skip()))
                .put(
                    parallelTest1Target,
                    new BuildResult(parallelTest1, BUILT_LOCALLY, CacheResult.skip()))
                .put(
                    parallelTest2Target,
                    new BuildResult(parallelTest2, BUILT_LOCALLY, CacheResult.skip()))
                .put(
                    parallelTest3Target,
                    new BuildResult(parallelTest3, BUILT_LOCALLY, CacheResult.skip()))
                .build(),
            ImmutableMap.<BuildTarget, RuleKey>builder()
                .put(separateTest1Target, new RuleKey("00"))
                .put(separateTest2Target, new RuleKey("00"))
                .put(separateTest3Target, new RuleKey("00"))
                .put(parallelTest1Target, new RuleKey("00"))
                .put(parallelTest2Target, new RuleKey("00"))
                .put(parallelTest3Target, new RuleKey("00"))
                .build());
    ExecutionContext fakeExecutionContext =
        TestExecutionContext.newBuilder().setProjectFilesystem(new FakeProjectFilesystem()).build();
    DefaultStepRunner stepRunner = new DefaultStepRunner(fakeExecutionContext);
    int ret =
        TestRunning.runTests(
            commandRunnerParams,
            ImmutableList.<TestRule>of(
                separateTest1,
                parallelTest1,
                separateTest2,
                parallelTest2,
                separateTest3,
                parallelTest3),
            FakeBuildContext.NOOP_CONTEXT,
            fakeExecutionContext,
            DEFAULT_OPTIONS,
            service,
            fakeBuildEngine,
            stepRunner);

    assertThat(ret, equalTo(0));

    // The tests not marked as separate could run in any order -- but they must run
    // before the separate test steps.
    ImmutableSet<Optional<Integer>> expectedParallelStepExecutionOrderSet =
        ImmutableSet.<Optional<Integer>>builder()
            .add(Optional.of(0))
            .add(Optional.of(1))
            .add(Optional.of(2))
            .add(Optional.of(3))
            .add(Optional.of(4))
            .add(Optional.of(5))
            .build();

    ImmutableSet<Optional<Integer>> actualParallelStepExecutionOrderSet =
        ImmutableSet.<Optional<Integer>>builder()
            .add(parallelTestStep1.getExecutionBeginOrder())
            .add(parallelTestStep1.getExecutionEndOrder())
            .add(parallelTestStep2.getExecutionBeginOrder())
            .add(parallelTestStep2.getExecutionEndOrder())
            .add(parallelTestStep3.getExecutionBeginOrder())
            .add(parallelTestStep3.getExecutionEndOrder())
            .build();

    LOG.debug(
        "Expected parallel execution order: %s Actual parallel execution order: %s",
        expectedParallelStepExecutionOrderSet, actualParallelStepExecutionOrderSet);

    // We allow the parallel steps to begin and end in any order (note the thread
    // pool of size 3 above), so we use a set.
    assertThat(actualParallelStepExecutionOrderSet, equalTo(expectedParallelStepExecutionOrderSet));

    // The separate test steps must begin and end in a specific order, so we use a list.
    ImmutableList<Optional<Integer>> expectedSeparateStepExecutionOrderList =
        ImmutableList.<Optional<Integer>>builder()
            .add(Optional.of(6))
            .add(Optional.of(7))
            .add(Optional.of(8))
            .add(Optional.of(9))
            .add(Optional.of(10))
            .add(Optional.of(11))
            .build();

    ImmutableList<Optional<Integer>> actualSeparateStepExecutionOrderList =
        ImmutableList.<Optional<Integer>>builder()
            .add(separateTestStep1.getExecutionBeginOrder())
            .add(separateTestStep1.getExecutionEndOrder())
            .add(separateTestStep2.getExecutionBeginOrder())
            .add(separateTestStep2.getExecutionEndOrder())
            .add(separateTestStep3.getExecutionBeginOrder())
            .add(separateTestStep3.getExecutionEndOrder())
            .build();

    LOG.debug(
        "Expected separate execution order: %s Actual separate execution order: %s",
        expectedSeparateStepExecutionOrderList, actualSeparateStepExecutionOrderList);

    assertThat(
        actualSeparateStepExecutionOrderList, equalTo(expectedSeparateStepExecutionOrderList));
  }
Example #11
0
  @Test
  public void whenAllTestsAreSeparateTestsRunInOrder() throws Exception {
    CommandRunnerParams commandRunnerParams = CommandRunnerParamsForTesting.builder().build();

    AtomicInteger atomicExecutionOrder = new AtomicInteger(0);
    ExecutionOrderAwareFakeStep separateTestStep1 =
        new ExecutionOrderAwareFakeStep("teststep1", "teststep1", 0, atomicExecutionOrder);
    final TestResults fakeTestResults =
        new TestResults(
            ImmutableList.of(
                new TestCaseSummary(
                    "TestCase",
                    ImmutableList.of(
                        new TestResultSummary(
                            "TestCaseResult",
                            "passTest",
                            ResultType.SUCCESS,
                            5000,
                            null,
                            null,
                            null,
                            null)))));
    BuildTarget separateTest1Target = BuildTargetFactory.newInstance("//:test1");
    FakeTestRule separateTest1 =
        new FakeTestRule(
            BuildRuleParamsFactory.createTrivialBuildRuleParams(separateTest1Target),
            new SourcePathResolver(new BuildRuleResolver()),
            ImmutableSet.<Label>of(),
            Optional.of(Paths.get("separateTestStep1OutputDir")),
            true, // runTestSeparately
            ImmutableList.<Step>of(separateTestStep1),
            new Callable<TestResults>() {
              @Override
              public TestResults call() {
                return fakeTestResults;
              }
            });

    ExecutionOrderAwareFakeStep separateTestStep2 =
        new ExecutionOrderAwareFakeStep("teststep2", "teststep2", 0, atomicExecutionOrder);
    BuildTarget separateTest2Target = BuildTargetFactory.newInstance("//:test2");
    FakeTestRule separateTest2 =
        new FakeTestRule(
            BuildRuleParamsFactory.createTrivialBuildRuleParams(separateTest2Target),
            new SourcePathResolver(new BuildRuleResolver()),
            ImmutableSet.<Label>of(),
            Optional.of(Paths.get("separateTestStep2OutputDir")),
            true, // runTestSeparately
            ImmutableList.<Step>of(separateTestStep2),
            new Callable<TestResults>() {
              @Override
              public TestResults call() {
                return fakeTestResults;
              }
            });

    ExecutionOrderAwareFakeStep separateTestStep3 =
        new ExecutionOrderAwareFakeStep("teststep3", "teststep3", 0, atomicExecutionOrder);
    BuildTarget separateTest3Target = BuildTargetFactory.newInstance("//:test3");
    FakeTestRule separateTest3 =
        new FakeTestRule(
            BuildRuleParamsFactory.createTrivialBuildRuleParams(separateTest3Target),
            new SourcePathResolver(new BuildRuleResolver()),
            ImmutableSet.<Label>of(),
            Optional.of(Paths.get("separateTestStep3OutputDir")),
            true, // runTestSeparately
            ImmutableList.<Step>of(separateTestStep3),
            new Callable<TestResults>() {
              @Override
              public TestResults call() {
                return fakeTestResults;
              }
            });

    // We explicitly use an actual thread pool here; the logic should ensure the
    // separate tests are run in the correct order.
    ListeningExecutorService service =
        MoreExecutors.listeningDecorator(Executors.newFixedThreadPool(3));
    FakeBuildEngine fakeBuildEngine =
        new FakeBuildEngine(
            ImmutableMap.of(
                separateTest1Target,
                    new BuildResult(separateTest1, BUILT_LOCALLY, CacheResult.skip()),
                separateTest2Target,
                    new BuildResult(separateTest2, BUILT_LOCALLY, CacheResult.skip()),
                separateTest3Target,
                    new BuildResult(separateTest3, BUILT_LOCALLY, CacheResult.skip())),
            ImmutableMap.of(
                separateTest1Target, new RuleKey("00"),
                separateTest2Target, new RuleKey("00"),
                separateTest3Target, new RuleKey("00")));
    ExecutionContext fakeExecutionContext =
        TestExecutionContext.newBuilder().setProjectFilesystem(new FakeProjectFilesystem()).build();
    DefaultStepRunner stepRunner = new DefaultStepRunner(fakeExecutionContext);
    int ret =
        TestRunning.runTests(
            commandRunnerParams,
            ImmutableList.<TestRule>of(separateTest1, separateTest2, separateTest3),
            FakeBuildContext.NOOP_CONTEXT,
            fakeExecutionContext,
            DEFAULT_OPTIONS,
            service,
            fakeBuildEngine,
            stepRunner);

    assertThat(ret, equalTo(0));
    assertThat(separateTestStep1.getExecutionBeginOrder(), equalTo(Optional.of(0)));
    assertThat(separateTestStep1.getExecutionEndOrder(), equalTo(Optional.of(1)));
    assertThat(separateTestStep2.getExecutionBeginOrder(), equalTo(Optional.of(2)));
    assertThat(separateTestStep2.getExecutionEndOrder(), equalTo(Optional.of(3)));
    assertThat(separateTestStep3.getExecutionBeginOrder(), equalTo(Optional.of(4)));
    assertThat(separateTestStep3.getExecutionEndOrder(), equalTo(Optional.of(5)));
  }
Example #12
0
  /** Tests the --xml flag, ensuring that test result data is correctly formatted. */
  @Test
  public void testXmlGeneration() throws Exception {
    // Set up sample test data.
    TestResultSummary result1 =
        new TestResultSummary(
            /* testCaseName */ "TestCase",
            /* testName */ "passTest",
            /* type */ ResultType.SUCCESS,
            /* time */ 5000,
            /* message */ null,
            /* stacktrace */ null,
            /* stdOut */ null,
            /* stdErr */ null);
    TestResultSummary result2 =
        new TestResultSummary(
            /* testCaseName */ "TestCase",
            /* testName */ "failWithMsg",
            /* type */ ResultType.FAILURE,
            /* time */ 7000,
            /* message */ "Index out of bounds!",
            /* stacktrace */ "Stacktrace",
            /* stdOut */ null,
            /* stdErr */ null);
    TestResultSummary result3 =
        new TestResultSummary(
            /* testCaseName */ "TestCase",
            /* testName */ "failNoMsg",
            /* isSuccess */
            /* type */ ResultType.SUCCESS,
            /* time */ 4000,
            /* message */ null,
            /* stacktrace */ null,
            /* stdOut */ null,
            /* stdErr */ null);
    List<TestResultSummary> resultList = ImmutableList.of(result1, result2, result3);

    TestCaseSummary testCase = new TestCaseSummary("TestCase", resultList);
    List<TestCaseSummary> testCases = ImmutableList.of(testCase);

    TestResults testResults = new TestResults(testCases);
    List<TestResults> testResultsList = ImmutableList.of(testResults);

    // Call the XML generation method with our test data.
    StringWriter writer = new StringWriter();
    TestRunning.writeXmlOutput(testResultsList, writer);
    ByteArrayInputStream resultStream = new ByteArrayInputStream(writer.toString().getBytes());

    // Convert the raw XML data into a DOM object, which we will check.
    DocumentBuilderFactory dbf = DocumentBuilderFactory.newInstance();
    DocumentBuilder docBuilder = dbf.newDocumentBuilder();
    Document doc = docBuilder.parse(resultStream);

    // Check for exactly one <tests> tag.
    NodeList testsList = doc.getElementsByTagName("tests");
    assertEquals(testsList.getLength(), 1);

    // Check for exactly one <test> tag.
    Element testsEl = (Element) testsList.item(0);
    NodeList testList = testsEl.getElementsByTagName("test");
    assertEquals(testList.getLength(), 1);

    // Check for exactly three <testresult> tags.
    // There should be two failures and one success.
    Element testEl = (Element) testList.item(0);
    NodeList resultsList = testEl.getElementsByTagName("testresult");
    assertEquals(resultsList.getLength(), 3);

    // Verify the text elements of the first <testresult> tag.
    Element passResultEl = (Element) resultsList.item(0);
    assertEquals(passResultEl.getAttribute("name"), "passTest");
    assertEquals(passResultEl.getAttribute("time"), "5000");
    checkXmlTextContents(passResultEl, "message", "");
    checkXmlTextContents(passResultEl, "stacktrace", "");

    // Verify the text elements of the second <testresult> tag.
    assertEquals(testEl.getAttribute("name"), "TestCase");
    Element failResultEl1 = (Element) resultsList.item(1);
    assertEquals(failResultEl1.getAttribute("name"), "failWithMsg");
    assertEquals(failResultEl1.getAttribute("time"), "7000");
    checkXmlTextContents(failResultEl1, "message", "Index out of bounds!");
    checkXmlTextContents(failResultEl1, "stacktrace", "Stacktrace");

    // Verify the text elements of the third <testresult> tag.
    Element failResultEl2 = (Element) resultsList.item(2);
    assertEquals(failResultEl2.getAttribute("name"), "failNoMsg");
    assertEquals(failResultEl2.getAttribute("time"), "4000");
    checkXmlTextContents(failResultEl2, "message", "");
    checkXmlTextContents(failResultEl2, "stacktrace", "");
  }