Commit Graph

194 Commits

Author SHA1 Message Date
Aleksandra Martyniuk
e0ce711e4f compaction: do not swallow compaction_stopped_exception for reshape
Loop in shard_reshaping_compaction_task_impl::run relies on whether
sstables::compaction_stopped_exception is thrown from run_custom_job.
The exception is swallowed for each type of compaction
in compaction_manager::perform_task.

Rethrow an exception in perfrom task for reshape compaction.

Fixes: #15058.

Closes #15067
2023-08-21 12:41:55 +03:00
Aleksandra Martyniuk
e9d94894f1 compaction: release resources of compaction executors
Before compaction task executors started inheriting from
compaction_task_impl, they were destructed immediately after
compaction finished. Destructors of executors and their
fields performed actions that affected global structures and
statistics and had impact on compaction process.

Currently, task executors are kept in memory much longer, as their
are tracked by task manager. Thus, destructors are not called just
after the compaction, which results in compaction stats not being
updated, which causes e.g. infinite cleanup loop.

Add release_resources() method which is called at the end
of compaction process and does what destructors used to.

Fixes: #14966.
Fixes: #15030.

Closes #15005
2023-08-16 15:51:17 +03:00
Aleksandra Martyniuk
db932c7106 compaction: hold gate immediately after task executor is created
If make_task call in compaction_manager::perform_compaction yields,
compaction_task_executor::_compaction_state may be gone and gate
won't be held.

Hold gate immediately after compaction_task_executor is created.
Add comment not to call prepare_task without preparation.

Refs: #14971.
Fixes: #14977.

Closes #14999
2023-08-11 13:56:38 +02:00
Botond Dénes
108e510a23 Merge 'Update sstable_requiring_cleanup on compaction completion' from Benny Halevy
Currently `sstable_requiring_cleanup` is updated using `compacting_sstable_registration`, but that mechanism is not used by offstrategy compaction, leading to #14304.

This series introduces `compaction_manager::on_compaction_completion` that intercepts the call
to the table::on_compaction_completion. This allows us to update `sstable_requiring_cleanup` right before the compacted sstables are deleted, making sure they are no leaked to `sstable_requiring_cleanup`, which would hold a reference to them until cleanup attempts to clean them up.

`cleanup_incremental_compaction_test` was adjusted to observe the sstables `on_delete` (by adding a new observer event) to detect the case where cleanup attempts to delete the leaked sstables and fails since they were already deleted from the file system by offstrategy compaction. The test fails with the fix and passes with it.

Fixes #14304

Closes #14858

* github.com:scylladb/scylladb:
  compaction_manager: on_compaction_completion: erase sstables from sstables_requiring_cleanup
  compaction/leveled_compaction_strategy: ideal_level_for_input: special case max_sstable_size==0
  sstable: add on_delete observer
  compaction_manager: add on_compaction_completion
  sstable_compaction_test: cleanup_incremental_compaction_test: verify sstables_requiring_cleanup is empty
2023-08-09 11:03:45 +03:00
Kefu Chai
47c9b25bac compaction_manager: correct comment on compaction_task_executor::state
when it comes to `regular_compaction_task_executor`, we repeat the
compaction until the compaction can not proceed, so after an iteration
of compaction completes successfully, the task can still continue with
yet another round of the compaction as it sees appropriate. so let's
update the comment to reflect this fact.

Signed-off-by: Kefu Chai <kefu.chai@scylladb.com>

Closes #14891
2023-08-09 09:49:18 +03:00
Benny Halevy
df66895080 compaction_manager: add on_compaction_completion
Pass the call to the table on_compaction_completion
so we can manage the sstables requiring cleanup state
along the way.

Signed-off-by: Benny Halevy <bhalevy@scylladb.com>
2023-08-08 08:12:05 +03:00
Benny Halevy
ea64ae54f8 sstable_compaction_test: cleanup_incremental_compaction_test: verify sstables_requiring_cleanup is empty
Make sure that there are no sstables_requiring_cleanup
after cleanup compaction.

Signed-off-by: Benny Halevy <bhalevy@scylladb.com>
2023-08-08 08:12:01 +03:00
Botond Dénes
4d538e1363 Merge 'Task manager tasks covering compaction group compaction' from Aleksandra Martyniuk
All compaction task executors, except for regular compaction one,
become task manager compaction tasks.

Creating and starting of major_compaction_task_executor is modified
to be consistent with other compaction task executors.

Closes #14505

* github.com:scylladb/scylladb:
  test: extend test_compaction_task.py to cover compaction group tasks
  compaction: turn custom_task_executor into compaction_task_impl
  compaction: turn sstables_task_executor into sstables_compaction_task_impl
  compaction: change sstables compaction tasks type
  compaction: move table_upgrade_sstables_compaction_task_impl
  compaction: pass task_info through sstables compaction
  compaction: turn offstrategy_compaction_task_executor into offstrategy_compaction_task_impl
  compaction: turn cleanup_compaction_task_executor into cleanup_compaction_task_impl
  comapction: use optional task info in major compaction
  compaction: use perform_compaction in compaction_manager::perform_major_compaction
2023-08-04 10:11:00 +03:00
Kefu Chai
6c66030b7b compaction: add formatter for compaction_task_executor
add fmt formatter for `compaction_task_executor::state` and
`compaction_task_executor` and its derived classes.

this is a part of a series to migrating from `operator<<(ostream&, ..)`
based formatting to fmtlib based formatting. the goal here is to enable
fmtlib to print `compaction_task_executor`, its derived classes and
`compaction_task_executor::state` without the help of `operator<<`.

since all of the callers of 'operator<<' of these types now use
formatters, the operator<< are removed in this change. the helpers
like `to_string()` and `describe()` are removed as well, as it'd
be more consistent if we always use fmtlib for formatting instead
of inventing APIs with different names.

Refs #13245

Signed-off-by: Kefu Chai <kefu.chai@scylladb.com>

Closes #14906
2023-08-02 09:15:43 +03:00
Aleksandra Martyniuk
139e147ae1 compaction: turn custom_task_executor into compaction_task_impl
custom_task_executor inherits both from compaction_task_executor
and compaction_task_impl.
2023-07-28 10:51:55 +02:00
Aleksandra Martyniuk
1853a5a355 compaction: turn sstables_task_executor into sstables_compaction_task_impl
sstables_task_executor inherits both from compaction_task_executor
and sstables_compaction_task_impl.

Delete unused perform_task_on_all_files version.
2023-07-28 10:51:55 +02:00
Aleksandra Martyniuk
71db8645d5 compaction: pass task_info through sstables compaction 2023-07-28 10:51:55 +02:00
Aleksandra Martyniuk
4e439ac957 compaction: turn offstrategy_compaction_task_executor into offstrategy_compaction_task_impl
offstrategy_compaction_task_executor inherits both from compaction_task_executor
and offstrategy_compaction_task_impl.
2023-07-28 10:51:55 +02:00
Aleksandra Martyniuk
92f2987217 compaction: turn cleanup_compaction_task_executor into cleanup_compaction_task_impl
cleanup_compaction_task_executor inherits both from compaction_task_executor
and cleanup_compaction_task_impl.

Add a new version of compaction_manager::perform_task_on_all_files
which accepts only the tasks that are derived from compaction_task_impl.
After all task executors' conversions are done, the new version replaces
the original one.
2023-07-28 10:48:58 +02:00
Aleksandra Martyniuk
8317e4dd7f comapction: use optional task info in major compaction
To make it consistent with the upcoming methods, methods triggering
major compaction get std::optional<tasks::task_info> as an argument.

Thanks to that we can distinguish between a task that has no parent
and the task which won't be registered in task manager.
2023-07-28 09:25:21 +02:00
Kefu Chai
1b7bde2e9e compaction_manager: use range in compacting_sstable_registration
simpler than the "begin, end" iterator pair. and also tighten the
type constraints, now require the value type to be
sstables::shared_sstable. this matches what we are expecting in
the implementation.

Signed-off-by: Kefu Chai <kefu.chai@scylladb.com>

Closes #14678
2023-07-27 09:40:20 +03:00
Kefu Chai
fdf61d2f7c compaction_manager: prevent gc-only sstables from being compacted
before this change, there are chances that the temporary sstables
created for collecting the GC-able data create by a certain
compaction can be picked up by another compaction job. this
wastes the CPU cycles, adds write amplification, and causes
inefficiency.

in general, these GC-only SSTables are created with the same run id
as those non-GC SSTables, but when a new sstable exhausts input
sstable(s), we proactively replace the old main set with a new one
so that we can free up the space as soon as possible. so the
GC-only SSTables are added to the new main set along with
the non-GC SSTables, but since the former have good chance to
overlap the latter. these GC-only SSTables are assigned with
different run ids. but we fail to register them to the
`compaction_manager` when replacing the main sstable set.
that's why future compactions pick them up when performing compaction,
when the compaction which created them is not yet completed.

so, in this change,

* to prevent sstables in the transient stage from being picked
  up by regular compactions, a new interface class is introduced
  so that the sstable is always added to registration before
  it is added to sstable set, and removed from registration after
  it is removed from sstable set. the struct helps to consolidate
  the regitration related logic in a single place, and helps to
  make it more obvious that the timespan of an sstable in
  the registration should cover that in the sstable set.
* use a different run_id for the gc sstable run, as it can
  overlap with the output sstable run. the run_id for the
  gc sstable run is created only when the gc sstable writer
  is created. because the gc sstables is not always created
  for all compactions.

please note, all (indirect) callers of
`compaction_task_executor::compact_sstables()` passes a non-empty
`std::function` to this function, so there is no need to check for
empty before calling it. so in this change, the check is dropped.

Fixes #14560
Signed-off-by: Kefu Chai <kefu.chai@scylladb.com>

Closes #14725
2023-07-20 15:47:48 +03:00
Aleksandra Martyniuk
e3b068be4d compaction: add compaction_manager::perform_compaction method 2023-07-17 15:54:33 +02:00
Aleksandra Martyniuk
33cb156ee3 compaction: switch state after compaction is done
Compaction task executors which inherit from compaction_task_impl
may stay in memory after the compaction is finished.
Thus, state switch cannot happen in destructor.

Switch state to none in perform_task defer.
2023-07-17 15:54:33 +02:00
Kefu Chai
057701299c compaction_manager: remove unnecessary include
also, remove unnecessary forward declarations.

* compaction_manager_test_task_executor is only referenced
  in the friend declaration. but this declaration does not need
  a forward declaration of the friend class
* compaction_manager_test_task_executor is not used anywhere.

Signed-off-by: Kefu Chai <kefu.chai@scylladb.com>

Closes #14680
2023-07-13 14:59:39 +03:00
Aleksandra Martyniuk
4922f4cf80 compaction: take gate holder out of task executor
In the following commits, classes deriving from compaction_task_executor
will be alive longer than they are kept in compaction_manager::_tasks.
Thus, the compaction_task_executor::_gate_holder would be held,
blocking other compactions.

compaction_task_executor::_gate_holder is moved outside of
compaction_task_executor object.
2023-06-20 12:12:45 +02:00
Aleksandra Martyniuk
e317ffe23a compaction: extend signature of some methods
Extend a signature of table::compact_all_sstables and
compaction_manager::perform_major_compaction so that they get
the info of a covering task.

This allows to easily create child tasks that cover compaction group
compaction.
2023-06-20 10:45:34 +02:00
Aleksandra Martyniuk
3007fbeee3 compaction: rename compaction_task_executor methods
compaction_task_executor methods are renamed to prevent name
colisions between compaction_task_executor
and tasks::task_manager::task::impl.
2023-06-20 10:45:34 +02:00
Raphael S. Carvalho
156d771101 compaction: Fix sstable cleanup after resharding on refresh
Problem can be reproduced easily:
1) wrote some sstables with smp 1
2) shut down scylla
3) moved sstables to upload
4) restarted scylla with smp 2
5) ran refresh (resharding happens, adds sstable to cleanup
set and never removes it)
6) cleanup (tries to cleanup resharded sstables which were
leaked in the cleanup set)

Bumps into assert "Assertion `!sst->is_shared()' failed", as
cleanup picks a shared sstable that was leaked and already
processed by resharding.

Fix is about not inserting shared sstables into cleanup set,
as shared sstables are restricted to resharding and cannot
be processed later by cleanup (nor it should because
resharding itself cleaned up its input files).

Dtest: https://github.com/scylladb/scylla-dtest/pull/3206

Fixes #14001.

Signed-off-by: Raphael S. Carvalho <raphaelsc@scylladb.com>

Closes #14147
2023-06-06 12:14:03 +03:00
Benny Halevy
a5a8020ecd compaction_manager: perform_cleanup: wait until all candidates are cleaned up
cleanup_compaction should resolve only after all
sstables that require cleanup are cleaned up.

Since it is possible that some of them are in staging
and therefore cannot be cleaned up, retry once a second
until they become eligible.

Timeout if there is no progress within 5 minutes
to prevent hanging due to view building bug.

Fixes #9559

Signed-off-by: Benny Halevy <bhalevy@scylladb.com>
2023-05-17 11:31:07 +03:00
Benny Halevy
2f61de8f7b table, compaction_manager: prevent cross shard access to owned_ranges_ptr
Seen after f1bbf705f9 in debug mode

distributed_loader collect_all_shared_sstables copies
compaction::owned_ranges_ptr (lw_shared_ptr<const
dht::token_range_vector>)
across shards.

Since update_sstable_cleanup_state is synchronous, it can
be passed a const refrence to the token_range_vector instead.
It is ok to access the memory read-only across shards
and since this happens on start-up, there are no special
performance requirements.

Fixes #13631

Signed-off-by: Benny Halevy <bhalevy@scylladb.com>
2023-04-23 15:12:13 +03:00
Benny Halevy
b3192b9f16 compaction: refactor compaction_state out of compaction_manager
To use it both from compaction_manager and compaction_descriptor
in a following patch.

Signed-off-by: Benny Halevy <bhalevy@scylladb.com>
2023-04-10 23:28:16 +03:00
Benny Halevy
cac60a09ac compaction_manager: refactor get_candidates
Allow getting candidates for compaction
from an arbitrary range of sstable, not only
the in_strategy_sstables.

To be used by perform_cleanup to mark all sstables
that require cleanup, even if they can't be
compacted at this time.

Signed-off-by: Benny Halevy <bhalevy@scylladb.com>
2023-04-10 23:16:57 +03:00
Benny Halevy
bbfe839a73 compaction_manager: get_candidates: mark as const
Signed-off-by: Benny Halevy <bhalevy@scylladb.com>
2023-04-10 23:16:12 +03:00
Benny Halevy
6ebafe74b9 table, compaction_manager: add requires_cleanup
Returns true iff any of the sstables in the set
requries cleanup.

Signed-off-by: Benny Halevy <bhalevy@scylladb.com>
2023-04-10 23:14:36 +03:00
Benny Halevy
d0690b64c1 table, compaction_manager: add update_sstable_cleanup_state
update_sstable_cleanup_state calls needs_cleanup and
inserts (or erases) the sstable into the respective
compaction_state.sstables_requiring_cleanup set.

Signed-off-by: Benny Halevy <bhalevy@scylladb.com>
2023-04-10 23:10:55 +03:00
Benny Halevy
1baca96de1 compaction_manager: needs_cleanup: delete unused schema param
It isn't needed.  The sstable already has a schema.

Signed-off-by: Benny Halevy <bhalevy@scylladb.com>
2023-04-10 23:03:53 +03:00
Benny Halevy
09df04c919 compaction: move owned_ranges into descriptor
Move the owned_ranges_ptr, currently used only by
cleanup and upgrade compactions, to the generic
compaction descriptor so we apply cleanup in other
compaction types.

Signed-off-by: Benny Halevy <bhalevy@scylladb.com>
2023-04-10 22:52:12 +03:00
Botond Dénes
9a02315c6b Merge 'Compaction reevaluation bug fixes' from Raphael "Raph" Carvalho
A problem in compaction reevaluation can cause the SSTable set to be left uncompacted for indefinite amount of time, potentially causing space and read amplification to be suboptimal.

Two revaluation problems are being fixed, one after off-strategy compaction ended, and another in compaction manager which intends to periodically reevaluate a need for compaction.

Fixes https://github.com/scylladb/scylladb/issues/13429.
Fixes https://github.com/scylladb/scylladb/issues/13430.

Closes #13431

* github.com:scylladb/scylladb:
  compaction: Make compaction reevaluation actually periodic
  replica: Reevaluate regular compaction on off-strategy completion
2023-04-05 13:51:21 +03:00
Raphael S. Carvalho
156ac0a67a compaction: Make compaction reevaluation actually periodic
The manager intended to periodically reevaluate compaction need for
each registered table. But it's not working as intended.
The reevaluation is one-off.

This means that compaction was not kicking in later for a table, with
low to none write activity, that had expired data 1 hour from now.

Also make sure that reevaluation happens within the compaction
scheduling group.

Fixes #13430.

Signed-off-by: Raphael S. Carvalho <raphaelsc@scylladb.com>
2023-04-04 09:16:19 -03:00
Aleksandra Martyniuk
d7d570e39d compaction: rename compaction::task
To avoid confusion with task manager tasks compaction::task is renamed
to compaction::compaction_task_exector. All inheriting classes are
modified similarly.
2023-03-29 15:23:18 +02:00
Aleksandra Martyniuk
f24391fbe4 compaction: move compaction_manager::task out of compaction manager
compaction_manager::task needs to be accessed from task manager compaction
tasks. Thus, compaction_manager::task and all inheriting classes are moved
from compaction manager to compaction namespace.
2023-03-29 15:21:24 +02:00
Aleksandra Martyniuk
37cafec9d5 compaction: move sstable_task definition to source file 2023-03-29 14:53:43 +02:00
Aleksandra Martyniuk
4f67c0c36a compaction: add compaction module getter to compaction manager 2023-02-20 11:19:29 +01:00
Pavel Emelyanov
52f69643b6 api, compaction_manager: Get compaction history via manager
Right now the API handler directly calls static method from system
keyspace. Patching it to call compaction manager instead will let the
latter use on-board plugged system keyspace for that. If the system
keyspace is not plugged, it means early boot or late shutdown, not a
good time to get compaction history anyway.

Signed-off-by: Pavel Emelyanov <xemul@scylladb.com>
2023-02-16 11:27:38 +03:00
Aleksandra Martyniuk
12789adb95 compaction: test: pass task_manager to compaction_manager in test environment
Each instance of compaction manager should have compaction module pointer
initialized. All contructors get task_manager reference with which
the module is created.
2023-02-03 15:15:11 +01:00
Aleksandra Martyniuk
47ef689077 compaction: create and register task manager's module for compaction
As an initial part of integration of compaction with task manager, compaction
module is added. Compaction module inherits from tasks::task_manager::module
and shared_ptr to it is kept in compaction manager. No compaction tasks are
created yet.
2023-02-03 13:52:30 +01:00
Avi Kivity
d2c44cba77 compaction_manager: make postponed_compactions_reevaluation() return a future
postponed_compactions_reevaluation() runs until compaction_manager is
stopped, checking if it needs to launch new compactions.

Make it return a future instead of stashing its completion somewhere.
This makes is easier to convert it to a coroutine.
2022-12-05 21:58:48 +02:00
Raphael S. Carvalho
d61b4f9dfb compaction_manager: Delete compaction_state's move constructor
compaction_state shouldn't be moved once emplaced. moving it could
theoretically cause task's gate holder to have a dangling pointer to
compaction_state's gate, but turns out gate's move ctor will actually
fail under this assertion:
assert(!_count && "gate reassigned with outstanding requests");

Cannot happen today, but let's make it more future proof.

Signed-off-by: Raphael S. Carvalho <raphaelsc@scylladb.com>

Closes #12167
2022-12-02 20:56:57 +03:00
Raphael S. Carvalho
b88acffd66 replica: Allow one compaction_backlog_tracker for each compaction_group
Today, compaction_backlog_tracker is managed in each compaction_strategy
implementation. So every compaction strategy is managing its own
tracker and providing a reference to it through get_backlog_tracker().

But this prevents each group from having its own tracker, because
there's only a single compaction_strategy instance per table.
To remove this limitation, compaction_strategy impl will no longer
manage trackers but will instead provide an interface for trackers
to be created, such that each compaction group will be allowed to
have its own tracker, which will be managed by compaction manager.

On compaction strategy change, table will update each group with
the new tracker, which is created using the previously introduced
ompaction_group_sstable_set_updater.

Now table's backlog will be the sum of all compaction_group backlogs.
The normalization factor is applied on the sum, so we don't have
to adjust each individual backlog to any factor.

Signed-off-by: Raphael S. Carvalho <raphaelsc@scylladb.com>
2022-11-11 09:22:51 -03:00
Raphael S. Carvalho
1ec0ef18a5 compaction/table_state: Introduce get_backlog_tracker()
This interface will be helpful for allowing replica::table, unit
tests and sstables::compaction to access the compaction group's tracker
which will be managed by the compaction manager, once we complete
the decoupling work.

Signed-off-by: Raphael S. Carvalho <raphaelsc@scylladb.com>
2022-11-11 09:17:36 -03:00
Pavel Emelyanov
f9b57df471 database: Plug/unplug system_keyspace
There's a circular dependency between system_keyspace and database. The
former needs the latter because it needs to execula local requests via
query_processor. The latter needs the former via compaction manager and
large data handler, database depends on both and these too need to
insert their entries into system keyspace.

To cut this loop the compaction manager and large data handler both get
a weak reference on the system keysace. Once system keyspace starts is
activcates this reference via the database call. When system keyspace is
shutdown-ed on stop, it deactivates the reference.

Technically the weak reference is implemented by marking the system_k.s.
object as async_sharded_service, and the "reference" in question is the
shared_from_this() pointer. When compaction manager or large data
handler need to update a system keyspace's table, they both hold an
extra reference on the system keyspace until the entry is committed,
thus making sure that sys._k.s. doesn't stop from under their feet. At
the same time, unplugging the reference on shutdown makes sure that no
new entries update will appear and the system_k.s. will eventually be
released.

It's not a C++ classical reference, because system_keyspace starts after
and stops before database.

Signed-off-by: Pavel Emelyanov <xemul@scylladb.com>
2022-10-10 16:20:59 +03:00
Raphael S. Carvalho
888660fa44 compaction_manager: Make remove() and stop_ongoing_compactions() noexcept
stop_ongoing_compactions() is made noexcept too as it's called from
remove() and we want to make the latter noexcept, to allow compaction
group to qualify its stop function as noexcept too.

Signed-off-by: Raphael S. Carvalho <raphaelsc@scylladb.com>
2022-09-11 14:26:59 -03:00
Benny Halevy
e9cfe9e572 tombstone_gc: deglobalize repair_history_maps
Move the thread-local instances of the
per-table repair history maps into compaction_manager.

Fixes #11208

Signed-off-by: Benny Halevy <bhalevy@scylladb.com>
2022-09-07 07:43:15 +03:00
Benny Halevy
8b841e1207 compaction_manager: add tombstone_gc_state
Add a tombstone_gc_state member and methods to get it.

Currently the tombstone_gc_state is default constructed,
but a following patch will move the thread-local
repair history maps into the compaction_manager as a member
and then the _tombstone_gc_state member will be initialized
from that member.

Signed-off-by: Benny Halevy <bhalevy@scylladb.com>
2022-09-06 23:02:54 +03:00