aboutsummaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
authorrobdrynkin <robdrynkin@yandex-team.com>2023-10-06 18:25:46 +0300
committerrobdrynkin <robdrynkin@yandex-team.com>2023-10-06 21:01:29 +0300
commita8f808af42d92f92f79a0473f9c069ce8b2c178b (patch)
treea8615848ef243774aec1be855d8770126c5a792b
parentb70412b8025dd0f7e40ff3484da3d49fbf5faf98 (diff)
downloadydb-a8f808af42d92f92f79a0473f9c069ce8b2c178b.tar.gz
KIKIMR-19469: Restart vdisk button
-rw-r--r--.mapping.json5
-rw-r--r--ydb/core/base/blobstorage.h2
-rw-r--r--ydb/core/blobstorage/base/blobstorage_events.h13
-rw-r--r--ydb/core/blobstorage/nodewarden/blobstorage_node_warden_ut.cpp2
-rw-r--r--ydb/core/blobstorage/nodewarden/node_warden_impl.h2
-rw-r--r--ydb/core/blobstorage/nodewarden/node_warden_vdisk.cpp19
-rw-r--r--ydb/core/blobstorage/pdisk/blobstorage_pdisk_ut_actions.h6
-rw-r--r--ydb/core/blobstorage/pdisk/blobstorage_pdisk_ut_http_request.h7
-rw-r--r--ydb/core/blobstorage/pdisk/mock/pdisk_mock.cpp126
-rw-r--r--ydb/core/blobstorage/pdisk/mock/pdisk_mock.h7
-rw-r--r--ydb/core/blobstorage/ut_blobstorage/CMakeLists.darwin-x86_64.txt1
-rw-r--r--ydb/core/blobstorage/ut_blobstorage/CMakeLists.linux-aarch64.txt1
-rw-r--r--ydb/core/blobstorage/ut_blobstorage/CMakeLists.linux-x86_64.txt1
-rw-r--r--ydb/core/blobstorage/ut_blobstorage/CMakeLists.windows-x86_64.txt1
-rw-r--r--ydb/core/blobstorage/ut_blobstorage/lib/env.h2
-rw-r--r--ydb/core/blobstorage/ut_blobstorage/ut_vdisk_restart/CMakeLists.darwin-x86_64.txt74
-rw-r--r--ydb/core/blobstorage/ut_blobstorage/ut_vdisk_restart/CMakeLists.linux-aarch64.txt77
-rw-r--r--ydb/core/blobstorage/ut_blobstorage/ut_vdisk_restart/CMakeLists.linux-x86_64.txt79
-rw-r--r--ydb/core/blobstorage/ut_blobstorage/ut_vdisk_restart/CMakeLists.txt17
-rw-r--r--ydb/core/blobstorage/ut_blobstorage/ut_vdisk_restart/CMakeLists.windows-x86_64.txt67
-rw-r--r--ydb/core/blobstorage/ut_blobstorage/ut_vdisk_restart/ya.make17
-rw-r--r--ydb/core/blobstorage/ut_blobstorage/vdisk_restart.cpp64
-rw-r--r--ydb/core/blobstorage/ut_blobstorage/ya.make1
-rw-r--r--ydb/core/blobstorage/vdisk/skeleton/blobstorage_monactors.cpp63
-rw-r--r--ydb/core/blobstorage/vdisk/skeleton/blobstorage_monactors.h4
-rw-r--r--ydb/core/blobstorage/vdisk/skeleton/blobstorage_skeletonfront.cpp11
26 files changed, 656 insertions, 13 deletions
diff --git a/.mapping.json b/.mapping.json
index 7d001aaae8..e6f2333474 100644
--- a/.mapping.json
+++ b/.mapping.json
@@ -3449,6 +3449,11 @@
"ydb/core/blobstorage/ut_blobstorage/ut_scrub/CMakeLists.linux-x86_64.txt":"",
"ydb/core/blobstorage/ut_blobstorage/ut_scrub/CMakeLists.txt":"",
"ydb/core/blobstorage/ut_blobstorage/ut_scrub/CMakeLists.windows-x86_64.txt":"",
+ "ydb/core/blobstorage/ut_blobstorage/ut_vdisk_restart/CMakeLists.darwin-x86_64.txt":"",
+ "ydb/core/blobstorage/ut_blobstorage/ut_vdisk_restart/CMakeLists.linux-aarch64.txt":"",
+ "ydb/core/blobstorage/ut_blobstorage/ut_vdisk_restart/CMakeLists.linux-x86_64.txt":"",
+ "ydb/core/blobstorage/ut_blobstorage/ut_vdisk_restart/CMakeLists.txt":"",
+ "ydb/core/blobstorage/ut_blobstorage/ut_vdisk_restart/CMakeLists.windows-x86_64.txt":"",
"ydb/core/blobstorage/ut_group/CMakeLists.darwin-x86_64.txt":"",
"ydb/core/blobstorage/ut_group/CMakeLists.linux-aarch64.txt":"",
"ydb/core/blobstorage/ut_group/CMakeLists.linux-x86_64.txt":"",
diff --git a/ydb/core/base/blobstorage.h b/ydb/core/base/blobstorage.h
index c3c1f02abb..f92e7441a5 100644
--- a/ydb/core/base/blobstorage.h
+++ b/ydb/core/base/blobstorage.h
@@ -851,6 +851,7 @@ struct TEvBlobStorage {
// node controller internal messages
EvRegisterNodeRetry = EvPut + 14 * 512,
EvAskRestartPDisk,
+ EvAskRestartVDisk,
EvRestartPDisk,
EvRestartPDiskResult,
EvNodeWardenQueryGroupInfo,
@@ -2354,6 +2355,7 @@ struct TEvBlobStorage {
struct TEvBunchOfEvents;
struct TEvAskRestartPDisk;
+ struct TEvAskRestartVDisk;
struct TEvRestartPDisk;
struct TEvRestartPDiskResult;
};
diff --git a/ydb/core/blobstorage/base/blobstorage_events.h b/ydb/core/blobstorage/base/blobstorage_events.h
index 41c7cd087b..dedd8437e3 100644
--- a/ydb/core/blobstorage/base/blobstorage_events.h
+++ b/ydb/core/blobstorage/base/blobstorage_events.h
@@ -431,6 +431,19 @@ namespace NKikimr {
{}
};
+ struct TEvBlobStorage::TEvAskRestartVDisk : TEventLocal<TEvAskRestartVDisk, EvAskRestartVDisk> {
+ const ui32 PDiskId;
+ const TVDiskID VDiskId;
+
+ TEvAskRestartVDisk(
+ const ui32 pDiskId,
+ const TVDiskID& vDiskId
+ )
+ : PDiskId(pDiskId)
+ , VDiskId(vDiskId)
+ {}
+ };
+
struct TEvBlobStorage::TEvRestartPDisk : TEventLocal<TEvRestartPDisk, EvRestartPDisk> {
const ui32 PDiskId;
const NPDisk::TMainKey MainKey;
diff --git a/ydb/core/blobstorage/nodewarden/blobstorage_node_warden_ut.cpp b/ydb/core/blobstorage/nodewarden/blobstorage_node_warden_ut.cpp
index 9ae7f93854..2e72ab6c0c 100644
--- a/ydb/core/blobstorage/nodewarden/blobstorage_node_warden_ut.cpp
+++ b/ydb/core/blobstorage/nodewarden/blobstorage_node_warden_ut.cpp
@@ -807,7 +807,7 @@ Y_UNIT_TEST_SUITE(TBlobStorageWardenTest) {
Setup(runtime, "", nullptr);
auto edge = runtime.AllocateEdgeActor(0);
TActorId nodeWarden = MakeBlobStorageNodeWardenID(edge.NodeId());
- THttpRequest HttpRequest;
+ THttpRequestMock HttpRequest;
NMonitoring::TMonService2HttpRequest monService2HttpRequest(nullptr, &HttpRequest, nullptr, nullptr, path,
nullptr);
runtime.Send(new IEventHandle(nodeWarden, edge, new NMon::TEvHttpInfo(monService2HttpRequest)), 0);
diff --git a/ydb/core/blobstorage/nodewarden/node_warden_impl.h b/ydb/core/blobstorage/nodewarden/node_warden_impl.h
index 7c23f262ca..90dd50c512 100644
--- a/ydb/core/blobstorage/nodewarden/node_warden_impl.h
+++ b/ydb/core/blobstorage/nodewarden/node_warden_impl.h
@@ -464,6 +464,7 @@ namespace NKikimr::NStorage {
void Handle(TEvBlobStorage::TEvDropDonor::TPtr ev);
void Handle(TEvBlobStorage::TEvAskRestartPDisk::TPtr ev);
+ void Handle(TEvBlobStorage::TEvAskRestartVDisk::TPtr ev);
void Handle(TEvBlobStorage::TEvRestartPDiskResult::TPtr ev);
void FillInVDiskStatus(google::protobuf::RepeatedPtrField<NKikimrBlobStorage::TVDiskStatus> *pb, bool initial);
@@ -535,6 +536,7 @@ namespace NKikimr::NStorage {
hFunc(TEvStatusUpdate, Handle);
hFunc(TEvBlobStorage::TEvDropDonor, Handle);
hFunc(TEvBlobStorage::TEvAskRestartPDisk, Handle);
+ hFunc(TEvBlobStorage::TEvAskRestartVDisk, Handle);
hFunc(TEvBlobStorage::TEvRestartPDiskResult, Handle);
hFunc(TEvGroupStatReport, Handle);
diff --git a/ydb/core/blobstorage/nodewarden/node_warden_vdisk.cpp b/ydb/core/blobstorage/nodewarden/node_warden_vdisk.cpp
index 56093a131c..aec69ad075 100644
--- a/ydb/core/blobstorage/nodewarden/node_warden_vdisk.cpp
+++ b/ydb/core/blobstorage/nodewarden/node_warden_vdisk.cpp
@@ -6,6 +6,8 @@
namespace NKikimr::NStorage {
+ constexpr TDuration PDISK_CONFIDENCE_DELAY = TDuration::Seconds(15);
+
void TNodeWarden::DestroyLocalVDisk(TVDiskRecord& vdisk) {
STLOG(PRI_INFO, BS_NODE, NW35, "DestroyLocalVDisk", (VDiskId, vdisk.GetVDiskId()), (VSlotId, vdisk.GetVSlotId()));
Y_VERIFY(!vdisk.RuntimeData);
@@ -267,7 +269,7 @@ namespace NKikimr::NStorage {
StartLocalVDiskActor(record, TDuration::Zero());
} else if (record.RuntimeData->DonorMode < record.Config.HasDonorMode() || record.RuntimeData->ReadOnly != record.Config.GetReadOnly()) {
PoisonLocalVDisk(record);
- StartLocalVDiskActor(record, TDuration::Seconds(15) /* PDisk confidence delay */);
+ StartLocalVDiskActor(record, PDISK_CONFIDENCE_DELAY);
}
}
@@ -285,6 +287,21 @@ namespace NKikimr::NStorage {
}
}
+ void TNodeWarden::Handle(TEvBlobStorage::TEvAskRestartVDisk::TPtr ev) {
+ const auto& [pDiskId, vDiskId] = *ev->Get();
+ const auto nodeId = SelfId().NodeId(); // Skeleton and NodeWarden are on the same node
+ TVSlotId slotId(nodeId, pDiskId, 0);
+
+ for (auto it = LocalVDisks.lower_bound(slotId); it != LocalVDisks.end() && it->first.NodeId == nodeId && it->first.PDiskId == pDiskId; ++it) {
+ auto& record = it->second;
+ if (record.GetVDiskId() == vDiskId) {
+ PoisonLocalVDisk(record);
+ StartLocalVDiskActor(record, PDISK_CONFIDENCE_DELAY);
+ break;
+ }
+ }
+ }
+
void TNodeWarden::Handle(TEvBlobStorage::TEvDropDonor::TPtr ev) {
auto *msg = ev->Get();
const TVSlotId vslotId(msg->NodeId, msg->PDiskId, msg->VSlotId);
diff --git a/ydb/core/blobstorage/pdisk/blobstorage_pdisk_ut_actions.h b/ydb/core/blobstorage/pdisk/blobstorage_pdisk_ut_actions.h
index 52cd8bef13..92789f5bca 100644
--- a/ydb/core/blobstorage/pdisk/blobstorage_pdisk_ut_actions.h
+++ b/ydb/core/blobstorage/pdisk/blobstorage_pdisk_ut_actions.h
@@ -1301,7 +1301,7 @@ public:
};
class TTestHttpInfo : public TBaseTest {
- THttpRequest HttpRequest;
+ THttpRequestMock HttpRequest;
NMonitoring::TMonService2HttpRequest MonService2HttpRequest;
void TestFSM(const TActorContext &ctx);
@@ -1313,7 +1313,7 @@ public:
};
class TTestHttpInfoFileDoesntExist : public TBaseTest {
- THttpRequest HttpRequest;
+ THttpRequestMock HttpRequest;
NMonitoring::TMonService2HttpRequest MonService2HttpRequest;
void TestFSM(const TActorContext &ctx);
@@ -1326,7 +1326,7 @@ public:
class TTestBootingState : public TBaseTest {
const ui32 HttpRequestsCount = 1000;
- THttpRequest HttpRequest;
+ THttpRequestMock HttpRequest;
NMonitoring::TMonService2HttpRequest MonService2HttpRequest;
bool EvYardAnswered = false;
ui32 AnsweredRequests = 0;
diff --git a/ydb/core/blobstorage/pdisk/blobstorage_pdisk_ut_http_request.h b/ydb/core/blobstorage/pdisk/blobstorage_pdisk_ut_http_request.h
index 7f4a18c762..bd597495cb 100644
--- a/ydb/core/blobstorage/pdisk/blobstorage_pdisk_ut_http_request.h
+++ b/ydb/core/blobstorage/pdisk/blobstorage_pdisk_ut_http_request.h
@@ -3,18 +3,19 @@
namespace NKikimr {
-struct THttpRequest : NMonitoring::IHttpRequest {
+struct THttpRequestMock : NMonitoring::IHttpRequest {
TCgiParameters CgiParameters;
THttpHeaders HttpHeaders;
+ TString Path;
- ~THttpRequest() {}
+ ~THttpRequestMock() {}
const char* GetURI() const override {
return "";
}
const char* GetPath() const override {
- return "";
+ return Path.c_str();
}
const TCgiParameters& GetParams() const override {
diff --git a/ydb/core/blobstorage/pdisk/mock/pdisk_mock.cpp b/ydb/core/blobstorage/pdisk/mock/pdisk_mock.cpp
index d12674684e..8f5aa08a4b 100644
--- a/ydb/core/blobstorage/pdisk/mock/pdisk_mock.cpp
+++ b/ydb/core/blobstorage/pdisk/mock/pdisk_mock.cpp
@@ -45,6 +45,7 @@ struct TPDiskMockState::TImpl {
TIntervalSet<ui64> Corrupted;
NPDisk::TStatusFlags StatusFlags;
THashSet<TVDiskID> ReadOnlyVDisks;
+ TString StateErrorReason;
TImpl(ui32 nodeId, ui32 pdiskId, ui64 pdiskGuid, ui64 size, ui32 chunkSize)
: NodeId(nodeId)
@@ -221,6 +222,15 @@ struct TPDiskMockState::TImpl {
return ChunkSize;
}
+ TMaybe<TOwner> GetOwner(const TVDiskID& vDiskId) const {
+ for (auto& [ownerId, owner] : Owners) {
+ if (owner.VDiskId.GroupID == vDiskId.GroupID && owner.VDiskId.VDisk == vDiskId.VDisk) {
+ return owner;
+ }
+ }
+ return Nothing();
+ }
+
TIntervalSet<i64> GetWrittenAreas(ui32 chunkIdx) const {
TIntervalSet<i64> res;
for (auto& [ownerId, owner] : Owners) {
@@ -308,12 +318,23 @@ void TPDiskMockState::SetReadOnly(const TVDiskID& vDiskId, bool isReadOnly) {
Impl->SetReadOnly(vDiskId, isReadOnly);
}
+TString& TPDiskMockState::GetStateErrorReason() {
+ return Impl->StateErrorReason;
+}
+
TPDiskMockState::TPtr TPDiskMockState::Snapshot() {
auto res = MakeIntrusive<TPDiskMockState>(std::make_unique<TImpl>(*Impl));
res->Impl->AdjustRefs();
return res;
}
+TMaybe<NPDisk::TOwnerRound> TPDiskMockState::GetOwnerRound(const TVDiskID& vDiskId) const {
+ if (auto owner = Impl->GetOwner(vDiskId)) {
+ return owner->OwnerRound;
+ }
+ return Nothing();
+}
+
class TPDiskMockActor : public TActorBootstrapped<TPDiskMockActor> {
enum {
EvResume = EventSpaceBegin(TEvents::ES_PRIVATE),
@@ -339,7 +360,7 @@ public:
}
void Bootstrap() {
- Become(&TThis::StateFunc);
+ Become(&TThis::StateNormal);
ReportMetrics();
}
@@ -814,7 +835,89 @@ public:
return Impl.StatusFlags;
}
- STRICT_STFUNC(StateFunc,
+ void ErrorHandle(NPDisk::TEvYardInit::TPtr &ev) {
+ Send(ev->Sender, new NPDisk::TEvYardInitResult(NKikimrProto::CORRUPTED, State->GetStateErrorReason()));
+ }
+
+ void ErrorHandle(NPDisk::TEvCheckSpace::TPtr &ev) {
+ Send(ev->Sender, new NPDisk::TEvCheckSpaceResult(NKikimrProto::CORRUPTED, 0, 0, 0, 0, 0, State->GetStateErrorReason()));
+ }
+
+ void ErrorHandle(NPDisk::TEvLog::TPtr &ev) {
+ const NPDisk::TEvLog &evLog = *ev->Get();
+ THolder<NPDisk::TEvLogResult> result(new NPDisk::TEvLogResult(NKikimrProto::CORRUPTED, 0, State->GetStateErrorReason()));
+ result->Results.push_back(NPDisk::TEvLogResult::TRecord(evLog.Lsn, evLog.Cookie));
+ Send(ev->Sender, result.Release());
+ }
+
+ void ErrorHandle(NPDisk::TEvMultiLog::TPtr &ev) {
+ const NPDisk::TEvMultiLog &evMultiLog = *ev->Get();
+ THolder<NPDisk::TEvLogResult> result(new NPDisk::TEvLogResult(NKikimrProto::CORRUPTED, 0, State->GetStateErrorReason()));
+ for (auto &log : evMultiLog.Logs) {
+ result->Results.push_back(NPDisk::TEvLogResult::TRecord(log->Lsn, log->Cookie));
+ }
+ Send(ev->Sender, result.Release());
+ }
+
+ void ErrorHandle(NPDisk::TEvReadLog::TPtr &ev) {
+ const NPDisk::TEvReadLog &evReadLog = *ev->Get();
+ THolder<NPDisk::TEvReadLogResult> result(new NPDisk::TEvReadLogResult(
+ NKikimrProto::CORRUPTED, evReadLog.Position, evReadLog.Position, true, 0, State->GetStateErrorReason(), evReadLog.Owner));
+ Send(ev->Sender, result.Release());
+ }
+
+ void ErrorHandle(NPDisk::TEvChunkWrite::TPtr &ev) {
+ const NPDisk::TEvChunkWrite &evChunkWrite = *ev->Get();
+ Send(ev->Sender, new NPDisk::TEvChunkWriteResult(NKikimrProto::CORRUPTED,
+ evChunkWrite.ChunkIdx, evChunkWrite.Cookie, 0, State->GetStateErrorReason()));
+ }
+
+ void ErrorHandle(NPDisk::TEvChunkRead::TPtr &ev) {
+ const NPDisk::TEvChunkRead &evChunkRead = *ev->Get();
+ THolder<NPDisk::TEvChunkReadResult> result = MakeHolder<NPDisk::TEvChunkReadResult>(NKikimrProto::CORRUPTED,
+ evChunkRead.ChunkIdx, evChunkRead.Offset, evChunkRead.Cookie, 0, "PDisk is in error state");
+ Send(ev->Sender, result.Release());
+ }
+
+ void ErrorHandle(NPDisk::TEvHarakiri::TPtr &ev) {
+ Send(ev->Sender, new NPDisk::TEvHarakiriResult(NKikimrProto::CORRUPTED, 0, State->GetStateErrorReason()));
+ }
+
+ void ErrorHandle(NPDisk::TEvSlay::TPtr &ev) {
+ const NPDisk::TEvSlay &evSlay = *ev->Get();
+ Send(ev->Sender, new NPDisk::TEvSlayResult(NKikimrProto::CORRUPTED, 0,
+ evSlay.VDiskId, evSlay.SlayOwnerRound, evSlay.PDiskId, evSlay.VSlotId, State->GetStateErrorReason()));
+ }
+
+ void ErrorHandle(NPDisk::TEvChunkReserve::TPtr &ev) {
+ Send(ev->Sender, new NPDisk::TEvChunkReserveResult(NKikimrProto::CORRUPTED, 0, State->GetStateErrorReason()));
+ }
+
+ void ErrorHandle(NPDisk::TEvChunkForget::TPtr &ev) {
+ Send(ev->Sender, new NPDisk::TEvChunkForgetResult(NKikimrProto::CORRUPTED, 0, State->GetStateErrorReason()));
+ }
+
+ void ErrorHandle(NPDisk::TEvYardControl::TPtr &ev) {
+ const NPDisk::TEvYardControl &evControl = *ev->Get();
+ Send(ev->Sender, new NPDisk::TEvYardControlResult(NKikimrProto::CORRUPTED, evControl.Cookie, State->GetStateErrorReason()));
+ }
+
+ void ErrorHandle(NPDisk::TEvAskForCutLog::TPtr &ev) {
+ // Just ignore the event, can't send cut log in this state.
+ Y_UNUSED(ev);
+ }
+
+ void HandleMoveToErrorState() {
+ Impl.StateErrorReason = "Some error reason";
+ Become(&TThis::StateError);
+ }
+
+ void HandleMoveToNormalState() {
+ Impl.StateErrorReason = "";
+ Become(&TThis::StateNormal);
+ }
+
+ STRICT_STFUNC(StateNormal,
hFunc(NPDisk::TEvYardInit, Handle);
hFunc(NPDisk::TEvLog, Handle);
hFunc(NPDisk::TEvChunkForget, Handle);
@@ -829,6 +932,25 @@ public:
hFunc(NPDisk::TEvHarakiri, Handle);
hFunc(NPDisk::TEvConfigureScheduler, Handle);
cFunc(TEvents::TSystem::Wakeup, ReportMetrics);
+
+ cFunc(EvBecomeError, HandleMoveToErrorState);
+ )
+
+ STRICT_STFUNC(StateError,
+ hFunc(NPDisk::TEvYardInit, ErrorHandle);
+ hFunc(NPDisk::TEvCheckSpace, ErrorHandle);
+ hFunc(NPDisk::TEvLog, ErrorHandle);
+ hFunc(NPDisk::TEvMultiLog, ErrorHandle);
+ hFunc(NPDisk::TEvReadLog, ErrorHandle);
+ hFunc(NPDisk::TEvChunkWrite, ErrorHandle);
+ hFunc(NPDisk::TEvChunkRead, ErrorHandle);
+ hFunc(NPDisk::TEvHarakiri, ErrorHandle);
+ hFunc(NPDisk::TEvSlay, ErrorHandle);
+ hFunc(NPDisk::TEvChunkReserve, ErrorHandle);
+ hFunc(NPDisk::TEvChunkForget, ErrorHandle);
+
+ cFunc(TEvents::TSystem::Wakeup, ReportMetrics);
+ cFunc(EvBecomeNormal, HandleMoveToNormalState);
)
};
diff --git a/ydb/core/blobstorage/pdisk/mock/pdisk_mock.h b/ydb/core/blobstorage/pdisk/mock/pdisk_mock.h
index 62a4b863de..1b5c2f9a3b 100644
--- a/ydb/core/blobstorage/pdisk/mock/pdisk_mock.h
+++ b/ydb/core/blobstorage/pdisk/mock/pdisk_mock.h
@@ -7,6 +7,11 @@
namespace NKikimr {
+ enum EPDiskMockEvents {
+ EvBecomeError = TEvBlobStorage::EvEnd + 1,
+ EvBecomeNormal
+ };
+
class TPDiskMockState : public TThrRefBase {
struct TImpl;
std::unique_ptr<TImpl> Impl;
@@ -22,11 +27,13 @@ namespace NKikimr {
void SetCorruptedArea(ui32 chunkIdx, ui32 begin, ui32 end, bool enabled);
std::set<ui32> GetChunks();
+ TMaybe<NPDisk::TOwnerRound> GetOwnerRound(const TVDiskID& vDiskId) const;
ui32 GetChunkSize() const;
TIntervalSet<i64> GetWrittenAreas(ui32 chunkIdx) const;
void TrimQuery();
void SetStatusFlags(NKikimrBlobStorage::TPDiskSpaceColor::E spaceColor);
void SetStatusFlags(NPDisk::TStatusFlags flags);
+ TString& GetStateErrorReason();
TPtr Snapshot(); // create a copy of PDisk whole state
diff --git a/ydb/core/blobstorage/ut_blobstorage/CMakeLists.darwin-x86_64.txt b/ydb/core/blobstorage/ut_blobstorage/CMakeLists.darwin-x86_64.txt
index 5f94d3258c..f9b38bd4a3 100644
--- a/ydb/core/blobstorage/ut_blobstorage/CMakeLists.darwin-x86_64.txt
+++ b/ydb/core/blobstorage/ut_blobstorage/CMakeLists.darwin-x86_64.txt
@@ -15,6 +15,7 @@ add_subdirectory(ut_osiris)
add_subdirectory(ut_read_only_vdisk)
add_subdirectory(ut_replication)
add_subdirectory(ut_scrub)
+add_subdirectory(ut_vdisk_restart)
add_executable(ydb-core-blobstorage-ut_blobstorage)
target_link_libraries(ydb-core-blobstorage-ut_blobstorage PUBLIC
diff --git a/ydb/core/blobstorage/ut_blobstorage/CMakeLists.linux-aarch64.txt b/ydb/core/blobstorage/ut_blobstorage/CMakeLists.linux-aarch64.txt
index b369f934b0..dfb076e3fb 100644
--- a/ydb/core/blobstorage/ut_blobstorage/CMakeLists.linux-aarch64.txt
+++ b/ydb/core/blobstorage/ut_blobstorage/CMakeLists.linux-aarch64.txt
@@ -15,6 +15,7 @@ add_subdirectory(ut_osiris)
add_subdirectory(ut_read_only_vdisk)
add_subdirectory(ut_replication)
add_subdirectory(ut_scrub)
+add_subdirectory(ut_vdisk_restart)
add_executable(ydb-core-blobstorage-ut_blobstorage)
target_link_libraries(ydb-core-blobstorage-ut_blobstorage PUBLIC
diff --git a/ydb/core/blobstorage/ut_blobstorage/CMakeLists.linux-x86_64.txt b/ydb/core/blobstorage/ut_blobstorage/CMakeLists.linux-x86_64.txt
index 02389cc29f..831e212021 100644
--- a/ydb/core/blobstorage/ut_blobstorage/CMakeLists.linux-x86_64.txt
+++ b/ydb/core/blobstorage/ut_blobstorage/CMakeLists.linux-x86_64.txt
@@ -15,6 +15,7 @@ add_subdirectory(ut_osiris)
add_subdirectory(ut_read_only_vdisk)
add_subdirectory(ut_replication)
add_subdirectory(ut_scrub)
+add_subdirectory(ut_vdisk_restart)
add_executable(ydb-core-blobstorage-ut_blobstorage)
target_link_libraries(ydb-core-blobstorage-ut_blobstorage PUBLIC
diff --git a/ydb/core/blobstorage/ut_blobstorage/CMakeLists.windows-x86_64.txt b/ydb/core/blobstorage/ut_blobstorage/CMakeLists.windows-x86_64.txt
index 984f0184b1..6850778337 100644
--- a/ydb/core/blobstorage/ut_blobstorage/CMakeLists.windows-x86_64.txt
+++ b/ydb/core/blobstorage/ut_blobstorage/CMakeLists.windows-x86_64.txt
@@ -15,6 +15,7 @@ add_subdirectory(ut_osiris)
add_subdirectory(ut_read_only_vdisk)
add_subdirectory(ut_replication)
add_subdirectory(ut_scrub)
+add_subdirectory(ut_vdisk_restart)
add_executable(ydb-core-blobstorage-ut_blobstorage)
target_link_libraries(ydb-core-blobstorage-ut_blobstorage PUBLIC
diff --git a/ydb/core/blobstorage/ut_blobstorage/lib/env.h b/ydb/core/blobstorage/ut_blobstorage/lib/env.h
index 493aa7cb01..f71efb94c5 100644
--- a/ydb/core/blobstorage/ut_blobstorage/lib/env.h
+++ b/ydb/core/blobstorage/ut_blobstorage/lib/env.h
@@ -19,6 +19,7 @@ struct TEnvironmentSetup {
const ui32 NumGroups = 1;
TIntrusivePtr<NFake::TProxyDS> Group0 = MakeIntrusive<NFake::TProxyDS>();
std::map<std::pair<ui32, ui32>, TIntrusivePtr<TPDiskMockState>> PDiskMockStates;
+ TVector<TActorId> PDiskActors;
std::set<TActorId> CommencedReplication;
std::unordered_map<ui32, TString> Cache;
@@ -58,6 +59,7 @@ struct TEnvironmentSetup {
const TActorId& actorId = ctx.Register(CreatePDiskMockActor(state), TMailboxType::HTSwap, poolId);
const TActorId& serviceId = MakeBlobStoragePDiskID(nodeId, pdiskId);
ctx.ExecutorThread.ActorSystem->RegisterLocalService(serviceId, actorId);
+ Env.PDiskActors.push_back(actorId);
}
};
diff --git a/ydb/core/blobstorage/ut_blobstorage/ut_vdisk_restart/CMakeLists.darwin-x86_64.txt b/ydb/core/blobstorage/ut_blobstorage/ut_vdisk_restart/CMakeLists.darwin-x86_64.txt
new file mode 100644
index 0000000000..379dd6aafc
--- /dev/null
+++ b/ydb/core/blobstorage/ut_blobstorage/ut_vdisk_restart/CMakeLists.darwin-x86_64.txt
@@ -0,0 +1,74 @@
+
+# This file was generated by the build system used internally in the Yandex monorepo.
+# Only simple modifications are allowed (adding source-files to targets, adding simple properties
+# like target_include_directories). These modifications will be ported to original
+# ya.make files by maintainers. Any complex modifications which can't be ported back to the
+# original buildsystem will not be accepted.
+
+
+
+add_executable(blobstorage-ut_blobstorage-ut_vdisk_restart)
+target_include_directories(blobstorage-ut_blobstorage-ut_vdisk_restart PRIVATE
+ ${CMAKE_SOURCE_DIR}/ydb/core/blobstorage/ut_blobstorage
+)
+target_link_libraries(blobstorage-ut_blobstorage-ut_vdisk_restart PUBLIC
+ contrib-libs-cxxsupp
+ yutil
+ library-cpp-cpuid_check
+ cpp-testing-unittest_main
+ blobstorage-ut_blobstorage-lib
+)
+target_link_options(blobstorage-ut_blobstorage-ut_vdisk_restart PRIVATE
+ -Wl,-platform_version,macos,11.0,11.0
+ -fPIC
+ -fPIC
+ -framework
+ CoreFoundation
+)
+target_sources(blobstorage-ut_blobstorage-ut_vdisk_restart PRIVATE
+ ${CMAKE_SOURCE_DIR}/ydb/core/blobstorage/ut_blobstorage/vdisk_restart.cpp
+)
+set_property(
+ TARGET
+ blobstorage-ut_blobstorage-ut_vdisk_restart
+ PROPERTY
+ SPLIT_FACTOR
+ 10
+)
+add_yunittest(
+ NAME
+ blobstorage-ut_blobstorage-ut_vdisk_restart
+ TEST_TARGET
+ blobstorage-ut_blobstorage-ut_vdisk_restart
+ TEST_ARG
+ --print-before-suite
+ --print-before-test
+ --fork-tests
+ --print-times
+ --show-fails
+)
+set_yunittest_property(
+ TEST
+ blobstorage-ut_blobstorage-ut_vdisk_restart
+ PROPERTY
+ LABELS
+ MEDIUM
+)
+set_yunittest_property(
+ TEST
+ blobstorage-ut_blobstorage-ut_vdisk_restart
+ PROPERTY
+ PROCESSORS
+ 1
+)
+set_yunittest_property(
+ TEST
+ blobstorage-ut_blobstorage-ut_vdisk_restart
+ PROPERTY
+ TIMEOUT
+ 600
+)
+target_allocator(blobstorage-ut_blobstorage-ut_vdisk_restart
+ system_allocator
+)
+vcs_info(blobstorage-ut_blobstorage-ut_vdisk_restart)
diff --git a/ydb/core/blobstorage/ut_blobstorage/ut_vdisk_restart/CMakeLists.linux-aarch64.txt b/ydb/core/blobstorage/ut_blobstorage/ut_vdisk_restart/CMakeLists.linux-aarch64.txt
new file mode 100644
index 0000000000..1026c68db9
--- /dev/null
+++ b/ydb/core/blobstorage/ut_blobstorage/ut_vdisk_restart/CMakeLists.linux-aarch64.txt
@@ -0,0 +1,77 @@
+
+# This file was generated by the build system used internally in the Yandex monorepo.
+# Only simple modifications are allowed (adding source-files to targets, adding simple properties
+# like target_include_directories). These modifications will be ported to original
+# ya.make files by maintainers. Any complex modifications which can't be ported back to the
+# original buildsystem will not be accepted.
+
+
+
+add_executable(blobstorage-ut_blobstorage-ut_vdisk_restart)
+target_include_directories(blobstorage-ut_blobstorage-ut_vdisk_restart PRIVATE
+ ${CMAKE_SOURCE_DIR}/ydb/core/blobstorage/ut_blobstorage
+)
+target_link_libraries(blobstorage-ut_blobstorage-ut_vdisk_restart PUBLIC
+ contrib-libs-linux-headers
+ contrib-libs-cxxsupp
+ yutil
+ cpp-testing-unittest_main
+ blobstorage-ut_blobstorage-lib
+)
+target_link_options(blobstorage-ut_blobstorage-ut_vdisk_restart PRIVATE
+ -ldl
+ -lrt
+ -Wl,--no-as-needed
+ -fPIC
+ -fPIC
+ -lpthread
+ -lrt
+ -ldl
+)
+target_sources(blobstorage-ut_blobstorage-ut_vdisk_restart PRIVATE
+ ${CMAKE_SOURCE_DIR}/ydb/core/blobstorage/ut_blobstorage/vdisk_restart.cpp
+)
+set_property(
+ TARGET
+ blobstorage-ut_blobstorage-ut_vdisk_restart
+ PROPERTY
+ SPLIT_FACTOR
+ 10
+)
+add_yunittest(
+ NAME
+ blobstorage-ut_blobstorage-ut_vdisk_restart
+ TEST_TARGET
+ blobstorage-ut_blobstorage-ut_vdisk_restart
+ TEST_ARG
+ --print-before-suite
+ --print-before-test
+ --fork-tests
+ --print-times
+ --show-fails
+)
+set_yunittest_property(
+ TEST
+ blobstorage-ut_blobstorage-ut_vdisk_restart
+ PROPERTY
+ LABELS
+ MEDIUM
+)
+set_yunittest_property(
+ TEST
+ blobstorage-ut_blobstorage-ut_vdisk_restart
+ PROPERTY
+ PROCESSORS
+ 1
+)
+set_yunittest_property(
+ TEST
+ blobstorage-ut_blobstorage-ut_vdisk_restart
+ PROPERTY
+ TIMEOUT
+ 600
+)
+target_allocator(blobstorage-ut_blobstorage-ut_vdisk_restart
+ cpp-malloc-jemalloc
+)
+vcs_info(blobstorage-ut_blobstorage-ut_vdisk_restart)
diff --git a/ydb/core/blobstorage/ut_blobstorage/ut_vdisk_restart/CMakeLists.linux-x86_64.txt b/ydb/core/blobstorage/ut_blobstorage/ut_vdisk_restart/CMakeLists.linux-x86_64.txt
new file mode 100644
index 0000000000..7d6211c778
--- /dev/null
+++ b/ydb/core/blobstorage/ut_blobstorage/ut_vdisk_restart/CMakeLists.linux-x86_64.txt
@@ -0,0 +1,79 @@
+
+# This file was generated by the build system used internally in the Yandex monorepo.
+# Only simple modifications are allowed (adding source-files to targets, adding simple properties
+# like target_include_directories). These modifications will be ported to original
+# ya.make files by maintainers. Any complex modifications which can't be ported back to the
+# original buildsystem will not be accepted.
+
+
+
+add_executable(blobstorage-ut_blobstorage-ut_vdisk_restart)
+target_include_directories(blobstorage-ut_blobstorage-ut_vdisk_restart PRIVATE
+ ${CMAKE_SOURCE_DIR}/ydb/core/blobstorage/ut_blobstorage
+)
+target_link_libraries(blobstorage-ut_blobstorage-ut_vdisk_restart PUBLIC
+ contrib-libs-linux-headers
+ contrib-libs-cxxsupp
+ yutil
+ library-cpp-cpuid_check
+ cpp-testing-unittest_main
+ blobstorage-ut_blobstorage-lib
+)
+target_link_options(blobstorage-ut_blobstorage-ut_vdisk_restart PRIVATE
+ -ldl
+ -lrt
+ -Wl,--no-as-needed
+ -fPIC
+ -fPIC
+ -lpthread
+ -lrt
+ -ldl
+)
+target_sources(blobstorage-ut_blobstorage-ut_vdisk_restart PRIVATE
+ ${CMAKE_SOURCE_DIR}/ydb/core/blobstorage/ut_blobstorage/vdisk_restart.cpp
+)
+set_property(
+ TARGET
+ blobstorage-ut_blobstorage-ut_vdisk_restart
+ PROPERTY
+ SPLIT_FACTOR
+ 10
+)
+add_yunittest(
+ NAME
+ blobstorage-ut_blobstorage-ut_vdisk_restart
+ TEST_TARGET
+ blobstorage-ut_blobstorage-ut_vdisk_restart
+ TEST_ARG
+ --print-before-suite
+ --print-before-test
+ --fork-tests
+ --print-times
+ --show-fails
+)
+set_yunittest_property(
+ TEST
+ blobstorage-ut_blobstorage-ut_vdisk_restart
+ PROPERTY
+ LABELS
+ MEDIUM
+)
+set_yunittest_property(
+ TEST
+ blobstorage-ut_blobstorage-ut_vdisk_restart
+ PROPERTY
+ PROCESSORS
+ 1
+)
+set_yunittest_property(
+ TEST
+ blobstorage-ut_blobstorage-ut_vdisk_restart
+ PROPERTY
+ TIMEOUT
+ 600
+)
+target_allocator(blobstorage-ut_blobstorage-ut_vdisk_restart
+ cpp-malloc-tcmalloc
+ libs-tcmalloc-no_percpu_cache
+)
+vcs_info(blobstorage-ut_blobstorage-ut_vdisk_restart)
diff --git a/ydb/core/blobstorage/ut_blobstorage/ut_vdisk_restart/CMakeLists.txt b/ydb/core/blobstorage/ut_blobstorage/ut_vdisk_restart/CMakeLists.txt
new file mode 100644
index 0000000000..f8b31df0c1
--- /dev/null
+++ b/ydb/core/blobstorage/ut_blobstorage/ut_vdisk_restart/CMakeLists.txt
@@ -0,0 +1,17 @@
+
+# This file was generated by the build system used internally in the Yandex monorepo.
+# Only simple modifications are allowed (adding source-files to targets, adding simple properties
+# like target_include_directories). These modifications will be ported to original
+# ya.make files by maintainers. Any complex modifications which can't be ported back to the
+# original buildsystem will not be accepted.
+
+
+if (CMAKE_SYSTEM_NAME STREQUAL "Linux" AND CMAKE_SYSTEM_PROCESSOR STREQUAL "aarch64" AND NOT HAVE_CUDA)
+ include(CMakeLists.linux-aarch64.txt)
+elseif (CMAKE_SYSTEM_NAME STREQUAL "Darwin" AND CMAKE_SYSTEM_PROCESSOR STREQUAL "x86_64")
+ include(CMakeLists.darwin-x86_64.txt)
+elseif (WIN32 AND CMAKE_SYSTEM_PROCESSOR STREQUAL "AMD64" AND NOT HAVE_CUDA)
+ include(CMakeLists.windows-x86_64.txt)
+elseif (CMAKE_SYSTEM_NAME STREQUAL "Linux" AND CMAKE_SYSTEM_PROCESSOR STREQUAL "x86_64" AND NOT HAVE_CUDA)
+ include(CMakeLists.linux-x86_64.txt)
+endif()
diff --git a/ydb/core/blobstorage/ut_blobstorage/ut_vdisk_restart/CMakeLists.windows-x86_64.txt b/ydb/core/blobstorage/ut_blobstorage/ut_vdisk_restart/CMakeLists.windows-x86_64.txt
new file mode 100644
index 0000000000..40828e0922
--- /dev/null
+++ b/ydb/core/blobstorage/ut_blobstorage/ut_vdisk_restart/CMakeLists.windows-x86_64.txt
@@ -0,0 +1,67 @@
+
+# This file was generated by the build system used internally in the Yandex monorepo.
+# Only simple modifications are allowed (adding source-files to targets, adding simple properties
+# like target_include_directories). These modifications will be ported to original
+# ya.make files by maintainers. Any complex modifications which can't be ported back to the
+# original buildsystem will not be accepted.
+
+
+
+add_executable(blobstorage-ut_blobstorage-ut_vdisk_restart)
+target_include_directories(blobstorage-ut_blobstorage-ut_vdisk_restart PRIVATE
+ ${CMAKE_SOURCE_DIR}/ydb/core/blobstorage/ut_blobstorage
+)
+target_link_libraries(blobstorage-ut_blobstorage-ut_vdisk_restart PUBLIC
+ contrib-libs-cxxsupp
+ yutil
+ library-cpp-cpuid_check
+ cpp-testing-unittest_main
+ blobstorage-ut_blobstorage-lib
+)
+target_sources(blobstorage-ut_blobstorage-ut_vdisk_restart PRIVATE
+ ${CMAKE_SOURCE_DIR}/ydb/core/blobstorage/ut_blobstorage/vdisk_restart.cpp
+)
+set_property(
+ TARGET
+ blobstorage-ut_blobstorage-ut_vdisk_restart
+ PROPERTY
+ SPLIT_FACTOR
+ 10
+)
+add_yunittest(
+ NAME
+ blobstorage-ut_blobstorage-ut_vdisk_restart
+ TEST_TARGET
+ blobstorage-ut_blobstorage-ut_vdisk_restart
+ TEST_ARG
+ --print-before-suite
+ --print-before-test
+ --fork-tests
+ --print-times
+ --show-fails
+)
+set_yunittest_property(
+ TEST
+ blobstorage-ut_blobstorage-ut_vdisk_restart
+ PROPERTY
+ LABELS
+ MEDIUM
+)
+set_yunittest_property(
+ TEST
+ blobstorage-ut_blobstorage-ut_vdisk_restart
+ PROPERTY
+ PROCESSORS
+ 1
+)
+set_yunittest_property(
+ TEST
+ blobstorage-ut_blobstorage-ut_vdisk_restart
+ PROPERTY
+ TIMEOUT
+ 600
+)
+target_allocator(blobstorage-ut_blobstorage-ut_vdisk_restart
+ system_allocator
+)
+vcs_info(blobstorage-ut_blobstorage-ut_vdisk_restart)
diff --git a/ydb/core/blobstorage/ut_blobstorage/ut_vdisk_restart/ya.make b/ydb/core/blobstorage/ut_blobstorage/ut_vdisk_restart/ya.make
new file mode 100644
index 0000000000..063edc83d4
--- /dev/null
+++ b/ydb/core/blobstorage/ut_blobstorage/ut_vdisk_restart/ya.make
@@ -0,0 +1,17 @@
+UNITTEST_FOR(ydb/core/blobstorage/ut_blobstorage)
+
+ FORK_SUBTESTS()
+
+ SIZE(MEDIUM)
+
+ TIMEOUT(600)
+
+ SRCS(
+ vdisk_restart.cpp
+ )
+
+ PEERDIR(
+ ydb/core/blobstorage/ut_blobstorage/lib
+ )
+
+END()
diff --git a/ydb/core/blobstorage/ut_blobstorage/vdisk_restart.cpp b/ydb/core/blobstorage/ut_blobstorage/vdisk_restart.cpp
new file mode 100644
index 0000000000..a6b02c63f1
--- /dev/null
+++ b/ydb/core/blobstorage/ut_blobstorage/vdisk_restart.cpp
@@ -0,0 +1,64 @@
+#include <ydb/core/blobstorage/ut_blobstorage/lib/env.h>
+
+#include <ydb/core/blobstorage/pdisk/blobstorage_pdisk_ut_http_request.h>
+
+
+Y_UNIT_TEST_SUITE(VDiskRestart) {
+
+ Y_UNIT_TEST(Simple) {
+ TEnvironmentSetup env({
+ .NodeCount = 8,
+ .VDiskReplPausedAtStart = false,
+ .Erasure = TBlobStorageGroupType::Erasure4Plus2Block,
+ });
+ env.CreateBoxAndPool(1, 1);
+ env.Sim(TDuration::Minutes(1));
+
+ auto groups = env.GetGroups();
+ UNIT_ASSERT_VALUES_EQUAL(groups.size(), 1);
+
+ auto groupInfo = env.GetGroupInfo(groups.front());
+
+
+ ui32 pos = 0;
+ auto vDiskActorId = groupInfo->GetActorId(pos);
+ auto baseConfig = env.FetchBaseConfig();
+ const TVDiskID& someVDisk = groupInfo->GetVDiskId(pos);
+ const auto& somePDisk = baseConfig.GetPDisk(pos);
+ const auto& someVSlot = baseConfig.GetVSlot(pos);
+ auto getOwnerRound = [&]() {
+ return env.PDiskMockStates[{somePDisk.GetNodeId(), somePDisk.GetPDiskId()}]->GetOwnerRound(someVDisk);
+ };
+ auto currentRound = getOwnerRound();
+
+ const TActorId sender = env.Runtime->AllocateEdgeActor(vDiskActorId.NodeId(), __FILE__, __LINE__);
+
+ THttpRequestMock httpRequest;
+ httpRequest.CgiParameters.InsertUnescaped("type", "restart");
+ httpRequest.Path = Sprintf("/actors/vdisks/vdisk%09" PRIu32 "_%09" PRIu32, somePDisk.GetPDiskId(), someVSlot.GetVSlotId().GetVSlotId());
+ NMonitoring::TMonService2HttpRequest monService2HttpRequest(nullptr, &httpRequest, nullptr, nullptr, "", nullptr);
+ auto ev = std::make_unique<NMon::TEvHttpInfo>(monService2HttpRequest);
+
+ auto sendPDiskEvent = [&](EPDiskMockEvents ev) {
+ for (const auto& pDisk: env.PDiskActors) {
+ env.Runtime->WrapInActorContext(sender, [&] () {
+ env.Runtime->Send(new IEventHandle(ev, 0, pDisk, sender, nullptr, 0));
+ });
+ }
+ };
+ sendPDiskEvent(EvBecomeError);
+ env.Sim(TDuration::Seconds(1));
+
+ env.Runtime->WrapInActorContext(sender, [&] () {
+ env.Runtime->Send(new IEventHandle(vDiskActorId, sender, ev.release()));
+ });
+ auto res = env.WaitForEdgeActorEvent<NMon::TEvHttpInfoRes>(sender, false);
+ UNIT_ASSERT_VALUES_UNEQUAL(res->Get()->Answer.find("VDisk restart request has been sent"), std::string::npos);
+
+ env.Sim(TDuration::Seconds(10));
+ sendPDiskEvent(EvBecomeNormal);
+ env.Sim(TDuration::Seconds(10));
+
+ UNIT_ASSERT_VALUES_UNEQUAL(currentRound, getOwnerRound());
+ }
+}
diff --git a/ydb/core/blobstorage/ut_blobstorage/ya.make b/ydb/core/blobstorage/ut_blobstorage/ya.make
index ce95915d31..c2acdec391 100644
--- a/ydb/core/blobstorage/ut_blobstorage/ya.make
+++ b/ydb/core/blobstorage/ut_blobstorage/ya.make
@@ -67,4 +67,5 @@ RECURSE_FOR_TESTS(
ut_osiris
ut_replication
ut_scrub
+ ut_vdisk_restart
)
diff --git a/ydb/core/blobstorage/vdisk/skeleton/blobstorage_monactors.cpp b/ydb/core/blobstorage/vdisk/skeleton/blobstorage_monactors.cpp
index 8dda48b7c2..e2c611338d 100644
--- a/ydb/core/blobstorage/vdisk/skeleton/blobstorage_monactors.cpp
+++ b/ydb/core/blobstorage/vdisk/skeleton/blobstorage_monactors.cpp
@@ -3,6 +3,8 @@
#include "skeleton_mon_dbmainpage.h"
#include "skeleton_mon_util.h"
+#include <ydb/core/blobstorage/base/blobstorage_events.h>
+
#include <library/cpp/actors/core/hfunc.h>
#include <library/cpp/actors/core/actor_bootstrapped.h>
#include <library/cpp/actors/core/mon.h>
@@ -983,6 +985,49 @@ namespace NKikimr {
{}
};
+ class TRestartVDiskActor : public TActorBootstrapped<TRestartVDiskActor> {
+ const ui32 PDiskId;
+ const TVDiskID VDiskId;
+ const TActorId WardenId;
+ const TActorId NotifyId;
+ const TActorId Sender;
+
+ friend class TActorBootstrapped<TRestartVDiskActor>;
+
+ void Bootstrap(const TActorContext &ctx) {
+ ctx.Send(WardenId, new TEvBlobStorage::TEvAskRestartVDisk(PDiskId, VDiskId));
+ ctx.Send(NotifyId, new TEvents::TEvActorDied);
+ ctx.Send(Sender, new NMon::TEvHttpInfoRes(MakeReply()));
+ Die(ctx);
+ }
+
+ TString MakeReply() const {
+ TStringStream str;
+ HTML(str) {
+ str << "VDisk restart request has been sent <br>\n"
+ << "<a class=\"btn btn-default\" href=\"?\">Go back to the main VDisk page</a>";
+ }
+ return str.Str();
+ }
+
+ public:
+ TRestartVDiskActor(
+ const ui32 pDiskId,
+ const TVDiskID &vDiskId,
+ const TActorId &wardenId,
+ const TActorId &notifyId,
+ const TActorId &sender
+ )
+ : TActorBootstrapped<TRestartVDiskActor>()
+ , PDiskId(pDiskId)
+ , VDiskId(vDiskId)
+ , WardenId(wardenId)
+ , NotifyId(notifyId)
+ , Sender(sender)
+ {
+ }
+ };
+
////////////////////////////////////////////////////////////////////////////
// TSkeletonFrontMonMainPageActor
////////////////////////////////////////////////////////////////////////////
@@ -1064,6 +1109,10 @@ namespace NKikimr {
{}
};
+ bool IsVDiskRestartAllowed(NKikimrWhiteboard::EVDiskState state) {
+ return state == NKikimrWhiteboard::EVDiskState::PDiskError;
+ }
+
////////////////////////////////////////////////////////////////////////////
// SKELETON FRONT MON REQUEST HANDLER
////////////////////////////////////////////////////////////////////////////
@@ -1074,7 +1123,8 @@ namespace NKikimr {
TIntrusivePtr<TVDiskConfig> cfg,
const std::shared_ptr<TBlobStorageGroupInfo::TTopology> &top,
NMon::TEvHttpInfo::TPtr &ev,
- const TString &frontHtml) {
+ const TString &frontHtml,
+ const NMonGroup::TVDiskStateGroup& vDiskMonGroup) {
const TCgiParameters& cgi = ev->Get()->Request.GetParams();
const TString &type = cgi.Get("type");
@@ -1104,6 +1154,17 @@ namespace NKikimr {
ev, NKikimrBlobStorage::StatHugeAction, dbname);
} else if (type == "dbmainpage") {
return CreateMonDbMainPageActor(selfVDiskId, notifyId, skeletonFrontID, skeletonID, ev);
+ } else if (type == "restart") {
+ if (IsVDiskRestartAllowed(vDiskMonGroup.VDiskState())) {
+ return new TRestartVDiskActor(
+ cfg->BaseInfo.PDiskId, selfVDiskId, MakeBlobStorageNodeWardenID(skeletonFrontID.NodeId()), notifyId, ev->Sender
+ );
+ } else {
+ return new TMonErrorActor(notifyId, ev,
+ "VDisk restart in the normal state is not allowed <br>\n"
+ "<a class=\"btn btn-default\" href=\"?\">Go back to the main VDisk page</a>"
+ );
+ }
} else {
auto s = Sprintf("Unknown value '%s' for CGI parameter 'type'", type.data());
return new TMonErrorActor(notifyId, ev, s);
diff --git a/ydb/core/blobstorage/vdisk/skeleton/blobstorage_monactors.h b/ydb/core/blobstorage/vdisk/skeleton/blobstorage_monactors.h
index a05d0641a7..1eafd9ae69 100644
--- a/ydb/core/blobstorage/vdisk/skeleton/blobstorage_monactors.h
+++ b/ydb/core/blobstorage/vdisk/skeleton/blobstorage_monactors.h
@@ -21,7 +21,8 @@ namespace NKikimr {
TIntrusivePtr<TVDiskConfig> cfg,
const std::shared_ptr<TBlobStorageGroupInfo::TTopology> &top,
NMon::TEvHttpInfo::TPtr &ev,
- const TString &frontHtml);
+ const TString &frontHtml,
+ const NMonGroup::TVDiskStateGroup& vDiskMonGroup);
IActor *CreateFrontSkeletonGetLogoBlobRequestHandler(const TVDiskID &selfVDiskId,
const TActorId &notifyId,
@@ -30,6 +31,7 @@ namespace NKikimr {
const std::shared_ptr<TBlobStorageGroupInfo::TTopology> &top,
TEvGetLogoBlobRequest::TPtr &ev);
+ bool IsVDiskRestartAllowed(NKikimrWhiteboard::EVDiskState state);
} // NKikimr
diff --git a/ydb/core/blobstorage/vdisk/skeleton/blobstorage_skeletonfront.cpp b/ydb/core/blobstorage/vdisk/skeleton/blobstorage_skeletonfront.cpp
index dadb329e7b..5c7cda83ba 100644
--- a/ydb/core/blobstorage/vdisk/skeleton/blobstorage_skeletonfront.cpp
+++ b/ydb/core/blobstorage/vdisk/skeleton/blobstorage_skeletonfront.cpp
@@ -926,6 +926,15 @@ namespace NKikimr {
}
}
}
+ {
+ str << "<a class=\"btn btn-default\" href=\"?type=restart\" "
+ << (
+ IsVDiskRestartAllowed(VDiskMonGroup.VDiskState())
+ ? "style='background:Tomato' "
+ : "disabled style='background:LightGray' "
+ )
+ << ">Restart</a>";
+ }
}
}
}
@@ -1535,7 +1544,7 @@ namespace NKikimr {
TString html = (type == TString()) ? GenerateHtmlState(ctx) : TString();
auto aid = ctx.Register(CreateFrontSkeletonMonRequestHandler(SelfVDiskId, ctx.SelfID, SkeletonId,
- ctx.SelfID, Config, Top, ev, html));
+ ctx.SelfID, Config, Top, ev, html, VDiskMonGroup));
ActiveActors.Insert(aid);
}