diff options
-rw-r--r-- | src/mongo/executor/remote_command_retry_policy.h | 77 | ||||
-rw-r--r-- | src/mongo/executor/remote_command_runner_test.cpp | 25 | ||||
-rw-r--r-- | src/mongo/executor/remote_command_targeter.h | 82 |
3 files changed, 184 insertions, 0 deletions
diff --git a/src/mongo/executor/remote_command_retry_policy.h b/src/mongo/executor/remote_command_retry_policy.h new file mode 100644 index 00000000000..ea0d09613c8 --- /dev/null +++ b/src/mongo/executor/remote_command_retry_policy.h @@ -0,0 +1,77 @@ +/** + * Copyright (C) 2022-present MongoDB, Inc. + * + * This program is free software: you can redistribute it and/or modify + * it under the terms of the Server Side Public License, version 1, + * as published by MongoDB, Inc. + * + * This program is distributed in the hope that it will be useful, + * but WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + * Server Side Public License for more details. + * + * You should have received a copy of the Server Side Public License + * along with this program. If not, see + * <http://www.mongodb.com/licensing/server-side-public-license>. + * + * As a special exception, the copyright holders give permission to link the + * code of portions of this program with the OpenSSL library under certain + * conditions as described in each individual source file and distribute + * linked combinations including the program with the OpenSSL library. You + * must comply with the Server Side Public License in all respects for + * all of the code used other than as permitted herein. If you modify file(s) + * with this exception, you may extend this exception to your version of the + * file(s), but you are not obligated to do so. If you do not wish to do so, + * delete this exception statement from your version. If you delete this + * exception statement from all source files in the program, then also delete + * it in the license file. + */ + +#pragma once + +#include "mongo/base/status.h" +#include "mongo/bson/bsonobj.h" +#include "mongo/executor/remote_command_request.h" +#include "mongo/util/duration.h" +#include "mongo/util/time_support.h" +#include <string> + +namespace mongo { +namespace executor { +namespace remote_command_runner { + +class RemoteCommandRetryPolicy { +public: + /** + * Given an error, returns true if the scheduler should retry the remote command. + */ + virtual bool shouldRetry(Status s) const = 0; + + /** + * Retry scheduler should wait this long in between retrying remote commands. + */ + virtual Milliseconds getNextRetryDelay() = 0; + + virtual BSONObj toBSON() const = 0; + + virtual ~RemoteCommandRetryPolicy() = default; +}; + +class RemoteCommandNoRetryPolicy : public RemoteCommandRetryPolicy { +public: + bool shouldRetry(Status s) const override final { + return false; + } + + Milliseconds getNextRetryDelay() override final { + return Milliseconds::zero(); + } + + BSONObj toBSON() const override final { + return BSON("retryPolicyType" + << "NoRetryPolicy"); + } +}; +} // namespace remote_command_runner +} // namespace executor +} // namespace mongo diff --git a/src/mongo/executor/remote_command_runner_test.cpp b/src/mongo/executor/remote_command_runner_test.cpp index 2534c3f949e..2623db371af 100644 --- a/src/mongo/executor/remote_command_runner_test.cpp +++ b/src/mongo/executor/remote_command_runner_test.cpp @@ -27,7 +27,9 @@ * it in the license file. */ +#include "mongo/executor/remote_command_retry_policy.h" #include "mongo/executor/remote_command_runner.h" +#include "mongo/executor/remote_command_targeter.h" #include "mongo/bson/oid.h" #include "mongo/db/repl/hello_gen.h" @@ -39,6 +41,7 @@ #include "mongo/rpc/topology_version_gen.h" #include "mongo/unittest/bson_test_util.h" #include "mongo/unittest/unittest.h" +#include "mongo/util/duration.h" #include "mongo/util/future.h" #include <memory> @@ -196,6 +199,28 @@ TEST_F(RemoteCommandRunnerTestFixture, WriteError) { ASSERT_THROWS_CODE(resultFuture.get(), DBException, ErrorCodes::DocumentValidationFailure); } +/* + * Basic Targeter that returns the host that invoked it. + */ +TEST_F(RemoteCommandRunnerTestFixture, LocalTargeter) { + RemoteCommandLocalHostTargeter t; + auto targetFuture = t.resolve(_cancellationToken); + auto target = targetFuture.get(); + + ASSERT_EQ(target.size(), 1); + ASSERT_EQ(HostAndPort("localhost", serverGlobalParams.port), target[0]); +} + +/* + * Basic RetryPolicy that never retries. + */ +TEST_F(RemoteCommandRunnerTestFixture, NoRetry) { + RemoteCommandNoRetryPolicy p; + + ASSERT_FALSE(p.shouldRetry(Status(ErrorCodes::BadValue, "mock"))); + ASSERT_EQUALS(p.getNextRetryDelay(), Milliseconds::zero()); +} + } // namespace } // namespace remote_command_runner } // namespace executor diff --git a/src/mongo/executor/remote_command_targeter.h b/src/mongo/executor/remote_command_targeter.h new file mode 100644 index 00000000000..2af287d6c8e --- /dev/null +++ b/src/mongo/executor/remote_command_targeter.h @@ -0,0 +1,82 @@ +/** + * Copyright (C) 2022-present MongoDB, Inc. + * + * This program is free software: you can redistribute it and/or modify + * it under the terms of the Server Side Public License, version 1, + * as published by MongoDB, Inc. + * + * This program is distributed in the hope that it will be useful, + * but WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + * Server Side Public License for more details. + * + * You should have received a copy of the Server Side Public License + * along with this program. If not, see + * <http://www.mongodb.com/licensing/server-side-public-license>. + * + * As a special exception, the copyright holders give permission to link the + * code of portions of this program with the OpenSSL library under certain + * conditions as described in each individual source file and distribute + * linked combinations including the program with the OpenSSL library. You + * must comply with the Server Side Public License in all respects for + * all of the code used other than as permitted herein. If you modify file(s) + * with this exception, you may extend this exception to your version of the + * file(s), but you are not obligated to do so. If you do not wish to do so, + * delete this exception statement from your version. If you delete this + * exception statement from all source files in the program, then also delete + * it in the license file. + */ + +#pragma once + +#include "mongo/base/status.h" +#include "mongo/client/read_preference.h" +#include "mongo/db/auth/validated_tenancy_scope.h" +#include "mongo/db/operation_context.h" +#include "mongo/db/server_options.h" +#include "mongo/util/assert_util.h" +#include "mongo/util/cancellation.h" +#include "mongo/util/future.h" +#include "mongo/util/net/hostandport.h" +#include <vector> + +namespace mongo { +namespace executor { +namespace remote_command_runner { + +class RemoteCommandHostTargeter { +public: + RemoteCommandHostTargeter() = default; + + virtual ~RemoteCommandHostTargeter() = default; + + /* + * Returns a collection of possible Hosts on which the command may run based on the specific + * settings (ReadPreference, etc.) of the targeter. + */ + virtual SemiFuture<std::vector<HostAndPort>> resolve(CancellationToken t) = 0; + + /* + * Informs the RemoteHostTargeter that an error happened when trying to run a command on a + * HostAndPort. Allows the targeter to update its view of the cluster's topology if network + * or shutdown errors are recieved. + */ + virtual void onRemoteCommandError(HostAndPort h, Status s) = 0; +}; + +class RemoteCommandLocalHostTargeter : public RemoteCommandHostTargeter { +public: + RemoteCommandLocalHostTargeter() = default; + + SemiFuture<std::vector<HostAndPort>> resolve(CancellationToken t) override final { + HostAndPort h = HostAndPort("localhost", serverGlobalParams.port); + std::vector<HostAndPort> hostList{h}; + + return SemiFuture<std::vector<HostAndPort>>::makeReady(hostList); + } + + void onRemoteCommandError(HostAndPort h, Status s) override final {} +}; +} // namespace remote_command_runner +} // namespace executor +} // namespace mongo |