Skip to content

Commit

Permalink
Improve the Sync_MultipleSyncAgentsNotAllowed test
Browse files Browse the repository at this point in the history
  • Loading branch information
tgoyne committed May 29, 2024
1 parent 21ed9fe commit fd05f55
Show file tree
Hide file tree
Showing 4 changed files with 48 additions and 48 deletions.
18 changes: 0 additions & 18 deletions src/realm/sync/network/default_socket.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -543,24 +543,6 @@ void DefaultSocketProvider::start()
state_wait_for(lock, State::Running);
}

void DefaultSocketProvider::OnlyForTesting::run_event_loop_on_current_thread(DefaultSocketProvider* provider)
{
{
util::CheckedLockGuard lk(provider->m_mutex);
REALM_ASSERT(provider->m_state == State::Stopped);
provider->do_state_update(State::Starting);
}

provider->event_loop();
}

void DefaultSocketProvider::OnlyForTesting::prep_event_loop_for_restart(DefaultSocketProvider* provider)
{
util::CheckedLockGuard lk(provider->m_mutex);
REALM_ASSERT(provider->m_state == State::Stopped);
provider->m_service.reset();
}

void DefaultSocketProvider::event_loop()
{
m_logger_ptr->trace("Default event loop: thread running");
Expand Down
8 changes: 0 additions & 8 deletions src/realm/sync/network/default_socket.hpp
Original file line number Diff line number Diff line change
Expand Up @@ -76,14 +76,6 @@ class DefaultSocketProvider : public SyncSocketProvider {
return std::unique_ptr<Timer>(new DefaultSocketProvider::Timer(m_service, delay, std::move(handler)));
}

struct OnlyForTesting {
// Runs the event loop as though start() was called on the current thread so that the caller
// can catch and handle any thrown exceptions in tests.
static void run_event_loop_on_current_thread(DefaultSocketProvider* provider);

static void prep_event_loop_for_restart(DefaultSocketProvider* provider);
};

private:
enum class State { Starting, Running, Stopping, Stopped };

Expand Down
5 changes: 4 additions & 1 deletion test/sync_fixtures.hpp
Original file line number Diff line number Diff line change
Expand Up @@ -464,6 +464,8 @@ class MultiClientServerFixture {
std::set<file_ident_type> server_disable_download_for;

std::function<Server::SessionBootstrapCallback> server_session_bootstrap_callback;

std::shared_ptr<BindingCallbackThreadObserver> socket_provider_observer;
};


Expand Down Expand Up @@ -541,7 +543,8 @@ class MultiClientServerFixture {
Client::Config config_2;

m_client_socket_providers.push_back(std::make_shared<websocket::DefaultSocketProvider>(
m_client_loggers[i], "", nullptr, websocket::DefaultSocketProvider::AutoStart{false}));
m_client_loggers[i], "", config.socket_provider_observer,
websocket::DefaultSocketProvider::AutoStart{false}));
config_2.socket_provider = m_client_socket_providers.back();
config_2.logger = m_client_loggers[i];
config_2.reconnect_mode = ReconnectMode::testing;
Expand Down
65 changes: 44 additions & 21 deletions test/test_sync.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -3804,30 +3804,53 @@ TEST(Sync_MultipleSyncAgentsNotAllowed)
// particular session participant over the "temporally overlapping access"
// relation.

TEST_DIR(server_dir);
TEST_CLIENT_DB(db);
Client::Config config;
config.logger = test_context.logger;
auto socket_provider = std::make_shared<websocket::DefaultSocketProvider>(
config.logger, "", nullptr, websocket::DefaultSocketProvider::AutoStart{false});
config.socket_provider = socket_provider;
config.reconnect_mode = ReconnectMode::testing;
Client client{config};
{
Session::Config config_1;
config_1.realm_identifier = "blablabla";
Session::Config config_2;
config_2.realm_identifier = config_1.realm_identifier;
Session session_1{client, db, nullptr, nullptr, std::move(config_1)};
Session session_2{client, db, nullptr, nullptr, std::move(config_2)};
session_1.bind();
session_2.bind();
CHECK_THROW(
websocket::DefaultSocketProvider::OnlyForTesting::run_event_loop_on_current_thread(socket_provider.get()),
MultipleSyncAgents);
websocket::DefaultSocketProvider::OnlyForTesting::prep_event_loop_for_restart(socket_provider.get());

auto pf = util::make_promise_future<void>();
struct Observer : BindingCallbackThreadObserver {
unit_test::TestContext& test_context;
util::Promise<void>& got_error;
Observer(unit_test::TestContext& test_context, util::Promise<void>& got_error)
: test_context(test_context)
, got_error(got_error)
{
}

bool has_handle_error() override
{
return true;
}
bool handle_error(const std::exception& e) override
{
CHECK(dynamic_cast<const MultipleSyncAgents*>(&e));
got_error.emplace_value();
return true;
}
};

auto observer = std::make_shared<Observer>(test_context, pf.promise);
ClientServerFixture::Config config;
config.socket_provider_observer = observer;
ClientServerFixture fixture(server_dir, test_context, std::move(config));
fixture.start();

{
Session session = fixture.make_session(db, "/test");
session.bind();
Session session2 = fixture.make_session(db, "/test");
session2.bind();
pf.future.get();

// The exception caused the event loop to stop so we need to restart it
fixture.start_client(0);
}

socket_provider->start();
// Verify that after the error occurs (and is ignored) things are still
// in a functional state
Session session = fixture.make_session(db, "/test");
session.bind();
session.wait_for_upload_complete_or_client_stopped();
}

TEST(Sync_CancelReconnectDelay)
Expand Down

0 comments on commit fd05f55

Please sign in to comment.