Unload forum topic information after all messages are unloaded.

This commit is contained in:
levlam 2022-11-15 17:37:31 +03:00
parent ab165bd34d
commit ff31fa1b52
3 changed files with 45 additions and 5 deletions

View File

@ -217,9 +217,8 @@ void ForumTopicManager::on_forum_topic_created(DialogId dialog_id, unique_ptr<Fo
TRY_STATUS_PROMISE(promise, G()->close_status());
CHECK(forum_topic_info != nullptr);
auto *dialog_topics = add_dialog_topics(dialog_id);
MessageId top_thread_message_id = forum_topic_info->get_top_thread_message_id();
auto topic = add_topic(dialog_topics, top_thread_message_id);
auto topic = add_topic(dialog_id, top_thread_message_id);
if (topic->info_ == nullptr) {
topic->info_ = std::move(forum_topic_info);
send_update_forum_topic_info(dialog_id, topic->info_.get());
@ -364,6 +363,10 @@ ForumTopicManager::Topic *ForumTopicManager::add_topic(DialogTopics *dialog_topi
return topic;
}
ForumTopicManager::Topic *ForumTopicManager::add_topic(DialogId dialog_id, MessageId top_thread_message_id) {
return add_topic(add_dialog_topics(dialog_id), top_thread_message_id);
}
ForumTopicInfo *ForumTopicManager::get_topic_info(DialogId dialog_id, MessageId top_thread_message_id) {
auto *dialog_topics = dialog_topics_.get_pointer(dialog_id);
if (dialog_topics == nullptr) {
@ -401,4 +404,21 @@ void ForumTopicManager::send_update_forum_topic_info(DialogId dialog_id, const F
send_closure(G()->td(), &Td::send_update, get_update_forum_topic_info(dialog_id, topic_info));
}
void ForumTopicManager::on_topic_message_count_changed(DialogId dialog_id, MessageId top_thread_message_id, int diff) {
if (!can_be_forum(dialog_id) || !top_thread_message_id.is_valid()) {
LOG(ERROR) << "Change by " << diff << " number of loaded messages in thread of " << top_thread_message_id << " in "
<< dialog_id;
return;
}
auto dialog_topics = add_dialog_topics(dialog_id);
auto topic = add_topic(dialog_topics, top_thread_message_id);
topic->message_count_ += diff;
CHECK(topic->message_count_ >= 0);
if (topic->message_count_ == 0) {
// TODO kepp topics in the topic list
dialog_topics->topics_.erase(top_thread_message_id);
}
}
} // namespace td

View File

@ -54,11 +54,14 @@ class ForumTopicManager final : public Actor {
void on_get_forum_topics(DialogId dialog_id, vector<tl_object_ptr<telegram_api::ForumTopic>> &&forum_topics,
const char *source);
void on_topic_message_count_changed(DialogId dialog_id, MessageId top_thread_message_id, int diff);
private:
static constexpr size_t MAX_FORUM_TOPIC_TITLE_LENGTH = 128; // server side limit for forum topic title
struct Topic {
unique_ptr<ForumTopicInfo> info_;
int32 message_count_ = 0;
};
struct DialogTopics {
@ -75,6 +78,8 @@ class ForumTopicManager final : public Actor {
static Topic *add_topic(DialogTopics *dialog_topics, MessageId top_thread_message_id);
Topic *add_topic(DialogId dialog_id, MessageId top_thread_message_id);
ForumTopicInfo *get_topic_info(DialogId dialog_id, MessageId top_thread_message_id);
const ForumTopicInfo *get_topic_info(DialogId dialog_id, MessageId top_thread_message_id) const;

View File

@ -16840,6 +16840,9 @@ void MessagesManager::on_message_deleted(Dialog *d, Message *m, bool is_permanen
if (m->message_id.is_yet_unsent() || dialog_type == DialogType::SecretChat) {
delete_random_id_to_message_id_correspondence(d, m->random_id, m->message_id);
}
if (m->is_topic_message) {
td_->forum_topic_manager_->on_topic_message_count_changed(d->dialog_id, m->top_thread_message_id, -1);
}
added_message_count_--;
}
@ -16884,6 +16887,7 @@ unique_ptr<MessagesManager::Message> MessagesManager::do_delete_scheduled_messag
remove_message_file_sources(d->dialog_id, m);
auto result = treap_delete_message(v);
CHECK(m == result.get());
if (message_id.is_scheduled_server()) {
size_t erased_count = d->scheduled_message_date.erase(message_id.get_scheduled_server_message_id());
@ -16892,10 +16896,13 @@ unique_ptr<MessagesManager::Message> MessagesManager::do_delete_scheduled_messag
cancel_send_deleted_message(d->dialog_id, result.get(), is_permanently_deleted);
unregister_message_content(td_, result->content.get(), {d->dialog_id, message_id}, "do_delete_scheduled_message");
unregister_message_content(td_, m->content.get(), {d->dialog_id, message_id}, "do_delete_scheduled_message");
unregister_message_reply(d->dialog_id, m);
if (message_id.is_yet_unsent()) {
delete_random_id_to_message_id_correspondence(d, result->random_id, result->message_id);
delete_random_id_to_message_id_correspondence(d, m->random_id, m->message_id);
}
if (m->is_topic_message) {
td_->forum_topic_manager_->on_topic_message_count_changed(d->dialog_id, m->top_thread_message_id, -1);
}
return result;
@ -25488,7 +25495,7 @@ tl_object_ptr<td_api::message> MessagesManager::get_message_object(DialogId dial
auto reply_to_message_id = for_event_log ? static_cast<int64>(0) : m->reply_to_message_id.get();
auto reply_in_dialog_id =
reply_to_message_id == 0 ? DialogId() : (m->reply_in_dialog_id.is_valid() ? m->reply_in_dialog_id : dialog_id);
auto top_thread_message_id = for_event_log || is_scheduled ? static_cast<int64>(0) : m->top_thread_message_id.get();
auto top_thread_message_id = for_event_log ? static_cast<int64>(0) : m->top_thread_message_id.get();
auto contains_unread_mention = for_event_log ? false : m->contains_unread_mention;
auto date = is_scheduled ? 0 : m->date;
auto edit_date = m->hide_edit_date ? 0 : m->edit_date;
@ -35861,6 +35868,10 @@ MessagesManager::Message *MessagesManager::add_message_to_dialog(Dialog *d, uniq
}
}
if (m->is_topic_message) {
td_->forum_topic_manager_->on_topic_message_count_changed(dialog_id, m->top_thread_message_id, +1);
}
Message *result_message = treap_insert_message(&d->messages, std::move(message));
CHECK(result_message != nullptr);
CHECK(result_message == m);
@ -36064,6 +36075,10 @@ MessagesManager::Message *MessagesManager::add_scheduled_message_to_dialog(Dialo
date = m->date;
}
if (m->is_topic_message) {
td_->forum_topic_manager_->on_topic_message_count_changed(dialog_id, m->top_thread_message_id, +1);
}
Message *result_message = treap_insert_message(&d->scheduled_messages, std::move(message));
CHECK(result_message != nullptr);
CHECK(d->scheduled_messages != nullptr);