From 9d4087b101adb8f2e592a9e7cc4a597df6d38a14 Mon Sep 17 00:00:00 2001 From: levlam Date: Sun, 9 Jul 2023 16:01:14 +0300 Subject: [PATCH] Ensure that stories are sent in the correct order. --- td/telegram/StoryManager.cpp | 44 ++++++++++++++++++++++++++++++++---- td/telegram/StoryManager.h | 15 ++++++++++++ 2 files changed, 55 insertions(+), 4 deletions(-) diff --git a/td/telegram/StoryManager.cpp b/td/telegram/StoryManager.cpp index b6b79d6ec..bc65b3a5f 100644 --- a/td/telegram/StoryManager.cpp +++ b/td/telegram/StoryManager.cpp @@ -716,6 +716,11 @@ StoryManager::PendingStory::PendingStory(DialogId dialog_id, StoryId story_id, u , story_(std::move(story)) { } +StoryManager::ReadyToSendStory::ReadyToSendStory(FileId file_id, unique_ptr &&pending_story, + telegram_api::object_ptr &&input_file) + : file_id_(file_id), pending_story_(std::move(pending_story)), input_file_(std::move(input_file)) { +} + template void StoryManager::Story::store(StorerT &storer) const { using td::store; @@ -2743,6 +2748,8 @@ void StoryManager::send_story(td_api::object_ptr &&in td::make_unique(dialog_id, StoryId(), ++send_story_count_, random_id, std::move(story)); pending_story->log_event_id_ = save_send_story_log_event(pending_story.get()); + yet_unsent_stories_.insert(pending_story->send_story_num_); + do_send_story(std::move(pending_story), {}); promise.set_value(get_story_object({dialog_id, StoryId()}, story_ptr)); @@ -2838,7 +2845,11 @@ void StoryManager::on_upload_story(FileId file_id, telegram_api::object_ptrcreate_handler()->send(file_id, std::move(pending_story), std::move(input_file)); + auto send_story_num = pending_story->send_story_num_; + LOG(INFO) << "Story " << send_story_num << " is ready to be sent"; + ready_to_send_stories_.emplace( + send_story_num, td::make_unique(file_id, std::move(pending_story), std::move(input_file))); + try_send_story(); } } @@ -2863,6 +2874,25 @@ void StoryManager::on_upload_story_error(FileId file_id, Status status) { delete_pending_story(file_id, std::move(pending_story), std::move(status)); } +void StoryManager::try_send_story() { + if (yet_unsent_stories_.empty()) { + LOG(INFO) << "There is no more stories to send"; + return; + } + auto send_story_num = *yet_unsent_stories_.begin(); + auto it = ready_to_send_stories_.find(send_story_num); + if (it == ready_to_send_stories_.end()) { + LOG(INFO) << "Story " << send_story_num << " isn't ready to be sent or is being sent"; + return; + } + auto ready_to_send_story = std::move(it->second); + ready_to_send_stories_.erase(it); + + td_->create_handler()->send(ready_to_send_story->file_id_, + std::move(ready_to_send_story->pending_story_), + std::move(ready_to_send_story->input_file_)); +} + void StoryManager::on_send_story_file_parts_missing(unique_ptr &&pending_story, vector &&bad_parts) { do_send_story(std::move(pending_story), std::move(bad_parts)); } @@ -3039,10 +3069,15 @@ void StoryManager::delete_pending_story(FileId file_id, unique_ptr } else { fail_promises(promises, std::move(status)); } - } + CHECK(pending_story->log_event_id_ == 0); + } else { + LOG(INFO) << "Finish sending of story " << pending_story->send_story_num_; + yet_unsent_stories_.erase(pending_story->send_story_num_); + try_send_story(); - if (pending_story->log_event_id_ != 0) { - binlog_erase(G()->td_db()->get_binlog(), pending_story->log_event_id_); + if (pending_story->log_event_id_ != 0) { + binlog_erase(G()->td_db()->get_binlog(), pending_story->log_event_id_); + } } } @@ -3268,6 +3303,7 @@ void StoryManager::on_binlog_events(vector &&events) { CHECK(!pending_story->story_id_.is_server()); pending_story->send_story_num_ = send_story_count_; pending_story->story_->content_ = dup_story_content(td_, pending_story->story_->content_.get()); + yet_unsent_stories_.insert(pending_story->send_story_num_); do_send_story(std::move(pending_story), {}); break; } diff --git a/td/telegram/StoryManager.h b/td/telegram/StoryManager.h index 348716664..6105d1ffc 100644 --- a/td/telegram/StoryManager.h +++ b/td/telegram/StoryManager.h @@ -99,6 +99,15 @@ class StoryManager final : public Actor { void parse(ParserT &parser); }; + struct ReadyToSendStory { + FileId file_id_; + unique_ptr pending_story_; + telegram_api::object_ptr input_file_; + + ReadyToSendStory(FileId file_id, unique_ptr &&pending_story, + telegram_api::object_ptr &&input_file); + }; + struct PendingStoryViews { FlatHashSet story_ids_; bool has_query_ = false; @@ -368,6 +377,8 @@ class StoryManager final : public Actor { void on_upload_story_error(FileId file_id, Status status); + void try_send_story(); + void do_edit_story(FileId file_id, unique_ptr &&pending_story, telegram_api::object_ptr input_file); @@ -437,6 +448,10 @@ class StoryManager final : public Actor { FlatHashMap, FileIdHash> being_uploaded_files_; + std::set yet_unsent_stories_; + + FlatHashMap> ready_to_send_stories_; + StoryList story_lists_[2]; uint32 send_story_count_ = 0;