service: Rename topology::transition_state::tablet_split_finalization
This transition state will be reused by merge completion, so let's rename it to tablet_resize_finalization. The completion handling path will also be reused, so let's rename functions involved similarly. The old name "tablet split finalization" is deprecated but still recognized and points to the correct transition. Otherwise, the reverse lookup would fail when populating topology system table which last state was split finalization. NOTE: I thought of adding a new tablet_merge_finalization, but it would complicate things since more than one table could be ready for either split or merge, so you need a generic transition state for handling resize completion. Signed-off-by: Raphael S. Carvalho <raphaelsc@scylladb.com>
This commit is contained in:
@@ -369,7 +369,7 @@ emits a decision to finalize the split request. The finalization is serialized w
|
||||
doubling tablet count would interfere with the migration process.
|
||||
|
||||
When the state machine leaves the migration track, and there are tablets waiting for tablet split to
|
||||
be finalized, the topology will transition into `tablet_split_finalization` state. At this moment, there will
|
||||
be finalized, the topology will transition into `tablet_resize_finalization` state. At this moment, there will
|
||||
be no migration running in the system. A global token metadata barrier is executed to make sure that no
|
||||
process e.g. repair will be holding stale metadata when finalizing split. After that, the new tablet map,
|
||||
which is a result of splitting each preexisting tablet into two, is committed to group0.
|
||||
|
||||
@@ -756,7 +756,7 @@ future<> storage_service::topology_state_load(state_change_hint hint) {
|
||||
[[fallthrough]];
|
||||
case topology::transition_state::tablet_migration:
|
||||
[[fallthrough]];
|
||||
case topology::transition_state::tablet_split_finalization:
|
||||
case topology::transition_state::tablet_resize_finalization:
|
||||
[[fallthrough]];
|
||||
case topology::transition_state::commit_cdc_generation:
|
||||
[[fallthrough]];
|
||||
|
||||
@@ -2538,7 +2538,7 @@ public:
|
||||
load_balancer_stats_manager& stats() {
|
||||
return _load_balancer_stats;
|
||||
}
|
||||
|
||||
private:
|
||||
// The splitting of tablets today is completely based on the power-of-two constraint.
|
||||
// A tablet of id X is split into 2 new tablets, which new ids are (x << 1) and
|
||||
// (x << 1) + 1.
|
||||
@@ -2565,6 +2565,14 @@ public:
|
||||
table, tablets.tablet_count(), new_tablets.tablet_count());
|
||||
co_return std::move(new_tablets);
|
||||
}
|
||||
public:
|
||||
future<tablet_map> resize_tablets(token_metadata_ptr tm, table_id table) {
|
||||
auto& tmap = tm->tablets().get_tablet_map(table);
|
||||
if (tmap.needs_split()) {
|
||||
return split_tablets(std::move(tm), table);
|
||||
}
|
||||
throw std::logic_error(format("Table {} cannot be resized", table));
|
||||
}
|
||||
|
||||
// FIXME: Handle materialized views.
|
||||
};
|
||||
@@ -2598,8 +2606,8 @@ void tablet_allocator::set_use_table_aware_balancing(bool use_tablet_aware_balan
|
||||
impl().set_use_tablet_aware_balancing(use_tablet_aware_balancing);
|
||||
}
|
||||
|
||||
future<locator::tablet_map> tablet_allocator::split_tablets(locator::token_metadata_ptr tm, table_id table) {
|
||||
return impl().split_tablets(std::move(tm), table);
|
||||
future<locator::tablet_map> tablet_allocator::resize_tablets(locator::token_metadata_ptr tm, table_id table) {
|
||||
return impl().resize_tablets(std::move(tm), table);
|
||||
}
|
||||
|
||||
tablet_allocator_impl& tablet_allocator::impl() {
|
||||
|
||||
@@ -234,7 +234,7 @@ public:
|
||||
|
||||
void set_use_table_aware_balancing(bool);
|
||||
|
||||
future<locator::tablet_map> split_tablets(locator::token_metadata_ptr, table_id);
|
||||
future<locator::tablet_map> resize_tablets(locator::token_metadata_ptr, table_id);
|
||||
|
||||
/// Should be called when the node is no longer a leader.
|
||||
void on_leadership_lost();
|
||||
|
||||
@@ -1464,7 +1464,7 @@ class topology_coordinator : public endpoint_lifecycle_subscriber {
|
||||
co_await update_topology_state(std::move(guard), std::move(updates), "Finished tablet migration");
|
||||
}
|
||||
|
||||
future<> handle_tablet_split_finalization(group0_guard g) {
|
||||
future<> handle_tablet_resize_finalization(group0_guard g) {
|
||||
// Executes a global barrier to guarantee that any process (e.g. repair) holding stale version
|
||||
// of token metadata will complete before we update topology.
|
||||
auto guard = co_await global_tablet_token_metadata_barrier(std::move(g));
|
||||
@@ -1477,7 +1477,7 @@ class topology_coordinator : public endpoint_lifecycle_subscriber {
|
||||
|
||||
for (auto& table_id : plan.resize_plan().finalize_resize) {
|
||||
auto s = _db.find_schema(table_id);
|
||||
auto new_tablet_map = co_await _tablet_allocator.split_tablets(tm, table_id);
|
||||
auto new_tablet_map = co_await _tablet_allocator.resize_tablets(tm, table_id);
|
||||
updates.emplace_back(co_await replica::tablet_map_to_mutation(
|
||||
new_tablet_map,
|
||||
table_id,
|
||||
@@ -2095,8 +2095,8 @@ class topology_coordinator : public endpoint_lifecycle_subscriber {
|
||||
case topology::transition_state::tablet_migration:
|
||||
co_await handle_tablet_migration(std::move(guard), false);
|
||||
break;
|
||||
case topology::transition_state::tablet_split_finalization:
|
||||
co_await handle_tablet_split_finalization(std::move(guard));
|
||||
case topology::transition_state::tablet_resize_finalization:
|
||||
co_await handle_tablet_resize_finalization(std::move(guard));
|
||||
break;
|
||||
case topology::transition_state::left_token_ring: {
|
||||
auto node = get_node_to_work_on(std::move(guard));
|
||||
@@ -2544,8 +2544,8 @@ class topology_coordinator : public endpoint_lifecycle_subscriber {
|
||||
// Returns true if the state machine was transitioned into tablet migration path.
|
||||
future<bool> maybe_start_tablet_migration(group0_guard);
|
||||
|
||||
// Returns true if the state machine was transitioned into tablet split finalization path.
|
||||
future<bool> maybe_start_tablet_split_finalization(group0_guard, const table_resize_plan& plan);
|
||||
// Returns true if the state machine was transitioned into tablet resize finalization path.
|
||||
future<bool> maybe_start_tablet_resize_finalization(group0_guard, const table_resize_plan& plan);
|
||||
|
||||
future<locator::load_stats> refresh_tablet_load_stats();
|
||||
future<> start_tablet_load_stats_refresher();
|
||||
@@ -2638,10 +2638,10 @@ future<bool> topology_coordinator::maybe_start_tablet_migration(group0_guard gua
|
||||
|
||||
co_await generate_migration_updates(updates, guard, plan);
|
||||
|
||||
// We only want to consider transitioning into tablet split finalization path, if there's no other work
|
||||
// We only want to consider transitioning into tablet resize finalization path, if there's no other work
|
||||
// to be done (e.g. start migration or/and emit split decision).
|
||||
if (updates.empty()) {
|
||||
co_return co_await maybe_start_tablet_split_finalization(std::move(guard), plan.resize_plan());
|
||||
co_return co_await maybe_start_tablet_resize_finalization(std::move(guard), plan.resize_plan());
|
||||
}
|
||||
|
||||
updates.emplace_back(
|
||||
@@ -2654,7 +2654,7 @@ future<bool> topology_coordinator::maybe_start_tablet_migration(group0_guard gua
|
||||
co_return true;
|
||||
}
|
||||
|
||||
future<bool> topology_coordinator::maybe_start_tablet_split_finalization(group0_guard guard, const table_resize_plan& plan) {
|
||||
future<bool> topology_coordinator::maybe_start_tablet_resize_finalization(group0_guard guard, const table_resize_plan& plan) {
|
||||
if (plan.finalize_resize.empty()) {
|
||||
co_return false;
|
||||
}
|
||||
@@ -2666,11 +2666,11 @@ future<bool> topology_coordinator::maybe_start_tablet_split_finalization(group0_
|
||||
|
||||
updates.emplace_back(
|
||||
topology_mutation_builder(guard.write_timestamp())
|
||||
.set_transition_state(topology::transition_state::tablet_split_finalization)
|
||||
.set_transition_state(topology::transition_state::tablet_resize_finalization)
|
||||
.set_version(_topo_sm._topology.version + 1)
|
||||
.build());
|
||||
|
||||
co_await update_topology_state(std::move(guard), std::move(updates), "Started tablet split finalization");
|
||||
co_await update_topology_state(std::move(guard), std::move(updates), "Started tablet resize finalization");
|
||||
co_return true;
|
||||
}
|
||||
|
||||
|
||||
@@ -147,18 +147,27 @@ static std::unordered_map<topology::transition_state, sstring> transition_state_
|
||||
{topology::transition_state::write_both_read_old, "write both read old"},
|
||||
{topology::transition_state::write_both_read_new, "write both read new"},
|
||||
{topology::transition_state::tablet_migration, "tablet migration"},
|
||||
{topology::transition_state::tablet_split_finalization, "tablet split finalization"},
|
||||
{topology::transition_state::tablet_resize_finalization, "tablet resize finalization"},
|
||||
{topology::transition_state::tablet_draining, "tablet draining"},
|
||||
{topology::transition_state::left_token_ring, "left token ring"},
|
||||
{topology::transition_state::rollback_to_normal, "rollback to normal"},
|
||||
};
|
||||
|
||||
// Allows old deprecated names to be recognized and point to the correct transition.
|
||||
static std::unordered_map<sstring, topology::transition_state> deprecated_name_to_transition_state = {
|
||||
{"tablet split finalization", topology::transition_state::tablet_resize_finalization},
|
||||
};
|
||||
|
||||
topology::transition_state transition_state_from_string(const sstring& s) {
|
||||
for (auto&& e : transition_state_to_name_map) {
|
||||
if (e.second == s) {
|
||||
return e.first;
|
||||
}
|
||||
}
|
||||
auto it = deprecated_name_to_transition_state.find(s);
|
||||
if (it != deprecated_name_to_transition_state.end()) {
|
||||
return it->second;
|
||||
}
|
||||
on_internal_error(tsmlogger, format("cannot map name {} to transition_state", s));
|
||||
}
|
||||
|
||||
|
||||
@@ -110,7 +110,7 @@ struct topology {
|
||||
write_both_read_old,
|
||||
write_both_read_new,
|
||||
tablet_migration,
|
||||
tablet_split_finalization,
|
||||
tablet_resize_finalization,
|
||||
left_token_ring,
|
||||
rollback_to_normal,
|
||||
};
|
||||
|
||||
@@ -33,6 +33,7 @@
|
||||
#include "utils/error_injection.hh"
|
||||
#include "utils/to_string.hh"
|
||||
#include "service/topology_coordinator.hh"
|
||||
#include "service/topology_state_machine.hh"
|
||||
|
||||
#include <boost/regex.hpp>
|
||||
|
||||
@@ -3316,3 +3317,10 @@ SEASTAR_TEST_CASE(test_explicit_tablets_disable) {
|
||||
co_await test_create_keyspace("test_explictly_enabled_0", true, cfg, 0);
|
||||
co_await test_create_keyspace("test_explictly_enabled_128", true, cfg, 128);
|
||||
}
|
||||
|
||||
SEASTAR_TEST_CASE(test_recognition_of_deprecated_name_for_resize_transition) {
|
||||
using transition_state = service::topology::transition_state;
|
||||
BOOST_REQUIRE_EQUAL(service::transition_state_from_string("tablet split finalization"), transition_state::tablet_resize_finalization);
|
||||
BOOST_REQUIRE_EQUAL(service::transition_state_from_string("tablet resize finalization"), transition_state::tablet_resize_finalization);
|
||||
return make_ready_future<>();
|
||||
}
|
||||
|
||||
Reference in New Issue
Block a user