ClickHouse/dbms/src/Storages/MergeTree/MergeTreePartsMover.h

99 lines
2.6 KiB
C++
Raw Normal View History

2019-08-19 14:40:12 +00:00
#pragma once
#include <functional>
#include <vector>
2019-09-02 11:35:53 +00:00
#include <optional>
#include <Storages/MergeTree/MergeTreeData.h>
#include <Storages/MergeTree/MergeTreeDataPart.h>
#include <Common/ActionBlocker.h>
#include <Common/DiskSpaceMonitor.h>
2019-08-19 14:40:12 +00:00
namespace DB
{
2019-09-02 11:35:53 +00:00
namespace ErrorCodes
{
extern const int LOGICAL_ERROR;
}
2019-08-19 14:40:12 +00:00
struct MargeTreeMoveEntry
{
MergeTreeData::DataPartPtr part;
DiskSpace::ReservationPtr reserved_space;
MargeTreeMoveEntry(const MergeTreeData::DataPartPtr & part_, DiskSpace::ReservationPtr reservation_)
: part(part_),
reserved_space(std::move(reservation_))
{
}
};
using MergeTreeMovingParts = std::vector<MargeTreeMoveEntry>;
2019-09-02 11:35:53 +00:00
struct MovingPartsTagger
{
MergeTreeMovingParts parts_to_move;
std::unique_lock<std::mutex> background_lock;
MergeTreeData::DataParts & all_moving_parts;
MovingPartsTagger(MergeTreeMovingParts && moving_parts_,
std::unique_lock<std::mutex> && background_lock_,
MergeTreeData::DataParts & all_moving_data_parts_)
: parts_to_move(std::move(moving_parts_))
, background_lock(std::move(background_lock_))
, all_moving_parts(all_moving_data_parts_)
{
if (!background_lock)
throw Exception("Cannot tag moving parts without background lock.", ErrorCodes::LOGICAL_ERROR);
for (const auto & moving_part : parts_to_move)
2019-09-03 09:18:02 +00:00
if (!all_moving_parts.emplace(moving_part.part).second)
2019-09-02 11:35:53 +00:00
throw Exception("Cannot move part '" + moving_part.part->name + "'. It's already moving.", ErrorCodes::LOGICAL_ERROR);
background_lock.unlock();
}
~MovingPartsTagger()
{
background_lock.lock();
for (const auto & moving_part : parts_to_move)
{
/// Something went completely wrong
if (!all_moving_parts.count(moving_part.part))
std::terminate();
all_moving_parts.erase(moving_part.part);
}
}
};
2019-08-19 14:40:12 +00:00
class MergeTreePartsMover
{
using AllowedMovingPredicate = std::function<bool (const MergeTreeData::DataPartPtr &, String * reason)>;
public:
MergeTreePartsMover(MergeTreeData & data_)
: data(data_)
, log(&Poco::Logger::get("MergeTreePartsMover"))
{
}
bool selectPartsToMove(
MergeTreeMovingParts & parts_to_move,
const AllowedMovingPredicate & can_move);
MergeTreeData::DataPartsVector cloneParts(const MergeTreeMovingParts & parts);
bool swapClonedParts(const MergeTreeData::DataPartsVector & cloned_parts, String * out_reason);
2019-09-02 11:35:53 +00:00
public:
ActionBlocker moves_blocker;
2019-08-19 14:40:12 +00:00
private:
MergeTreeData & data;
Logger * log;
};
}