Browse Source

Convert some action.execute cases to using NodeClient (#43715)

There are several cases where execute is called on actions directly,
mostly within other action implementations. Now that transport client is
gone, these internal actions can be registered just like normal actions,
and called with the NodeClient to execute locally on the same node. This
commit converts a few of these cases for shard level actions to use this
approach.
Ryan Ernst 6 years ago
parent
commit
1f3a45cfac
20 changed files with 129 additions and 79 deletions
  1. 47 0
      server/src/main/java/org/elasticsearch/action/Action2.java
  2. 12 16
      server/src/main/java/org/elasticsearch/action/ActionModule.java
  3. 7 5
      server/src/main/java/org/elasticsearch/action/admin/indices/mapping/get/TransportGetFieldMappingsAction.java
  4. 3 0
      server/src/main/java/org/elasticsearch/action/admin/indices/mapping/get/TransportGetFieldMappingsIndexAction.java
  5. 4 8
      server/src/main/java/org/elasticsearch/action/bulk/TransportBulkAction.java
  6. 7 0
      server/src/main/java/org/elasticsearch/action/bulk/TransportShardBulkAction.java
  7. 8 7
      server/src/main/java/org/elasticsearch/action/fieldcaps/TransportFieldCapabilitiesAction.java
  8. 4 0
      server/src/main/java/org/elasticsearch/action/fieldcaps/TransportFieldCapabilitiesIndexAction.java
  9. 5 4
      server/src/main/java/org/elasticsearch/action/get/TransportMultiGetAction.java
  10. 3 0
      server/src/main/java/org/elasticsearch/action/get/TransportShardMultiGetAction.java
  11. 5 4
      server/src/main/java/org/elasticsearch/action/termvectors/TransportMultiTermVectorsAction.java
  12. 7 0
      server/src/main/java/org/elasticsearch/action/termvectors/TransportShardMultiTermsVectorAction.java
  13. 5 20
      server/src/main/java/org/elasticsearch/plugins/ActionPlugin.java
  14. 1 1
      server/src/test/java/org/elasticsearch/action/bulk/TransportBulkActionIndicesThatCannotBeCreatedTests.java
  15. 1 1
      server/src/test/java/org/elasticsearch/action/bulk/TransportBulkActionIngestTests.java
  16. 1 1
      server/src/test/java/org/elasticsearch/action/bulk/TransportBulkActionTests.java
  17. 0 4
      server/src/test/java/org/elasticsearch/action/bulk/TransportBulkActionTookTests.java
  18. 2 2
      server/src/test/java/org/elasticsearch/action/get/TransportMultiGetActionTests.java
  19. 2 2
      server/src/test/java/org/elasticsearch/action/termvectors/TransportMultiTermVectorsActionTests.java
  20. 5 4
      server/src/test/java/org/elasticsearch/snapshots/SnapshotResiliencyTests.java

+ 47 - 0
server/src/main/java/org/elasticsearch/action/Action2.java

@@ -0,0 +1,47 @@
+/*
+ * Licensed to Elasticsearch under one or more contributor
+ * license agreements. See the NOTICE file distributed with
+ * this work for additional information regarding copyright
+ * ownership. Elasticsearch 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.elasticsearch.action;
+
+
+import org.elasticsearch.common.io.stream.Writeable;
+
+/**
+ * An action for which the response class implements {@link org.elasticsearch.common.io.stream.Writeable}.
+ */
+public class Action2<Response extends ActionResponse> extends Action<Response> {
+    private final Writeable.Reader<Response> responseReader;
+
+    public Action2(String name, Writeable.Reader<Response> responseReader) {
+        super(name);
+        this.responseReader = responseReader;
+    }
+
+    @Override
+    public Response newResponse() {
+        throw new UnsupportedOperationException();
+    }
+
+    /**
+     * Get a reader that can create a new instance of the class from a {@link org.elasticsearch.common.io.stream.StreamInput}
+     */
+    public Writeable.Reader<Response> getResponseReader() {
+        return responseReader;
+    }
+}

+ 12 - 16
server/src/main/java/org/elasticsearch/action/ActionModule.java

@@ -412,9 +412,8 @@ public class ActionModule extends AbstractModule {
             }
 
             public <Request extends ActionRequest, Response extends ActionResponse> void register(
-                Action<Response> action, Class<? extends TransportAction<Request, Response>> transportAction,
-                Class<?>... supportTransportActions) {
-                register(new ActionHandler<>(action, transportAction, supportTransportActions));
+                Action<Response> action, Class<? extends TransportAction<Request, Response>> transportAction) {
+                register(new ActionHandler<>(action, transportAction));
             }
         }
         ActionRegistry actions = new ActionRegistry();
@@ -460,8 +459,8 @@ public class ActionModule extends AbstractModule {
         actions.register(OpenIndexAction.INSTANCE, TransportOpenIndexAction.class);
         actions.register(CloseIndexAction.INSTANCE, TransportCloseIndexAction.class);
         actions.register(GetMappingsAction.INSTANCE, TransportGetMappingsAction.class);
-        actions.register(GetFieldMappingsAction.INSTANCE, TransportGetFieldMappingsAction.class,
-                TransportGetFieldMappingsIndexAction.class);
+        actions.register(GetFieldMappingsAction.INSTANCE, TransportGetFieldMappingsAction.class);
+        actions.register(TransportGetFieldMappingsIndexAction.ACTION_INSTANCE, TransportGetFieldMappingsIndexAction.class);
         actions.register(PutMappingAction.INSTANCE, TransportPutMappingAction.class);
         actions.register(IndicesAliasesAction.INSTANCE, TransportIndicesAliasesAction.class);
         actions.register(UpdateSettingsAction.INSTANCE, TransportUpdateSettingsAction.class);
@@ -484,14 +483,14 @@ public class ActionModule extends AbstractModule {
         actions.register(IndexAction.INSTANCE, TransportIndexAction.class);
         actions.register(GetAction.INSTANCE, TransportGetAction.class);
         actions.register(TermVectorsAction.INSTANCE, TransportTermVectorsAction.class);
-        actions.register(MultiTermVectorsAction.INSTANCE, TransportMultiTermVectorsAction.class,
-                TransportShardMultiTermsVectorAction.class);
+        actions.register(MultiTermVectorsAction.INSTANCE, TransportMultiTermVectorsAction.class);
+        actions.register(TransportShardMultiTermsVectorAction.ACTION_INSTANCE, TransportShardMultiTermsVectorAction.class);
         actions.register(DeleteAction.INSTANCE, TransportDeleteAction.class);
         actions.register(UpdateAction.INSTANCE, TransportUpdateAction.class);
-        actions.register(MultiGetAction.INSTANCE, TransportMultiGetAction.class,
-                TransportShardMultiGetAction.class);
-        actions.register(BulkAction.INSTANCE, TransportBulkAction.class,
-                TransportShardBulkAction.class);
+        actions.register(MultiGetAction.INSTANCE, TransportMultiGetAction.class);
+        actions.register(TransportShardMultiGetAction.ACTION_INSTANCE, TransportShardMultiGetAction.class);
+        actions.register(BulkAction.INSTANCE, TransportBulkAction.class);
+        actions.register(TransportShardBulkAction.ACTION_INSTANCE, TransportShardBulkAction.class);
         actions.register(SearchAction.INSTANCE, TransportSearchAction.class);
         actions.register(SearchScrollAction.INSTANCE, TransportSearchScrollAction.class);
         actions.register(MultiSearchAction.INSTANCE, TransportMultiSearchAction.class);
@@ -505,8 +504,8 @@ public class ActionModule extends AbstractModule {
         actions.register(GetStoredScriptAction.INSTANCE, TransportGetStoredScriptAction.class);
         actions.register(DeleteStoredScriptAction.INSTANCE, TransportDeleteStoredScriptAction.class);
 
-        actions.register(FieldCapabilitiesAction.INSTANCE, TransportFieldCapabilitiesAction.class,
-            TransportFieldCapabilitiesIndexAction.class);
+        actions.register(FieldCapabilitiesAction.INSTANCE, TransportFieldCapabilitiesAction.class);
+        actions.register(TransportFieldCapabilitiesIndexAction.ACTION_INSTANCE, TransportFieldCapabilitiesIndexAction.class);
 
         actions.register(PutPipelineAction.INSTANCE, PutPipelineTransportAction.class);
         actions.register(GetPipelineAction.INSTANCE, GetPipelineTransportAction.class);
@@ -693,9 +692,6 @@ public class ActionModule extends AbstractModule {
             // bind the action as eager singleton, so the map binder one will reuse it
             bind(action.getTransportAction()).asEagerSingleton();
             transportActionsBinder.addBinding(action.getAction()).to(action.getTransportAction()).asEagerSingleton();
-            for (Class<?> supportAction : action.getSupportTransportActions()) {
-                bind(supportAction).asEagerSingleton();
-            }
         }
 
     }

+ 7 - 5
server/src/main/java/org/elasticsearch/action/admin/indices/mapping/get/TransportGetFieldMappingsAction.java

@@ -22,6 +22,7 @@ package org.elasticsearch.action.admin.indices.mapping.get;
 import org.elasticsearch.action.ActionListener;
 import org.elasticsearch.action.support.ActionFilters;
 import org.elasticsearch.action.support.HandledTransportAction;
+import org.elasticsearch.client.node.NodeClient;
 import org.elasticsearch.cluster.ClusterState;
 import org.elasticsearch.cluster.metadata.IndexNameExpressionResolver;
 import org.elasticsearch.cluster.service.ClusterService;
@@ -39,17 +40,17 @@ import static java.util.Collections.unmodifiableMap;
 public class TransportGetFieldMappingsAction extends HandledTransportAction<GetFieldMappingsRequest, GetFieldMappingsResponse> {
 
     private final ClusterService clusterService;
-    private final TransportGetFieldMappingsIndexAction shardAction;
     private final IndexNameExpressionResolver indexNameExpressionResolver;
+    private final NodeClient client;
 
     @Inject
     public TransportGetFieldMappingsAction(TransportService transportService, ClusterService clusterService,
-                                           TransportGetFieldMappingsIndexAction shardAction,
-                                           ActionFilters actionFilters, IndexNameExpressionResolver indexNameExpressionResolver) {
+                                           ActionFilters actionFilters, IndexNameExpressionResolver indexNameExpressionResolver,
+                                           NodeClient client) {
         super(GetFieldMappingsAction.NAME, transportService, actionFilters, GetFieldMappingsRequest::new);
         this.clusterService = clusterService;
-        this.shardAction = shardAction;
         this.indexNameExpressionResolver = indexNameExpressionResolver;
+        this.client = client;
     }
 
     @Override
@@ -66,7 +67,8 @@ public class TransportGetFieldMappingsAction extends HandledTransportAction<GetF
             boolean probablySingleFieldRequest = concreteIndices.length == 1 && request.types().length == 1 && request.fields().length == 1;
             for (final String index : concreteIndices) {
                 GetFieldMappingsIndexRequest shardRequest = new GetFieldMappingsIndexRequest(request, index, probablySingleFieldRequest);
-                shardAction.execute(shardRequest, new ActionListener<GetFieldMappingsResponse>() {
+
+                client.executeLocally(TransportGetFieldMappingsIndexAction.ACTION_INSTANCE, shardRequest, new ActionListener<>() {
                     @Override
                     public void onResponse(GetFieldMappingsResponse result) {
                         indexResponses.set(indexCounter.getAndIncrement(), result);

+ 3 - 0
server/src/main/java/org/elasticsearch/action/admin/indices/mapping/get/TransportGetFieldMappingsIndexAction.java

@@ -21,6 +21,8 @@ package org.elasticsearch.action.admin.indices.mapping.get;
 
 import org.elasticsearch.ElasticsearchException;
 import org.elasticsearch.Version;
+import org.elasticsearch.action.Action;
+import org.elasticsearch.action.Action2;
 import org.elasticsearch.action.admin.indices.mapping.get.GetFieldMappingsResponse.FieldMappingMetaData;
 import org.elasticsearch.action.support.ActionFilters;
 import org.elasticsearch.action.support.single.shard.TransportSingleShardAction;
@@ -63,6 +65,7 @@ public class TransportGetFieldMappingsIndexAction
         extends TransportSingleShardAction<GetFieldMappingsIndexRequest, GetFieldMappingsResponse> {
 
     private static final String ACTION_NAME = GetFieldMappingsAction.NAME + "[index]";
+    public static final Action<GetFieldMappingsResponse> ACTION_INSTANCE = new Action2<>(ACTION_NAME, GetFieldMappingsResponse::new);
 
     protected final ClusterService clusterService;
     private final IndicesService indicesService;

+ 4 - 8
server/src/main/java/org/elasticsearch/action/bulk/TransportBulkAction.java

@@ -96,7 +96,6 @@ public class TransportBulkAction extends HandledTransportAction<BulkRequest, Bul
     private final AutoCreateIndex autoCreateIndex;
     private final ClusterService clusterService;
     private final IngestService ingestService;
-    private final TransportShardBulkAction shardBulkAction;
     private final LongSupplier relativeTimeProvider;
     private final IngestActionForwarder ingestForwarder;
     private final NodeClient client;
@@ -105,24 +104,21 @@ public class TransportBulkAction extends HandledTransportAction<BulkRequest, Bul
     @Inject
     public TransportBulkAction(ThreadPool threadPool, TransportService transportService,
                                ClusterService clusterService, IngestService ingestService,
-                               TransportShardBulkAction shardBulkAction, NodeClient client,
-                               ActionFilters actionFilters, IndexNameExpressionResolver indexNameExpressionResolver,
+                               NodeClient client, ActionFilters actionFilters, IndexNameExpressionResolver indexNameExpressionResolver,
                                AutoCreateIndex autoCreateIndex) {
-        this(threadPool, transportService, clusterService, ingestService, shardBulkAction, client, actionFilters,
+        this(threadPool, transportService, clusterService, ingestService, client, actionFilters,
             indexNameExpressionResolver, autoCreateIndex, System::nanoTime);
     }
 
     public TransportBulkAction(ThreadPool threadPool, TransportService transportService,
                                ClusterService clusterService, IngestService ingestService,
-                               TransportShardBulkAction shardBulkAction, NodeClient client,
-                               ActionFilters actionFilters, IndexNameExpressionResolver indexNameExpressionResolver,
+                               NodeClient client, ActionFilters actionFilters, IndexNameExpressionResolver indexNameExpressionResolver,
                                AutoCreateIndex autoCreateIndex, LongSupplier relativeTimeProvider) {
         super(BulkAction.NAME, transportService, actionFilters, (Supplier<BulkRequest>) BulkRequest::new, ThreadPool.Names.WRITE);
         Objects.requireNonNull(relativeTimeProvider);
         this.threadPool = threadPool;
         this.clusterService = clusterService;
         this.ingestService = ingestService;
-        this.shardBulkAction = shardBulkAction;
         this.autoCreateIndex = autoCreateIndex;
         this.relativeTimeProvider = relativeTimeProvider;
         this.ingestForwarder = new IngestActionForwarder(transportService);
@@ -440,7 +436,7 @@ public class TransportBulkAction extends HandledTransportAction<BulkRequest, Bul
                 if (task != null) {
                     bulkShardRequest.setParentTask(nodeId, task.getId());
                 }
-                shardBulkAction.execute(bulkShardRequest, new ActionListener<BulkShardResponse>() {
+                client.executeLocally(TransportShardBulkAction.ACTION_INSTANCE, bulkShardRequest, new ActionListener<>() {
                     @Override
                     public void onResponse(BulkShardResponse bulkShardResponse) {
                         for (BulkItemResponse bulkItemResponse : bulkShardResponse.getResponses()) {

+ 7 - 0
server/src/main/java/org/elasticsearch/action/bulk/TransportShardBulkAction.java

@@ -24,6 +24,7 @@ import org.apache.logging.log4j.Logger;
 import org.apache.logging.log4j.message.ParameterizedMessage;
 import org.apache.logging.log4j.util.MessageSupplier;
 import org.elasticsearch.ExceptionsHelper;
+import org.elasticsearch.action.Action;
 import org.elasticsearch.action.ActionListener;
 import org.elasticsearch.action.ActionRunnable;
 import org.elasticsearch.action.DocWriteRequest;
@@ -77,6 +78,12 @@ import java.util.function.LongSupplier;
 public class TransportShardBulkAction extends TransportWriteAction<BulkShardRequest, BulkShardRequest, BulkShardResponse> {
 
     public static final String ACTION_NAME = BulkAction.NAME + "[s]";
+    public static final Action<BulkShardResponse> ACTION_INSTANCE = new Action<>(ACTION_NAME) {
+        @Override
+        public BulkShardResponse newResponse() {
+            return new BulkShardResponse();
+        }
+    };
 
     private static final Logger logger = LogManager.getLogger(TransportShardBulkAction.class);
 

+ 8 - 7
server/src/main/java/org/elasticsearch/action/fieldcaps/TransportFieldCapabilitiesAction.java

@@ -24,6 +24,7 @@ import org.elasticsearch.action.OriginalIndices;
 import org.elasticsearch.action.support.ActionFilters;
 import org.elasticsearch.action.support.HandledTransportAction;
 import org.elasticsearch.client.Client;
+import org.elasticsearch.client.node.NodeClient;
 import org.elasticsearch.cluster.ClusterState;
 import org.elasticsearch.cluster.metadata.IndexNameExpressionResolver;
 import org.elasticsearch.cluster.service.ClusterService;
@@ -47,21 +48,20 @@ import java.util.Set;
 
 public class TransportFieldCapabilitiesAction extends HandledTransportAction<FieldCapabilitiesRequest, FieldCapabilitiesResponse> {
     private final ThreadPool threadPool;
+    private final NodeClient client;
     private final ClusterService clusterService;
-    private final TransportFieldCapabilitiesIndexAction shardAction;
     private final RemoteClusterService remoteClusterService;
     private final IndexNameExpressionResolver indexNameExpressionResolver;
 
     @Inject
-    public TransportFieldCapabilitiesAction(TransportService transportService,
-                                            ClusterService clusterService, ThreadPool threadPool,
-                                            TransportFieldCapabilitiesIndexAction shardAction,
-                                            ActionFilters actionFilters, IndexNameExpressionResolver indexNameExpressionResolver) {
+    public TransportFieldCapabilitiesAction(TransportService transportService, ClusterService clusterService, ThreadPool threadPool,
+                                            NodeClient client, ActionFilters actionFilters,
+                                            IndexNameExpressionResolver indexNameExpressionResolver) {
         super(FieldCapabilitiesAction.NAME, transportService, actionFilters, FieldCapabilitiesRequest::new);
         this.threadPool = threadPool;
+        this.client = client;
         this.clusterService = clusterService;
         this.remoteClusterService = transportService.getRemoteClusterService();
-        this.shardAction = shardAction;
         this.indexNameExpressionResolver = indexNameExpressionResolver;
     }
 
@@ -108,7 +108,8 @@ public class TransportFieldCapabilitiesAction extends HandledTransportAction<Fie
                 }
             };
             for (String index : concreteIndices) {
-                shardAction.execute(new FieldCapabilitiesIndexRequest(request.fields(), index, localIndices), innerListener);
+                client.executeLocally(TransportFieldCapabilitiesIndexAction.ACTION_INSTANCE,
+                    new FieldCapabilitiesIndexRequest(request.fields(), index, localIndices), innerListener);
             }
 
             // this is the cross cluster part of this API - we force the other cluster to not merge the results but instead

+ 4 - 0
server/src/main/java/org/elasticsearch/action/fieldcaps/TransportFieldCapabilitiesIndexAction.java

@@ -19,6 +19,8 @@
 
 package org.elasticsearch.action.fieldcaps;
 
+import org.elasticsearch.action.Action;
+import org.elasticsearch.action.Action2;
 import org.elasticsearch.action.support.ActionFilters;
 import org.elasticsearch.action.support.single.shard.TransportSingleShardAction;
 import org.elasticsearch.cluster.ClusterState;
@@ -47,6 +49,8 @@ public class TransportFieldCapabilitiesIndexAction extends TransportSingleShardA
     FieldCapabilitiesIndexResponse> {
 
     private static final String ACTION_NAME = FieldCapabilitiesAction.NAME + "[index]";
+    public static final Action<FieldCapabilitiesIndexResponse> ACTION_INSTANCE =
+        new Action2<>(ACTION_NAME, FieldCapabilitiesIndexResponse::new);
 
     private final IndicesService indicesService;
 

+ 5 - 4
server/src/main/java/org/elasticsearch/action/get/TransportMultiGetAction.java

@@ -23,6 +23,7 @@ import org.elasticsearch.action.ActionListener;
 import org.elasticsearch.action.RoutingMissingException;
 import org.elasticsearch.action.support.ActionFilters;
 import org.elasticsearch.action.support.HandledTransportAction;
+import org.elasticsearch.client.node.NodeClient;
 import org.elasticsearch.cluster.ClusterState;
 import org.elasticsearch.cluster.block.ClusterBlockLevel;
 import org.elasticsearch.cluster.metadata.IndexNameExpressionResolver;
@@ -40,16 +41,16 @@ import java.util.concurrent.atomic.AtomicInteger;
 public class TransportMultiGetAction extends HandledTransportAction<MultiGetRequest, MultiGetResponse> {
 
     private final ClusterService clusterService;
-    private final TransportShardMultiGetAction shardAction;
+    private final NodeClient client;
     private final IndexNameExpressionResolver indexNameExpressionResolver;
 
     @Inject
     public TransportMultiGetAction(TransportService transportService, ClusterService clusterService,
-                                   TransportShardMultiGetAction shardAction, ActionFilters actionFilters,
+                                   NodeClient client, ActionFilters actionFilters,
                                    IndexNameExpressionResolver resolver) {
         super(MultiGetAction.NAME, transportService, actionFilters, MultiGetRequest::new);
         this.clusterService = clusterService;
-        this.shardAction = shardAction;
+        this.client = client;
         this.indexNameExpressionResolver = resolver;
     }
 
@@ -105,7 +106,7 @@ public class TransportMultiGetAction extends HandledTransportAction<MultiGetRequ
         final AtomicInteger counter = new AtomicInteger(shardRequests.size());
 
         for (final MultiGetShardRequest shardRequest : shardRequests.values()) {
-            shardAction.execute(shardRequest, new ActionListener<MultiGetShardResponse>() {
+            client.executeLocally(TransportShardMultiGetAction.ACTION_INSTANCE, shardRequest, new ActionListener<>() {
                 @Override
                 public void onResponse(MultiGetShardResponse response) {
                     for (int i = 0; i < response.locations.size(); i++) {

+ 3 - 0
server/src/main/java/org/elasticsearch/action/get/TransportShardMultiGetAction.java

@@ -20,6 +20,8 @@
 package org.elasticsearch.action.get;
 
 import org.apache.logging.log4j.message.ParameterizedMessage;
+import org.elasticsearch.action.Action;
+import org.elasticsearch.action.Action2;
 import org.elasticsearch.action.support.ActionFilters;
 import org.elasticsearch.action.support.TransportActions;
 import org.elasticsearch.action.support.single.shard.TransportSingleShardAction;
@@ -40,6 +42,7 @@ import org.elasticsearch.transport.TransportService;
 public class TransportShardMultiGetAction extends TransportSingleShardAction<MultiGetShardRequest, MultiGetShardResponse> {
 
     private static final String ACTION_NAME = MultiGetAction.NAME + "[shard]";
+    public static final Action<MultiGetShardResponse> ACTION_INSTANCE = new Action2<>(ACTION_NAME, MultiGetShardResponse::new);
 
     private final IndicesService indicesService;
 

+ 5 - 4
server/src/main/java/org/elasticsearch/action/termvectors/TransportMultiTermVectorsAction.java

@@ -23,6 +23,7 @@ import org.elasticsearch.action.ActionListener;
 import org.elasticsearch.action.RoutingMissingException;
 import org.elasticsearch.action.support.ActionFilters;
 import org.elasticsearch.action.support.HandledTransportAction;
+import org.elasticsearch.client.node.NodeClient;
 import org.elasticsearch.cluster.ClusterState;
 import org.elasticsearch.cluster.block.ClusterBlockLevel;
 import org.elasticsearch.cluster.metadata.IndexNameExpressionResolver;
@@ -41,16 +42,16 @@ import java.util.concurrent.atomic.AtomicInteger;
 public class TransportMultiTermVectorsAction extends HandledTransportAction<MultiTermVectorsRequest, MultiTermVectorsResponse> {
 
     private final ClusterService clusterService;
-    private final TransportShardMultiTermsVectorAction shardAction;
+    private final NodeClient client;
     private final IndexNameExpressionResolver indexNameExpressionResolver;
 
     @Inject
     public TransportMultiTermVectorsAction(TransportService transportService, ClusterService clusterService,
-                                           TransportShardMultiTermsVectorAction shardAction, ActionFilters actionFilters,
+                                           NodeClient client, ActionFilters actionFilters,
                                            IndexNameExpressionResolver indexNameExpressionResolver) {
         super(MultiTermVectorsAction.NAME, transportService, actionFilters, MultiTermVectorsRequest::new);
         this.clusterService = clusterService;
-        this.shardAction = shardAction;
+        this.client = client;
         this.indexNameExpressionResolver = indexNameExpressionResolver;
     }
 
@@ -106,7 +107,7 @@ public class TransportMultiTermVectorsAction extends HandledTransportAction<Mult
         final AtomicInteger counter = new AtomicInteger(shardRequests.size());
 
         for (final MultiTermVectorsShardRequest shardRequest : shardRequests.values()) {
-            shardAction.execute(shardRequest, new ActionListener<MultiTermVectorsShardResponse>() {
+            client.executeLocally(TransportShardMultiTermsVectorAction.ACTION_INSTANCE, shardRequest, new ActionListener<>() {
                 @Override
                 public void onResponse(MultiTermVectorsShardResponse response) {
                     for (int i = 0; i < response.locations.size(); i++) {

+ 7 - 0
server/src/main/java/org/elasticsearch/action/termvectors/TransportShardMultiTermsVectorAction.java

@@ -20,6 +20,7 @@
 package org.elasticsearch.action.termvectors;
 
 import org.apache.logging.log4j.message.ParameterizedMessage;
+import org.elasticsearch.action.Action;
 import org.elasticsearch.action.support.ActionFilters;
 import org.elasticsearch.action.support.TransportActions;
 import org.elasticsearch.action.support.single.shard.TransportSingleShardAction;
@@ -43,6 +44,12 @@ public class TransportShardMultiTermsVectorAction extends
     private final IndicesService indicesService;
 
     private static final String ACTION_NAME = MultiTermVectorsAction.NAME + "[shard]";
+    public static final Action<MultiTermVectorsShardResponse> ACTION_INSTANCE = new Action<>(ACTION_NAME) {
+        @Override
+        public MultiTermVectorsShardResponse newResponse() {
+            return new MultiTermVectorsShardResponse();
+        }
+    };
 
     @Inject
     public TransportShardMultiTermsVectorAction(ClusterService clusterService, TransportService transportService,

+ 5 - 20
server/src/main/java/org/elasticsearch/plugins/ActionPlugin.java

@@ -27,10 +27,8 @@ import org.elasticsearch.action.admin.indices.alias.IndicesAliasesRequest;
 import org.elasticsearch.action.admin.indices.mapping.put.PutMappingRequest;
 import org.elasticsearch.action.support.ActionFilter;
 import org.elasticsearch.action.support.TransportAction;
-import org.elasticsearch.action.support.TransportActions;
 import org.elasticsearch.cluster.metadata.IndexNameExpressionResolver;
 import org.elasticsearch.cluster.node.DiscoveryNodes;
-import org.elasticsearch.common.Strings;
 import org.elasticsearch.common.settings.ClusterSettings;
 import org.elasticsearch.common.settings.IndexScopedSettings;
 import org.elasticsearch.common.settings.Settings;
@@ -132,17 +130,13 @@ public interface ActionPlugin {
     final class ActionHandler<Request extends ActionRequest, Response extends ActionResponse> {
         private final Action<Response> action;
         private final Class<? extends TransportAction<Request, Response>> transportAction;
-        private final Class<?>[] supportTransportActions;
 
         /**
-         * Create a record of an action, the {@linkplain TransportAction} that handles it, and any supporting {@linkplain TransportActions}
-         * that are needed by that {@linkplain TransportAction}.
+         * Create a record of an action, the {@linkplain TransportAction} that handles it.
          */
-        public ActionHandler(Action<Response> action, Class<? extends TransportAction<Request, Response>> transportAction,
-                             Class<?>... supportTransportActions) {
+        public ActionHandler(Action<Response> action, Class<? extends TransportAction<Request, Response>> transportAction) {
             this.action = action;
             this.transportAction = transportAction;
-            this.supportTransportActions = supportTransportActions;
         }
 
         public Action<Response> getAction() {
@@ -153,17 +147,9 @@ public interface ActionPlugin {
             return transportAction;
         }
 
-        public Class<?>[] getSupportTransportActions() {
-            return supportTransportActions;
-        }
-
         @Override
         public String toString() {
-            StringBuilder b = new StringBuilder().append(action.name()).append(" is handled by ").append(transportAction.getName());
-            if (supportTransportActions.length > 0) {
-                b.append('[').append(Strings.arrayToCommaDelimitedString(supportTransportActions)).append(']');
-            }
-            return b.toString();
+            return action.name() + " is handled by " + transportAction.getName();
         }
 
         @Override
@@ -173,13 +159,12 @@ public interface ActionPlugin {
             }
             ActionHandler<?, ?> other = (ActionHandler<?, ?>) obj;
             return Objects.equals(action, other.action)
-                    && Objects.equals(transportAction, other.transportAction)
-                    && Objects.deepEquals(supportTransportActions, other.supportTransportActions);
+                    && Objects.equals(transportAction, other.transportAction);
         }
 
         @Override
         public int hashCode() {
-            return Objects.hash(action, transportAction, supportTransportActions);
+            return Objects.hash(action, transportAction);
         }
     }
 

+ 1 - 1
server/src/test/java/org/elasticsearch/action/bulk/TransportBulkActionIndicesThatCannotBeCreatedTests.java

@@ -110,7 +110,7 @@ public class TransportBulkActionIndicesThatCannotBeCreatedTests extends ESTestCa
         final ExecutorService direct = EsExecutors.newDirectExecutorService();
         when(threadPool.executor(anyString())).thenReturn(direct);
         TransportBulkAction action = new TransportBulkAction(threadPool, mock(TransportService.class), clusterService,
-                null, null, null, mock(ActionFilters.class), null, null) {
+                null, null, mock(ActionFilters.class), null, null) {
             @Override
             void executeBulk(Task task, BulkRequest bulkRequest, long startTimeNanos, ActionListener<BulkResponse> listener,
                     AtomicArray<BulkItemResponse> responses, Map<String, IndexNotFoundException> indicesThatCannotBeCreated) {

+ 1 - 1
server/src/test/java/org/elasticsearch/action/bulk/TransportBulkActionIngestTests.java

@@ -133,7 +133,7 @@ public class TransportBulkActionIngestTests extends ESTestCase {
 
         TestTransportBulkAction() {
             super(threadPool, transportService, clusterService, ingestService,
-                null, null, new ActionFilters(Collections.emptySet()), null,
+                null, new ActionFilters(Collections.emptySet()), null,
                 new AutoCreateIndex(
                     SETTINGS, new ClusterSettings(SETTINGS, ClusterSettings.BUILT_IN_CLUSTER_SETTINGS),
                     new IndexNameExpressionResolver()

+ 1 - 1
server/src/test/java/org/elasticsearch/action/bulk/TransportBulkActionTests.java

@@ -59,7 +59,7 @@ public class TransportBulkActionTests extends ESTestCase {
         boolean indexCreated = false; // set when the "real" index is created
 
         TestTransportBulkAction() {
-            super(TransportBulkActionTests.this.threadPool, transportService, clusterService, null, null,
+            super(TransportBulkActionTests.this.threadPool, transportService, clusterService, null,
                     null, new ActionFilters(Collections.emptySet()), new Resolver(),
                     new AutoCreateIndex(Settings.EMPTY, clusterService.getClusterSettings(), new Resolver()));
         }

+ 0 - 4
server/src/test/java/org/elasticsearch/action/bulk/TransportBulkActionTookTests.java

@@ -115,7 +115,6 @@ public class TransportBulkActionTookTests extends ESTestCase {
                     threadPool,
                     transportService,
                     clusterService,
-                    null,
                     client,
                     actionFilters,
                     resolver,
@@ -139,7 +138,6 @@ public class TransportBulkActionTookTests extends ESTestCase {
                     threadPool,
                     transportService,
                     clusterService,
-                    null,
                     client,
                     actionFilters,
                     resolver,
@@ -218,7 +216,6 @@ public class TransportBulkActionTookTests extends ESTestCase {
                 ThreadPool threadPool,
                 TransportService transportService,
                 ClusterService clusterService,
-                TransportShardBulkAction shardBulkAction,
                 NodeClient client,
                 ActionFilters actionFilters,
                 IndexNameExpressionResolver indexNameExpressionResolver,
@@ -229,7 +226,6 @@ public class TransportBulkActionTookTests extends ESTestCase {
                     transportService,
                     clusterService,
                     null,
-                    shardBulkAction,
                     client,
                     actionFilters,
                     indexNameExpressionResolver,

+ 2 - 2
server/src/test/java/org/elasticsearch/action/get/TransportMultiGetActionTests.java

@@ -170,7 +170,7 @@ public class TransportMultiGetActionTests extends ESTestCase {
         request.add(new MultiGetRequest.Item("index1", "_doc", "2"));
 
         final AtomicBoolean shardActionInvoked = new AtomicBoolean(false);
-        transportAction = new TransportMultiGetAction(transportService, clusterService, shardAction,
+        transportAction = new TransportMultiGetAction(transportService, clusterService, client,
             new ActionFilters(emptySet()), new Resolver()) {
             @Override
             protected void executeShardAction(final ActionListener<MultiGetResponse> listener,
@@ -195,7 +195,7 @@ public class TransportMultiGetActionTests extends ESTestCase {
         request.add(new MultiGetRequest.Item("index2", "_doc", "2"));
 
         final AtomicBoolean shardActionInvoked = new AtomicBoolean(false);
-        transportAction = new TransportMultiGetAction(transportService, clusterService, shardAction,
+        transportAction = new TransportMultiGetAction(transportService, clusterService, client,
             new ActionFilters(emptySet()), new Resolver()) {
             @Override
             protected void executeShardAction(final ActionListener<MultiGetResponse> listener,

+ 2 - 2
server/src/test/java/org/elasticsearch/action/termvectors/TransportMultiTermVectorsActionTests.java

@@ -172,7 +172,7 @@ public class TransportMultiTermVectorsActionTests extends ESTestCase {
         request.add(new TermVectorsRequest("index2", "2"));
 
         final AtomicBoolean shardActionInvoked = new AtomicBoolean(false);
-        transportAction = new TransportMultiTermVectorsAction(transportService, clusterService, shardAction,
+        transportAction = new TransportMultiTermVectorsAction(transportService, clusterService, client,
             new ActionFilters(emptySet()), new Resolver()) {
             @Override
             protected void executeShardAction(final ActionListener<MultiTermVectorsResponse> listener,
@@ -197,7 +197,7 @@ public class TransportMultiTermVectorsActionTests extends ESTestCase {
         request.add(new TermVectorsRequest("index2", "2"));
 
         final AtomicBoolean shardActionInvoked = new AtomicBoolean(false);
-        transportAction = new TransportMultiTermVectorsAction(transportService, clusterService, shardAction,
+        transportAction = new TransportMultiTermVectorsAction(transportService, clusterService, client,
             new ActionFilters(emptySet()), new Resolver()) {
             @Override
             protected void executeShardAction(final ActionListener<MultiTermVectorsResponse> listener,

+ 5 - 4
server/src/test/java/org/elasticsearch/snapshots/SnapshotResiliencyTests.java

@@ -1018,18 +1018,19 @@ public class SnapshotResiliencyTests extends ESTestCase {
                 ));
             final MappingUpdatedAction mappingUpdatedAction = new MappingUpdatedAction(settings, clusterSettings);
             mappingUpdatedAction.setClient(client);
-            final TransportShardBulkAction transportShardBulkAction = new TransportShardBulkAction(settings, transportService,
-                clusterService, indicesService, threadPool, shardStateAction, mappingUpdatedAction, new UpdateHelper(scriptService),
-                actionFilters, indexNameExpressionResolver);
             actions.put(BulkAction.INSTANCE,
                 new TransportBulkAction(threadPool, transportService, clusterService,
                     new IngestService(
                         clusterService, threadPool, environment, scriptService,
                         new AnalysisModule(environment, Collections.emptyList()).getAnalysisRegistry(),
                         Collections.emptyList()),
-                    transportShardBulkAction, client, actionFilters, indexNameExpressionResolver,
+                    client, actionFilters, indexNameExpressionResolver,
                     new AutoCreateIndex(settings, clusterSettings, indexNameExpressionResolver)
                 ));
+            final TransportShardBulkAction transportShardBulkAction = new TransportShardBulkAction(settings, transportService,
+                clusterService, indicesService, threadPool, shardStateAction, mappingUpdatedAction, new UpdateHelper(scriptService),
+                actionFilters, indexNameExpressionResolver);
+            actions.put(TransportShardBulkAction.ACTION_INSTANCE, transportShardBulkAction);
             final RestoreService restoreService = new RestoreService(
                 clusterService, repositoriesService, allocationService,
                 metaDataCreateIndexService,