Actions `cluster:admin/repository/analyze/blob` and `cluster:admin/repository/analyze/register` and so on are only invoked via the transport service, they do not need to register as client actions so we can drop the `ActionType` instance. Instead the root `RepositoryAnalyzeAction` should create and register all these transport actions itself. But even the root `RepositoryAnalyzeAction` should not be an `ActionType` derivative, we should just declare an `ActionType` instance directly. Moreover we can use `ActionType#localOnly` since the client action does not run on remote clusters.
x-pack/plugin/snapshot-repo-test-kit/src/main/java/org/elasticsearch/repositories/blobstore/testkit/RepositoryAnalyzeAction.java
cancellationListener.addListener(new CheckForCancelListener());
            task.addListener(() -> setFirstFailure(new RepositoryVerificationException(request.repositoryName, "analysis cancelled")));
            final Random random = new Random(request.getSeed());
            final List<DiscoveryNode> nodes = getSnapshotNodes(discoveryNodes);
            if (minClusterTransportVersion.onOrAfter(TransportVersions.V_8_8_0)) {
                final String contendedRegisterName = CONTENDED_REGISTER_NAME_PREFIX + UUIDs.randomBase64UUID(random);
                final AtomicBoolean contendedRegisterAnalysisComplete = new AtomicBoolean();
                try (
                    var registerRefs = new RefCountingRunnable(
                        finalRegisterValueVerifier(
                            contendedRegisterName,
                            random,
                            Releasables.wrap(requestRefs.acquire(), () -> contendedRegisterAnalysisComplete.set(true))
                        )
                    )
                ) {
                    final int registerOperations = Math.max(nodes.size(), request.getConcurrency());
                    for (int i = 0; i < registerOperations; i++) {
                        final ContendedRegisterAnalyzeAction.Request registerAnalyzeRequest = new ContendedRegisterAnalyzeAction.Request(
                            request.getRepositoryName(),
                            blobPath,
                            contendedRegisterName,
                            registerOperations,
                            random.nextInt((registerOperations + 1) * 2)
                        );
                        final DiscoveryNode node = nodes.get(i < nodes.size() ? i : random.nextInt(nodes.size()));
                        final Releasable registerRef = registerRefs.acquire();
                        queue.add(ref -> runContendedRegisterAnalysis(Releasables.wrap(registerRef, ref), registerAnalyzeRequest, node));
                    }
                }