Avoid copying when adding users/chats to binlog.

This commit is contained in:
levlam 2022-07-23 11:00:46 +03:00
parent 4cf1e02479
commit bc83832e03

View File

@ -8767,23 +8767,24 @@ void ContactsManager::on_get_user(tl_object_ptr<telegram_api::User> &&user_ptr,
class ContactsManager::UserLogEvent { class ContactsManager::UserLogEvent {
public: public:
UserId user_id; UserId user_id;
User u; const User *u_in = nullptr;
unique_ptr<User> u_out;
UserLogEvent() = default; UserLogEvent() = default;
UserLogEvent(UserId user_id, const User &u) : user_id(user_id), u(u) { UserLogEvent(UserId user_id, const User *u) : user_id(user_id), u_in(u) {
} }
template <class StorerT> template <class StorerT>
void store(StorerT &storer) const { void store(StorerT &storer) const {
td::store(user_id, storer); td::store(user_id, storer);
td::store(u, storer); td::store(*u_in, storer);
} }
template <class ParserT> template <class ParserT>
void parse(ParserT &parser) { void parse(ParserT &parser) {
td::parse(user_id, parser); td::parse(user_id, parser);
td::parse(u, parser); td::parse(u_out, parser);
} }
}; };
@ -8794,7 +8795,7 @@ void ContactsManager::save_user(User *u, UserId user_id, bool from_binlog) {
CHECK(u != nullptr); CHECK(u != nullptr);
if (!u->is_saved || !u->is_status_saved) { // TODO more effective handling of !u->is_status_saved if (!u->is_saved || !u->is_status_saved) { // TODO more effective handling of !u->is_status_saved
if (!from_binlog) { if (!from_binlog) {
auto log_event = UserLogEvent(user_id, *u); auto log_event = UserLogEvent(user_id, u);
auto storer = get_log_event_storer(log_event); auto storer = get_log_event_storer(log_event);
if (u->log_event_id == 0) { if (u->log_event_id == 0) {
u->log_event_id = binlog_add(G()->td_db()->get_binlog(), LogEvent::HandlerType::Users, storer); u->log_event_id = binlog_add(G()->td_db()->get_binlog(), LogEvent::HandlerType::Users, storer);
@ -8824,8 +8825,8 @@ void ContactsManager::on_binlog_user_event(BinlogEvent &&event) {
} }
LOG(INFO) << "Add " << user_id << " from binlog"; LOG(INFO) << "Add " << user_id << " from binlog";
User *u = add_user(user_id, "on_binlog_user_event"); User *u = users_.emplace(user_id, std::move(log_event.u_out)).first->second.get();
*u = std::move(log_event.u); // users come from binlog before all other events, so just add them CHECK(u != nullptr);
u->log_event_id = event.id_; u->log_event_id = event.id_;
@ -9073,23 +9074,24 @@ ContactsManager::User *ContactsManager::get_user_force_impl(UserId user_id) {
class ContactsManager::ChatLogEvent { class ContactsManager::ChatLogEvent {
public: public:
ChatId chat_id; ChatId chat_id;
Chat c; const Chat *c_in = nullptr;
unique_ptr<Chat> c_out;
ChatLogEvent() = default; ChatLogEvent() = default;
ChatLogEvent(ChatId chat_id, const Chat &c) : chat_id(chat_id), c(c) { ChatLogEvent(ChatId chat_id, const Chat *c) : chat_id(chat_id), c_in(c) {
} }
template <class StorerT> template <class StorerT>
void store(StorerT &storer) const { void store(StorerT &storer) const {
td::store(chat_id, storer); td::store(chat_id, storer);
td::store(c, storer); td::store(*c_in, storer);
} }
template <class ParserT> template <class ParserT>
void parse(ParserT &parser) { void parse(ParserT &parser) {
td::parse(chat_id, parser); td::parse(chat_id, parser);
td::parse(c, parser); td::parse(c_out, parser);
} }
}; };
@ -9100,7 +9102,7 @@ void ContactsManager::save_chat(Chat *c, ChatId chat_id, bool from_binlog) {
CHECK(c != nullptr); CHECK(c != nullptr);
if (!c->is_saved) { if (!c->is_saved) {
if (!from_binlog) { if (!from_binlog) {
auto log_event = ChatLogEvent(chat_id, *c); auto log_event = ChatLogEvent(chat_id, c);
auto storer = get_log_event_storer(log_event); auto storer = get_log_event_storer(log_event);
if (c->log_event_id == 0) { if (c->log_event_id == 0) {
c->log_event_id = binlog_add(G()->td_db()->get_binlog(), LogEvent::HandlerType::Chats, storer); c->log_event_id = binlog_add(G()->td_db()->get_binlog(), LogEvent::HandlerType::Chats, storer);
@ -9131,8 +9133,8 @@ void ContactsManager::on_binlog_chat_event(BinlogEvent &&event) {
} }
LOG(INFO) << "Add " << chat_id << " from binlog"; LOG(INFO) << "Add " << chat_id << " from binlog";
Chat *c = add_chat(chat_id); Chat *c = chats_.emplace(chat_id, std::move(log_event.c_out)).first->second.get();
*c = std::move(log_event.c); // chats come from binlog before all other events, so just add them CHECK(c != nullptr);
c->log_event_id = event.id_; c->log_event_id = event.id_;
@ -9310,23 +9312,24 @@ ContactsManager::Chat *ContactsManager::get_chat_force(ChatId chat_id) {
class ContactsManager::ChannelLogEvent { class ContactsManager::ChannelLogEvent {
public: public:
ChannelId channel_id; ChannelId channel_id;
Channel c; const Channel *c_in = nullptr;
unique_ptr<Channel> c_out;
ChannelLogEvent() = default; ChannelLogEvent() = default;
ChannelLogEvent(ChannelId channel_id, const Channel &c) : channel_id(channel_id), c(c) { ChannelLogEvent(ChannelId channel_id, const Channel *c) : channel_id(channel_id), c_in(c) {
} }
template <class StorerT> template <class StorerT>
void store(StorerT &storer) const { void store(StorerT &storer) const {
td::store(channel_id, storer); td::store(channel_id, storer);
td::store(c, storer); td::store(*c_in, storer);
} }
template <class ParserT> template <class ParserT>
void parse(ParserT &parser) { void parse(ParserT &parser) {
td::parse(channel_id, parser); td::parse(channel_id, parser);
td::parse(c, parser); td::parse(c_out, parser);
} }
}; };
@ -9337,7 +9340,7 @@ void ContactsManager::save_channel(Channel *c, ChannelId channel_id, bool from_b
CHECK(c != nullptr); CHECK(c != nullptr);
if (!c->is_saved) { if (!c->is_saved) {
if (!from_binlog) { if (!from_binlog) {
auto log_event = ChannelLogEvent(channel_id, *c); auto log_event = ChannelLogEvent(channel_id, c);
auto storer = get_log_event_storer(log_event); auto storer = get_log_event_storer(log_event);
if (c->log_event_id == 0) { if (c->log_event_id == 0) {
c->log_event_id = binlog_add(G()->td_db()->get_binlog(), LogEvent::HandlerType::Channels, storer); c->log_event_id = binlog_add(G()->td_db()->get_binlog(), LogEvent::HandlerType::Channels, storer);
@ -9368,8 +9371,8 @@ void ContactsManager::on_binlog_channel_event(BinlogEvent &&event) {
} }
LOG(INFO) << "Add " << channel_id << " from binlog"; LOG(INFO) << "Add " << channel_id << " from binlog";
Channel *c = add_channel(channel_id, "on_binlog_channel_event"); Channel *c = channels_.emplace(channel_id, std::move(log_event.c_out)).first->second.get();
*c = std::move(log_event.c); // channels come from binlog before all other events, so just add them CHECK(c != nullptr);
c->log_event_id = event.id_; c->log_event_id = event.id_;
@ -9563,23 +9566,24 @@ ContactsManager::Channel *ContactsManager::get_channel_force(ChannelId channel_i
class ContactsManager::SecretChatLogEvent { class ContactsManager::SecretChatLogEvent {
public: public:
SecretChatId secret_chat_id; SecretChatId secret_chat_id;
SecretChat c; const SecretChat *c_in = nullptr;
unique_ptr<SecretChat> c_out;
SecretChatLogEvent() = default; SecretChatLogEvent() = default;
SecretChatLogEvent(SecretChatId secret_chat_id, const SecretChat &c) : secret_chat_id(secret_chat_id), c(c) { SecretChatLogEvent(SecretChatId secret_chat_id, const SecretChat *c) : secret_chat_id(secret_chat_id), c_in(c) {
} }
template <class StorerT> template <class StorerT>
void store(StorerT &storer) const { void store(StorerT &storer) const {
td::store(secret_chat_id, storer); td::store(secret_chat_id, storer);
td::store(c, storer); td::store(*c_in, storer);
} }
template <class ParserT> template <class ParserT>
void parse(ParserT &parser) { void parse(ParserT &parser) {
td::parse(secret_chat_id, parser); td::parse(secret_chat_id, parser);
td::parse(c, parser); td::parse(c_out, parser);
} }
}; };
@ -9590,7 +9594,7 @@ void ContactsManager::save_secret_chat(SecretChat *c, SecretChatId secret_chat_i
CHECK(c != nullptr); CHECK(c != nullptr);
if (!c->is_saved) { if (!c->is_saved) {
if (!from_binlog) { if (!from_binlog) {
auto log_event = SecretChatLogEvent(secret_chat_id, *c); auto log_event = SecretChatLogEvent(secret_chat_id, c);
auto storer = get_log_event_storer(log_event); auto storer = get_log_event_storer(log_event);
if (c->log_event_id == 0) { if (c->log_event_id == 0) {
c->log_event_id = binlog_add(G()->td_db()->get_binlog(), LogEvent::HandlerType::SecretChatInfos, storer); c->log_event_id = binlog_add(G()->td_db()->get_binlog(), LogEvent::HandlerType::SecretChatInfos, storer);
@ -9621,8 +9625,8 @@ void ContactsManager::on_binlog_secret_chat_event(BinlogEvent &&event) {
} }
LOG(INFO) << "Add " << secret_chat_id << " from binlog"; LOG(INFO) << "Add " << secret_chat_id << " from binlog";
SecretChat *c = add_secret_chat(secret_chat_id); SecretChat *c = secret_chats_.emplace(secret_chat_id, std::move(log_event.c_out)).first->second.get();
*c = std::move(log_event.c); // secret chats come from binlog before all other events, so just add them CHECK(c != nullptr);
c->log_event_id = event.id_; c->log_event_id = event.id_;