You are viewing a plain text version of this content. The canonical link for it is here.
Posted to commits@hbase.apache.org by zh...@apache.org on 2026/06/16 09:56:06 UTC

(hbase) branch branch-2 updated: HBASE-30200 Cleanup all junit4 references in hbase code base (#8320) (#8323)

This is an automated email from the ASF dual-hosted git repository.

Apache9 pushed a commit to branch branch-2
in repository https://gitbox.apache.org/repos/asf/hbase.git


The following commit(s) were added to refs/heads/branch-2 by this push:
     new ac18cc13594 HBASE-30200 Cleanup all junit4 references in hbase code base (#8320) (#8323)
ac18cc13594 is described below

commit ac18cc13594ca6de988a0f49ea7648e620c37799
Author: Duo Zhang <zh...@apache.org>
AuthorDate: Tue Jun 16 17:56:00 2026 +0800

    HBASE-30200 Cleanup all junit4 references in hbase code base (#8320) (#8323)
    
    (cherry picked from commit adc1b9a326c4f8729ec025062c9f0745ce87156f)
    
    Signed-off-by: Xiao Liu <li...@apache.org>
---
 hbase-assembly/pom.xml                             |   4 +-
 hbase-asyncfs/pom.xml                              |   5 +
 hbase-backup/pom.xml                               |   5 +
 .../apache/hadoop/hbase/backup/BackupTestUtil.java |   2 +-
 .../TestIncrementalBackupMergeWithBulkLoad.java    |   6 +-
 .../hbase/client/ConnectionImplementation.java     |   2 +
 hbase-common/pom.xml                               |   5 -
 .../org/apache/hadoop/hbase/ClassTestFinder.java   |  53 ++-
 .../apache/hadoop/hbase/HBaseClassTestRule.java    | 168 ---------
 .../hadoop/hbase/HBaseClassTestRuleChecker.java    |  66 ----
 .../apache/hadoop/hbase/HBaseJupiterExtension.java |   2 +-
 .../hadoop/hbase/ResourceCheckerJUnitListener.java |  77 ----
 .../org/apache/hadoop/hbase/SystemExitRule.java    |  56 ---
 .../org/apache/hadoop/hbase/TableNameTestRule.java |  59 ---
 .../hbase/TestBuildThreadDiagnosticString.java     |   2 +-
 .../hadoop/hbase/TestHBaseClassTestRule.java       | 150 --------
 .../apache/hadoop/hbase/TestSecurityManager.java   |   8 +-
 .../apache/hadoop/hbase/TestSystemExitInTest.java  |  36 --
 ...ner.java => TimedOutTestsThreadDumpHelper.java} |  32 +-
 .../apache/hadoop/hbase/logging/TestJul2Slf4j.java |   1 -
 .../hadoop/hbase/logging/TestLog4jUtils.java       |   1 -
 hbase-common/src/test/java/org/junit/Assert.java   | 255 +++++++++++++
 .../zstd/TestZstdDictionarySplitMerge.java         |  27 +-
 ...estCoprocessorServiceBackwardCompatibility.java |  23 +-
 .../coprocessor/TestRowProcessorEndpoint.java      |  24 +-
 .../hadoop/hbase/coprocessor/TestSecureExport.java |   3 +-
 .../row/stats/TestRowStatisticsEventHandler.java   |   8 +-
 hbase-http/pom.xml                                 | 120 +-----
 hbase-it/pom.xml                                   |   5 +
 .../hbase/IntegrationTestDDLMasterFailover.java    |  55 ++-
 .../IntegrationTestRegionReplicaReplication.java   |  13 +-
 .../hadoop/hbase/IntegrationTestsDriver.java       |  35 +-
 .../StripeCompactionsPerformanceEvaluation.java    |   5 +-
 .../actions/UnbalanceKillAndRebalanceAction.java   |   7 +-
 ...stConnectionImplementationCacheMasterState.java |  31 +-
 .../IntegrationTestTableSnapshotInputFormat.java   |  12 +-
 hbase-mapreduce/pom.xml                            |   5 +
 .../mapreduce/TestCellBasedImportExport2.java      |   4 +-
 hbase-rest/pom.xml                                 |   5 +
 .../hadoop/hbase/rest/TestStatusResource.java      |   4 +-
 hbase-rsgroup/pom.xml                              |   5 -
 .../rsgroup/TestDetermineRSGroupInfoForTable.java  |  30 +-
 .../hadoop/hbase/rsgroup/TestRSGroupUtil.java      |  30 +-
 .../hbase/rsgroup/VerifyingRSGroupAdminClient.java |  11 +-
 hbase-server/pom.xml                               |  68 ----
 .../hbase/ClearUserNamespacesAndTablesRule.java    | 152 --------
 .../org/apache/hadoop/hbase/ConnectionRule.java    | 133 -------
 .../org/apache/hadoop/hbase/GenericTestUtils.java  |   2 +-
 .../org/apache/hadoop/hbase/HBaseTestCase.java     | 403 ---------------------
 .../org/apache/hadoop/hbase/MiniClusterRule.java   | 155 --------
 .../apache/hadoop/hbase/TestCheckTestClasses.java  |  62 ----
 .../io/hfile/bucket/TestBucketCacheRefCnt.java     |   3 +-
 ...ochasticLoadBalancerRegionReplicaSameHosts.java |   4 +-
 .../regionserver/TestDumpReplicationQueues.java    |   2 -
 .../hadoop/hbase/trace/OpenTelemetryClassRule.java | 126 -------
 .../hadoop/hbase/trace/OpenTelemetryTestRule.java  |  39 --
 .../hbase/util/ProcessBasedLocalHBaseCluster.java  |   4 -
 hbase-shaded/hbase-shaded-check-invariants/pom.xml |   5 -
 .../hbase-shaded-testing-util-tester/pom.xml       |   5 -
 .../shaded/TestShadedHBaseTestingUtility.java      |  24 +-
 .../pom.xml                                        |   5 -
 hbase-testing-util/pom.xml                         |  11 +-
 .../hbase/thrift/TestThriftHttpServerBase.java     |  22 +-
 .../thrift2/TestThriftHBaseServiceHandler.java     |   3 +-
 pom.xml                                            |  76 ++--
 65 files changed, 561 insertions(+), 2200 deletions(-)

diff --git a/hbase-assembly/pom.xml b/hbase-assembly/pom.xml
index 8ff8fcdf2a7..b9915b61333 100644
--- a/hbase-assembly/pom.xml
+++ b/hbase-assembly/pom.xml
@@ -403,8 +403,8 @@
           <scope>compile</scope>
         </dependency>
         <dependency>
-          <groupId>org.junit.vintage</groupId>
-          <artifactId>junit-vintage-engine</artifactId>
+          <groupId>org.hamcrest</groupId>
+          <artifactId>hamcrest-core</artifactId>
           <scope>compile</scope>
         </dependency>
         <dependency>
diff --git a/hbase-asyncfs/pom.xml b/hbase-asyncfs/pom.xml
index ad2e7d805df..4fe6870fa97 100644
--- a/hbase-asyncfs/pom.xml
+++ b/hbase-asyncfs/pom.xml
@@ -83,6 +83,11 @@
       <artifactId>junit-jupiter-params</artifactId>
       <scope>test</scope>
     </dependency>
+    <dependency>
+      <groupId>org.hamcrest</groupId>
+      <artifactId>hamcrest-library</artifactId>
+      <scope>test</scope>
+    </dependency>
     <dependency>
       <groupId>org.bouncycastle</groupId>
       <artifactId>bcprov-jdk18on</artifactId>
diff --git a/hbase-backup/pom.xml b/hbase-backup/pom.xml
index 769e3c669c3..61f7ac09101 100644
--- a/hbase-backup/pom.xml
+++ b/hbase-backup/pom.xml
@@ -177,6 +177,11 @@
       <artifactId>junit-jupiter-params</artifactId>
       <scope>test</scope>
     </dependency>
+    <dependency>
+      <groupId>org.hamcrest</groupId>
+      <artifactId>hamcrest-library</artifactId>
+      <scope>test</scope>
+    </dependency>
   </dependencies>
   <build>
     <plugins>
diff --git a/hbase-backup/src/test/java/org/apache/hadoop/hbase/backup/BackupTestUtil.java b/hbase-backup/src/test/java/org/apache/hadoop/hbase/backup/BackupTestUtil.java
index 3665eeb7a76..5d49ed574d5 100644
--- a/hbase-backup/src/test/java/org/apache/hadoop/hbase/backup/BackupTestUtil.java
+++ b/hbase-backup/src/test/java/org/apache/hadoop/hbase/backup/BackupTestUtil.java
@@ -17,7 +17,7 @@
  */
 package org.apache.hadoop.hbase.backup;
 
-import static org.junit.Assert.assertEquals;
+import static org.junit.jupiter.api.Assertions.assertEquals;
 
 import java.io.IOException;
 import org.apache.hadoop.conf.Configuration;
diff --git a/hbase-backup/src/test/java/org/apache/hadoop/hbase/backup/TestIncrementalBackupMergeWithBulkLoad.java b/hbase-backup/src/test/java/org/apache/hadoop/hbase/backup/TestIncrementalBackupMergeWithBulkLoad.java
index 4d4076f28c0..702ecbb5a3b 100644
--- a/hbase-backup/src/test/java/org/apache/hadoop/hbase/backup/TestIncrementalBackupMergeWithBulkLoad.java
+++ b/hbase-backup/src/test/java/org/apache/hadoop/hbase/backup/TestIncrementalBackupMergeWithBulkLoad.java
@@ -22,9 +22,9 @@ import static org.apache.hadoop.hbase.backup.BackupTestUtil.enableBackup;
 import static org.apache.hadoop.hbase.backup.BackupTestUtil.verifyBackup;
 import static org.apache.hadoop.hbase.backup.BackupType.FULL;
 import static org.apache.hadoop.hbase.backup.BackupType.INCREMENTAL;
-import static org.junit.Assert.assertEquals;
-import static org.junit.Assert.assertFalse;
-import static org.junit.Assert.assertTrue;
+import static org.junit.jupiter.api.Assertions.assertEquals;
+import static org.junit.jupiter.api.Assertions.assertFalse;
+import static org.junit.jupiter.api.Assertions.assertTrue;
 
 import java.io.IOException;
 import java.nio.ByteBuffer;
diff --git a/hbase-client/src/main/java/org/apache/hadoop/hbase/client/ConnectionImplementation.java b/hbase-client/src/main/java/org/apache/hadoop/hbase/client/ConnectionImplementation.java
index 66975cde622..9ac74e85bfc 100644
--- a/hbase-client/src/main/java/org/apache/hadoop/hbase/client/ConnectionImplementation.java
+++ b/hbase-client/src/main/java/org/apache/hadoop/hbase/client/ConnectionImplementation.java
@@ -1092,6 +1092,8 @@ public class ConnectionImplementation implements ClusterConnection, Closeable {
             // the parent in the above condition, so we may have already reached a region which does
             // not contains us.
             if (!regionInfo.containsRow(row)) {
+              LOG.debug("RegionInfo {} does not contains row {}", regionInfo,
+                Bytes.toStringBinary(row));
               throw new IOException(
                 "Unable to find region for " + Bytes.toStringBinary(row) + " in " + tableName);
             }
diff --git a/hbase-common/pom.xml b/hbase-common/pom.xml
index f018ea1d742..f89cadf308b 100644
--- a/hbase-common/pom.xml
+++ b/hbase-common/pom.xml
@@ -124,11 +124,6 @@
       <artifactId>junit-jupiter-params</artifactId>
       <scope>test</scope>
     </dependency>
-    <dependency>
-      <groupId>org.junit.vintage</groupId>
-      <artifactId>junit-vintage-engine</artifactId>
-      <scope>test</scope>
-    </dependency>
     <dependency>
       <groupId>org.awaitility</groupId>
       <artifactId>awaitility</artifactId>
diff --git a/hbase-common/src/test/java/org/apache/hadoop/hbase/ClassTestFinder.java b/hbase-common/src/test/java/org/apache/hadoop/hbase/ClassTestFinder.java
index dc51187e3cf..998b1fa4eb0 100644
--- a/hbase-common/src/test/java/org/apache/hadoop/hbase/ClassTestFinder.java
+++ b/hbase-common/src/test/java/org/apache/hadoop/hbase/ClassTestFinder.java
@@ -22,9 +22,7 @@ import java.lang.reflect.Modifier;
 import java.util.ArrayList;
 import java.util.List;
 import java.util.regex.Pattern;
-import org.junit.experimental.categories.Category;
 import org.junit.jupiter.api.Tag;
-import org.junit.runners.Suite;
 
 /**
  * ClassFinder that is pre-configured with filters that will only allow test classes. The name is
@@ -36,26 +34,24 @@ public class ClassTestFinder extends ClassFinder {
     super(new TestFileNameFilter(), new TestFileNameFilter(), new TestClassFilter());
   }
 
-  public ClassTestFinder(Class<?> category) {
-    super(new TestFileNameFilter(), new TestFileNameFilter(), new TestClassFilter(category));
+  public ClassTestFinder(Class<?> tag) {
+    super(new TestFileNameFilter(), new TestFileNameFilter(), new TestClassFilter(tag));
   }
 
-  public static Class<?>[] getCategoryAnnotations(Class<?> c) {
-    Category category = c.getAnnotation(Category.class);
-    if (category != null) {
-      return category.value();
-    }
-    return new Class<?>[0];
-  }
-
-  public static String[] getTagAnnotations(Class<?> c) {
+  public static Class<?>[] getTagAnnotations(Class<?> c) {
     // TODO handle optional Tags annotation
     Tag[] tags = c.getAnnotationsByType(Tag.class);
-    List<String> values = new ArrayList<>();
-    for (Tag tag : tags) {
-      values.add(tag.value());
+    List<Class<?>> values = new ArrayList<>();
+    if (tags != null) {
+      for (Tag tag : tags) {
+        try {
+          values.add(Class.forName(tag.value()));
+        } catch (ClassNotFoundException e) {
+          throw new RuntimeException(e);
+        }
+      }
     }
-    return values.toArray(new String[values.size()]);
+    return values.toArray(new Class<?>[values.size()]);
   }
 
   /** Filters both test classes and anything in the hadoop-compat modules */
@@ -79,10 +75,10 @@ public class ClassTestFinder extends ClassFinder {
    * is annotated with org.junit.Test OR - the class is annotated with Suite.SuiteClasses
    */
   public static class TestClassFilter implements ClassFilter {
-    private Class<?> categoryAnnotation = null;
+    private Class<?> tagAnnotation = null;
 
     public TestClassFilter(Class<?> categoryAnnotation) {
-      this.categoryAnnotation = categoryAnnotation;
+      this.tagAnnotation = categoryAnnotation;
     }
 
     public TestClassFilter() {
@@ -91,7 +87,7 @@ public class ClassTestFinder extends ClassFinder {
 
     @Override
     public boolean isCandidateClass(Class<?> c) {
-      return isTestClass(c) && isCategorizedClass(c);
+      return isTestClass(c) && isTagedClass(c);
     }
 
     private boolean isTestClass(Class<?> c) {
@@ -99,15 +95,8 @@ public class ClassTestFinder extends ClassFinder {
         return false;
       }
 
-      if (c.getAnnotation(Suite.SuiteClasses.class) != null) {
-        return true;
-      }
-
       for (Method met : c.getMethods()) {
-        if (
-          met.getAnnotation(org.junit.Test.class) != null
-            || met.getAnnotation(org.junit.jupiter.api.Test.class) != null
-        ) {
+        if (met.getAnnotation(org.junit.jupiter.api.Test.class) != null) {
           return true;
         }
       }
@@ -115,12 +104,12 @@ public class ClassTestFinder extends ClassFinder {
       return false;
     }
 
-    private boolean isCategorizedClass(Class<?> c) {
-      if (this.categoryAnnotation == null) {
+    private boolean isTagedClass(Class<?> c) {
+      if (this.tagAnnotation == null) {
         return true;
       }
-      for (Class<?> cc : getCategoryAnnotations(c)) {
-        if (cc.equals(this.categoryAnnotation)) {
+      for (Class<?> cc : getTagAnnotations(c)) {
+        if (cc.equals(this.tagAnnotation)) {
           return true;
         }
       }
diff --git a/hbase-common/src/test/java/org/apache/hadoop/hbase/HBaseClassTestRule.java b/hbase-common/src/test/java/org/apache/hadoop/hbase/HBaseClassTestRule.java
deleted file mode 100644
index 73f5442b6a7..00000000000
--- a/hbase-common/src/test/java/org/apache/hadoop/hbase/HBaseClassTestRule.java
+++ /dev/null
@@ -1,168 +0,0 @@
-/*
- * 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.
- */
-package org.apache.hadoop.hbase;
-
-import edu.umd.cs.findbugs.annotations.NonNull;
-import java.lang.reflect.InvocationTargetException;
-import java.lang.reflect.Method;
-import java.lang.reflect.Modifier;
-import java.util.Arrays;
-import java.util.Collection;
-import java.util.Collections;
-import java.util.List;
-import java.util.Set;
-import java.util.concurrent.TimeUnit;
-import org.apache.hadoop.hbase.testclassification.IntegrationTests;
-import org.apache.hadoop.hbase.testclassification.LargeTests;
-import org.apache.hadoop.hbase.testclassification.MediumTests;
-import org.apache.hadoop.hbase.testclassification.SmallTests;
-import org.apache.yetus.audience.InterfaceAudience;
-import org.junit.experimental.categories.Category;
-import org.junit.rules.TestRule;
-import org.junit.rules.Timeout;
-import org.junit.runner.Description;
-import org.junit.runner.RunWith;
-import org.junit.runners.Parameterized;
-import org.junit.runners.Parameterized.Parameters;
-import org.junit.runners.model.Statement;
-import org.slf4j.Logger;
-import org.slf4j.LoggerFactory;
-
-import org.apache.hbase.thirdparty.com.google.common.collect.Iterables;
-import org.apache.hbase.thirdparty.com.google.common.collect.Sets;
-
-/**
- * The class level TestRule for all the tests. Every test class should have a {@code ClassRule} with
- * it.
- * <p>
- * For now it only sets a test method timeout based off the test categories small, medium, large.
- * Based on junit Timeout TestRule; see https://github.com/junit-team/junit/wiki/Rules
- */
-@InterfaceAudience.Private
-public final class HBaseClassTestRule implements TestRule {
-  private static final Logger LOG = LoggerFactory.getLogger(HBaseClassTestRule.class);
-  public static final Set<Class<?>> UNIT_TEST_CLASSES = Collections.unmodifiableSet(
-    Sets.<Class<?>> newHashSet(SmallTests.class, MediumTests.class, LargeTests.class));
-
-  // Each unit test has this timeout.
-  private static long PER_UNIT_TEST_TIMEOUT_MINS = 13;
-
-  private final Class<?> clazz;
-
-  private final Timeout timeout;
-
-  private final SystemExitRule systemExitRule = new SystemExitRule();
-
-  private HBaseClassTestRule(Class<?> clazz, Timeout timeout) {
-    this.clazz = clazz;
-    this.timeout = timeout;
-  }
-
-  /**
-   * Mainly used for {@link HBaseClassTestRuleChecker} to confirm that we use the correct class to
-   * generate timeout ClassRule.
-   */
-  public Class<?> getClazz() {
-    return clazz;
-  }
-
-  private static long getTimeoutInSeconds(Class<?> clazz) {
-    Category[] categories = clazz.getAnnotationsByType(Category.class);
-    // Starting JUnit 4.13, it appears that the timeout is applied across all the parameterized
-    // runs. So the timeout is multiplied by number of parameterized runs.
-    int numParams = getNumParameters(clazz);
-    // @Category is not repeatable -- it is only possible to get an array of length zero or one.
-    if (categories.length == 1) {
-      for (Class<?> c : categories[0].value()) {
-        if (UNIT_TEST_CLASSES.contains(c)) {
-          long timeout = numParams * PER_UNIT_TEST_TIMEOUT_MINS;
-          LOG.info("Test {} timeout: {} mins", clazz, timeout);
-          return TimeUnit.MINUTES.toSeconds(timeout);
-        }
-        if (c == IntegrationTests.class) {
-          return TimeUnit.MINUTES.toSeconds(Long.MAX_VALUE);
-        }
-      }
-    }
-    throw new IllegalArgumentException(
-      clazz.getName() + " does not have SmallTests/MediumTests/LargeTests in @Category");
-  }
-
-  /**
-   * @param clazz Test class that is running.
-   * @return the number of parameters for this given test class. If the test is not parameterized or
-   *         if there is any issue determining the number of parameters, returns 1.
-   */
-  static int getNumParameters(Class<?> clazz) {
-    RunWith[] runWiths = clazz.getAnnotationsByType(RunWith.class);
-    boolean testParameterized = runWiths != null
-      && Arrays.stream(runWiths).anyMatch((r) -> r.value().equals(Parameterized.class));
-    if (!testParameterized) {
-      return 1;
-    }
-    for (Method method : clazz.getMethods()) {
-      if (!isParametersMethod(method)) {
-        continue;
-      }
-      // Found the parameters method. Figure out the number of parameters.
-      Object parameters;
-      try {
-        parameters = method.invoke(clazz);
-      } catch (IllegalAccessException | InvocationTargetException e) {
-        LOG.warn("Error invoking parameters method {} in test class {}", method.getName(), clazz,
-          e);
-        continue;
-      }
-      if (parameters instanceof List) {
-        return ((List) parameters).size();
-      } else if (parameters instanceof Collection) {
-        return ((Collection) parameters).size();
-      } else if (parameters instanceof Iterable) {
-        return Iterables.size((Iterable) parameters);
-      } else if (parameters instanceof Object[]) {
-        return ((Object[]) parameters).length;
-      }
-    }
-    LOG.warn("Unable to determine parameters size. Returning the default of 1.");
-    return 1;
-  }
-
-  /**
-   * Helper method that checks if the input method is a valid JUnit @Parameters method.
-   * @param method Input method.
-   * @return true if the method is a valid JUnit parameters method, false otherwise.
-   */
-  private static boolean isParametersMethod(@NonNull Method method) {
-    // A valid parameters method is public static and with @Parameters annotation.
-    boolean methodPublicStatic =
-      Modifier.isPublic(method.getModifiers()) && Modifier.isStatic(method.getModifiers());
-    Parameters[] params = method.getAnnotationsByType(Parameters.class);
-    return methodPublicStatic && (params != null && params.length > 0);
-  }
-
-  public static HBaseClassTestRule forClass(Class<?> clazz) {
-    return new HBaseClassTestRule(clazz, Timeout.builder().withLookingForStuckThread(true)
-      .withTimeout(getTimeoutInSeconds(clazz), TimeUnit.SECONDS).build());
-  }
-
-  @Override
-  public Statement apply(Statement base, Description description) {
-    return systemExitRule.apply(timeout.apply(base, description), description);
-  }
-
-}
diff --git a/hbase-common/src/test/java/org/apache/hadoop/hbase/HBaseClassTestRuleChecker.java b/hbase-common/src/test/java/org/apache/hadoop/hbase/HBaseClassTestRuleChecker.java
deleted file mode 100644
index d6ee1ccaaee..00000000000
--- a/hbase-common/src/test/java/org/apache/hadoop/hbase/HBaseClassTestRuleChecker.java
+++ /dev/null
@@ -1,66 +0,0 @@
-/*
- * 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.
- */
-package org.apache.hadoop.hbase;
-
-import static org.junit.Assert.assertEquals;
-import static org.junit.Assert.fail;
-
-import java.lang.reflect.Field;
-import java.lang.reflect.Modifier;
-import org.apache.hadoop.hbase.testclassification.IntegrationTests;
-import org.apache.yetus.audience.InterfaceAudience;
-import org.junit.ClassRule;
-import org.junit.experimental.categories.Category;
-import org.junit.runner.Description;
-import org.junit.runner.notification.RunListener;
-import org.junit.runner.notification.RunListener.ThreadSafe;
-
-/**
- * A RunListener to confirm that we have a {@link HBaseClassTestRule} class rule for every test.
- */
-@InterfaceAudience.Private
-@ThreadSafe
-public class HBaseClassTestRuleChecker extends RunListener {
-
-  @Override
-  public void testStarted(Description description) throws Exception {
-    Category[] categories = description.getTestClass().getAnnotationsByType(Category.class);
-
-    // @Category is not repeatable -- it is only possible to get an array of length zero or one.
-    if (categories.length == 1) {
-      for (Class<?> c : categories[0].value()) {
-        if (c == IntegrationTests.class) {
-          return;
-        }
-      }
-    }
-    for (Field field : description.getTestClass().getFields()) {
-      if (
-        Modifier.isStatic(field.getModifiers()) && field.getType() == HBaseClassTestRule.class
-          && field.isAnnotationPresent(ClassRule.class)
-      ) {
-        HBaseClassTestRule timeout = (HBaseClassTestRule) field.get(null);
-        assertEquals("The HBaseClassTestRule ClassRule in " + description.getTestClass().getName()
-          + " is for " + timeout.getClazz().getName(), description.getTestClass(),
-          timeout.getClazz());
-        return;
-      }
-    }
-    fail("No HBaseClassTestRule ClassRule for " + description.getTestClass().getName());
-  }
-}
diff --git a/hbase-common/src/test/java/org/apache/hadoop/hbase/HBaseJupiterExtension.java b/hbase-common/src/test/java/org/apache/hadoop/hbase/HBaseJupiterExtension.java
index 9d4ea87e0ec..1c606568c30 100644
--- a/hbase-common/src/test/java/org/apache/hadoop/hbase/HBaseJupiterExtension.java
+++ b/hbase-common/src/test/java/org/apache/hadoop/hbase/HBaseJupiterExtension.java
@@ -178,7 +178,7 @@ public class HBaseJupiterExtension implements InvocationInterceptor, BeforeAllCa
 
   private void printThreadDump() {
     LOG.info("====> TEST TIMED OUT. PRINTING THREAD DUMP. <====");
-    LOG.info(TimedOutTestsListener.buildThreadDiagnosticString());
+    LOG.info(TimedOutTestsThreadDumpHelper.buildThreadDiagnosticString());
   }
 
   @Override
diff --git a/hbase-common/src/test/java/org/apache/hadoop/hbase/ResourceCheckerJUnitListener.java b/hbase-common/src/test/java/org/apache/hadoop/hbase/ResourceCheckerJUnitListener.java
deleted file mode 100644
index 2a796cc4077..00000000000
--- a/hbase-common/src/test/java/org/apache/hadoop/hbase/ResourceCheckerJUnitListener.java
+++ /dev/null
@@ -1,77 +0,0 @@
-/*
- * 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.
- */
-package org.apache.hadoop.hbase;
-
-import java.util.Map;
-import java.util.concurrent.ConcurrentHashMap;
-import org.junit.runner.notification.RunListener;
-
-/**
- * Listen to the test progress and check the usage of:
- * <ul>
- * <li>threads</li>
- * <li>open file descriptor</li>
- * <li>max open file descriptor</li>
- * </ul>
- * <p>
- * When surefire forkMode=once/always/perthread, this code is executed on the forked process.
- */
-public class ResourceCheckerJUnitListener extends RunListener {
-
-  private final Map<String, ResourceChecker> rcs = new ConcurrentHashMap<>();
-
-  /**
-   * To be implemented by sub classes if they want to add specific ResourceAnalyzer.
-   */
-  protected void addResourceAnalyzer(ResourceChecker rc) {
-  }
-
-  private void start(String testName) {
-    ResourceChecker rc = new ResourceChecker(testName);
-    JUnitResourceCheckers.addResourceAnalyzer(rc);
-    addResourceAnalyzer(rc);
-    rcs.put(testName, rc);
-    rc.start();
-  }
-
-  private void end(String testName) {
-    ResourceChecker rc = rcs.remove(testName);
-    assert rc != null;
-    rc.end();
-  }
-
-  /**
-   * Get the test name from the JUnit Description
-   * @return the string for the short test name
-   */
-  private String descriptionToShortTestName(org.junit.runner.Description description) {
-    final int toRemove = "org.apache.hadoop.hbase.".length();
-    return description.getTestClass().getName().substring(toRemove) + "#"
-      + description.getMethodName();
-  }
-
-  @Override
-  public void testStarted(org.junit.runner.Description description) throws java.lang.Exception {
-    start(descriptionToShortTestName(description));
-  }
-
-  @Override
-  public void testFinished(org.junit.runner.Description description) throws java.lang.Exception {
-    end(descriptionToShortTestName(description));
-  }
-}
diff --git a/hbase-common/src/test/java/org/apache/hadoop/hbase/SystemExitRule.java b/hbase-common/src/test/java/org/apache/hadoop/hbase/SystemExitRule.java
deleted file mode 100644
index 4e3642cdb3b..00000000000
--- a/hbase-common/src/test/java/org/apache/hadoop/hbase/SystemExitRule.java
+++ /dev/null
@@ -1,56 +0,0 @@
-/*
- * 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.
- */
-package org.apache.hadoop.hbase;
-
-import org.junit.rules.TestRule;
-import org.junit.runner.Description;
-import org.junit.runners.model.Statement;
-
-/*
-* Test rules to prevent System.exit or Runtime.halt from exiting
-* the JVM - instead an exception is thrown.
-* */
-public class SystemExitRule implements TestRule {
-  final static SecurityManager securityManager = new TestSecurityManager();
-
-  @Override
-  public Statement apply(final Statement s, Description d) {
-    return new Statement() {
-      @Override
-      public void evaluate() throws Throwable {
-
-        try {
-          forbidSystemExitCall();
-          s.evaluate();
-        } finally {
-          System.setSecurityManager(null);
-        }
-      }
-
-    };
-  };
-
-  // Exiting the JVM is not allowed in tests and this exception is thrown instead
-  // when it is done
-  public static class SystemExitInTestException extends SecurityException {
-  }
-
-  private static void forbidSystemExitCall() {
-    System.setSecurityManager(securityManager);
-  }
-}
diff --git a/hbase-common/src/test/java/org/apache/hadoop/hbase/TableNameTestRule.java b/hbase-common/src/test/java/org/apache/hadoop/hbase/TableNameTestRule.java
deleted file mode 100644
index ef73abd042e..00000000000
--- a/hbase-common/src/test/java/org/apache/hadoop/hbase/TableNameTestRule.java
+++ /dev/null
@@ -1,59 +0,0 @@
-/*
- * 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.
- */
-package org.apache.hadoop.hbase;
-
-import org.junit.rules.TestWatcher;
-import org.junit.runner.Description;
-
-/**
- * Returns a {@code TableName} based on currently running test method name. Supports tests built on
- * the {@link org.junit.runners.Parameterized} runner.
- * @deprecated Use {@link TableNameTestExtension} instead, once we finish the migration of JUnit5,
- *             which means we do not need {@link TableNameTestRule} any more, we can remove these
- *             dependencies, see
- *             <a href="https://issues.apache.org/jira/browse/HBASE-23671">HBASE-23671</a> for more
- *             details.
- */
-@Deprecated
-public class TableNameTestRule extends TestWatcher {
-
-  private TableName tableName;
-
-  @Override
-  protected void starting(Description description) {
-    tableName = TableName.valueOf(cleanUpTestName(description.getMethodName()));
-  }
-
-  /**
-   * Helper to handle parameterized method names. Unlike regular test methods, parameterized method
-   * names look like 'foo[x]'. This is problematic for tests that use this name for HBase tables.
-   * This helper strips out the parameter suffixes.
-   * @return current test method name with out parameterized suffixes.
-   */
-  public static String cleanUpTestName(String methodName) {
-    int index = methodName.indexOf('[');
-    if (index == -1) {
-      return methodName;
-    }
-    return methodName.substring(0, index);
-  }
-
-  public TableName getTableName() {
-    return tableName;
-  }
-}
diff --git a/hbase-common/src/test/java/org/apache/hadoop/hbase/TestBuildThreadDiagnosticString.java b/hbase-common/src/test/java/org/apache/hadoop/hbase/TestBuildThreadDiagnosticString.java
index 74a4448983e..6e4ce1f69ce 100644
--- a/hbase-common/src/test/java/org/apache/hadoop/hbase/TestBuildThreadDiagnosticString.java
+++ b/hbase-common/src/test/java/org/apache/hadoop/hbase/TestBuildThreadDiagnosticString.java
@@ -35,7 +35,7 @@ public class TestBuildThreadDiagnosticString {
 
   @Test
   public void test() {
-    String threadDump = TimedOutTestsListener.buildThreadDiagnosticString();
+    String threadDump = TimedOutTestsThreadDumpHelper.buildThreadDiagnosticString();
     LOG.info(threadDump);
     assertThat(threadDump,
       containsString(getClass().getName() + ".test(" + getClass().getSimpleName() + ".java:"));
diff --git a/hbase-common/src/test/java/org/apache/hadoop/hbase/TestHBaseClassTestRule.java b/hbase-common/src/test/java/org/apache/hadoop/hbase/TestHBaseClassTestRule.java
deleted file mode 100644
index dc2b13c1c3e..00000000000
--- a/hbase-common/src/test/java/org/apache/hadoop/hbase/TestHBaseClassTestRule.java
+++ /dev/null
@@ -1,150 +0,0 @@
-/*
- * 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.
- */
-package org.apache.hadoop.hbase;
-
-import static junit.framework.TestCase.assertEquals;
-
-import java.util.Arrays;
-import java.util.Collection;
-import java.util.List;
-import org.apache.hadoop.hbase.testclassification.SmallTests;
-import org.junit.ClassRule;
-import org.junit.Test;
-import org.junit.experimental.categories.Category;
-import org.junit.runner.RunWith;
-import org.junit.runners.Parameterized;
-import org.junit.runners.Parameterized.Parameters;
-
-import org.apache.hbase.thirdparty.com.google.common.collect.Iterables;
-
-/**
- * Tests HBaseClassTestRule.
- */
-@Category(SmallTests.class)
-public class TestHBaseClassTestRule {
-
-  @ClassRule
-  public static final HBaseClassTestRule CLASS_RULE =
-    HBaseClassTestRule.forClass(TestHBaseClassTestRule.class);
-
-  // Test input classes of various kinds.
-  private static class NonParameterizedClass {
-    void dummy() {
-    }
-
-    int dummy(int a) {
-      return 0;
-    }
-  }
-
-  @RunWith(Parameterized.class)
-  private static class ParameterizedClassWithNoParametersMethod {
-    void dummy() {
-    }
-  }
-
-  @RunWith(Parameterized.class)
-  @SuppressWarnings("UnusedMethod")
-  private static class InValidParameterizedClass {
-    // Not valid because parameters method is private.
-    @Parameters
-    private static List<Object> parameters() {
-      return Arrays.asList(1, 2, 3, 4);
-    }
-
-    int dummy(int a) {
-      return 0;
-    }
-  }
-
-  @RunWith(Parameterized.class)
-  private static class ValidParameterizedClass1 {
-    @Parameters
-    public static List<Object> parameters() {
-      return Arrays.asList(1, 2, 3, 4, 5);
-    }
-
-    int dummy(int a) {
-      return 0;
-    }
-  }
-
-  @RunWith(Parameterized.class)
-  private static class ValidParameterizedClass2 {
-    @Parameters
-    public static Object[] parameters() {
-      return new Integer[] { 1, 2, 3, 4, 5, 6 };
-    }
-  }
-
-  @RunWith(Parameterized.class)
-  private static class ValidParameterizedClass3 {
-    @Parameters
-    public static Iterable<Integer> parameters() {
-      return Arrays.asList(1, 2, 3, 4, 5, 6, 7);
-    }
-  }
-
-  @RunWith(Parameterized.class)
-  private static class ValidParameterizedClass4 {
-    @Parameters
-    public static Collection<Integer> parameters() {
-      return Arrays.asList(1, 2, 3, 4, 5, 6, 7, 8, 9);
-    }
-  }
-
-  @RunWith(Parameterized.class)
-  private static class ExtendedParameterizedClass1 extends ValidParameterizedClass1 {
-    // Should be inferred from the parent class.
-    int dummy2(int a) {
-      return 0;
-    }
-  }
-
-  @RunWith(Parameterized.class)
-  private static class ExtendedParameterizedClass2 extends ValidParameterizedClass1 {
-    // Should override the parent parameters class.
-    @Parameters
-    public static List<Object> parameters() {
-      return Arrays.asList(1, 2, 3);
-    }
-  }
-
-  @Test
-  public void testNumParameters() {
-    // Invalid cases, expected to return 1.
-    assertEquals(HBaseClassTestRule.getNumParameters(NonParameterizedClass.class), 1);
-    assertEquals(
-      HBaseClassTestRule.getNumParameters(ParameterizedClassWithNoParametersMethod.class), 1);
-    assertEquals(HBaseClassTestRule.getNumParameters(InValidParameterizedClass.class), 1);
-    // Valid parameterized classes.
-    assertEquals(HBaseClassTestRule.getNumParameters(ValidParameterizedClass1.class),
-      ValidParameterizedClass1.parameters().size());
-    assertEquals(HBaseClassTestRule.getNumParameters(ValidParameterizedClass2.class),
-      ValidParameterizedClass2.parameters().length);
-    assertEquals(HBaseClassTestRule.getNumParameters(ValidParameterizedClass3.class),
-      Iterables.size(ValidParameterizedClass3.parameters()));
-    assertEquals(HBaseClassTestRule.getNumParameters(ValidParameterizedClass4.class),
-      ValidParameterizedClass4.parameters().size());
-    // Testing inheritance.
-    assertEquals(HBaseClassTestRule.getNumParameters(ExtendedParameterizedClass1.class),
-      ValidParameterizedClass1.parameters().size());
-    assertEquals(HBaseClassTestRule.getNumParameters(ExtendedParameterizedClass2.class),
-      ExtendedParameterizedClass2.parameters().size());
-  }
-}
diff --git a/hbase-common/src/test/java/org/apache/hadoop/hbase/TestSecurityManager.java b/hbase-common/src/test/java/org/apache/hadoop/hbase/TestSecurityManager.java
index 030efa97709..22c7cf5c09d 100644
--- a/hbase-common/src/test/java/org/apache/hadoop/hbase/TestSecurityManager.java
+++ b/hbase-common/src/test/java/org/apache/hadoop/hbase/TestSecurityManager.java
@@ -27,9 +27,15 @@ import java.security.Permission;
 * TODO: Look at still using this in those tests
 * */
 public class TestSecurityManager extends SecurityManager {
+
+  // Exiting the JVM is not allowed in tests and this exception is thrown instead
+  // when it is done
+  public static class SystemExitInTestException extends SecurityException {
+  }
+
   @Override
   public void checkExit(int status) {
-    throw new SystemExitRule.SystemExitInTestException();
+    throw new SystemExitInTestException();
   }
 
   @Override
diff --git a/hbase-common/src/test/java/org/apache/hadoop/hbase/TestSystemExitInTest.java b/hbase-common/src/test/java/org/apache/hadoop/hbase/TestSystemExitInTest.java
deleted file mode 100644
index 54fece09f39..00000000000
--- a/hbase-common/src/test/java/org/apache/hadoop/hbase/TestSystemExitInTest.java
+++ /dev/null
@@ -1,36 +0,0 @@
-/*
- * 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.
- */
-package org.apache.hadoop.hbase;
-
-import static org.junit.jupiter.api.Assertions.assertThrows;
-
-import org.apache.hadoop.hbase.testclassification.MiscTests;
-import org.apache.hadoop.hbase.testclassification.SmallTests;
-import org.junit.jupiter.api.Tag;
-import org.junit.jupiter.api.Test;
-
-@Tag(MiscTests.TAG)
-@Tag(SmallTests.TAG)
-public class TestSystemExitInTest {
-
-  @Test
-  public void testSystemExit() {
-    assertThrows(SystemExitRule.SystemExitInTestException.class, () -> System.exit(1));
-  }
-
-}
diff --git a/hbase-common/src/test/java/org/apache/hadoop/hbase/TimedOutTestsListener.java b/hbase-common/src/test/java/org/apache/hadoop/hbase/TimedOutTestsThreadDumpHelper.java
similarity index 83%
rename from hbase-common/src/test/java/org/apache/hadoop/hbase/TimedOutTestsListener.java
rename to hbase-common/src/test/java/org/apache/hadoop/hbase/TimedOutTestsThreadDumpHelper.java
index 253d1735977..f10d76b5696 100644
--- a/hbase-common/src/test/java/org/apache/hadoop/hbase/TimedOutTestsListener.java
+++ b/hbase-common/src/test/java/org/apache/hadoop/hbase/TimedOutTestsThreadDumpHelper.java
@@ -17,7 +17,6 @@
  */
 package org.apache.hadoop.hbase;
 
-import java.io.OutputStreamWriter;
 import java.io.PrintWriter;
 import java.io.StringWriter;
 import java.lang.management.LockInfo;
@@ -25,49 +24,24 @@ import java.lang.management.ManagementFactory;
 import java.lang.management.MonitorInfo;
 import java.lang.management.ThreadInfo;
 import java.lang.management.ThreadMXBean;
-import java.nio.charset.StandardCharsets;
 import java.time.Instant;
 import java.time.ZoneId;
 import java.time.format.DateTimeFormatter;
 import java.util.Locale;
 import java.util.Map;
-import org.junit.runner.notification.Failure;
-import org.junit.runner.notification.RunListener;
 
 /**
  * JUnit run listener which prints full thread dump into System.err in case a test is failed due to
  * timeout.
  */
-public class TimedOutTestsListener extends RunListener {
-
-  private static final String TEST_TIMED_OUT_PREFIX = "test timed out after";
+public final class TimedOutTestsThreadDumpHelper {
 
   private static final DateTimeFormatter TIMESTAMP_FORMATTER =
     DateTimeFormatter.ofPattern("yyyy-MM-dd HH:mm:ss,SSS Z").withZone(ZoneId.systemDefault());
 
-  private static String INDENT = "    ";
-
-  private final PrintWriter output;
-
-  public TimedOutTestsListener() {
-    this.output = new PrintWriter(new OutputStreamWriter(System.err, StandardCharsets.UTF_8));
-  }
-
-  public TimedOutTestsListener(PrintWriter output) {
-    this.output = output;
-  }
+  private static final String INDENT = "    ";
 
-  @Override
-  public void testFailure(Failure failure) throws Exception {
-    if (
-      failure != null && failure.getMessage() != null
-        && failure.getMessage().startsWith(TEST_TIMED_OUT_PREFIX)
-    ) {
-      output.println("====> TEST TIMED OUT. PRINTING THREAD DUMP. <====");
-      output.println();
-      output.print(buildThreadDiagnosticString());
-    }
-    output.flush();
+  private TimedOutTestsThreadDumpHelper() {
   }
 
   public static String buildThreadDiagnosticString() {
diff --git a/hbase-common/src/test/java/org/apache/hadoop/hbase/logging/TestJul2Slf4j.java b/hbase-common/src/test/java/org/apache/hadoop/hbase/logging/TestJul2Slf4j.java
index 1e270ec6e1a..443d4a4f00e 100644
--- a/hbase-common/src/test/java/org/apache/hadoop/hbase/logging/TestJul2Slf4j.java
+++ b/hbase-common/src/test/java/org/apache/hadoop/hbase/logging/TestJul2Slf4j.java
@@ -27,7 +27,6 @@ import static org.mockito.Mockito.when;
 
 import java.io.IOException;
 import java.util.concurrent.atomic.AtomicReference;
-import org.apache.hadoop.hbase.HBaseClassTestRule;
 import org.apache.hadoop.hbase.testclassification.MiscTests;
 import org.apache.hadoop.hbase.testclassification.SmallTests;
 import org.junit.jupiter.api.AfterEach;
diff --git a/hbase-common/src/test/java/org/apache/hadoop/hbase/logging/TestLog4jUtils.java b/hbase-common/src/test/java/org/apache/hadoop/hbase/logging/TestLog4jUtils.java
index de8b169fb2d..00cba91e075 100644
--- a/hbase-common/src/test/java/org/apache/hadoop/hbase/logging/TestLog4jUtils.java
+++ b/hbase-common/src/test/java/org/apache/hadoop/hbase/logging/TestLog4jUtils.java
@@ -21,7 +21,6 @@ import static org.junit.jupiter.api.Assertions.assertEquals;
 import static org.junit.jupiter.api.Assertions.assertTrue;
 
 import java.io.IOException;
-import org.apache.hadoop.hbase.HBaseClassTestRule;
 import org.apache.hadoop.hbase.testclassification.MiscTests;
 import org.apache.hadoop.hbase.testclassification.SmallTests;
 import org.junit.jupiter.api.Tag;
diff --git a/hbase-common/src/test/java/org/junit/Assert.java b/hbase-common/src/test/java/org/junit/Assert.java
new file mode 100644
index 00000000000..b3b51231c97
--- /dev/null
+++ b/hbase-common/src/test/java/org/junit/Assert.java
@@ -0,0 +1,255 @@
+/*
+ * 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.
+ */
+package org.junit;
+
+import com.google.errorprone.annotations.RestrictedApi;
+import org.junit.jupiter.api.Assertions;
+
+/**
+ * JUnit4-compatible shim that delegates all calls to JUnit5 {@link Assertions}. Exists so that
+ * third-party test utilities(especially hadoop mini cluster related classes) compiled against
+ * JUnit4 can resolve {@code org.junit.Assert} without pulling in the real junit4 dependency.
+ */
+public final class Assert {
+
+  private Assert() {
+  }
+
+  @RestrictedApi(explanation = "Only for thirdparty code, use JUnit5 Assertions in HBase")
+  public static void assertTrue(String message, boolean condition) {
+    Assertions.assertTrue(condition, message);
+  }
+
+  @RestrictedApi(explanation = "Only for thirdparty code, use JUnit5 Assertions in HBase")
+  public static void assertTrue(boolean condition) {
+    Assertions.assertTrue(condition);
+  }
+
+  @RestrictedApi(explanation = "Only for thirdparty code, use JUnit5 Assertions in HBase")
+  public static void assertFalse(String message, boolean condition) {
+    Assertions.assertFalse(condition, message);
+  }
+
+  @RestrictedApi(explanation = "Only for thirdparty code, use JUnit5 Assertions in HBase")
+  public static void assertFalse(boolean condition) {
+    Assertions.assertFalse(condition);
+  }
+
+  @RestrictedApi(explanation = "Only for thirdparty code, use JUnit5 Assertions in HBase")
+  public static void fail(String message) {
+    Assertions.fail(message);
+  }
+
+  @RestrictedApi(explanation = "Only for thirdparty code, use JUnit5 Assertions in HBase")
+  public static void fail() {
+    Assertions.fail();
+  }
+
+  @RestrictedApi(explanation = "Only for thirdparty code, use JUnit5 Assertions in HBase")
+  public static void assertEquals(String message, Object expected, Object actual) {
+    Assertions.assertEquals(expected, actual, message);
+  }
+
+  @RestrictedApi(explanation = "Only for thirdparty code, use JUnit5 Assertions in HBase")
+  public static void assertEquals(Object expected, Object actual) {
+    Assertions.assertEquals(expected, actual);
+  }
+
+  @RestrictedApi(explanation = "Only for thirdparty code, use JUnit5 Assertions in HBase")
+  public static void assertEquals(String message, long expected, long actual) {
+    Assertions.assertEquals(expected, actual, message);
+  }
+
+  @RestrictedApi(explanation = "Only for thirdparty code, use JUnit5 Assertions in HBase")
+  public static void assertEquals(long expected, long actual) {
+    Assertions.assertEquals(expected, actual);
+  }
+
+  @RestrictedApi(explanation = "Only for thirdparty code, use JUnit5 Assertions in HBase")
+  public static void assertEquals(double expected, double actual, double delta) {
+    Assertions.assertEquals(expected, actual, delta);
+  }
+
+  @RestrictedApi(explanation = "Only for thirdparty code, use JUnit5 Assertions in HBase")
+  public static void assertEquals(String message, double expected, double actual, double delta) {
+    Assertions.assertEquals(expected, actual, delta, message);
+  }
+
+  @RestrictedApi(explanation = "Only for thirdparty code, use JUnit5 Assertions in HBase")
+  public static void assertEquals(float expected, float actual, float delta) {
+    Assertions.assertEquals(expected, actual, delta);
+  }
+
+  @RestrictedApi(explanation = "Only for thirdparty code, use JUnit5 Assertions in HBase")
+  public static void assertEquals(String message, float expected, float actual, float delta) {
+    Assertions.assertEquals(expected, actual, delta, message);
+  }
+
+  @RestrictedApi(explanation = "Only for thirdparty code, use JUnit5 Assertions in HBase")
+  public static void assertNotEquals(String message, Object unexpected, Object actual) {
+    Assertions.assertNotEquals(unexpected, actual, message);
+  }
+
+  @RestrictedApi(explanation = "Only for thirdparty code, use JUnit5 Assertions in HBase")
+  public static void assertNotEquals(Object unexpected, Object actual) {
+    Assertions.assertNotEquals(unexpected, actual);
+  }
+
+  @RestrictedApi(explanation = "Only for thirdparty code, use JUnit5 Assertions in HBase")
+  public static void assertNotEquals(String message, long unexpected, long actual) {
+    Assertions.assertNotEquals(unexpected, actual, message);
+  }
+
+  @RestrictedApi(explanation = "Only for thirdparty code, use JUnit5 Assertions in HBase")
+  public static void assertNotEquals(long unexpected, long actual) {
+    Assertions.assertNotEquals(unexpected, actual);
+  }
+
+  @RestrictedApi(explanation = "Only for thirdparty code, use JUnit5 Assertions in HBase")
+  public static void assertNotEquals(double unexpected, double actual, double delta) {
+    Assertions.assertNotEquals(unexpected, actual, delta);
+  }
+
+  @RestrictedApi(explanation = "Only for thirdparty code, use JUnit5 Assertions in HBase")
+  public static void assertNotEquals(String message, double unexpected, double actual,
+    double delta) {
+    Assertions.assertNotEquals(unexpected, actual, delta, message);
+  }
+
+  @RestrictedApi(explanation = "Only for thirdparty code, use JUnit5 Assertions in HBase")
+  public static void assertNotNull(String message, Object object) {
+    Assertions.assertNotNull(object, message);
+  }
+
+  @RestrictedApi(explanation = "Only for thirdparty code, use JUnit5 Assertions in HBase")
+  public static void assertNotNull(Object object) {
+    Assertions.assertNotNull(object);
+  }
+
+  @RestrictedApi(explanation = "Only for thirdparty code, use JUnit5 Assertions in HBase")
+  public static void assertNull(String message, Object object) {
+    Assertions.assertNull(object, message);
+  }
+
+  @RestrictedApi(explanation = "Only for thirdparty code, use JUnit5 Assertions in HBase")
+  public static void assertNull(Object object) {
+    Assertions.assertNull(object);
+  }
+
+  @RestrictedApi(explanation = "Only for thirdparty code, use JUnit5 Assertions in HBase")
+  public static void assertSame(String message, Object expected, Object actual) {
+    Assertions.assertSame(expected, actual, message);
+  }
+
+  @RestrictedApi(explanation = "Only for thirdparty code, use JUnit5 Assertions in HBase")
+  public static void assertSame(Object expected, Object actual) {
+    Assertions.assertSame(expected, actual);
+  }
+
+  @RestrictedApi(explanation = "Only for thirdparty code, use JUnit5 Assertions in HBase")
+  public static void assertNotSame(String message, Object unexpected, Object actual) {
+    Assertions.assertNotSame(unexpected, actual, message);
+  }
+
+  @RestrictedApi(explanation = "Only for thirdparty code, use JUnit5 Assertions in HBase")
+  public static void assertNotSame(Object unexpected, Object actual) {
+    Assertions.assertNotSame(unexpected, actual);
+  }
+
+  @RestrictedApi(explanation = "Only for thirdparty code, use JUnit5 Assertions in HBase")
+  public static void assertArrayEquals(String message, Object[] expecteds, Object[] actuals) {
+    Assertions.assertArrayEquals(expecteds, actuals, message);
+  }
+
+  @RestrictedApi(explanation = "Only for thirdparty code, use JUnit5 Assertions in HBase")
+  public static void assertArrayEquals(Object[] expecteds, Object[] actuals) {
+    Assertions.assertArrayEquals(expecteds, actuals);
+  }
+
+  @RestrictedApi(explanation = "Only for thirdparty code, use JUnit5 Assertions in HBase")
+  public static void assertArrayEquals(String message, byte[] expecteds, byte[] actuals) {
+    Assertions.assertArrayEquals(expecteds, actuals, message);
+  }
+
+  @RestrictedApi(explanation = "Only for thirdparty code, use JUnit5 Assertions in HBase")
+  public static void assertArrayEquals(byte[] expecteds, byte[] actuals) {
+    Assertions.assertArrayEquals(expecteds, actuals);
+  }
+
+  @RestrictedApi(explanation = "Only for thirdparty code, use JUnit5 Assertions in HBase")
+  public static void assertArrayEquals(String message, char[] expecteds, char[] actuals) {
+    Assertions.assertArrayEquals(expecteds, actuals, message);
+  }
+
+  @RestrictedApi(explanation = "Only for thirdparty code, use JUnit5 Assertions in HBase")
+  public static void assertArrayEquals(char[] expecteds, char[] actuals) {
+    Assertions.assertArrayEquals(expecteds, actuals);
+  }
+
+  @RestrictedApi(explanation = "Only for thirdparty code, use JUnit5 Assertions in HBase")
+  public static void assertArrayEquals(String message, short[] expecteds, short[] actuals) {
+    Assertions.assertArrayEquals(expecteds, actuals, message);
+  }
+
+  @RestrictedApi(explanation = "Only for thirdparty code, use JUnit5 Assertions in HBase")
+  public static void assertArrayEquals(short[] expecteds, short[] actuals) {
+    Assertions.assertArrayEquals(expecteds, actuals);
+  }
+
+  @RestrictedApi(explanation = "Only for thirdparty code, use JUnit5 Assertions in HBase")
+  public static void assertArrayEquals(String message, int[] expecteds, int[] actuals) {
+    Assertions.assertArrayEquals(expecteds, actuals, message);
+  }
+
+  @RestrictedApi(explanation = "Only for thirdparty code, use JUnit5 Assertions in HBase")
+  public static void assertArrayEquals(int[] expecteds, int[] actuals) {
+    Assertions.assertArrayEquals(expecteds, actuals);
+  }
+
+  @RestrictedApi(explanation = "Only for thirdparty code, use JUnit5 Assertions in HBase")
+  public static void assertArrayEquals(String message, long[] expecteds, long[] actuals) {
+    Assertions.assertArrayEquals(expecteds, actuals, message);
+  }
+
+  @RestrictedApi(explanation = "Only for thirdparty code, use JUnit5 Assertions in HBase")
+  public static void assertArrayEquals(long[] expecteds, long[] actuals) {
+    Assertions.assertArrayEquals(expecteds, actuals);
+  }
+
+  @RestrictedApi(explanation = "Only for thirdparty code, use JUnit5 Assertions in HBase")
+  public static void assertArrayEquals(String message, double[] expecteds, double[] actuals,
+    double delta) {
+    Assertions.assertArrayEquals(expecteds, actuals, delta, message);
+  }
+
+  @RestrictedApi(explanation = "Only for thirdparty code, use JUnit5 Assertions in HBase")
+  public static void assertArrayEquals(double[] expecteds, double[] actuals, double delta) {
+    Assertions.assertArrayEquals(expecteds, actuals, delta);
+  }
+
+  @RestrictedApi(explanation = "Only for thirdparty code, use JUnit5 Assertions in HBase")
+  public static void assertArrayEquals(String message, float[] expecteds, float[] actuals,
+    float delta) {
+    Assertions.assertArrayEquals(expecteds, actuals, delta, message);
+  }
+
+  @RestrictedApi(explanation = "Only for thirdparty code, use JUnit5 Assertions in HBase")
+  public static void assertArrayEquals(float[] expecteds, float[] actuals, float delta) {
+    Assertions.assertArrayEquals(expecteds, actuals, delta);
+  }
+}
diff --git a/hbase-compression/hbase-compression-zstd/src/test/java/org/apache/hadoop/hbase/io/compress/zstd/TestZstdDictionarySplitMerge.java b/hbase-compression/hbase-compression-zstd/src/test/java/org/apache/hadoop/hbase/io/compress/zstd/TestZstdDictionarySplitMerge.java
index d3b356bd5e6..85cdef001a7 100644
--- a/hbase-compression/hbase-compression-zstd/src/test/java/org/apache/hadoop/hbase/io/compress/zstd/TestZstdDictionarySplitMerge.java
+++ b/hbase-compression/hbase-compression-zstd/src/test/java/org/apache/hadoop/hbase/io/compress/zstd/TestZstdDictionarySplitMerge.java
@@ -51,6 +51,7 @@ import org.junit.jupiter.api.Test;
 public class TestZstdDictionarySplitMerge {
 
   private static final HBaseTestingUtility TEST_UTIL = new HBaseTestingUtility();
+  private static int numRows = 10_000;
   private static Configuration conf;
 
   @BeforeAll
@@ -82,16 +83,16 @@ public class TestZstdDictionarySplitMerge {
         .setConfiguration(ZstdCodec.ZSTD_DICTIONARY_KEY, dictionaryPath).build())
       .build();
     final Admin admin = TEST_UTIL.getAdmin();
-    admin.createTable(td, new byte[][] { Bytes.toBytes(1) });
+    admin.createTable(td, new byte[][] { Bytes.toBytes(String.valueOf(1)) });
     TEST_UTIL.waitTableAvailable(tableName);
     // Load some data
     Table t = ConnectionFactory.createConnection(conf).getTable(tableName);
-    TEST_UTIL.loadNumericRows(t, cfName, 0, 100_000);
+    TEST_UTIL.loadNumericRows(t, cfName, 0, numRows);
     admin.flush(tableName);
     assertTrue(DictionaryCache.contains(dictionaryPath), "Dictionary was not loaded");
-    TEST_UTIL.verifyNumericRows(t, cfName, 0, 100_000, 0);
+    TEST_UTIL.verifyNumericRows(t, cfName, 0, numRows, 0);
     // Test split procedure
-    admin.split(tableName, Bytes.toBytes(50_000));
+    admin.split(tableName, Bytes.toBytes(String.valueOf(numRows / 2)));
     TEST_UTIL.waitFor(30000, new ExplainingPredicate<Exception>() {
       @Override
       public boolean evaluate() throws Exception {
@@ -104,30 +105,36 @@ public class TestZstdDictionarySplitMerge {
       }
     });
     TEST_UTIL.waitUntilNoRegionsInTransition();
-    TEST_UTIL.verifyNumericRows(t, cfName, 0, 100_000, 0);
+    TEST_UTIL.verifyNumericRows(t, cfName, 0, numRows, 0);
     // Test merge procedure
     RegionInfo regionA = null;
     RegionInfo regionB = null;
+
     for (RegionInfo region : admin.getRegions(tableName)) {
       if (region.getStartKey().length == 0) {
         regionA = region;
-      } else if (Bytes.equals(region.getStartKey(), Bytes.toBytes(1))) {
+      } else if (Bytes.equals(region.getStartKey(), Bytes.toBytes(String.valueOf(1)))) {
         regionB = region;
       }
     }
     assertNotNull(regionA);
     assertNotNull(regionB);
+
+    // major compact before merging otherwise the regions are not mergable
+    TEST_UTIL.compact(tableName, true);
+    admin.reopenTableRegions(tableName);
+
     admin
       .mergeRegionsAsync(new byte[][] { regionA.getRegionName(), regionB.getRegionName() }, false)
-      .get(30, TimeUnit.SECONDS);
+      .get(300, TimeUnit.SECONDS);
     assertEquals(2, admin.getRegions(tableName).size());
     ServerName expected = TEST_UTIL.getMiniHBaseCluster().getRegionServer(0).getServerName();
     assertEquals(expected, TEST_UTIL.getConnection().getRegionLocator(tableName)
-      .getRegionLocation(Bytes.toBytes(1), true).getServerName());
+      .getRegionLocation(Bytes.toBytes(String.valueOf(1)), true).getServerName());
     try (AsyncConnection asyncConn = ConnectionFactory.createAsyncConnection(conf).get()) {
       assertEquals(expected, asyncConn.getRegionLocator(tableName)
-        .getRegionLocation(Bytes.toBytes(1), true).get().getServerName());
+        .getRegionLocation(Bytes.toBytes(String.valueOf(1)), true).get().getServerName());
     }
-    TEST_UTIL.verifyNumericRows(t, cfName, 0, 100_000, 0);
+    TEST_UTIL.verifyNumericRows(t, cfName, 0, numRows, 0);
   }
 }
diff --git a/hbase-endpoint/src/test/java/org/apache/hadoop/hbase/coprocessor/TestCoprocessorServiceBackwardCompatibility.java b/hbase-endpoint/src/test/java/org/apache/hadoop/hbase/coprocessor/TestCoprocessorServiceBackwardCompatibility.java
index fecc9088aef..3ed890e2770 100644
--- a/hbase-endpoint/src/test/java/org/apache/hadoop/hbase/coprocessor/TestCoprocessorServiceBackwardCompatibility.java
+++ b/hbase-endpoint/src/test/java/org/apache/hadoop/hbase/coprocessor/TestCoprocessorServiceBackwardCompatibility.java
@@ -17,34 +17,31 @@
  */
 package org.apache.hadoop.hbase.coprocessor;
 
-import static org.junit.Assert.assertEquals;
+import static org.junit.jupiter.api.Assertions.assertEquals;
 
 import com.google.protobuf.RpcCallback;
 import com.google.protobuf.RpcController;
 import com.google.protobuf.Service;
 import org.apache.hadoop.conf.Configuration;
-import org.apache.hadoop.hbase.HBaseClassTestRule;
 import org.apache.hadoop.hbase.HBaseTestingUtility;
 import org.apache.hadoop.hbase.TableName;
 import org.apache.hadoop.hbase.coprocessor.protobuf.generated.DummyRegionServerEndpointProtos.DummyRequest;
 import org.apache.hadoop.hbase.coprocessor.protobuf.generated.DummyRegionServerEndpointProtos.DummyResponse;
 import org.apache.hadoop.hbase.coprocessor.protobuf.generated.DummyRegionServerEndpointProtos.DummyService;
+import org.apache.hadoop.hbase.testclassification.CoprocessorTests;
 import org.apache.hadoop.hbase.testclassification.MediumTests;
 import org.apache.hadoop.hbase.util.Bytes;
-import org.junit.AfterClass;
-import org.junit.BeforeClass;
-import org.junit.ClassRule;
-import org.junit.Test;
-import org.junit.experimental.categories.Category;
+import org.junit.jupiter.api.AfterAll;
+import org.junit.jupiter.api.BeforeAll;
+import org.junit.jupiter.api.Tag;
+import org.junit.jupiter.api.Test;
 
 /**
  * Tests to ensure that 2.0 is backward compatible in loading CoprocessorService.
  */
-@Category({ MediumTests.class })
+@Tag(CoprocessorTests.TAG)
+@Tag(MediumTests.TAG)
 public class TestCoprocessorServiceBackwardCompatibility {
-  @ClassRule
-  public static final HBaseClassTestRule CLASS_RULE =
-    HBaseClassTestRule.forClass(TestCoprocessorServiceBackwardCompatibility.class);
 
   private static HBaseTestingUtility TEST_UTIL = null;
   private static Configuration CONF = null;
@@ -87,7 +84,7 @@ public class TestCoprocessorServiceBackwardCompatibility {
     }
   }
 
-  @BeforeClass
+  @BeforeAll
   public static void setupBeforeClass() throws Exception {
     TEST_UTIL = new HBaseTestingUtility();
     CONF = TEST_UTIL.getConfiguration();
@@ -100,7 +97,7 @@ public class TestCoprocessorServiceBackwardCompatibility {
     TEST_UTIL.startMiniCluster();
   }
 
-  @AfterClass
+  @AfterAll
   public static void tearDownAfter() throws Exception {
     TEST_UTIL.shutdownMiniCluster();
   }
diff --git a/hbase-endpoint/src/test/java/org/apache/hadoop/hbase/coprocessor/TestRowProcessorEndpoint.java b/hbase-endpoint/src/test/java/org/apache/hadoop/hbase/coprocessor/TestRowProcessorEndpoint.java
index 74c6022b423..f0238567e5d 100644
--- a/hbase-endpoint/src/test/java/org/apache/hadoop/hbase/coprocessor/TestRowProcessorEndpoint.java
+++ b/hbase-endpoint/src/test/java/org/apache/hadoop/hbase/coprocessor/TestRowProcessorEndpoint.java
@@ -17,8 +17,8 @@
  */
 package org.apache.hadoop.hbase.coprocessor;
 
-import static org.junit.Assert.assertEquals;
-import static org.junit.Assert.assertTrue;
+import static org.junit.jupiter.api.Assertions.assertEquals;
+import static org.junit.jupiter.api.Assertions.assertTrue;
 
 import com.google.protobuf.Message;
 import java.io.IOException;
@@ -35,7 +35,6 @@ import java.util.concurrent.atomic.AtomicLong;
 import org.apache.hadoop.conf.Configuration;
 import org.apache.hadoop.hbase.Cell;
 import org.apache.hadoop.hbase.CellUtil;
-import org.apache.hadoop.hbase.HBaseClassTestRule;
 import org.apache.hadoop.hbase.HBaseTestingUtility;
 import org.apache.hadoop.hbase.HConstants;
 import org.apache.hadoop.hbase.KeyValue;
@@ -70,11 +69,10 @@ import org.apache.hadoop.hbase.testclassification.MediumTests;
 import org.apache.hadoop.hbase.util.ByteStringer;
 import org.apache.hadoop.hbase.util.Bytes;
 import org.apache.hadoop.hbase.wal.WALEdit;
-import org.junit.AfterClass;
-import org.junit.BeforeClass;
-import org.junit.ClassRule;
-import org.junit.Test;
-import org.junit.experimental.categories.Category;
+import org.junit.jupiter.api.AfterAll;
+import org.junit.jupiter.api.BeforeAll;
+import org.junit.jupiter.api.Tag;
+import org.junit.jupiter.api.Test;
 import org.slf4j.Logger;
 import org.slf4j.LoggerFactory;
 
@@ -82,11 +80,9 @@ import org.slf4j.LoggerFactory;
  * Verifies ProcessEndpoint works. The tested RowProcessor performs two scans and a
  * read-modify-write.
  */
-@Category({ CoprocessorTests.class, MediumTests.class })
+@Tag(CoprocessorTests.TAG)
+@Tag(MediumTests.TAG)
 public class TestRowProcessorEndpoint {
-  @ClassRule
-  public static final HBaseClassTestRule CLASS_RULE =
-    HBaseClassTestRule.forClass(TestRowProcessorEndpoint.class);
 
   private static final Logger LOG = LoggerFactory.getLogger(TestRowProcessorEndpoint.class);
 
@@ -116,7 +112,7 @@ public class TestRowProcessorEndpoint {
   private volatile CountDownLatch startSignal;
   private volatile CountDownLatch doneSignal;
 
-  @BeforeClass
+  @BeforeAll
   public static void setupBeforeClass() throws Exception {
     Configuration conf = util.getConfiguration();
     conf.setStrings(CoprocessorHost.REGION_COPROCESSOR_CONF_KEY,
@@ -127,7 +123,7 @@ public class TestRowProcessorEndpoint {
     util.startMiniCluster();
   }
 
-  @AfterClass
+  @AfterAll
   public static void tearDownAfterClass() throws Exception {
     util.shutdownMiniCluster();
   }
diff --git a/hbase-endpoint/src/test/java/org/apache/hadoop/hbase/coprocessor/TestSecureExport.java b/hbase-endpoint/src/test/java/org/apache/hadoop/hbase/coprocessor/TestSecureExport.java
index bad387a36f3..af11ba2453b 100644
--- a/hbase-endpoint/src/test/java/org/apache/hadoop/hbase/coprocessor/TestSecureExport.java
+++ b/hbase-endpoint/src/test/java/org/apache/hadoop/hbase/coprocessor/TestSecureExport.java
@@ -72,6 +72,7 @@ import org.junit.jupiter.api.AfterAll;
 import org.junit.jupiter.api.AfterEach;
 import org.junit.jupiter.api.BeforeAll;
 import org.junit.jupiter.api.BeforeEach;
+import org.junit.jupiter.api.Disabled;
 import org.junit.jupiter.api.Tag;
 import org.junit.jupiter.api.Test;
 import org.junit.jupiter.api.TestInfo;
@@ -302,7 +303,7 @@ public class TestSecureExport {
   }
 
   @Test
-  @org.junit.Ignore // See HBASE-23990
+  @Disabled // See HBASE-23990
   public void testVisibilityLabels() throws IOException, Throwable {
     final String exportTable = methodName + "_export";
     final String importTable = methodName + "_import";
diff --git a/hbase-examples/src/test/java/org/apache/hadoop/hbase/coprocessor/example/row/stats/TestRowStatisticsEventHandler.java b/hbase-examples/src/test/java/org/apache/hadoop/hbase/coprocessor/example/row/stats/TestRowStatisticsEventHandler.java
index 423f23073a7..fff85cd173f 100644
--- a/hbase-examples/src/test/java/org/apache/hadoop/hbase/coprocessor/example/row/stats/TestRowStatisticsEventHandler.java
+++ b/hbase-examples/src/test/java/org/apache/hadoop/hbase/coprocessor/example/row/stats/TestRowStatisticsEventHandler.java
@@ -17,7 +17,7 @@
  */
 package org.apache.hadoop.hbase.coprocessor.example.row.stats;
 
-import static org.junit.Assert.assertEquals;
+import static org.junit.jupiter.api.Assertions.assertEquals;
 import static org.mockito.ArgumentMatchers.any;
 import static org.mockito.Mockito.doNothing;
 import static org.mockito.Mockito.doThrow;
@@ -36,9 +36,9 @@ import org.apache.hadoop.hbase.metrics.Counter;
 import org.apache.hadoop.hbase.metrics.impl.CounterImpl;
 import org.apache.hadoop.hbase.testclassification.SmallTests;
 import org.apache.hadoop.hbase.util.Bytes;
-import org.junit.Before;
-import org.junit.Test;
+import org.junit.jupiter.api.BeforeEach;
 import org.junit.jupiter.api.Tag;
+import org.junit.jupiter.api.Test;
 
 @Tag(SmallTests.TAG)
 public class TestRowStatisticsEventHandler {
@@ -53,7 +53,7 @@ public class TestRowStatisticsEventHandler {
   private Counter failureCounter;
   private RowStatisticsEventHandler eventHandler;
 
-  @Before
+  @BeforeEach
   public void setup() {
     bufferedMutator = mock(BufferedMutator.class);
     failureCounter = new CounterImpl();
diff --git a/hbase-http/pom.xml b/hbase-http/pom.xml
index 3ac63e7f165..9ebe3946800 100644
--- a/hbase-http/pom.xml
+++ b/hbase-http/pom.xml
@@ -377,71 +377,6 @@
           <artifactId>kerb-simplekdc</artifactId>
           <scope>test</scope>
         </dependency>
-        <!--
-          The LDAP tests below are excluded from compilation/execution under Hadoop 2 (see
-          HBASE-28368). However, the aggregate "Test Javadoc" report runs under this default
-          profile and reads those test sources via -sourcepath, so the ApacheDS API packages
-          they import must be present on the javadoc classpath or the report fails to
-          resolve the imports.
-        -->
-        <dependency>
-          <groupId>org.apache.directory.server</groupId>
-          <artifactId>apacheds-core</artifactId>
-          <version>${apacheds.version}</version>
-          <scope>test</scope>
-          <exclusions>
-            <exclusion>
-              <groupId>org.bouncycastle</groupId>
-              <artifactId>bcprov-jdk15on</artifactId>
-            </exclusion>
-            <exclusion>
-              <groupId>org.bouncycastle</groupId>
-              <artifactId>bcpkix-jdk15on</artifactId>
-            </exclusion>
-          </exclusions>
-        </dependency>
-        <dependency>
-          <groupId>org.apache.directory.server</groupId>
-          <artifactId>apacheds-protocol-ldap</artifactId>
-          <version>${apacheds.version}</version>
-          <scope>test</scope>
-          <exclusions>
-            <exclusion>
-              <groupId>org.bouncycastle</groupId>
-              <artifactId>bcprov-jdk15on</artifactId>
-            </exclusion>
-          </exclusions>
-        </dependency>
-        <dependency>
-          <groupId>org.apache.directory.server</groupId>
-          <artifactId>apacheds-ldif-partition</artifactId>
-          <version>${apacheds.version}</version>
-          <scope>test</scope>
-        </dependency>
-        <dependency>
-          <groupId>org.apache.directory.api</groupId>
-          <artifactId>api-ldap-codec-core</artifactId>
-          <version>${ldap-api.version}</version>
-          <scope>test</scope>
-        </dependency>
-        <dependency>
-          <groupId>org.apache.directory.api</groupId>
-          <artifactId>api-ldap-model</artifactId>
-          <version>${ldap-api.version}</version>
-          <scope>test</scope>
-        </dependency>
-        <dependency>
-          <groupId>org.apache.directory.server</groupId>
-          <artifactId>apacheds-server-integ</artifactId>
-          <version>${apacheds.version}</version>
-          <scope>test</scope>
-          <exclusions>
-            <exclusion>
-              <groupId>log4j</groupId>
-              <artifactId>log4j</artifactId>
-            </exclusion>
-          </exclusions>
-        </dependency>
       </dependencies>
       <build>
         <plugins>
@@ -529,61 +464,8 @@
         </dependency>
         <dependency>
           <groupId>org.apache.directory.server</groupId>
-          <artifactId>apacheds-core</artifactId>
-          <version>${apacheds.version}</version>
-          <scope>test</scope>
-          <exclusions>
-            <exclusion>
-              <groupId>org.bouncycastle</groupId>
-              <artifactId>bcprov-jdk15on</artifactId>
-            </exclusion>
-            <exclusion>
-              <groupId>org.bouncycastle</groupId>
-              <artifactId>bcpkix-jdk15on</artifactId>
-            </exclusion>
-          </exclusions>
-        </dependency>
-        <dependency>
-          <groupId>org.apache.directory.server</groupId>
-          <artifactId>apacheds-protocol-ldap</artifactId>
-          <version>${apacheds.version}</version>
-          <scope>test</scope>
-          <exclusions>
-            <exclusion>
-              <groupId>org.bouncycastle</groupId>
-              <artifactId>bcprov-jdk15on</artifactId>
-            </exclusion>
-          </exclusions>
-        </dependency>
-        <dependency>
-          <groupId>org.apache.directory.server</groupId>
-          <artifactId>apacheds-ldif-partition</artifactId>
-          <version>${apacheds.version}</version>
-          <scope>test</scope>
-        </dependency>
-        <dependency>
-          <groupId>org.apache.directory.api</groupId>
-          <artifactId>api-ldap-codec-core</artifactId>
-          <version>${ldap-api.version}</version>
-          <scope>test</scope>
-        </dependency>
-        <dependency>
-          <groupId>org.apache.directory.api</groupId>
-          <artifactId>api-ldap-model</artifactId>
-          <version>${ldap-api.version}</version>
-          <scope>test</scope>
-        </dependency>
-        <dependency>
-          <groupId>org.apache.directory.server</groupId>
-          <artifactId>apacheds-server-integ</artifactId>
-          <version>${apacheds.version}</version>
+          <artifactId>apacheds-all</artifactId>
           <scope>test</scope>
-          <exclusions>
-            <exclusion>
-              <groupId>log4j</groupId>
-              <artifactId>log4j</artifactId>
-            </exclusion>
-          </exclusions>
         </dependency>
       </dependencies>
       <build>
diff --git a/hbase-it/pom.xml b/hbase-it/pom.xml
index b4821a74d4b..b84ebb6af5d 100644
--- a/hbase-it/pom.xml
+++ b/hbase-it/pom.xml
@@ -200,6 +200,11 @@
       <artifactId>junit-jupiter-params</artifactId>
       <scope>test</scope>
     </dependency>
+    <dependency>
+      <groupId>org.junit.platform</groupId>
+      <artifactId>junit-platform-launcher</artifactId>
+      <scope>test</scope>
+    </dependency>
     <dependency>
       <groupId>org.hamcrest</groupId>
       <artifactId>hamcrest-core</artifactId>
diff --git a/hbase-it/src/test/java/org/apache/hadoop/hbase/IntegrationTestDDLMasterFailover.java b/hbase-it/src/test/java/org/apache/hadoop/hbase/IntegrationTestDDLMasterFailover.java
index bdd7a681fe6..19c6d67db3e 100644
--- a/hbase-it/src/test/java/org/apache/hadoop/hbase/IntegrationTestDDLMasterFailover.java
+++ b/hbase-it/src/test/java/org/apache/hadoop/hbase/IntegrationTestDDLMasterFailover.java
@@ -17,7 +17,11 @@
  */
 package org.apache.hadoop.hbase;
 
+import static org.junit.jupiter.api.Assertions.assertEquals;
+import static org.junit.jupiter.api.Assertions.assertFalse;
+import static org.junit.jupiter.api.Assertions.assertNull;
 import static org.junit.jupiter.api.Assertions.assertTrue;
+import static org.junit.jupiter.api.Assertions.fail;
 
 import java.io.IOException;
 import java.util.ArrayList;
@@ -44,9 +48,8 @@ import org.apache.hadoop.hbase.util.HBaseFsck;
 import org.apache.hadoop.hbase.util.Threads;
 import org.apache.hadoop.hbase.util.hbck.HbckTestingUtil;
 import org.apache.hadoop.util.ToolRunner;
-import org.junit.Assert;
-import org.junit.Test;
-import org.junit.experimental.categories.Category;
+import org.junit.jupiter.api.Tag;
+import org.junit.jupiter.api.Test;
 import org.slf4j.Logger;
 import org.slf4j.LoggerFactory;
 
@@ -94,7 +97,7 @@ import org.slf4j.LoggerFactory;
  * -Dhbase.IntegrationTestDDLMasterFailover.numRegions=50 --monkey masterKilling
  */
 
-@Category(IntegrationTests.class)
+@Tag(IntegrationTests.TAG)
 public class IntegrationTestDDLMasterFailover extends IntegrationTestBase {
 
   private static final Logger LOG = LoggerFactory.getLogger(IntegrationTestDDLMasterFailover.class);
@@ -196,8 +199,7 @@ public class IntegrationTestDDLMasterFailover extends IntegrationTestBase {
         assertTrue(admin.getNamespaceDescriptor(nsName) != null,
           "Namespace: " + nsName + " in namespaceMap does not exist");
       } catch (NamespaceNotFoundException nsnfe) {
-        Assert
-          .fail("Namespace: " + nsName + " in namespaceMap does not exist: " + nsnfe.getMessage());
+        fail("Namespace: " + nsName + " in namespaceMap does not exist: " + nsnfe.getMessage());
       }
     }
     admin.close();
@@ -216,8 +218,8 @@ public class IntegrationTestDDLMasterFailover extends IntegrationTestBase {
         "Table: " + tableName + " in disabledTables is not disabled");
     }
     for (TableName tableName : deletedTables.keySet()) {
-      Assert.assertFalse("Table: " + tableName + " in deletedTables is not deleted",
-        admin.tableExists(tableName));
+      assertFalse(admin.tableExists(tableName),
+        "Table: " + tableName + " in deletedTables is not deleted");
     }
     admin.close();
   }
@@ -545,7 +547,7 @@ public class IntegrationTestDDLMasterFailover extends IntegrationTestBase {
         TableName tableName = selected.getTableName();
         LOG.info("Deleting table :" + selected);
         admin.deleteTable(tableName);
-        Assert.assertFalse("Table: " + selected + " was not deleted", admin.tableExists(tableName));
+        assertFalse(admin.tableExists(tableName), "Table: " + selected + " was not deleted");
         deletedTables.put(tableName, selected);
         LOG.info("Deleted table :" + selected);
       } catch (Exception e) {
@@ -644,10 +646,10 @@ public class IntegrationTestDDLMasterFailover extends IntegrationTestBase {
         TableDescriptor freshTableDesc = admin.getDescriptor(tableName);
         ColumnFamilyDescriptor freshColumnDesc =
           freshTableDesc.getColumnFamily(columnDesc.getName());
-        Assert.assertEquals("Column family: " + columnDesc + " was not altered",
-          freshColumnDesc.getMaxVersions(), versions);
-        Assert.assertEquals("Column family: " + freshColumnDesc + " was not altered",
-          freshColumnDesc.getMinVersions(), versions);
+        assertEquals(freshColumnDesc.getMaxVersions(), versions,
+          "Column family: " + columnDesc + " was not altered");
+        assertEquals(freshColumnDesc.getMinVersions(), versions,
+          "Column family: " + freshColumnDesc + " was not altered");
         assertTrue(admin.isTableDisabled(tableName),
           "After alter versions of column family, Table: " + tableName + " is not disabled");
         disabledTables.put(tableName, freshTableDesc);
@@ -695,11 +697,10 @@ public class IntegrationTestDDLMasterFailover extends IntegrationTestBase {
         TableDescriptor freshTableDesc = admin.getTableDescriptor(tableName);
         ColumnFamilyDescriptor freshColumnDesc =
           freshTableDesc.getColumnFamily(columnDesc.getName());
-        Assert.assertEquals("Encoding of column family: " + columnDesc + " was not altered",
-          freshColumnDesc.getDataBlockEncoding().getId(), id);
-        Assert.assertTrue(
-          "After alter encoding of column family, Table: " + tableName + " is not disabled",
-          admin.isTableDisabled(tableName));
+        assertEquals(freshColumnDesc.getDataBlockEncoding().getId(), id,
+          "Encoding of column family: " + columnDesc + " was not altered");
+        assertTrue(admin.isTableDisabled(tableName),
+          "After alter encoding of column family, Table: " + tableName + " is not disabled");
         disabledTables.put(tableName, freshTableDesc);
         LOG.info("Altered encoding of column family: " + freshColumnDesc + " to: " + id
           + " in table: " + tableName);
@@ -733,10 +734,10 @@ public class IntegrationTestDDLMasterFailover extends IntegrationTestBase {
         admin.deleteColumnFamily(tableName, cfd.getName());
         // assertion
         TableDescriptor freshTableDesc = admin.getDescriptor(tableName);
-        Assert.assertFalse("Column family: " + cfd + " was not added",
-          freshTableDesc.hasColumnFamily(cfd.getName()));
-        Assert.assertTrue("After delete column family, Table: " + tableName + " is not disabled",
-          admin.isTableDisabled(tableName));
+        assertFalse(freshTableDesc.hasColumnFamily(cfd.getName()),
+          "Column family: " + cfd + " was not added");
+        assertTrue(admin.isTableDisabled(tableName),
+          "After delete column family, Table: " + tableName + " is not disabled");
         disabledTables.put(tableName, freshTableDesc);
         LOG.info("Deleted column family: " + cfd + " from table: " + tableName);
       } catch (Exception e) {
@@ -784,8 +785,8 @@ public class IntegrationTestDDLMasterFailover extends IntegrationTestBase {
           table.put(put);
         }
         TableDescriptor freshTableDesc = admin.getDescriptor(tableName);
-        Assert.assertTrue("After insert, Table: " + tableName + " in not enabled",
-          admin.isTableEnabled(tableName));
+        assertTrue(admin.isTableEnabled(tableName),
+          "After insert, Table: " + tableName + " in not enabled");
         enabledTables.put(tableName, freshTableDesc);
         LOG.info("Added " + numRows + " rows to table: " + selected);
       } catch (Exception e) {
@@ -898,11 +899,9 @@ public class IntegrationTestDDLMasterFailover extends IntegrationTestBase {
     for (Worker worker : workers) {
       Exception e = worker.getSavedException();
       if (e != null) {
-        LOG.error("Found exception in thread: " + worker.getName());
-        e.printStackTrace();
+        LOG.error("Found exception in thread: " + worker.getName(), e);
       }
-      Assert.assertNull("Action failed: " + worker.getAction() + " in thread: " + worker.getName(),
-        e);
+      assertNull(e, "Action failed: " + worker.getAction() + " in thread: " + worker.getName());
     }
   }
 
diff --git a/hbase-it/src/test/java/org/apache/hadoop/hbase/IntegrationTestRegionReplicaReplication.java b/hbase-it/src/test/java/org/apache/hadoop/hbase/IntegrationTestRegionReplicaReplication.java
index 9462d0a47a9..ba2ad27629e 100644
--- a/hbase-it/src/test/java/org/apache/hadoop/hbase/IntegrationTestRegionReplicaReplication.java
+++ b/hbase-it/src/test/java/org/apache/hadoop/hbase/IntegrationTestRegionReplicaReplication.java
@@ -17,6 +17,8 @@
  */
 package org.apache.hadoop.hbase;
 
+import static org.junit.jupiter.api.Assertions.fail;
+
 import java.io.IOException;
 import java.util.List;
 import java.util.concurrent.BlockingQueue;
@@ -34,9 +36,8 @@ import org.apache.hadoop.hbase.util.Threads;
 import org.apache.hadoop.hbase.util.test.LoadTestDataGenerator;
 import org.apache.hadoop.util.StringUtils;
 import org.apache.hadoop.util.ToolRunner;
-import org.junit.Assert;
-import org.junit.Test;
-import org.junit.experimental.categories.Category;
+import org.junit.jupiter.api.Tag;
+import org.junit.jupiter.api.Test;
 
 import org.apache.hbase.thirdparty.com.google.common.collect.Lists;
 
@@ -67,7 +68,7 @@ import org.apache.hbase.thirdparty.com.google.common.collect.Lists;
  * -DIntegrationTestRegionReplicaReplication.num_write_threads=100
  * </pre>
  */
-@Category(IntegrationTests.class)
+@Tag(IntegrationTests.TAG)
 public class IntegrationTestRegionReplicaReplication extends IntegrationTestIngest {
 
   private static final String TEST_NAME =
@@ -194,7 +195,7 @@ public class IntegrationTestRegionReplicaReplication extends IntegrationTestInge
       if (0 != ret) {
         String errorMsg = "Load failed with error code " + ret;
         LOG.error(errorMsg);
-        Assert.fail(errorMsg);
+        fail(errorMsg);
       }
 
       args = Lists.newArrayList(getArgsForLoadTestTool("", "", startKey, numKeys));
@@ -211,7 +212,7 @@ public class IntegrationTestRegionReplicaReplication extends IntegrationTestInge
       if (0 != ret) {
         String errorMsg = "Load failed with error code " + ret;
         LOG.error(errorMsg);
-        Assert.fail(errorMsg);
+        fail(errorMsg);
       }
       startKey += numKeys;
     }
diff --git a/hbase-it/src/test/java/org/apache/hadoop/hbase/IntegrationTestsDriver.java b/hbase-it/src/test/java/org/apache/hadoop/hbase/IntegrationTestsDriver.java
index dcc2e3234da..bbe900ffff8 100644
--- a/hbase-it/src/test/java/org/apache/hadoop/hbase/IntegrationTestsDriver.java
+++ b/hbase-it/src/test/java/org/apache/hadoop/hbase/IntegrationTestsDriver.java
@@ -18,14 +18,20 @@
 package org.apache.hadoop.hbase;
 
 import java.io.IOException;
+import java.io.PrintWriter;
 import java.util.Set;
 import java.util.regex.Pattern;
 import org.apache.hadoop.hbase.testclassification.IntegrationTests;
 import org.apache.hadoop.hbase.util.AbstractHBaseTool;
 import org.apache.hadoop.util.ToolRunner;
-import org.junit.internal.TextListener;
-import org.junit.runner.JUnitCore;
-import org.junit.runner.Result;
+import org.junit.platform.engine.DiscoverySelector;
+import org.junit.platform.engine.discovery.DiscoverySelectors;
+import org.junit.platform.launcher.Launcher;
+import org.junit.platform.launcher.LauncherDiscoveryRequest;
+import org.junit.platform.launcher.core.LauncherDiscoveryRequestBuilder;
+import org.junit.platform.launcher.core.LauncherFactory;
+import org.junit.platform.launcher.listeners.SummaryGeneratingListener;
+import org.junit.platform.launcher.listeners.TestExecutionSummary;
 import org.slf4j.Logger;
 import org.slf4j.LoggerFactory;
 
@@ -95,6 +101,23 @@ public class IntegrationTestsDriver extends AbstractHBaseTool {
     return classes.toArray(new Class<?>[classes.size()]);
   }
 
+  private static int runTests(Class<?>[] classes) {
+    DiscoverySelector[] selectors = new DiscoverySelector[classes.length];
+    for (int i = 0; i < classes.length; i++) {
+      selectors[i] = DiscoverySelectors.selectClass(classes[i]);
+    }
+    LauncherDiscoveryRequest request =
+      LauncherDiscoveryRequestBuilder.request().selectors(selectors).build();
+    Launcher launcher = LauncherFactory.create();
+    SummaryGeneratingListener listener = new SummaryGeneratingListener();
+    launcher.registerTestExecutionListeners(listener);
+    launcher.execute(request);
+
+    TestExecutionSummary summary = listener.getSummary();
+    summary.printTo(new PrintWriter(System.out));
+    return summary.getTotalFailureCount() > 0 ? 1 : 0;
+  }
+
   @Override
   protected int doWork() throws Exception {
     // this is called from the command line, so we should set to use the distributed cluster
@@ -104,10 +127,6 @@ public class IntegrationTestsDriver extends AbstractHBaseTool {
     for (Class<?> aClass : classes) {
       LOG.info("  " + aClass);
     }
-    JUnitCore junit = new JUnitCore();
-    junit.addListener(new TextListener(System.out));
-    Result result = junit.run(classes);
-
-    return result.wasSuccessful() ? 0 : 1;
+    return runTests(classes);
   }
 }
diff --git a/hbase-it/src/test/java/org/apache/hadoop/hbase/StripeCompactionsPerformanceEvaluation.java b/hbase-it/src/test/java/org/apache/hadoop/hbase/StripeCompactionsPerformanceEvaluation.java
index 9c1b0fed4cc..1c59ba35df3 100644
--- a/hbase-it/src/test/java/org/apache/hadoop/hbase/StripeCompactionsPerformanceEvaluation.java
+++ b/hbase-it/src/test/java/org/apache/hadoop/hbase/StripeCompactionsPerformanceEvaluation.java
@@ -17,6 +17,8 @@
  */
 package org.apache.hadoop.hbase;
 
+import static org.junit.jupiter.api.Assertions.assertTrue;
+
 import java.io.IOException;
 import java.util.List;
 import java.util.Locale;
@@ -38,7 +40,6 @@ import org.apache.hadoop.hbase.util.MultiThreadedWriter;
 import org.apache.hadoop.hbase.util.RegionSplitter;
 import org.apache.hadoop.hbase.util.test.LoadTestDataGenerator;
 import org.apache.yetus.audience.InterfaceAudience;
-import org.junit.Assert;
 import org.slf4j.Logger;
 import org.slf4j.LoggerFactory;
 
@@ -257,7 +258,7 @@ public class StripeCompactionsPerformanceEvaluation extends AbstractHBaseTool {
      */
     status(description + " test took "
       + (EnvironmentEdgeManager.currentTime() - testStartTime) / 1000 + "sec");
-    Assert.assertTrue(success);
+    assertTrue(success);
   }
 
   private static void status(String s) {
diff --git a/hbase-it/src/test/java/org/apache/hadoop/hbase/chaos/actions/UnbalanceKillAndRebalanceAction.java b/hbase-it/src/test/java/org/apache/hadoop/hbase/chaos/actions/UnbalanceKillAndRebalanceAction.java
index 3a0f292e4a4..d46644f45d2 100644
--- a/hbase-it/src/test/java/org/apache/hadoop/hbase/chaos/actions/UnbalanceKillAndRebalanceAction.java
+++ b/hbase-it/src/test/java/org/apache/hadoop/hbase/chaos/actions/UnbalanceKillAndRebalanceAction.java
@@ -17,6 +17,8 @@
  */
 package org.apache.hadoop.hbase.chaos.actions;
 
+import static org.junit.jupiter.api.Assertions.assertTrue;
+
 import java.util.ArrayList;
 import java.util.HashSet;
 import java.util.List;
@@ -25,7 +27,6 @@ import java.util.Set;
 import java.util.concurrent.ThreadLocalRandom;
 import org.apache.hadoop.hbase.ClusterMetrics;
 import org.apache.hadoop.hbase.ServerName;
-import org.junit.Assert;
 import org.slf4j.Logger;
 import org.slf4j.LoggerFactory;
 
@@ -69,8 +70,8 @@ public class UnbalanceKillAndRebalanceAction extends Action {
     Set<ServerName> killedServers = new HashSet<>();
     int liveCount = (int) Math.ceil(FRC_SERVERS_THAT_HOARD_AND_LIVE * victimServers.size());
     int deadCount = (int) Math.ceil(FRC_SERVERS_THAT_HOARD_AND_DIE * victimServers.size());
-    Assert.assertTrue("There are not enough victim servers: " + victimServers.size(),
-      liveCount + deadCount < victimServers.size());
+    assertTrue(liveCount + deadCount < victimServers.size(),
+      "There are not enough victim servers: " + victimServers.size());
     Random rand = ThreadLocalRandom.current();
     List<ServerName> targetServers = new ArrayList<>(liveCount);
     for (int i = 0; i < liveCount + deadCount; ++i) {
diff --git a/hbase-it/src/test/java/org/apache/hadoop/hbase/client/TestConnectionImplementationCacheMasterState.java b/hbase-it/src/test/java/org/apache/hadoop/hbase/client/TestConnectionImplementationCacheMasterState.java
index e12207e7d92..a57b11f9290 100644
--- a/hbase-it/src/test/java/org/apache/hadoop/hbase/client/TestConnectionImplementationCacheMasterState.java
+++ b/hbase-it/src/test/java/org/apache/hadoop/hbase/client/TestConnectionImplementationCacheMasterState.java
@@ -17,41 +17,36 @@
  */
 package org.apache.hadoop.hbase.client;
 
+import static org.junit.jupiter.api.Assertions.assertFalse;
+
 import java.io.IOException;
 import java.lang.reflect.InvocationTargetException;
 import java.lang.reflect.Method;
 import java.lang.reflect.UndeclaredThrowableException;
 import org.apache.commons.lang3.reflect.FieldUtils;
 import org.apache.hadoop.conf.Configuration;
-import org.apache.hadoop.hbase.HBaseClassTestRule;
 import org.apache.hadoop.hbase.IntegrationTestingUtility;
 import org.apache.hadoop.hbase.security.UserProvider;
 import org.apache.hadoop.hbase.testclassification.ClientTests;
 import org.apache.hadoop.hbase.testclassification.MediumTests;
-import org.junit.AfterClass;
-import org.junit.Assert;
-import org.junit.BeforeClass;
-import org.junit.ClassRule;
-import org.junit.Test;
-import org.junit.experimental.categories.Category;
-import org.junit.runner.RunWith;
+import org.junit.jupiter.api.AfterAll;
+import org.junit.jupiter.api.BeforeAll;
+import org.junit.jupiter.api.Tag;
+import org.junit.jupiter.api.Test;
 import org.mockito.Mockito;
-import org.mockito.junit.MockitoJUnitRunner;
 
-@Category({ ClientTests.class, MediumTests.class })
-@RunWith(MockitoJUnitRunner.class)
+@Tag(ClientTests.TAG)
+@Tag(MediumTests.TAG)
 public class TestConnectionImplementationCacheMasterState {
-  @ClassRule
-  public static final HBaseClassTestRule CLASS_RULE =
-    HBaseClassTestRule.forClass(TestConnectionImplementationCacheMasterState.class);
+
   private static final IntegrationTestingUtility TEST_UTIL = new IntegrationTestingUtility();
 
-  @BeforeClass
+  @BeforeAll
   public static void beforeClass() throws Exception {
     TEST_UTIL.startMiniCluster(1);
   }
 
-  @AfterClass
+  @AfterAll
   public static void afterClass() throws Exception {
     TEST_UTIL.shutdownMiniCluster();
   }
@@ -117,7 +112,7 @@ public class TestConnectionImplementationCacheMasterState {
     // Verify that masterState is "false" because of to injected exception
     boolean isKeepAliveMasterRunning =
       (boolean) getIsKeepAliveMasterConnectedAndRunningMethod().invoke(conn);
-    Assert.assertFalse(isKeepAliveMasterRunning);
+    assertFalse(isKeepAliveMasterRunning);
     conn.close();
   }
 
@@ -137,7 +132,7 @@ public class TestConnectionImplementationCacheMasterState {
       (boolean) getIsKeepAliveMasterConnectedAndRunningMethod().invoke(conn);
 
     // Verify that masterState is "false" because of to injected exception
-    Assert.assertFalse(isKeepAliveMasterRunning);
+    assertFalse(isKeepAliveMasterRunning);
     conn.close();
   }
 
diff --git a/hbase-it/src/test/java/org/apache/hadoop/hbase/mapreduce/IntegrationTestTableSnapshotInputFormat.java b/hbase-it/src/test/java/org/apache/hadoop/hbase/mapreduce/IntegrationTestTableSnapshotInputFormat.java
index ec11284eb28..a6c795d39c7 100644
--- a/hbase-it/src/test/java/org/apache/hadoop/hbase/mapreduce/IntegrationTestTableSnapshotInputFormat.java
+++ b/hbase-it/src/test/java/org/apache/hadoop/hbase/mapreduce/IntegrationTestTableSnapshotInputFormat.java
@@ -28,9 +28,9 @@ import org.apache.hadoop.hbase.testclassification.IntegrationTests;
 import org.apache.hadoop.hbase.util.Bytes;
 import org.apache.hadoop.hbase.util.EnvironmentEdgeManager;
 import org.apache.hadoop.util.ToolRunner;
-import org.junit.After;
-import org.junit.Before;
-import org.junit.experimental.categories.Category;
+import org.junit.jupiter.api.AfterEach;
+import org.junit.jupiter.api.BeforeEach;
+import org.junit.jupiter.api.Tag;
 import org.slf4j.Logger;
 import org.slf4j.LoggerFactory;
 
@@ -61,7 +61,7 @@ import org.slf4j.LoggerFactory;
  * "IntegrationTestTableSnapshotInputFormat.tableDir" =&gt; temporary directory to restore the
  * snapshot files
  */
-@Category(IntegrationTests.class)
+@Tag(IntegrationTests.TAG)
 // Not runnable as a unit test. See TestTableSnapshotInputFormat
 public class IntegrationTestTableSnapshotInputFormat extends IntegrationTestBase {
   private static final Logger LOG =
@@ -97,7 +97,7 @@ public class IntegrationTestTableSnapshotInputFormat extends IntegrationTestBase
   }
 
   @Override
-  @Before
+  @BeforeEach
   public void setUp() throws Exception {
     super.setUp();
     util = getTestingUtil(getConf());
@@ -106,7 +106,7 @@ public class IntegrationTestTableSnapshotInputFormat extends IntegrationTestBase
   }
 
   @Override
-  @After
+  @AfterEach
   public void cleanUp() throws Exception {
     util.restoreCluster();
   }
diff --git a/hbase-mapreduce/pom.xml b/hbase-mapreduce/pom.xml
index 5d13e76fd4d..83de8419969 100644
--- a/hbase-mapreduce/pom.xml
+++ b/hbase-mapreduce/pom.xml
@@ -220,6 +220,11 @@
       <artifactId>awaitility</artifactId>
       <scope>test</scope>
     </dependency>
+    <dependency>
+      <groupId>org.hamcrest</groupId>
+      <artifactId>hamcrest-library</artifactId>
+      <scope>test</scope>
+    </dependency>
     <dependency>
       <groupId>org.slf4j</groupId>
       <artifactId>jcl-over-slf4j</artifactId>
diff --git a/hbase-mapreduce/src/test/java/org/apache/hadoop/hbase/mapreduce/TestCellBasedImportExport2.java b/hbase-mapreduce/src/test/java/org/apache/hadoop/hbase/mapreduce/TestCellBasedImportExport2.java
index a1d6293d454..7c95090cbb7 100644
--- a/hbase-mapreduce/src/test/java/org/apache/hadoop/hbase/mapreduce/TestCellBasedImportExport2.java
+++ b/hbase-mapreduce/src/test/java/org/apache/hadoop/hbase/mapreduce/TestCellBasedImportExport2.java
@@ -63,7 +63,7 @@ import org.apache.hadoop.hbase.filter.PrefixFilter;
 import org.apache.hadoop.hbase.io.ImmutableBytesWritable;
 import org.apache.hadoop.hbase.mapreduce.Import.CellImporter;
 import org.apache.hadoop.hbase.regionserver.wal.WALActionsListener;
-import org.apache.hadoop.hbase.testclassification.MediumTests;
+import org.apache.hadoop.hbase.testclassification.LargeTests;
 import org.apache.hadoop.hbase.testclassification.VerySlowMapReduceTests;
 import org.apache.hadoop.hbase.util.Bytes;
 import org.apache.hadoop.hbase.util.EnvironmentEdgeManager;
@@ -91,7 +91,7 @@ import org.slf4j.LoggerFactory;
  * Tests the table import and table export MR job functionality
  */
 @Tag(VerySlowMapReduceTests.TAG)
-@Tag(MediumTests.TAG)
+@Tag(LargeTests.TAG)
 public class TestCellBasedImportExport2 {
 
   private static final Logger LOG = LoggerFactory.getLogger(TestCellBasedImportExport2.class);
diff --git a/hbase-rest/pom.xml b/hbase-rest/pom.xml
index 8fdf48403ba..d1f33618692 100644
--- a/hbase-rest/pom.xml
+++ b/hbase-rest/pom.xml
@@ -214,6 +214,11 @@
       <artifactId>junit-jupiter-params</artifactId>
       <scope>test</scope>
     </dependency>
+    <dependency>
+      <groupId>org.hamcrest</groupId>
+      <artifactId>hamcrest-library</artifactId>
+      <scope>test</scope>
+    </dependency>
     <dependency>
       <groupId>org.mockito</groupId>
       <artifactId>mockito-core</artifactId>
diff --git a/hbase-rest/src/test/java/org/apache/hadoop/hbase/rest/TestStatusResource.java b/hbase-rest/src/test/java/org/apache/hadoop/hbase/rest/TestStatusResource.java
index 77c7b079831..2c87f14f6eb 100644
--- a/hbase-rest/src/test/java/org/apache/hadoop/hbase/rest/TestStatusResource.java
+++ b/hbase-rest/src/test/java/org/apache/hadoop/hbase/rest/TestStatusResource.java
@@ -17,10 +17,10 @@
  */
 package org.apache.hadoop.hbase.rest;
 
-import static org.junit.Assert.assertTrue;
 import static org.junit.jupiter.api.Assertions.assertEquals;
 import static org.junit.jupiter.api.Assertions.assertFalse;
 import static org.junit.jupiter.api.Assertions.assertNotNull;
+import static org.junit.jupiter.api.Assertions.assertTrue;
 
 import java.io.ByteArrayInputStream;
 import java.io.IOException;
@@ -56,7 +56,7 @@ public class TestStatusResource {
 
   private static void validate(StorageClusterStatusModel model) {
     assertNotNull(model);
-    assertTrue(model.getRegions() + ">= 1", model.getRegions() >= 1);
+    assertTrue(model.getRegions() >= 1, model.getRegions() + ">= 1");
     assertTrue(model.getRequests() >= 0);
     assertTrue(model.getAverageLoad() >= 0.0);
     assertNotNull(model.getLiveNodes());
diff --git a/hbase-rsgroup/pom.xml b/hbase-rsgroup/pom.xml
index aedb6cfe90a..927157ddbc5 100644
--- a/hbase-rsgroup/pom.xml
+++ b/hbase-rsgroup/pom.xml
@@ -175,11 +175,6 @@
       <artifactId>junit-jupiter-params</artifactId>
       <scope>test</scope>
     </dependency>
-    <dependency>
-      <groupId>org.junit.vintage</groupId>
-      <artifactId>junit-vintage-engine</artifactId>
-      <scope>test</scope>
-    </dependency>
   </dependencies>
   <build>
     <plugins>
diff --git a/hbase-rsgroup/src/test/java/org/apache/hadoop/hbase/rsgroup/TestDetermineRSGroupInfoForTable.java b/hbase-rsgroup/src/test/java/org/apache/hadoop/hbase/rsgroup/TestDetermineRSGroupInfoForTable.java
index 4a9bdce6d80..389bc3f4606 100644
--- a/hbase-rsgroup/src/test/java/org/apache/hadoop/hbase/rsgroup/TestDetermineRSGroupInfoForTable.java
+++ b/hbase-rsgroup/src/test/java/org/apache/hadoop/hbase/rsgroup/TestDetermineRSGroupInfoForTable.java
@@ -17,16 +17,15 @@
  */
 package org.apache.hadoop.hbase.rsgroup;
 
-import static org.junit.Assert.assertEquals;
-import static org.junit.Assert.assertTrue;
-import static org.mockito.Mockito.anyString;
+import static org.junit.jupiter.api.Assertions.assertEquals;
+import static org.junit.jupiter.api.Assertions.assertTrue;
+import static org.mockito.ArgumentMatchers.anyString;
 import static org.mockito.Mockito.mock;
 import static org.mockito.Mockito.when;
 
 import java.io.IOException;
 import java.util.Collections;
 import java.util.List;
-import org.apache.hadoop.hbase.HBaseClassTestRule;
 import org.apache.hadoop.hbase.HBaseTestingUtility;
 import org.apache.hadoop.hbase.HConstants;
 import org.apache.hadoop.hbase.NamespaceDescriptor;
@@ -38,26 +37,17 @@ import org.apache.hadoop.hbase.master.HMaster;
 import org.apache.hadoop.hbase.regionserver.HRegionServer;
 import org.apache.hadoop.hbase.rsgroup.RSGroupInfoManagerImpl.RSGroupMappingScript;
 import org.apache.hadoop.hbase.testclassification.MediumTests;
-import org.junit.AfterClass;
-import org.junit.BeforeClass;
-import org.junit.ClassRule;
-import org.junit.Test;
-import org.junit.experimental.categories.Category;
-import org.slf4j.Logger;
-import org.slf4j.LoggerFactory;
+import org.junit.jupiter.api.AfterAll;
+import org.junit.jupiter.api.BeforeAll;
+import org.junit.jupiter.api.Tag;
+import org.junit.jupiter.api.Test;
 
 /**
  * Test {@link RSGroupInfoManager#determineRSGroupInfoForTable(TableName)}
  */
-@Category({ MediumTests.class })
+@Tag(MediumTests.TAG)
 public class TestDetermineRSGroupInfoForTable {
 
-  private static final Logger LOG = LoggerFactory.getLogger(TestDetermineRSGroupInfoForTable.class);
-
-  @ClassRule
-  public static final HBaseClassTestRule CLASS_RULE =
-    HBaseClassTestRule.forClass(TestDetermineRSGroupInfoForTable.class);
-
   private static final HBaseTestingUtility UTIL = new HBaseTestingUtility();
 
   private static HMaster master;
@@ -75,7 +65,7 @@ public class TestDetermineRSGroupInfoForTable {
 
   private static final TableName TABLE_NAME = TableName.valueOf(NAMESPACE_NAME, "tb");
 
-  @BeforeClass
+  @BeforeAll
   public static void setUp() throws Exception {
     UTIL.getConfiguration().set(HConstants.HBASE_MASTER_LOADBALANCER_CLASS,
       RSGroupBasedLoadBalancer.class.getName());
@@ -103,7 +93,7 @@ public class TestDetermineRSGroupInfoForTable {
     admin.createNamespace(NamespaceDescriptor.create(OTHER_NAMESPACE_NAME).build());
   }
 
-  @AfterClass
+  @AfterAll
   public static void tearDown() throws Exception {
     admin.deleteNamespace(NAMESPACE_NAME);
 
diff --git a/hbase-rsgroup/src/test/java/org/apache/hadoop/hbase/rsgroup/TestRSGroupUtil.java b/hbase-rsgroup/src/test/java/org/apache/hadoop/hbase/rsgroup/TestRSGroupUtil.java
index eddb7a15388..52eea611e80 100644
--- a/hbase-rsgroup/src/test/java/org/apache/hadoop/hbase/rsgroup/TestRSGroupUtil.java
+++ b/hbase-rsgroup/src/test/java/org/apache/hadoop/hbase/rsgroup/TestRSGroupUtil.java
@@ -17,13 +17,12 @@
  */
 package org.apache.hadoop.hbase.rsgroup;
 
-import static org.junit.Assert.assertFalse;
-import static org.junit.Assert.assertTrue;
+import static org.junit.jupiter.api.Assertions.assertFalse;
+import static org.junit.jupiter.api.Assertions.assertTrue;
 
 import java.io.IOException;
 import java.util.Collections;
 import java.util.List;
-import org.apache.hadoop.hbase.HBaseClassTestRule;
 import org.apache.hadoop.hbase.HBaseTestingUtility;
 import org.apache.hadoop.hbase.HConstants;
 import org.apache.hadoop.hbase.Waiter.Predicate;
@@ -31,22 +30,13 @@ import org.apache.hadoop.hbase.coprocessor.CoprocessorHost;
 import org.apache.hadoop.hbase.master.HMaster;
 import org.apache.hadoop.hbase.regionserver.HRegionServer;
 import org.apache.hadoop.hbase.testclassification.MediumTests;
-import org.junit.AfterClass;
-import org.junit.BeforeClass;
-import org.junit.ClassRule;
-import org.junit.Test;
-import org.junit.experimental.categories.Category;
-import org.slf4j.Logger;
-import org.slf4j.LoggerFactory;
-
-@Category({ MediumTests.class })
-public class TestRSGroupUtil {
-
-  @ClassRule
-  public static final HBaseClassTestRule CLASS_RULE =
-    HBaseClassTestRule.forClass(TestRSGroupUtil.class);
+import org.junit.jupiter.api.AfterAll;
+import org.junit.jupiter.api.BeforeAll;
+import org.junit.jupiter.api.Tag;
+import org.junit.jupiter.api.Test;
 
-  private static final Logger LOG = LoggerFactory.getLogger(TestRSGroupUtil.class);
+@Tag(MediumTests.TAG)
+public class TestRSGroupUtil {
 
   private static final HBaseTestingUtility UTIL = new HBaseTestingUtility();
 
@@ -58,7 +48,7 @@ public class TestRSGroupUtil {
 
   private static RSGroupInfoManager rsGroupInfoManager;
 
-  @BeforeClass
+  @BeforeAll
   public static void setUp() throws Exception {
     UTIL.getConfiguration().set(HConstants.HBASE_MASTER_LOADBALANCER_CLASS,
       RSGroupBasedLoadBalancer.class.getName());
@@ -78,7 +68,7 @@ public class TestRSGroupUtil {
     rsGroupInfoManager = cps.get(0).getGroupInfoManager();
   }
 
-  @AfterClass
+  @AfterAll
   public static void tearDown() throws Exception {
     UTIL.shutdownMiniCluster();
   }
diff --git a/hbase-rsgroup/src/test/java/org/apache/hadoop/hbase/rsgroup/VerifyingRSGroupAdminClient.java b/hbase-rsgroup/src/test/java/org/apache/hadoop/hbase/rsgroup/VerifyingRSGroupAdminClient.java
index e1ca06e5528..963bae1889d 100644
--- a/hbase-rsgroup/src/test/java/org/apache/hadoop/hbase/rsgroup/VerifyingRSGroupAdminClient.java
+++ b/hbase-rsgroup/src/test/java/org/apache/hadoop/hbase/rsgroup/VerifyingRSGroupAdminClient.java
@@ -17,6 +17,9 @@
  */
 package org.apache.hadoop.hbase.rsgroup;
 
+import static org.junit.jupiter.api.Assertions.assertEquals;
+import static org.junit.jupiter.api.Assertions.assertTrue;
+
 import java.io.ByteArrayInputStream;
 import java.io.IOException;
 import java.util.List;
@@ -39,7 +42,6 @@ import org.apache.hadoop.hbase.zookeeper.ZKWatcher;
 import org.apache.hadoop.hbase.zookeeper.ZNodePaths;
 import org.apache.yetus.audience.InterfaceAudience;
 import org.apache.zookeeper.KeeperException;
-import org.junit.Assert;
 
 import org.apache.hbase.thirdparty.com.google.common.collect.Maps;
 import org.apache.hbase.thirdparty.com.google.common.collect.Sets;
@@ -148,8 +150,7 @@ public class VerifyingRSGroupAdminClient implements RSGroupAdmin {
         .getValue(RSGroupInfoManager.META_FAMILY_BYTES, RSGroupInfoManager.META_QUALIFIER_BYTES));
       groupMap.put(proto.getName(), RSGroupProtobufUtil.toGroupInfo(proto));
     }
-    Assert.assertEquals(Sets.newHashSet(groupMap.values()),
-      Sets.newHashSet(wrapped.listRSGroups()));
+    assertEquals(Sets.newHashSet(groupMap.values()), Sets.newHashSet(wrapped.listRSGroups()));
     try {
       String groupBasePath = ZNodePaths.joinZNode(zkw.getZNodePaths().baseZNode, "rsgroup");
       for (String znode : ZKUtil.listChildrenNoWatch(zkw, groupBasePath)) {
@@ -161,9 +162,9 @@ public class VerifyingRSGroupAdminClient implements RSGroupAdmin {
           zList.add(RSGroupProtobufUtil.toGroupInfo(RSGroupProtos.RSGroupInfo.parseFrom(bis)));
         }
       }
-      Assert.assertEquals(zList.size(), groupMap.size());
+      assertEquals(zList.size(), groupMap.size());
       for (RSGroupInfo RSGroupInfo : zList) {
-        Assert.assertTrue(groupMap.get(RSGroupInfo.getName()).equals(RSGroupInfo));
+        assertTrue(groupMap.get(RSGroupInfo.getName()).equals(RSGroupInfo));
       }
     } catch (KeeperException e) {
       throw new IOException("ZK verification failed", e);
diff --git a/hbase-server/pom.xml b/hbase-server/pom.xml
index b01a516ea8b..723d1da788d 100644
--- a/hbase-server/pom.xml
+++ b/hbase-server/pom.xml
@@ -309,11 +309,6 @@
       <artifactId>junit-jupiter-params</artifactId>
       <scope>test</scope>
     </dependency>
-    <dependency>
-      <groupId>org.junit.vintage</groupId>
-      <artifactId>junit-vintage-engine</artifactId>
-      <scope>test</scope>
-    </dependency>
     <dependency>
       <groupId>org.awaitility</groupId>
       <artifactId>awaitility</artifactId>
@@ -1029,69 +1024,6 @@
           <artifactId>hadoop-minikdc</artifactId>
           <scope>test</scope>
         </dependency>
-        <!--
-          TODO: The below apacheds dependencies are for passing TestCheckTestClasses under JDK8,
-          see HBASE-29117 for more details. Once we finish the migration of JUnit5, which means
-          we do not need TestCheckTestClasses any more, we can remove these dependencies.
-		-->
-        <dependency>
-          <groupId>org.apache.directory.server</groupId>
-          <artifactId>apacheds-core</artifactId>
-          <version>${apacheds.version}</version>
-          <scope>test</scope>
-          <exclusions>
-            <exclusion>
-              <groupId>org.bouncycastle</groupId>
-              <artifactId>bcprov-jdk15on</artifactId>
-            </exclusion>
-            <exclusion>
-              <groupId>org.bouncycastle</groupId>
-              <artifactId>bcpkix-jdk15on</artifactId>
-            </exclusion>
-          </exclusions>
-        </dependency>
-        <dependency>
-          <groupId>org.apache.directory.server</groupId>
-          <artifactId>apacheds-protocol-ldap</artifactId>
-          <version>${apacheds.version}</version>
-          <scope>test</scope>
-          <exclusions>
-            <exclusion>
-              <groupId>org.bouncycastle</groupId>
-              <artifactId>bcprov-jdk15on</artifactId>
-            </exclusion>
-          </exclusions>
-        </dependency>
-        <dependency>
-          <groupId>org.apache.directory.server</groupId>
-          <artifactId>apacheds-ldif-partition</artifactId>
-          <version>${apacheds.version}</version>
-          <scope>test</scope>
-        </dependency>
-        <dependency>
-          <groupId>org.apache.directory.api</groupId>
-          <artifactId>api-ldap-codec-core</artifactId>
-          <version>${ldap-api.version}</version>
-          <scope>test</scope>
-        </dependency>
-        <dependency>
-          <groupId>org.apache.directory.api</groupId>
-          <artifactId>api-ldap-model</artifactId>
-          <version>${ldap-api.version}</version>
-          <scope>test</scope>
-        </dependency>
-        <dependency>
-          <groupId>org.apache.directory.server</groupId>
-          <artifactId>apacheds-server-integ</artifactId>
-          <version>${apacheds.version}</version>
-          <scope>test</scope>
-          <exclusions>
-            <exclusion>
-              <groupId>log4j</groupId>
-              <artifactId>log4j</artifactId>
-            </exclusion>
-          </exclusions>
-        </dependency>
       </dependencies>
       <build>
         <plugins>
diff --git a/hbase-server/src/test/java/org/apache/hadoop/hbase/ClearUserNamespacesAndTablesRule.java b/hbase-server/src/test/java/org/apache/hadoop/hbase/ClearUserNamespacesAndTablesRule.java
deleted file mode 100644
index 87adccf2e3d..00000000000
--- a/hbase-server/src/test/java/org/apache/hadoop/hbase/ClearUserNamespacesAndTablesRule.java
+++ /dev/null
@@ -1,152 +0,0 @@
-/*
- * 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.
- */
-package org.apache.hadoop.hbase;
-
-import java.util.List;
-import java.util.Objects;
-import java.util.StringJoiner;
-import java.util.concurrent.CompletableFuture;
-import java.util.function.Supplier;
-import java.util.stream.Collectors;
-import org.apache.hadoop.hbase.client.AsyncAdmin;
-import org.apache.hadoop.hbase.client.AsyncConnection;
-import org.junit.ClassRule;
-import org.junit.Rule;
-import org.junit.rules.ExternalResource;
-import org.junit.rules.TestRule;
-import org.slf4j.Logger;
-import org.slf4j.LoggerFactory;
-
-/**
- * A {@link TestRule} that clears all user namespaces and tables {@link ExternalResource#before()
- * before} the test executes. Can be used in either the {@link Rule} or {@link ClassRule} positions.
- * Lazily realizes the provided {@link AsyncConnection} so as to avoid initialization races with
- * other {@link Rule Rules}. <b>Does not</b> {@link AsyncConnection#close() close()} provided
- * connection instance when finished.
- * </p>
- * Use in combination with {@link MiniClusterRule} and {@link ConnectionRule}, for example:
- *
- * <pre>
- * {
- *   &#64;code
- *   public class TestMyClass {
- *     &#64;ClassRule
- *     public static final MiniClusterRule miniClusterRule = MiniClusterRule.newBuilder().build();
- *
- *     private final ConnectionRule connectionRule =
- *       new ConnectionRule(miniClusterRule::createConnection);
- *     private final ClearUserNamespacesAndTablesRule clearUserNamespacesAndTablesRule =
- *       new ClearUserNamespacesAndTablesRule(connectionRule::getConnection);
- *
- *     &#64;Rule
- *     public TestRule rule =
- *       RuleChain.outerRule(connectionRule).around(clearUserNamespacesAndTablesRule);
- *   }
- * }
- * </pre>
- */
-public class ClearUserNamespacesAndTablesRule extends ExternalResource {
-  private static final Logger logger =
-    LoggerFactory.getLogger(ClearUserNamespacesAndTablesRule.class);
-
-  private final Supplier<AsyncConnection> connectionSupplier;
-  private AsyncAdmin admin;
-
-  public ClearUserNamespacesAndTablesRule(final Supplier<AsyncConnection> connectionSupplier) {
-    this.connectionSupplier = connectionSupplier;
-  }
-
-  @Override
-  protected void before() throws Throwable {
-    final AsyncConnection connection = Objects.requireNonNull(connectionSupplier.get());
-    admin = connection.getAdmin();
-
-    clearTablesAndNamespaces().join();
-  }
-
-  private CompletableFuture<Void> clearTablesAndNamespaces() {
-    return deleteUserTables().thenCompose(_void -> deleteUserNamespaces());
-  }
-
-  private CompletableFuture<Void> deleteUserTables() {
-    return listTableNames().thenApply(tableNames -> tableNames.stream()
-      .map(tableName -> disableIfEnabled(tableName).thenCompose(_void -> deleteTable(tableName)))
-      .toArray(CompletableFuture[]::new)).thenCompose(CompletableFuture::allOf);
-  }
-
-  private CompletableFuture<List<TableName>> listTableNames() {
-    return CompletableFuture.runAsync(() -> logger.trace("listing tables"))
-      .thenCompose(_void -> admin.listTableNames(false)).thenApply(tableNames -> {
-        if (logger.isTraceEnabled()) {
-          final StringJoiner joiner = new StringJoiner(", ", "[", "]");
-          tableNames.stream().map(TableName::getNameAsString).forEach(joiner::add);
-          logger.trace("found existing tables {}", joiner.toString());
-        }
-        return tableNames;
-      });
-  }
-
-  private CompletableFuture<Boolean> isTableEnabled(final TableName tableName) {
-    return admin.isTableEnabled(tableName).thenApply(isEnabled -> {
-      logger.trace("table {} is enabled.", tableName);
-      return isEnabled;
-    });
-  }
-
-  private CompletableFuture<Void> disableIfEnabled(final TableName tableName) {
-    return isTableEnabled(tableName).thenCompose(
-      isEnabled -> isEnabled ? disableTable(tableName) : CompletableFuture.completedFuture(null));
-  }
-
-  private CompletableFuture<Void> disableTable(final TableName tableName) {
-    return CompletableFuture.runAsync(() -> logger.trace("disabling enabled table {}", tableName))
-      .thenCompose(_void -> admin.disableTable(tableName));
-  }
-
-  private CompletableFuture<Void> deleteTable(final TableName tableName) {
-    return CompletableFuture.runAsync(() -> logger.trace("deleting disabled table {}", tableName))
-      .thenCompose(_void -> admin.deleteTable(tableName));
-  }
-
-  private CompletableFuture<List<String>> listUserNamespaces() {
-    return CompletableFuture.runAsync(() -> logger.trace("listing namespaces"))
-      .thenCompose(_void -> admin.listNamespaceDescriptors()).thenApply(namespaceDescriptors -> {
-        final StringJoiner joiner = new StringJoiner(", ", "[", "]");
-        final List<String> names = namespaceDescriptors.stream().map(NamespaceDescriptor::getName)
-          .peek(joiner::add).collect(Collectors.toList());
-        logger.trace("found existing namespaces {}", joiner);
-        return names;
-      })
-      .thenApply(namespaces -> namespaces.stream()
-        .filter(
-          namespace -> !Objects.equals(namespace, NamespaceDescriptor.SYSTEM_NAMESPACE.getName()))
-        .filter(
-          namespace -> !Objects.equals(namespace, NamespaceDescriptor.DEFAULT_NAMESPACE.getName()))
-        .collect(Collectors.toList()));
-  }
-
-  private CompletableFuture<Void> deleteNamespace(final String namespace) {
-    return CompletableFuture.runAsync(() -> logger.trace("deleting namespace {}", namespace))
-      .thenCompose(_void -> admin.deleteNamespace(namespace));
-  }
-
-  private CompletableFuture<Void> deleteUserNamespaces() {
-    return listUserNamespaces().thenCompose(namespaces -> CompletableFuture
-      .allOf(namespaces.stream().map(this::deleteNamespace).toArray(CompletableFuture[]::new)));
-  }
-}
diff --git a/hbase-server/src/test/java/org/apache/hadoop/hbase/ConnectionRule.java b/hbase-server/src/test/java/org/apache/hadoop/hbase/ConnectionRule.java
deleted file mode 100644
index bad2b498ce3..00000000000
--- a/hbase-server/src/test/java/org/apache/hadoop/hbase/ConnectionRule.java
+++ /dev/null
@@ -1,133 +0,0 @@
-/*
- * 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.
- */
-package org.apache.hadoop.hbase;
-
-import java.io.IOException;
-import java.util.concurrent.CompletableFuture;
-import java.util.function.Supplier;
-import org.apache.hadoop.hbase.client.AsyncConnection;
-import org.apache.hadoop.hbase.client.Connection;
-import org.junit.ClassRule;
-import org.junit.Rule;
-import org.junit.rules.ExternalResource;
-
-/**
- * A {@link Rule} that manages the lifecycle of an instance of {@link AsyncConnection}. Can be used
- * in either the {@link Rule} or {@link ClassRule} positions.
- * </p>
- * Use in combination with {@link MiniClusterRule}, for example:
- *
- * <pre>
- * {
- *   &#64;code
- *   public class TestMyClass {
- *     private static final MiniClusterRule miniClusterRule = MiniClusterRule.newBuilder().build();
- *     private static final ConnectionRule connectionRule =
- *       ConnectionRule.createAsyncConnectionRule(miniClusterRule::createConnection);
- *
- *     &#64;ClassRule
- *     public static final TestRule rule =
- *       RuleChain.outerRule(miniClusterRule).around(connectionRule);
- *   }
- * }
- * </pre>
- *
- * @deprecated Use {@link ConnectionExtension} instead, once we finish the migration of JUnit5,
- *             which means we do not need {@link ConnectionRule} any more, we can remove these
- *             dependencies, see
- *             <a href="https://issues.apache.org/jira/browse/HBASE-23671">HBASE-23671</a> for more
- *             details.
- */
-@Deprecated
-public final class ConnectionRule extends ExternalResource {
-
-  private final Supplier<Connection> connectionSupplier;
-  private final Supplier<CompletableFuture<AsyncConnection>> asyncConnectionSupplier;
-
-  private Connection connection;
-  private AsyncConnection asyncConnection;
-
-  public static ConnectionRule createConnectionRule(final Supplier<Connection> connectionSupplier) {
-    return new ConnectionRule(connectionSupplier, null);
-  }
-
-  public static ConnectionRule createAsyncConnectionRule(
-    final Supplier<CompletableFuture<AsyncConnection>> asyncConnectionSupplier) {
-    return new ConnectionRule(null, asyncConnectionSupplier);
-  }
-
-  public static ConnectionRule createConnectionRule(final Supplier<Connection> connectionSupplier,
-    final Supplier<CompletableFuture<AsyncConnection>> asyncConnectionSupplier) {
-    return new ConnectionRule(connectionSupplier, asyncConnectionSupplier);
-  }
-
-  private ConnectionRule(final Supplier<Connection> connectionSupplier,
-    final Supplier<CompletableFuture<AsyncConnection>> asyncConnectionSupplier) {
-    this.connectionSupplier = connectionSupplier;
-    this.asyncConnectionSupplier = asyncConnectionSupplier;
-  }
-
-  public Connection getConnection() {
-    if (connection == null) {
-      throw new IllegalStateException(
-        "ConnectionRule not initialized with a synchronous connection.");
-    }
-    return connection;
-  }
-
-  public AsyncConnection getAsyncConnection() {
-    if (asyncConnection == null) {
-      throw new IllegalStateException(
-        "ConnectionRule not initialized with an asynchronous connection.");
-    }
-    return asyncConnection;
-  }
-
-  @Override
-  protected void before() throws Throwable {
-    if (connectionSupplier != null) {
-      this.connection = connectionSupplier.get();
-    }
-    if (asyncConnectionSupplier != null) {
-      this.asyncConnection = asyncConnectionSupplier.get().join();
-    }
-  }
-
-  @Override
-  protected void after() {
-    CompletableFuture<Void> closeConnection = CompletableFuture.runAsync(() -> {
-      if (this.connection != null) {
-        try {
-          connection.close();
-        } catch (IOException e) {
-          throw new RuntimeException(e);
-        }
-      }
-    });
-    CompletableFuture<Void> closeAsyncConnection = CompletableFuture.runAsync(() -> {
-      if (this.asyncConnection != null) {
-        try {
-          asyncConnection.close();
-        } catch (IOException e) {
-          throw new RuntimeException(e);
-        }
-      }
-    });
-    CompletableFuture.allOf(closeConnection, closeAsyncConnection).join();
-  }
-}
diff --git a/hbase-server/src/test/java/org/apache/hadoop/hbase/GenericTestUtils.java b/hbase-server/src/test/java/org/apache/hadoop/hbase/GenericTestUtils.java
index 3a99623b5f1..6c15a28a629 100644
--- a/hbase-server/src/test/java/org/apache/hadoop/hbase/GenericTestUtils.java
+++ b/hbase-server/src/test/java/org/apache/hadoop/hbase/GenericTestUtils.java
@@ -106,7 +106,7 @@ public abstract class GenericTestUtils {
     } while (Time.now() - st < waitForMillis);
 
     throw new TimeoutException("Timed out waiting for condition. " + "Thread diagnostics:\n"
-      + TimedOutTestsListener.buildThreadDiagnosticString());
+      + TimedOutTestsThreadDumpHelper.buildThreadDiagnosticString());
   }
 
   /**
diff --git a/hbase-server/src/test/java/org/apache/hadoop/hbase/HBaseTestCase.java b/hbase-server/src/test/java/org/apache/hadoop/hbase/HBaseTestCase.java
deleted file mode 100644
index 57c3045a49a..00000000000
--- a/hbase-server/src/test/java/org/apache/hadoop/hbase/HBaseTestCase.java
+++ /dev/null
@@ -1,403 +0,0 @@
-/*
- * 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.
- */
-package org.apache.hadoop.hbase;
-
-import java.io.IOException;
-import java.nio.charset.StandardCharsets;
-import java.util.NavigableMap;
-import org.apache.hadoop.conf.Configuration;
-import org.apache.hadoop.fs.FileSystem;
-import org.apache.hadoop.fs.Path;
-import org.apache.hadoop.hbase.client.Durability;
-import org.apache.hadoop.hbase.client.Get;
-import org.apache.hadoop.hbase.client.Put;
-import org.apache.hadoop.hbase.client.Result;
-import org.apache.hadoop.hbase.client.Table;
-import org.apache.hadoop.hbase.log.HBaseMarkers;
-import org.apache.hadoop.hbase.regionserver.HRegion;
-import org.apache.hadoop.hbase.regionserver.Region;
-import org.apache.hadoop.hbase.regionserver.RegionAsTable;
-import org.apache.hadoop.hbase.util.Bytes;
-import org.apache.hadoop.hbase.util.CommonFSUtils;
-import org.apache.hadoop.hbase.util.FSTableDescriptors;
-import org.apache.hadoop.hdfs.MiniDFSCluster;
-import org.slf4j.Logger;
-import org.slf4j.LoggerFactory;
-
-/**
- * Abstract HBase test class. Initializes a few things that can come in handly like an
- * HBaseConfiguration and filesystem.
- * @deprecated since 2.0.0 and will be removed in 3.0.0. Write junit4 unit tests using
- *             {@link HBaseTestingUtility}.
- * @see HBaseTestingUtility
- * @see <a href="https://issues.apache.org/jira/browse/HBASE-11912">HBASE-11912</a>
- */
-@Deprecated
-public abstract class HBaseTestCase extends junit.framework.TestCase {
-  private static final Logger LOG = LoggerFactory.getLogger(HBaseTestCase.class);
-
-  protected final static byte[] fam1 = Bytes.toBytes("colfamily11");
-  protected final static byte[] fam2 = Bytes.toBytes("colfamily21");
-  protected final static byte[] fam3 = Bytes.toBytes("colfamily31");
-
-  protected static final byte[][] COLUMNS = { fam1, fam2, fam3 };
-
-  private boolean localfs = false;
-  protected static Path testDir = null;
-  protected FileSystem fs = null;
-  protected HRegion meta = null;
-  protected static final char FIRST_CHAR = 'a';
-  protected static final char LAST_CHAR = 'z';
-  protected static final String PUNCTUATION = "~`@#$%^&*()-_+=:;',.<>/?[]{}|";
-  protected static final byte[] START_KEY_BYTES = { FIRST_CHAR, FIRST_CHAR, FIRST_CHAR };
-  protected String START_KEY = new String(START_KEY_BYTES, HConstants.UTF8_CHARSET);
-  protected static final int MAXVERSIONS = 3;
-
-  protected final HBaseTestingUtility testUtil = new HBaseTestingUtility();
-
-  public volatile Configuration conf = testUtil.getConfiguration();
-  public final FSTableDescriptors fsTableDescriptors;
-  {
-    try {
-      fsTableDescriptors = new FSTableDescriptors(conf);
-    } catch (IOException e) {
-      throw new RuntimeException("Failed to init descriptors", e);
-    }
-  }
-
-  /** constructor */
-  public HBaseTestCase() {
-    super();
-  }
-
-  /**
-   *   */
-  public HBaseTestCase(String name) {
-    super(name);
-  }
-
-  /**
-   * Note that this method must be called after the mini hdfs cluster has started or we end up with
-   * a local file system.
-   */
-  @Override
-  protected void setUp() throws Exception {
-    super.setUp();
-    localfs = (conf.get("fs.defaultFS", "file:///").compareTo("file:///") == 0);
-
-    if (fs == null) {
-      this.fs = FileSystem.get(conf);
-    }
-    try {
-      if (localfs) {
-        testDir = getUnitTestdir(getName());
-        if (fs.exists(testDir)) {
-          fs.delete(testDir, true);
-        }
-      } else {
-        testDir = CommonFSUtils.getRootDir(conf);
-      }
-    } catch (Exception e) {
-      LOG.error(HBaseMarkers.FATAL, "error during setup", e);
-      throw e;
-    }
-  }
-
-  @Override
-  protected void tearDown() throws Exception {
-    try {
-      if (localfs) {
-        if (this.fs.exists(testDir)) {
-          this.fs.delete(testDir, true);
-        }
-      }
-    } catch (Exception e) {
-      LOG.error(HBaseMarkers.FATAL, "error during tear down", e);
-    }
-    super.tearDown();
-  }
-
-  /**
-   * @see HBaseTestingUtility#getBaseTestDir
-   * @return directory to use for this test
-   */
-  protected Path getUnitTestdir(String testName) {
-    return testUtil.getDataTestDir(testName);
-  }
-
-  /**
-   * You must call close on the returned region and then close on the log file it created. Do
-   * {@link HBaseTestingUtility#closeRegionAndWAL(HRegion)} to close both the region and the WAL.
-   * @return An {@link HRegion}
-   */
-  public HRegion createNewHRegion(HTableDescriptor desc, byte[] startKey, byte[] endKey)
-    throws IOException {
-    return createNewHRegion(desc, startKey, endKey, this.conf);
-  }
-
-  public HRegion createNewHRegion(HTableDescriptor desc, byte[] startKey, byte[] endKey,
-    Configuration conf) throws IOException {
-    HRegionInfo hri = new HRegionInfo(desc.getTableName(), startKey, endKey);
-    return HBaseTestingUtility.createRegionAndWAL(hri, testDir, conf, desc);
-  }
-
-  protected HRegion openClosedRegion(final HRegion closedRegion) throws IOException {
-    return HRegion.openHRegion(closedRegion, null);
-  }
-
-  /**
-   * Create a table of name {@code name} with {@link #COLUMNS} for families.
-   * @param name Name to give table.
-   * @return Column descriptor.
-   */
-  protected HTableDescriptor createTableDescriptor(final String name) {
-    return createTableDescriptor(name, MAXVERSIONS);
-  }
-
-  /**
-   * Create a table of name {@code name} with {@link #COLUMNS} for families.
-   * @param name     Name to give table.
-   * @param versions How many versions to allow per column.
-   * @return Column descriptor.
-   */
-  protected HTableDescriptor createTableDescriptor(final String name, final int versions) {
-    return createTableDescriptor(name, HColumnDescriptor.DEFAULT_MIN_VERSIONS, versions,
-      HConstants.FOREVER, HColumnDescriptor.DEFAULT_KEEP_DELETED);
-  }
-
-  /**
-   * Create a table of name {@code name} with {@link #COLUMNS} for families.
-   * @param name     Name to give table.
-   * @param versions How many versions to allow per column.
-   * @return Column descriptor.
-   */
-  protected HTableDescriptor createTableDescriptor(final String name, final int minVersions,
-    final int versions, final int ttl, KeepDeletedCells keepDeleted) {
-    HTableDescriptor htd = new HTableDescriptor(TableName.valueOf(name));
-    for (byte[] cfName : new byte[][] { fam1, fam2, fam3 }) {
-      htd.addFamily(
-        new HColumnDescriptor(cfName).setMinVersions(minVersions).setMaxVersions(versions)
-          .setKeepDeletedCells(keepDeleted).setBlockCacheEnabled(false).setTimeToLive(ttl));
-    }
-    return htd;
-  }
-
-  /**
-   * Add content to region <code>r</code> on the passed column <code>column</code>. Adds data of the
-   * from 'aaa', 'aab', etc where key and value are the same.
-   * @return count of what we added.
-   */
-  public static long addContent(final Region r, final byte[] columnFamily, final byte[] column)
-    throws IOException {
-    byte[] startKey = r.getRegionInfo().getStartKey();
-    byte[] endKey = r.getRegionInfo().getEndKey();
-    byte[] startKeyBytes = startKey;
-    if (startKeyBytes == null || startKeyBytes.length == 0) {
-      startKeyBytes = START_KEY_BYTES;
-    }
-    return addContent(new RegionAsTable(r), Bytes.toString(columnFamily), Bytes.toString(column),
-      startKeyBytes, endKey, -1);
-  }
-
-  public static long addContent(final Region r, final byte[] columnFamily) throws IOException {
-    return addContent(r, columnFamily, null);
-  }
-
-  /**
-   * Add content to region <code>r</code> on the passed column <code>column</code>. Adds data of the
-   * from 'aaa', 'aab', etc where key and value are the same.
-   * @return count of what we added.
-   */
-  public static long addContent(final Table updater, final String columnFamily) throws IOException {
-    return addContent(updater, columnFamily, START_KEY_BYTES, null);
-  }
-
-  public static long addContent(final Table updater, final String family, final String column)
-    throws IOException {
-    return addContent(updater, family, column, START_KEY_BYTES, null);
-  }
-
-  /**
-   * Add content to region <code>r</code> on the passed column <code>column</code>. Adds data of the
-   * from 'aaa', 'aab', etc where key and value are the same.
-   * @return count of what we added.
-   */
-  public static long addContent(final Table updater, final String columnFamily,
-    final byte[] startKeyBytes, final byte[] endKey) throws IOException {
-    return addContent(updater, columnFamily, null, startKeyBytes, endKey, -1);
-  }
-
-  public static long addContent(final Table updater, final String family, String column,
-    final byte[] startKeyBytes, final byte[] endKey) throws IOException {
-    return addContent(updater, family, column, startKeyBytes, endKey, -1);
-  }
-
-  /**
-   * Add content to region <code>r</code> on the passed column <code>column</code>. Adds data of the
-   * from 'aaa', 'aab', etc where key and value are the same.
-   * @return count of what we added.
-   */
-  public static long addContent(final Table updater, final String columnFamily, final String column,
-    final byte[] startKeyBytes, final byte[] endKey, final long ts) throws IOException {
-    long count = 0;
-    // Add rows of three characters. The first character starts with the
-    // 'a' character and runs up to 'z'. Per first character, we run the
-    // second character over same range. And same for the third so rows
-    // (and values) look like this: 'aaa', 'aab', 'aac', etc.
-    char secondCharStart = (char) startKeyBytes[1];
-    char thirdCharStart = (char) startKeyBytes[2];
-    EXIT: for (char c = (char) startKeyBytes[0]; c <= LAST_CHAR; c++) {
-      for (char d = secondCharStart; d <= LAST_CHAR; d++) {
-        for (char e = thirdCharStart; e <= LAST_CHAR; e++) {
-          byte[] t = new byte[] { (byte) c, (byte) d, (byte) e };
-          if (endKey != null && endKey.length > 0 && Bytes.compareTo(endKey, t) <= 0) {
-            break EXIT;
-          }
-          try {
-            Put put;
-            if (ts != -1) {
-              put = new Put(t, ts);
-            } else {
-              put = new Put(t);
-            }
-            try {
-              StringBuilder sb = new StringBuilder();
-              if (column != null && column.contains(":")) {
-                sb.append(column);
-              } else {
-                if (columnFamily != null) {
-                  sb.append(columnFamily);
-                  if (!columnFamily.endsWith(":")) {
-                    sb.append(":");
-                  }
-                  if (column != null) {
-                    sb.append(column);
-                  }
-                }
-              }
-              byte[][] split = CellUtil.parseColumn(Bytes.toBytes(sb.toString()));
-              if (split.length == 1) {
-                byte[] qualifier = new byte[0];
-                put.addColumn(split[0], qualifier, t);
-              } else {
-                put.addColumn(split[0], split[1], t);
-              }
-              put.setDurability(Durability.SKIP_WAL);
-              updater.put(put);
-              count++;
-            } catch (RuntimeException ex) {
-              ex.printStackTrace();
-              throw ex;
-            } catch (IOException ex) {
-              ex.printStackTrace();
-              throw ex;
-            }
-          } catch (RuntimeException ex) {
-            ex.printStackTrace();
-            throw ex;
-          } catch (IOException ex) {
-            ex.printStackTrace();
-            throw ex;
-          }
-        }
-        // Set start character back to FIRST_CHAR after we've done first loop.
-        thirdCharStart = FIRST_CHAR;
-      }
-      secondCharStart = FIRST_CHAR;
-    }
-    return count;
-  }
-
-  protected void assertResultEquals(final HRegion region, final byte[] row, final byte[] family,
-    final byte[] qualifier, final long timestamp, final byte[] value) throws IOException {
-    Get get = new Get(row);
-    get.setTimestamp(timestamp);
-    Result res = region.get(get);
-    NavigableMap<byte[], NavigableMap<byte[], NavigableMap<Long, byte[]>>> map = res.getMap();
-    byte[] res_value = map.get(family).get(qualifier).get(timestamp);
-
-    if (value == null) {
-      assertEquals(
-        Bytes.toString(family) + " " + Bytes.toString(qualifier) + " at timestamp " + timestamp,
-        null, res_value);
-    } else {
-      if (res_value == null) {
-        fail(Bytes.toString(family) + " " + Bytes.toString(qualifier) + " at timestamp " + timestamp
-          + "\" was expected to be \"" + Bytes.toStringBinary(value) + " but was null");
-      }
-      if (res_value != null) {
-        assertEquals(
-          Bytes.toString(family) + " " + Bytes.toString(qualifier) + " at timestamp " + timestamp,
-          value, new String(res_value, StandardCharsets.UTF_8));
-      }
-    }
-  }
-
-  /**
-   * Common method to close down a MiniDFSCluster and the associated file system
-   */
-  public static void shutdownDfs(MiniDFSCluster cluster) {
-    if (cluster != null) {
-      LOG.info("Shutting down Mini DFS ");
-      try {
-        cluster.shutdown();
-      } catch (Exception e) {
-        /// Can get a java.lang.reflect.UndeclaredThrowableException thrown
-        // here because of an InterruptedException. Don't let exceptions in
-        // here be cause of test failure.
-      }
-      try {
-        FileSystem fs = cluster.getFileSystem();
-        if (fs != null) {
-          LOG.info("Shutting down FileSystem");
-          fs.close();
-        }
-        FileSystem.closeAll();
-      } catch (IOException e) {
-        LOG.error("error closing file system", e);
-      }
-    }
-  }
-
-  /**
-   * You must call {@link #closeRootAndMeta()} when done after calling this method. It does cleanup.
-   */
-  protected void createMetaRegion() throws IOException {
-    FSTableDescriptors fsTableDescriptors = new FSTableDescriptors(conf);
-    meta = HBaseTestingUtility.createRegionAndWAL(HRegionInfo.FIRST_META_REGIONINFO, testDir, conf,
-      fsTableDescriptors.get(TableName.META_TABLE_NAME));
-  }
-
-  protected void closeRootAndMeta() throws IOException {
-    HBaseTestingUtility.closeRegionAndWAL(meta);
-  }
-
-  public static void assertByteEquals(byte[] expected, byte[] actual) {
-    if (Bytes.compareTo(expected, actual) != 0) {
-      throw new junit.framework.AssertionFailedError(
-        "expected:<" + Bytes.toString(expected) + "> but was:<" + Bytes.toString(actual) + ">");
-    }
-  }
-
-  public static void assertEquals(byte[] expected, byte[] actual) {
-    if (Bytes.compareTo(expected, actual) != 0) {
-      throw new junit.framework.AssertionFailedError("expected:<" + Bytes.toStringBinary(expected)
-        + "> but was:<" + Bytes.toStringBinary(actual) + ">");
-    }
-  }
-}
diff --git a/hbase-server/src/test/java/org/apache/hadoop/hbase/MiniClusterRule.java b/hbase-server/src/test/java/org/apache/hadoop/hbase/MiniClusterRule.java
deleted file mode 100644
index 2d035c87235..00000000000
--- a/hbase-server/src/test/java/org/apache/hadoop/hbase/MiniClusterRule.java
+++ /dev/null
@@ -1,155 +0,0 @@
-/*
- * 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.
- */
-package org.apache.hadoop.hbase;
-
-import java.io.IOException;
-import java.util.concurrent.CompletableFuture;
-import java.util.function.Supplier;
-import org.apache.hadoop.conf.Configuration;
-import org.apache.hadoop.hbase.client.AsyncConnection;
-import org.apache.hadoop.hbase.client.Connection;
-import org.apache.hadoop.hbase.client.ConnectionFactory;
-import org.junit.ClassRule;
-import org.junit.Rule;
-import org.junit.rules.ExternalResource;
-import org.junit.rules.TestRule;
-
-/**
- * A {@link TestRule} that manages an instance of the {@link MiniHBaseCluster}. Can be used in
- * either the {@link Rule} or {@link ClassRule} positions. Built on top of an instance of
- * {@link HBaseTestingUtility}, so be weary of intermixing direct use of that class with this Rule.
- * </p>
- * Use in combination with {@link ConnectionRule}, for example:
- *
- * <pre>
- * {
- *   &#64;code
- *   public class TestMyClass {
- *     &#64;ClassRule
- *     public static final MiniClusterRule miniClusterRule = MiniClusterRule.newBuilder().build();
- *
- *     &#64;Rule
- *     public final ConnectionRule connectionRule =
- *       ConnectionRule.createAsyncConnectionRule(miniClusterRule::createAsyncConnection);
- *   }
- * }
- * </pre>
- *
- * @deprecated Use {@link MiniClusterExtension} instead, Once we finish the migration of JUnit5,
- *             which means we do not need {@link MiniClusterRule} any more, we can remove these
- *             dependencies, see
- *             <a href="https://issues.apache.org/jira/browse/HBASE-23671">HBASE-23671</a> for more
- *             details.
- */
-@Deprecated
-public final class MiniClusterRule extends ExternalResource {
-
-  /**
-   * A builder for fluent composition of a new {@link MiniClusterRule}.
-   */
-  public static class Builder {
-
-    private StartMiniClusterOption miniClusterOption;
-    private Configuration conf;
-
-    /**
-     * Use the provided {@link StartMiniClusterOption} to construct the {@link MiniHBaseCluster}.
-     */
-    public Builder setMiniClusterOption(final StartMiniClusterOption miniClusterOption) {
-      this.miniClusterOption = miniClusterOption;
-      return this;
-    }
-
-    /**
-     * Seed the underlying {@link HBaseTestingUtility} with the provided {@link Configuration}.
-     */
-    public Builder setConfiguration(final Configuration conf) {
-      this.conf = conf;
-      return this;
-    }
-
-    public Builder setConfiguration(Supplier<Configuration> supplier) {
-      return setConfiguration(supplier.get());
-    }
-
-    public MiniClusterRule build() {
-      return new MiniClusterRule(conf,
-        miniClusterOption != null ? miniClusterOption : StartMiniClusterOption.builder().build());
-    }
-  }
-
-  private final HBaseTestingUtility testingUtility;
-  private final StartMiniClusterOption miniClusterOptions;
-
-  private MiniHBaseCluster miniCluster;
-
-  private MiniClusterRule(final Configuration conf,
-    final StartMiniClusterOption miniClusterOptions) {
-    this.testingUtility = new HBaseTestingUtility(conf);
-    this.miniClusterOptions = miniClusterOptions;
-  }
-
-  public static Builder newBuilder() {
-    return new Builder();
-  }
-
-  /** Returns the underlying instance of {@link HBaseTestingUtility} */
-  public HBaseTestingUtility getTestingUtility() {
-    return testingUtility;
-  }
-
-  /**
-   * Create a {@link Connection} to the managed {@link MiniHBaseCluster}. It's up to the caller to
-   * {@link Connection#close() close()} the connection when finished.
-   */
-  public Connection createConnection() {
-    if (miniCluster == null) {
-      throw new IllegalStateException("test cluster not initialized");
-    }
-    try {
-      return ConnectionFactory.createConnection(miniCluster.getConf());
-    } catch (IOException e) {
-      throw new RuntimeException(e);
-    }
-  }
-
-  /**
-   * Create a {@link AsyncConnection} to the managed {@link MiniHBaseCluster}. It's up to the caller
-   * to {@link AsyncConnection#close() close()} the connection when finished.
-   */
-  public CompletableFuture<AsyncConnection> createAsyncConnection() {
-    if (miniCluster == null) {
-      throw new IllegalStateException("test cluster not initialized");
-    }
-    return ConnectionFactory.createAsyncConnection(miniCluster.getConf());
-  }
-
-  @Override
-  protected void before() throws Throwable {
-    miniCluster = testingUtility.startMiniCluster(miniClusterOptions);
-  }
-
-  @Override
-  protected void after() {
-    try {
-      testingUtility.shutdownMiniCluster();
-    } catch (IOException e) {
-      throw new RuntimeException(e);
-    }
-  }
-}
diff --git a/hbase-server/src/test/java/org/apache/hadoop/hbase/TestCheckTestClasses.java b/hbase-server/src/test/java/org/apache/hadoop/hbase/TestCheckTestClasses.java
deleted file mode 100644
index 961bc83763f..00000000000
--- a/hbase-server/src/test/java/org/apache/hadoop/hbase/TestCheckTestClasses.java
+++ /dev/null
@@ -1,62 +0,0 @@
-/*
- * 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.
- */
-package org.apache.hadoop.hbase;
-
-import static org.junit.Assert.assertTrue;
-
-import java.util.List;
-import org.apache.hadoop.hbase.testclassification.MiscTests;
-import org.apache.hadoop.hbase.testclassification.SmallTests;
-import org.junit.ClassRule;
-import org.junit.Test;
-import org.junit.experimental.categories.Category;
-
-/**
- * Checks tests are categorized.
- * <p>
- * @deprecated Will be removed after we fully upgrade to junit5, so keep it as is.
- */
-@Deprecated
-@Category({ MiscTests.class, SmallTests.class })
-public class TestCheckTestClasses {
-
-  @ClassRule
-  public static final HBaseClassTestRule CLASS_RULE =
-    HBaseClassTestRule.forClass(TestCheckTestClasses.class);
-
-  /**
-   * Throws an assertion if we find a test class without category (small/medium/large/integration).
-   * List all the test classes without category in the assertion message.
-   */
-  @Test
-  public void checkClasses() throws Exception {
-    List<Class<?>> badClasses = new java.util.ArrayList<>();
-    ClassTestFinder classFinder = new ClassTestFinder();
-    for (Class<?> c : classFinder.findClasses(false)) {
-      if (
-        ClassTestFinder.getCategoryAnnotations(c).length == 0
-          && ClassTestFinder.getTagAnnotations(c).length == 0
-      ) {
-        badClasses.add(c);
-      }
-    }
-    assertTrue(
-      "There are " + badClasses.size() + " test classes without category and tag: " + badClasses,
-      badClasses.isEmpty());
-  }
-}
diff --git a/hbase-server/src/test/java/org/apache/hadoop/hbase/io/hfile/bucket/TestBucketCacheRefCnt.java b/hbase-server/src/test/java/org/apache/hadoop/hbase/io/hfile/bucket/TestBucketCacheRefCnt.java
index 08e7e8ea69e..b466719136c 100644
--- a/hbase-server/src/test/java/org/apache/hadoop/hbase/io/hfile/bucket/TestBucketCacheRefCnt.java
+++ b/hbase-server/src/test/java/org/apache/hadoop/hbase/io/hfile/bucket/TestBucketCacheRefCnt.java
@@ -45,6 +45,7 @@ import org.apache.hadoop.hbase.nio.ByteBuff;
 import org.apache.hadoop.hbase.nio.RefCnt;
 import org.apache.hadoop.hbase.testclassification.IOTests;
 import org.apache.hadoop.hbase.testclassification.SmallTests;
+import org.junit.jupiter.api.Disabled;
 import org.junit.jupiter.api.Tag;
 import org.junit.jupiter.api.Test;
 
@@ -101,7 +102,7 @@ public class TestBucketCacheRefCnt {
     }
   }
 
-  @org.junit.Ignore
+  @Disabled
   @Test // Disabled by HBASE-24079. Reenable issue HBASE-24082
   // Flakey TestBucketCacheRefCnt.testBlockInRAMCache:121 expected:<3> but was:<2>
   public void testBlockInRAMCache() throws IOException {
diff --git a/hbase-server/src/test/java/org/apache/hadoop/hbase/master/balancer/TestStochasticLoadBalancerRegionReplicaSameHosts.java b/hbase-server/src/test/java/org/apache/hadoop/hbase/master/balancer/TestStochasticLoadBalancerRegionReplicaSameHosts.java
index 995d8652ea0..423796d5950 100644
--- a/hbase-server/src/test/java/org/apache/hadoop/hbase/master/balancer/TestStochasticLoadBalancerRegionReplicaSameHosts.java
+++ b/hbase-server/src/test/java/org/apache/hadoop/hbase/master/balancer/TestStochasticLoadBalancerRegionReplicaSameHosts.java
@@ -17,6 +17,7 @@
  */
 package org.apache.hadoop.hbase.master.balancer;
 
+import java.time.Duration;
 import java.util.ArrayList;
 import java.util.List;
 import java.util.Map;
@@ -34,8 +35,7 @@ public class TestStochasticLoadBalancerRegionReplicaSameHosts extends BalancerTe
 
   @Test
   public void testRegionReplicationOnMidClusterSameHosts() {
-    conf.setLong(StochasticLoadBalancer.MAX_STEPS_KEY, 2000000L);
-    loadBalancer.onConfigurationChange(conf);
+    setMaxRunTime(Duration.ofSeconds(10));
     int numHosts = 30;
     int numRegions = 30 * 30;
     int replication = 3; // 3 replicas per region
diff --git a/hbase-server/src/test/java/org/apache/hadoop/hbase/replication/regionserver/TestDumpReplicationQueues.java b/hbase-server/src/test/java/org/apache/hadoop/hbase/replication/regionserver/TestDumpReplicationQueues.java
index 7385e13ea41..19b25adbcd6 100644
--- a/hbase-server/src/test/java/org/apache/hadoop/hbase/replication/regionserver/TestDumpReplicationQueues.java
+++ b/hbase-server/src/test/java/org/apache/hadoop/hbase/replication/regionserver/TestDumpReplicationQueues.java
@@ -34,7 +34,6 @@ import org.apache.hadoop.hbase.util.EnvironmentEdgeManager;
 import org.apache.hadoop.hbase.zookeeper.RecoverableZooKeeper;
 import org.apache.hadoop.hbase.zookeeper.ZKWatcher;
 import org.apache.hadoop.hbase.zookeeper.ZNodePaths;
-import org.junit.experimental.categories.Category;
 import org.junit.jupiter.api.Tag;
 import org.junit.jupiter.api.Test;
 
@@ -43,7 +42,6 @@ import org.junit.jupiter.api.Test;
  */
 @Tag(ReplicationTests.TAG)
 @Tag(SmallTests.TAG)
-@Category({ ReplicationTests.class, SmallTests.class })
 public class TestDumpReplicationQueues {
 
   /**
diff --git a/hbase-server/src/test/java/org/apache/hadoop/hbase/trace/OpenTelemetryClassRule.java b/hbase-server/src/test/java/org/apache/hadoop/hbase/trace/OpenTelemetryClassRule.java
deleted file mode 100644
index 7b5455f2011..00000000000
--- a/hbase-server/src/test/java/org/apache/hadoop/hbase/trace/OpenTelemetryClassRule.java
+++ /dev/null
@@ -1,126 +0,0 @@
-/*
- * 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.
- */
-package org.apache.hadoop.hbase.trace;
-
-import io.opentelemetry.api.GlobalOpenTelemetry;
-import io.opentelemetry.api.OpenTelemetry;
-import io.opentelemetry.api.trace.propagation.W3CTraceContextPropagator;
-import io.opentelemetry.context.propagation.ContextPropagators;
-import io.opentelemetry.sdk.OpenTelemetrySdk;
-import io.opentelemetry.sdk.testing.exporter.InMemorySpanExporter;
-import io.opentelemetry.sdk.testing.junit4.OpenTelemetryRule;
-import io.opentelemetry.sdk.trace.SdkTracerProvider;
-import io.opentelemetry.sdk.trace.data.SpanData;
-import io.opentelemetry.sdk.trace.export.SimpleSpanProcessor;
-import java.util.List;
-import org.junit.rules.ExternalResource;
-
-/**
- * <p>
- * Like {@link OpenTelemetryRule}, except modeled after the junit5 implementation
- * {@code OpenTelemetryExtension}. Use this class when you need to make asserts on {@link SpanData}
- * created on a MiniCluster. Make sure this rule initialized before the MiniCluster so that it can
- * register its instance of {@link OpenTelemetry} as the global instance before any server-side
- * component can call {@link TraceUtil#getGlobalTracer()}.
- * </p>
- * <p>
- * For example:
- * </p>
- *
- * <pre>
- * {
- *   &#64;code
- *   public class TestMyClass {
- *     private static final OpenTelemetryClassRule otelClassRule = OpenTelemetryClassRule.create();
- *     private static final MiniClusterRule miniClusterRule = MiniClusterRule.newBuilder().build();
- *     protected static final ConnectionRule connectionRule =
- *       ConnectionRule.createAsyncConnectionRule(miniClusterRule::createAsyncConnection);
- *
- *     &#64;ClassRule
- *     public static final TestRule classRule =
- *       RuleChain.outerRule(otelClassRule).around(miniClusterRule).around(connectionRule);
- *
- *     &#64;Rule
- *     public final OpenTelemetryTestRule otelTestRule = new OpenTelemetryTestRule(otelClassRule);
- *
- *     &#64;Test
- *     public void myTest() {
- *       // ...
- *       // do something that makes spans
- *       final List<SpanData> spans = otelClassRule.getSpans();
- *       // make assertions on them
- *     }
- *   }
- * }
- * </pre>
- *
- * @see <a href=
- *      "https://github.com/open-telemetry/opentelemetry-java/blob/9a330d0/sdk/testing/src/main/java/io/opentelemetry/sdk/testing/junit5/OpenTelemetryExtension.java">junit5/OpenTelemetryExtension.java</a>
- */
-public final class OpenTelemetryClassRule extends ExternalResource {
-
-  public static OpenTelemetryClassRule create() {
-    InMemorySpanExporter spanExporter = InMemorySpanExporter.create();
-
-    SdkTracerProvider tracerProvider = SdkTracerProvider.builder()
-      .addSpanProcessor(SimpleSpanProcessor.create(spanExporter)).build();
-
-    OpenTelemetrySdk openTelemetry = OpenTelemetrySdk.builder()
-      .setPropagators(ContextPropagators.create(W3CTraceContextPropagator.getInstance()))
-      .setTracerProvider(tracerProvider).build();
-
-    return new OpenTelemetryClassRule(openTelemetry, spanExporter);
-  }
-
-  private final OpenTelemetrySdk openTelemetry;
-  private final InMemorySpanExporter spanExporter;
-
-  private OpenTelemetryClassRule(final OpenTelemetrySdk openTelemetry,
-    final InMemorySpanExporter spanExporter) {
-    this.openTelemetry = openTelemetry;
-    this.spanExporter = spanExporter;
-  }
-
-  /** Returns the {@link OpenTelemetry} created by this Rule. */
-  public OpenTelemetry getOpenTelemetry() {
-    return openTelemetry;
-  }
-
-  /** Returns all the exported {@link SpanData} so far. */
-  public List<SpanData> getSpans() {
-    return spanExporter.getFinishedSpanItems();
-  }
-
-  /**
-   * Clears the collected exported {@link SpanData}.
-   */
-  public void clearSpans() {
-    spanExporter.reset();
-  }
-
-  @Override
-  protected void before() throws Throwable {
-    GlobalOpenTelemetry.resetForTest();
-    GlobalOpenTelemetry.set(openTelemetry);
-  }
-
-  @Override
-  protected void after() {
-    GlobalOpenTelemetry.resetForTest();
-  }
-}
diff --git a/hbase-server/src/test/java/org/apache/hadoop/hbase/trace/OpenTelemetryTestRule.java b/hbase-server/src/test/java/org/apache/hadoop/hbase/trace/OpenTelemetryTestRule.java
deleted file mode 100644
index a51dc2eff45..00000000000
--- a/hbase-server/src/test/java/org/apache/hadoop/hbase/trace/OpenTelemetryTestRule.java
+++ /dev/null
@@ -1,39 +0,0 @@
-/*
- * 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.
- */
-package org.apache.hadoop.hbase.trace;
-
-import org.junit.rules.ExternalResource;
-
-/**
- * Used alongside {@link OpenTelemetryClassRule}. See that class's javadoc for details on when to
- * use these classes instead of {@link io.opentelemetry.sdk.testing.junit4.OpenTelemetryRule} and an
- * example of how to use these classes together.
- */
-public final class OpenTelemetryTestRule extends ExternalResource {
-
-  private final OpenTelemetryClassRule classRuleSupplier;
-
-  public OpenTelemetryTestRule(final OpenTelemetryClassRule classRule) {
-    this.classRuleSupplier = classRule;
-  }
-
-  @Override
-  protected void before() throws Throwable {
-    classRuleSupplier.clearSpans();
-  }
-}
diff --git a/hbase-server/src/test/java/org/apache/hadoop/hbase/util/ProcessBasedLocalHBaseCluster.java b/hbase-server/src/test/java/org/apache/hadoop/hbase/util/ProcessBasedLocalHBaseCluster.java
index 21c49e61bad..525dafb7ae0 100644
--- a/hbase-server/src/test/java/org/apache/hadoop/hbase/util/ProcessBasedLocalHBaseCluster.java
+++ b/hbase-server/src/test/java/org/apache/hadoop/hbase/util/ProcessBasedLocalHBaseCluster.java
@@ -44,11 +44,8 @@ import org.apache.hadoop.hbase.HBaseTestingUtility;
 import org.apache.hadoop.hbase.HConstants;
 import org.apache.hadoop.hbase.MiniHBaseCluster;
 import org.apache.hadoop.hbase.TableName;
-import org.apache.hadoop.hbase.testclassification.LargeTests;
-import org.apache.hadoop.hbase.testclassification.MiscTests;
 import org.apache.hadoop.hbase.zookeeper.ZKUtil;
 import org.apache.hadoop.hdfs.MiniDFSCluster;
-import org.junit.experimental.categories.Category;
 import org.slf4j.Logger;
 import org.slf4j.LoggerFactory;
 
@@ -56,7 +53,6 @@ import org.slf4j.LoggerFactory;
  * A helper class for process-based mini-cluster tests. Unlike {@link MiniHBaseCluster}, starts
  * daemons as separate processes, allowing to do real kill testing.
  */
-@Category({ MiscTests.class, LargeTests.class })
 public class ProcessBasedLocalHBaseCluster {
 
   private final String hbaseHome, workDir;
diff --git a/hbase-shaded/hbase-shaded-check-invariants/pom.xml b/hbase-shaded/hbase-shaded-check-invariants/pom.xml
index a203e5b8dd6..d3bbd266052 100644
--- a/hbase-shaded/hbase-shaded-check-invariants/pom.xml
+++ b/hbase-shaded/hbase-shaded-check-invariants/pom.xml
@@ -84,11 +84,6 @@
       <artifactId>junit-jupiter-params</artifactId>
       <scope>provided</scope>
     </dependency>
-    <dependency>
-      <groupId>org.junit.vintage</groupId>
-      <artifactId>junit-vintage-engine</artifactId>
-      <scope>provided</scope>
-    </dependency>
     <dependency>
       <groupId>org.mockito</groupId>
       <artifactId>mockito-core</artifactId>
diff --git a/hbase-shaded/hbase-shaded-testing-util-tester/pom.xml b/hbase-shaded/hbase-shaded-testing-util-tester/pom.xml
index d387ed151de..6afd70b2e47 100644
--- a/hbase-shaded/hbase-shaded-testing-util-tester/pom.xml
+++ b/hbase-shaded/hbase-shaded-testing-util-tester/pom.xml
@@ -48,11 +48,6 @@
       <artifactId>junit-jupiter-params</artifactId>
       <scope>test</scope>
     </dependency>
-    <dependency>
-      <groupId>org.junit.vintage</groupId>
-      <artifactId>junit-vintage-engine</artifactId>
-      <scope>test</scope>
-    </dependency>
     <dependency>
       <groupId>org.apache.hbase</groupId>
       <artifactId>hbase-logging</artifactId>
diff --git a/hbase-shaded/hbase-shaded-testing-util-tester/src/test/java/org/apache/hbase/shaded/TestShadedHBaseTestingUtility.java b/hbase-shaded/hbase-shaded-testing-util-tester/src/test/java/org/apache/hbase/shaded/TestShadedHBaseTestingUtility.java
index 63c8b042286..474969768f4 100644
--- a/hbase-shaded/hbase-shaded-testing-util-tester/src/test/java/org/apache/hbase/shaded/TestShadedHBaseTestingUtility.java
+++ b/hbase-shaded/hbase-shaded-testing-util-tester/src/test/java/org/apache/hbase/shaded/TestShadedHBaseTestingUtility.java
@@ -17,9 +17,8 @@
  */
 package org.apache.hbase.shaded;
 
-import static org.junit.Assert.assertEquals;
+import static org.junit.jupiter.api.Assertions.assertEquals;
 
-import org.apache.hadoop.hbase.HBaseClassTestRule;
 import org.apache.hadoop.hbase.HBaseTestingUtility;
 import org.apache.hadoop.hbase.TableName;
 import org.apache.hadoop.hbase.client.Put;
@@ -27,26 +26,23 @@ import org.apache.hadoop.hbase.client.Table;
 import org.apache.hadoop.hbase.testclassification.ClientTests;
 import org.apache.hadoop.hbase.testclassification.MediumTests;
 import org.apache.hadoop.hbase.util.Bytes;
-import org.junit.AfterClass;
-import org.junit.BeforeClass;
-import org.junit.ClassRule;
-import org.junit.Test;
-import org.junit.experimental.categories.Category;
+import org.junit.jupiter.api.AfterAll;
+import org.junit.jupiter.api.BeforeAll;
+import org.junit.jupiter.api.Tag;
+import org.junit.jupiter.api.Test;
 
-@Category({ ClientTests.class, MediumTests.class })
+@Tag(ClientTests.TAG)
+@Tag(MediumTests.TAG)
 public class TestShadedHBaseTestingUtility {
-  private static final HBaseTestingUtility TEST_UTIL = new HBaseTestingUtility();
 
-  @ClassRule
-  public static final HBaseClassTestRule CLASS_RULE =
-    HBaseClassTestRule.forClass(TestShadedHBaseTestingUtility.class);
+  private static final HBaseTestingUtility TEST_UTIL = new HBaseTestingUtility();
 
-  @BeforeClass
+  @BeforeAll
   public static void setUp() throws Exception {
     TEST_UTIL.startMiniCluster();
   }
 
-  @AfterClass
+  @AfterAll
   public static void tearDown() throws Exception {
     TEST_UTIL.shutdownMiniCluster();
   }
diff --git a/hbase-shaded/hbase-shaded-with-hadoop-check-invariants/pom.xml b/hbase-shaded/hbase-shaded-with-hadoop-check-invariants/pom.xml
index 8f6ceb1a0bb..454e8376394 100644
--- a/hbase-shaded/hbase-shaded-with-hadoop-check-invariants/pom.xml
+++ b/hbase-shaded/hbase-shaded-with-hadoop-check-invariants/pom.xml
@@ -74,11 +74,6 @@
       <artifactId>junit-jupiter-params</artifactId>
       <scope>provided</scope>
     </dependency>
-    <dependency>
-      <groupId>org.junit.vintage</groupId>
-      <artifactId>junit-vintage-engine</artifactId>
-      <scope>provided</scope>
-    </dependency>
     <dependency>
       <groupId>org.mockito</groupId>
       <artifactId>mockito-core</artifactId>
diff --git a/hbase-testing-util/pom.xml b/hbase-testing-util/pom.xml
index 5fdab73616b..0808ebebf07 100644
--- a/hbase-testing-util/pom.xml
+++ b/hbase-testing-util/pom.xml
@@ -136,17 +136,22 @@
     <dependency>
       <groupId>org.junit.jupiter</groupId>
       <artifactId>junit-jupiter-api</artifactId>
-      <scope>test</scope>
+      <scope>compile</scope>
     </dependency>
     <dependency>
       <groupId>org.junit.jupiter</groupId>
       <artifactId>junit-jupiter-engine</artifactId>
-      <scope>test</scope>
+      <scope>compile</scope>
     </dependency>
     <dependency>
       <groupId>org.junit.jupiter</groupId>
       <artifactId>junit-jupiter-params</artifactId>
-      <scope>test</scope>
+      <scope>compile</scope>
+    </dependency>
+    <dependency>
+      <groupId>org.hamcrest</groupId>
+      <artifactId>hamcrest-library</artifactId>
+      <scope>compile</scope>
     </dependency>
     <dependency>
       <groupId>com.github.stephenc.findbugs</groupId>
diff --git a/hbase-thrift/src/test/java/org/apache/hadoop/hbase/thrift/TestThriftHttpServerBase.java b/hbase-thrift/src/test/java/org/apache/hadoop/hbase/thrift/TestThriftHttpServerBase.java
index 1f2c53ec69a..cc174cc0084 100644
--- a/hbase-thrift/src/test/java/org/apache/hadoop/hbase/thrift/TestThriftHttpServerBase.java
+++ b/hbase-thrift/src/test/java/org/apache/hadoop/hbase/thrift/TestThriftHttpServerBase.java
@@ -21,7 +21,6 @@ import static org.apache.hadoop.hbase.thrift.TestThriftServerCmdLine.createBound
 import static org.junit.jupiter.api.Assertions.assertEquals;
 import static org.junit.jupiter.api.Assertions.assertNotEquals;
 import static org.junit.jupiter.api.Assertions.assertThrows;
-import static org.junit.jupiter.api.Assertions.fail;
 
 import java.io.IOException;
 import java.net.HttpURLConnection;
@@ -40,7 +39,6 @@ import org.apache.thrift.protocol.TProtocol;
 import org.apache.thrift.transport.THttpClient;
 import org.apache.thrift.transport.TTransportException;
 import org.junit.jupiter.api.Test;
-import org.junit.rules.ExpectedException;
 import org.slf4j.Logger;
 import org.slf4j.LoggerFactory;
 
@@ -73,21 +71,11 @@ public class TestThriftHttpServerBase {
     Configuration conf = new Configuration(TEST_UTIL.getConfiguration());
     conf.set("hbase.thrift.security.qop", "privacy");
     conf.setBoolean("hbase.thrift.ssl.enabled", false);
-    ExpectedException thrown = ExpectedException.none();
-    ThriftServerRunner tsr = null;
-    try {
-      thrown.expect(IllegalArgumentException.class);
-      thrown.expectMessage(
-        "Thrift HTTP Server's QoP is privacy, " + "but hbase.thrift.ssl.enabled is false");
-      tsr = TestThriftServerCmdLine.createBoundServer(() -> new ThriftServer(conf));
-      fail("Thrift HTTP Server starts up even with wrong security configurations.");
-    } catch (Exception e) {
-      LOG.info("Expected!", e);
-    } finally {
-      if (tsr != null) {
-        tsr.close();
-      }
-    }
+    IllegalArgumentException e = assertThrows(IllegalArgumentException.class,
+      () -> TestThriftServerCmdLine.createBoundServer(() -> new ThriftServer(conf)),
+      "Thrift HTTP Server starts up even with wrong security configurations.");
+    assertEquals("Thrift HTTP Server's QoP is privacy, but hbase.thrift.ssl.enabled is false",
+      e.getMessage());
   }
 
   @Test
diff --git a/hbase-thrift/src/test/java/org/apache/hadoop/hbase/thrift2/TestThriftHBaseServiceHandler.java b/hbase-thrift/src/test/java/org/apache/hadoop/hbase/thrift2/TestThriftHBaseServiceHandler.java
index 3c98a1f2e62..bc0a151c80d 100644
--- a/hbase-thrift/src/test/java/org/apache/hadoop/hbase/thrift2/TestThriftHBaseServiceHandler.java
+++ b/hbase-thrift/src/test/java/org/apache/hadoop/hbase/thrift2/TestThriftHBaseServiceHandler.java
@@ -126,6 +126,7 @@ import org.junit.jupiter.api.AfterAll;
 import org.junit.jupiter.api.Assertions;
 import org.junit.jupiter.api.BeforeAll;
 import org.junit.jupiter.api.BeforeEach;
+import org.junit.jupiter.api.Disabled;
 import org.junit.jupiter.api.Tag;
 import org.junit.jupiter.api.Test;
 import org.junit.jupiter.api.TestInfo;
@@ -755,7 +756,7 @@ public class TestThriftHBaseServiceHandler {
    * Tests keeping a HBase scanner alive for long periods of time. Each call to getScannerRow()
    * should reset the ConnectionCache timeout for the scanner's connection
    */
-  @org.junit.Ignore
+  @Disabled
   @Test // Flakey. Diasabled by HBASE-24079. Renable with Fails with HBASE-24083.
   // Caused by: java.util.concurrent.RejectedExecutionException:
   // Task org.apache.hadoop.hbase.client.ResultBoundedCompletionService$QueueingFuture@e385431
diff --git a/pom.xml b/pom.xml
index ab2cc9b28fc..51c897b4452 100644
--- a/pom.xml
+++ b/pom.xml
@@ -596,7 +596,6 @@
     <tomcat.jasper.version>9.0.110</tomcat.jasper.version>
     <jruby.version>9.4.14.0</jruby.version>
     <junit.jupiter.version>5.13.4</junit.jupiter.version>
-    <junit.vintage.version>5.13.4</junit.vintage.version>
     <awaitility.version>4.3.0</awaitility.version>
     <hamcrest.version>1.3</hamcrest.version>
     <opentelemetry.version>1.49.0</opentelemetry.version>
@@ -797,9 +796,10 @@
     <vega.version>5.32.0</vega.version>
     <vega-embed.version>6.29.0</vega-embed.version>
     <vega-lite.version>5.23.0</vega-lite.version>
-    <!-- Required for testing LDAP integration -->
+    <!--
+      Required for testing LDAP integration for hadoop 3.x
+    -->
     <apacheds.version>2.0.0.AM27</apacheds.version>
-    <ldap-api.version>2.1.7</ldap-api.version>
   </properties>
   <!-- Sorted by groups of dependencies then groupId and artifactId -->
   <dependencyManagement>
@@ -1374,28 +1374,11 @@
         </exclusions>
       </dependency>
       <dependency>
-        <groupId>org.junit.jupiter</groupId>
-        <artifactId>junit-jupiter-api</artifactId>
+        <groupId>org.junit</groupId>
+        <artifactId>junit-bom</artifactId>
         <version>${junit.jupiter.version}</version>
-        <scope>test</scope>
-      </dependency>
-      <dependency>
-        <groupId>org.junit.jupiter</groupId>
-        <artifactId>junit-jupiter-engine</artifactId>
-        <version>${junit.jupiter.version}</version>
-        <scope>test</scope>
-      </dependency>
-      <dependency>
-        <groupId>org.junit.jupiter</groupId>
-        <artifactId>junit-jupiter-params</artifactId>
-        <version>${junit.jupiter.version}</version>
-        <scope>test</scope>
-      </dependency>
-      <dependency>
-        <groupId>org.junit.vintage</groupId>
-        <artifactId>junit-vintage-engine</artifactId>
-        <version>${junit.vintage.version}</version>
-        <scope>test</scope>
+        <type>pom</type>
+        <scope>import</scope>
       </dependency>
       <dependency>
         <groupId>org.awaitility</groupId>
@@ -2284,6 +2267,24 @@
               </rules>
             </configuration>
           </execution>
+          <execution>
+            <id>banned-junit4</id>
+            <goals>
+              <goal>enforce</goal>
+            </goals>
+            <configuration>
+              <rules>
+                <bannedDependencies>
+                  <excludes>
+                    <exclude>junit:junit</exclude>
+                    <exclude>org.junit.vintage:*</exclude>
+                  </excludes>
+                  <message>Use junit5 instead</message>
+                  <searchTransitive>true</searchTransitive>
+                </bannedDependencies>
+              </rules>
+            </configuration>
+          </execution>
           <execution>
             <id>check-aggregate-license</id>
             <goals>
@@ -2446,7 +2447,7 @@
                 <restrictImports implementation="de.skuzzle.enforcer.restrictimports.rule.RestrictImports">
                   <includeTestCode>true</includeTestCode>
                   <commentLineBufferSize>512</commentLineBufferSize>
-                  <reason>Use junit4 instead</reason>
+                  <reason>Use junit5 instead</reason>
                   <bannedImports>
                     <bannedImport>junit.framework.**</bannedImport>
                   </bannedImports>
@@ -4032,6 +4033,10 @@
                 <groupId>bouncycastle</groupId>
                 <artifactId>bcprov-jdk15</artifactId>
               </exclusion>
+              <exclusion>
+                <groupId>junit</groupId>
+                <artifactId>junit</artifactId>
+              </exclusion>
             </exclusions>
           </dependency>
           <dependency>
@@ -4039,7 +4044,6 @@
             <artifactId>hadoop-annotations</artifactId>
             <version>${hadoop-two.version}</version>
           </dependency>
-
           <dependency>
             <groupId>org.apache.hadoop</groupId>
             <artifactId>hadoop-distcp</artifactId>
@@ -4720,6 +4724,25 @@
                 <groupId>org.jline</groupId>
                 <artifactId>jline</artifactId>
               </exclusion>
+              <exclusion>
+                <groupId>junit</groupId>
+                <artifactId>junit</artifactId>
+              </exclusion>
+            </exclusions>
+          </dependency>
+          <dependency>
+            <groupId>org.apache.directory.server</groupId>
+            <artifactId>apacheds-all</artifactId>
+            <version>${apacheds.version}</version>
+            <exclusions>
+              <exclusion>
+                <groupId>org.bouncycastle</groupId>
+                <artifactId>bcprov-jdk15on</artifactId>
+              </exclusion>
+              <exclusion>
+                <groupId>org.bouncycastle</groupId>
+                <artifactId>bcpkix-jdk15on</artifactId>
+              </exclusion>
             </exclusions>
           </dependency>
           <dependency>
@@ -4727,7 +4750,6 @@
             <artifactId>hadoop-distcp</artifactId>
             <version>${hadoop-three.version}</version>
           </dependency>
-
           <dependency>
             <groupId>org.apache.hadoop</groupId>
             <artifactId>hadoop-hdfs-client</artifactId>