/*
 * 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.
 */

test {
    useJUnitPlatform()
    testLogging {
        events "passed", "skipped", "failed", "standard_error"
    }
    maxHeapSize = '2g'

    // Define default test timeouts to avoid everhanging tests.
    systemProperty 'junit.jupiter.execution.timeout.testable.method.default', '10m'
    systemProperty 'junit.jupiter.execution.timeout.lifecycle.method.default', '60s'

    // Enable auto-detection of JUnit 5 extensions to automatically apply DumpThreadsOnTimeout extension.
    systemProperty 'junit.jupiter.extensions.autodetection.enabled', true
}

dependencies {
    testImplementation libs.junit5.impl
    testImplementation libs.junit5.api
    testImplementation libs.junit5.params
    testImplementation libs.junit.pioneer

    testImplementation libs.jansi.core
    testImplementation libs.log4j.api
    testImplementation libs.log4j.core
    testImplementation libs.log4j.bridge
    testImplementation libs.slf4j.log4j
}
