/*
 * Licensed to the Apache Software Foundation (ASF) under one or more
 * contributor license agreements.  See the NOTICE file distributed with
 * this work for additional information regarding copyright ownership.
 * The ASF licenses this file to You under the Apache License, Version 2.0
 * (the "License"); you may not use this file except in compliance with
 * the License.  You may obtain a copy of the License at
 *
 *     http://www.apache.org/licenses/LICENSE-2.0
 *
 * Unless required by applicable law or agreed to in writing, software
 * distributed under the License is distributed on an "AS IS" BASIS,
 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
 * See the License for the specific language governing permissions and
 * limitations under the License.
 */

// If we run the test task with a filter we want to fail if no test actually ran (everything was excluded).

configure(allprojects) {
  plugins.withType(JavaPlugin) {
    tasks.withType(Test) {
      filter {
        failOnNoMatchingTests = false
      }
    }
  }
}

gradle.taskGraph.whenReady { graph ->
  def args = gradle.startParameter.taskNames
  def filters = args.findAll({ arg ->
    return arg == /--tests/
  })

  // Only apply the check if we are actually filtering.
  if (!filters.isEmpty()) {
    def testTasks = graph.allTasks.findAll { task -> task instanceof Test }
    // ... and there are some test tasks in the execution graph.
    if (!testTasks.isEmpty()) {
      def executedTests = 0
      def executedTasks = 0

      testTasks.each { task ->
        task.doFirst {
          executedTasks++
        }
        task.afterSuite { desc, result ->
          executedTests += result.testCount
        }
      }

      // After the build is finished, check the test count.
      gradle.buildFinished {
        if (executedTests == 0 && executedTasks > 0) {
          throw new GradleException("No tests found for the given filters?")
        }
      }
    }
  }
}

