From 447df93c2d9326a7950ecd3cf88ddfdfd5c50497 Mon Sep 17 00:00:00 2001 From: Ivan Baidakou Date: Wed, 28 Aug 2024 18:19:34 +0300 Subject: [PATCH] core, fs, add scan request --- CMakeLists.txt | 1 + src/fs/scan_scheduler.cpp | 35 +++++++++++++++++++++++++----- src/fs/scan_scheduler.h | 1 + src/model/diff/cluster_visitor.cpp | 5 +++++ src/model/diff/cluster_visitor.h | 2 ++ tests/085-scan-scheduler.cpp | 5 +++++ tests/diff-builder.cpp | 5 +++++ tests/diff-builder.h | 1 + 8 files changed, 49 insertions(+), 6 deletions(-) diff --git a/CMakeLists.txt b/CMakeLists.txt index e2daea7e..d05eea12 100644 --- a/CMakeLists.txt +++ b/CMakeLists.txt @@ -105,6 +105,7 @@ add_library(syncspirit_lib src/model/diff/local/file_availability.cpp src/model/diff/local/update.cpp src/model/diff/local/scan_finish.cpp + src/model/diff/local/scan_request.cpp src/model/diff/local/scan_start.cpp src/model/diff/modify/add_remote_folder_infos.cpp src/model/diff/modify/add_ignored_device.cpp diff --git a/src/fs/scan_scheduler.cpp b/src/fs/scan_scheduler.cpp index 2b74e88f..0922dec6 100644 --- a/src/fs/scan_scheduler.cpp +++ b/src/fs/scan_scheduler.cpp @@ -3,10 +3,10 @@ #include "scan_scheduler.h" #include "net/names.h" -#include "messages.h" #include "model/diff/modify/upsert_folder.h" -#include "model/diff/local/scan_start.h" #include "model/diff/local/scan_finish.h" +#include "model/diff/local/scan_request.h" +#include "model/diff/local/scan_start.h" using namespace syncspirit::fs; @@ -55,6 +55,15 @@ auto scan_scheduler_t::operator()(const model::diff::modify::upsert_folder_t &di return diff.visit_next(*this, custom); } +auto scan_scheduler_t::operator()(const model::diff::local::scan_request_t &diff, void *custom) noexcept + -> outcome::result { + scan_queue.emplace_back(diff.folder_id); + if (!scan_in_progress) { + scan_next_or_schedule(); + } + return diff.visit_next(*this, custom); +} + auto scan_scheduler_t::operator()(const model::diff::local::scan_finish_t &diff, void *custom) noexcept -> outcome::result { scan_in_progress = false; @@ -85,6 +94,23 @@ void scan_scheduler_t::scan_next_or_schedule() noexcept { } auto scan_scheduler_t::scan_next() noexcept -> schedule_option_t { + while (!scan_queue.empty()) { + auto folder_id = scan_queue.front(); + scan_queue.pop_front(); + if (!cluster->get_folders().by_id(folder_id)) { + continue; + } + for (auto it = scan_queue.begin(); it != scan_queue.end(); ) { + if (*it == folder_id) { + it = scan_queue.erase(it); + } else { + ++it; + } + } + initiate_scan(folder_id); + return {}; + } + auto folder = model::folder_ptr_t(); auto deadline = r::pt::ptime{}; auto now = r::pt::second_clock::local_time(); @@ -95,7 +121,6 @@ auto scan_scheduler_t::scan_next() noexcept -> schedule_option_t { } auto interval_s = r::pt::seconds{interval}; auto prev_scan = it.item->get_scan_finish(); - LOG_WARN(log, "{}, prev_scan = {}", it.item->get_id(), r::pt::to_simple_string(prev_scan)); auto it_deadline = prev_scan.is_not_a_date_time() ? now : prev_scan + interval_s; auto eq = it_deadline == deadline; auto select_it = !folder || it_deadline < deadline || @@ -107,8 +132,6 @@ auto scan_scheduler_t::scan_next() noexcept -> schedule_option_t { } if (folder && deadline <= now) { - LOG_WARN(log, "{}, deadline = {}, now = {}", folder->get_id(), r::pt::to_simple_string(deadline), - r::pt::to_simple_string(now)); initiate_scan(folder->get_id()); return {}; } @@ -130,7 +153,7 @@ void scan_scheduler_t::on_timer(r::request_id_t, bool cancelled) noexcept { } void scan_scheduler_t::initiate_scan(std::string_view folder_id) noexcept { - LOG_DEBUG(log, "iniating folder {} scan", folder_id); + LOG_DEBUG(log, "iniating folder '{}' scan", folder_id); auto diff = model::diff::cluster_diff_ptr_t{}; auto now = r::pt::microsec_clock::local_time(); diff = new model::diff::local::scan_start_t(folder_id, now); diff --git a/src/fs/scan_scheduler.h b/src/fs/scan_scheduler.h index a8f67cd7..6e78701a 100644 --- a/src/fs/scan_scheduler.h +++ b/src/fs/scan_scheduler.h @@ -58,6 +58,7 @@ struct SYNCSPIRIT_API scan_scheduler_t : public r::actor_base_t, private model:: void initiate_scan(std::string_view folder_id) noexcept; outcome::result operator()(const model::diff::modify::upsert_folder_t &, void *custom) noexcept override; + outcome::result operator()(const model::diff::local::scan_request_t &, void *custom) noexcept override; outcome::result operator()(const model::diff::local::scan_finish_t &, void *custom) noexcept override; model::cluster_ptr_t cluster; diff --git a/src/model/diff/cluster_visitor.cpp b/src/model/diff/cluster_visitor.cpp index 8a738de0..11c5a938 100644 --- a/src/model/diff/cluster_visitor.cpp +++ b/src/model/diff/cluster_visitor.cpp @@ -9,6 +9,7 @@ #include "load/pending_devices.h" #include "local/file_availability.h" #include "local/scan_finish.h" +#include "local/scan_request.h" #include "local/scan_start.h" #include "local/update.h" #include "modify/add_ignored_device.h" @@ -69,6 +70,10 @@ auto cluster_visitor_t::operator()(const local::scan_finish_t &diff, void *custo return diff.visit_next(*this, custom); } +auto cluster_visitor_t::operator()(const local::scan_request_t &diff, void *custom) noexcept -> outcome::result { + return diff.visit_next(*this, custom); +} + auto cluster_visitor_t::operator()(const local::scan_start_t &diff, void *custom) noexcept -> outcome::result { return diff.visit_next(*this, custom); } diff --git a/src/model/diff/cluster_visitor.h b/src/model/diff/cluster_visitor.h index 9bc4b9ac..34bc6aac 100644 --- a/src/model/diff/cluster_visitor.h +++ b/src/model/diff/cluster_visitor.h @@ -20,6 +20,7 @@ struct load_cluster_t; namespace local { struct file_availability_t; struct scan_finish_t; +struct scan_request_t; struct scan_start_t; struct update_t; } // namespace local @@ -64,6 +65,7 @@ template <> struct SYNCSPIRIT_API generic_visitor_t operator()(const local::file_availability_t &, void *custom) noexcept; virtual outcome::result operator()(const local::update_t &, void *custom) noexcept; virtual outcome::result operator()(const local::scan_finish_t &, void *custom) noexcept; + virtual outcome::result operator()(const local::scan_request_t &, void *custom) noexcept; virtual outcome::result operator()(const local::scan_start_t &, void *custom) noexcept; virtual outcome::result operator()(const peer::cluster_update_t &, void *custom) noexcept; diff --git a/tests/085-scan-scheduler.cpp b/tests/085-scan-scheduler.cpp index 2b5882e7..fec7cbd7 100644 --- a/tests/085-scan-scheduler.cpp +++ b/tests/085-scan-scheduler.cpp @@ -141,6 +141,11 @@ void test_2_folders() { sup->do_process(); REQUIRE(f1->is_scanning()); REQUIRE(!f2->is_scanning()); + + f2->set_scan_finish({}); + builder.scan_finish(f1_id, at).scan_request(f2_id).apply(*sup); + REQUIRE(!f1->is_scanning()); + REQUIRE(f2->is_scanning()); } }; F().run(); diff --git a/tests/diff-builder.cpp b/tests/diff-builder.cpp index c96c01d7..5d0d7590 100644 --- a/tests/diff-builder.cpp +++ b/tests/diff-builder.cpp @@ -5,6 +5,7 @@ #include "model/messages.h" #include "model/diff/local/update.h" #include "model/diff/local/scan_finish.h" +#include "model/diff/local/scan_request.h" #include "model/diff/local/scan_start.h" #include "model/diff/modify/add_ignored_device.h" #include "model/diff/modify/add_pending_device.h" @@ -260,6 +261,10 @@ diff_builder_t &diff_builder_t::scan_finish(std::string_view id, const r::pt::pt return assign(new model::diff::local::scan_finish_t(std::string(id), final_at)); } +diff_builder_t &diff_builder_t::scan_request(std::string_view id) noexcept { + return assign(new model::diff::local::scan_request_t(std::string(id))); +} + template static void generic_assign(Holder *holder, Diff *diff) noexcept { if (!(*holder)) { holder->reset(diff); diff --git a/tests/diff-builder.h b/tests/diff-builder.h index 7de3f751..0e06557e 100644 --- a/tests/diff-builder.h +++ b/tests/diff-builder.h @@ -85,6 +85,7 @@ struct SYNCSPIRIT_TEST_API diff_builder_t { diff_builder_t &remove_unknown_device(const model::pending_device_t &device) noexcept; diff_builder_t &scan_start(std::string_view id, const r::pt::ptime & = {}) noexcept; diff_builder_t &scan_finish(std::string_view id, const r::pt::ptime & = {}) noexcept; + diff_builder_t &scan_request(std::string_view id) noexcept; model::sequencer_t &get_sequencer() noexcept;