Add getChatMessageCount.saved_messages_topic.

This commit is contained in:
levlam 2024-01-16 00:30:37 +03:00
parent 7e3107b1d3
commit 8f019eeb73
5 changed files with 65 additions and 33 deletions

View File

@ -7258,8 +7258,9 @@ getChatMessageCalendar chat_id:int53 filter:SearchMessagesFilter from_message_id
//@description Returns approximate number of messages of the specified type in the chat //@description Returns approximate number of messages of the specified type in the chat
//@chat_id Identifier of the chat in which to count messages //@chat_id Identifier of the chat in which to count messages
//@filter Filter for message content; searchMessagesFilterEmpty is unsupported in this function //@filter Filter for message content; searchMessagesFilterEmpty is unsupported in this function
//@saved_messages_topic If not null, only messages in the specified Saved Messages topic will be counted; pass null to count all messages or for chats other than Saved Messages
//@return_local Pass true to get the number of messages without sending network requests, or -1 if the number of messages is unknown locally //@return_local Pass true to get the number of messages without sending network requests, or -1 if the number of messages is unknown locally
getChatMessageCount chat_id:int53 filter:SearchMessagesFilter return_local:Bool = Count; getChatMessageCount chat_id:int53 filter:SearchMessagesFilter saved_messages_topic:SavedMessagesTopic return_local:Bool = Count;
//@description Returns approximate 1-based position of a message among messages, which can be found by the specified filter in the chat. Cannot be used in secret chats //@description Returns approximate 1-based position of a message among messages, which can be found by the specified filter in the chat. Cannot be used in secret chats
//@chat_id Identifier of the chat in which to find message position //@chat_id Identifier of the chat in which to find message position

View File

@ -1910,19 +1910,21 @@ class GetSearchResultPositionsQuery final : public Td::ResultHandler {
class GetSearchCountersQuery final : public Td::ResultHandler { class GetSearchCountersQuery final : public Td::ResultHandler {
Promise<int32> promise_; Promise<int32> promise_;
DialogId dialog_id_; DialogId dialog_id_;
SavedMessagesTopicId saved_messages_topic_id_;
MessageSearchFilter filter_; MessageSearchFilter filter_;
public: public:
explicit GetSearchCountersQuery(Promise<int32> &&promise) : promise_(std::move(promise)) { explicit GetSearchCountersQuery(Promise<int32> &&promise) : promise_(std::move(promise)) {
} }
void send(DialogId dialog_id, MessageSearchFilter filter) { void send(DialogId dialog_id, SavedMessagesTopicId saved_messages_topic_id, MessageSearchFilter filter) {
auto input_peer = td_->dialog_manager_->get_input_peer(dialog_id, AccessRights::Read); auto input_peer = td_->dialog_manager_->get_input_peer(dialog_id, AccessRights::Read);
if (input_peer == nullptr) { if (input_peer == nullptr) {
return promise_.set_error(Status::Error(400, "Can't access the chat")); return promise_.set_error(Status::Error(400, "Can't access the chat"));
} }
dialog_id_ = dialog_id; dialog_id_ = dialog_id;
saved_messages_topic_id_ = saved_messages_topic_id;
filter_ = filter; filter_ = filter;
CHECK(filter != MessageSearchFilter::Empty); CHECK(filter != MessageSearchFilter::Empty);
@ -1933,8 +1935,14 @@ class GetSearchCountersQuery final : public Td::ResultHandler {
filters.push_back(get_input_messages_filter(filter)); filters.push_back(get_input_messages_filter(filter));
int32 flags = 0; int32 flags = 0;
send_query(G()->net_query_creator().create( telegram_api::object_ptr<telegram_api::InputPeer> saved_input_peer;
telegram_api::messages_getSearchCounters(flags, std::move(input_peer), nullptr, 0, std::move(filters)))); if (saved_messages_topic_id.is_valid()) {
flags |= telegram_api::messages_getSearchCounters::SAVED_PEER_ID_MASK;
saved_input_peer = saved_messages_topic_id.get_input_peer(td_);
CHECK(saved_input_peer != nullptr);
}
send_query(G()->net_query_creator().create(telegram_api::messages_getSearchCounters(
flags, std::move(input_peer), std::move(saved_input_peer), 0, std::move(filters))));
} }
void on_result(BufferSlice packet) final { void on_result(BufferSlice packet) final {
@ -1950,7 +1958,8 @@ class GetSearchCountersQuery final : public Td::ResultHandler {
return on_error(Status::Error(500, "Receive wrong response")); return on_error(Status::Error(500, "Receive wrong response"));
} }
td_->messages_manager_->on_get_dialog_message_count(dialog_id_, filter_, result[0]->count_, std::move(promise_)); td_->messages_manager_->on_get_dialog_message_count(dialog_id_, saved_messages_topic_id_, filter_,
result[0]->count_, std::move(promise_));
} }
void on_error(Status status) final { void on_error(Status status) final {
@ -8954,14 +8963,20 @@ void MessagesManager::on_failed_dialog_messages_search(DialogId dialog_id, int64
found_dialog_messages_.erase(it); found_dialog_messages_.erase(it);
} }
void MessagesManager::on_get_dialog_message_count(DialogId dialog_id, MessageSearchFilter filter, int32 total_count, void MessagesManager::on_get_dialog_message_count(DialogId dialog_id, SavedMessagesTopicId saved_messages_topic_id,
MessageSearchFilter filter, int32 total_count,
Promise<int32> &&promise) { Promise<int32> &&promise) {
LOG(INFO) << "Receive " << total_count << " message count in " << dialog_id << " with filter " << filter; LOG(INFO) << "Receive " << total_count << " message count in " << dialog_id << " with filter " << filter;
if (total_count < 0) { if (total_count < 0) {
LOG(ERROR) << "Receive total message count = " << total_count << " in " << dialog_id << " with filter " << filter; LOG(ERROR) << "Receive total message count = " << total_count << " in " << dialog_id << " with "
<< saved_messages_topic_id << " and filter " << filter;
total_count = 0; total_count = 0;
} }
if (saved_messages_topic_id.is_valid()) {
return promise.set_value(std::move(total_count));
}
Dialog *d = get_dialog(dialog_id); Dialog *d = get_dialog(dialog_id);
CHECK(d != nullptr); CHECK(d != nullptr);
CHECK(filter != MessageSearchFilter::Empty); CHECK(filter != MessageSearchFilter::Empty);
@ -21196,7 +21211,8 @@ void MessagesManager::on_get_dialog_sparse_message_positions(
promise.set_value(td_api::make_object<td_api::messagePositions>(positions->count_, std::move(message_positions))); promise.set_value(td_api::make_object<td_api::messagePositions>(positions->count_, std::move(message_positions)));
} }
void MessagesManager::get_dialog_message_count(DialogId dialog_id, MessageSearchFilter filter, bool return_local, void MessagesManager::get_dialog_message_count(DialogId dialog_id, SavedMessagesTopicId saved_messages_topic_id,
MessageSearchFilter filter, bool return_local,
Promise<int32> &&promise) { Promise<int32> &&promise) {
LOG(INFO) << "Get " << (return_local ? "local " : "") << "number of messages in " << dialog_id << " filtered by " LOG(INFO) << "Get " << (return_local ? "local " : "") << "number of messages in " << dialog_id << " filtered by "
<< filter; << filter;
@ -21210,31 +21226,44 @@ void MessagesManager::get_dialog_message_count(DialogId dialog_id, MessageSearch
return promise.set_error(Status::Error(400, "Can't use searchMessagesFilterEmpty")); return promise.set_error(Status::Error(400, "Can't use searchMessagesFilterEmpty"));
} }
auto dialog_type = dialog_id.get_type(); TRY_STATUS_PROMISE(promise, saved_messages_topic_id.is_valid_in(td_, dialog_id));
int32 message_count = d->message_count_by_index[message_search_filter_index(filter)]; if (saved_messages_topic_id.is_valid()) {
if (message_count == -1 && filter == MessageSearchFilter::UnreadMention) { if (filter == MessageSearchFilter::UnreadMention || filter == MessageSearchFilter::UnreadReaction ||
message_count = d->unread_mention_count; filter == MessageSearchFilter::FailedToSend) {
} return promise.set_value(static_cast<int32>(0));
if (message_count == -1 && filter == MessageSearchFilter::UnreadReaction) { }
message_count = d->unread_reaction_count; if (return_local) {
} return promise.set_value(static_cast<int32>(-1));
if (message_count != -1 || return_local || dialog_type == DialogType::SecretChat || }
filter == MessageSearchFilter::FailedToSend) { } else {
return promise.set_value(std::move(message_count)); auto dialog_type = dialog_id.get_type();
int32 message_count = d->message_count_by_index[message_search_filter_index(filter)];
if (message_count == -1 && filter == MessageSearchFilter::UnreadMention) {
message_count = d->unread_mention_count;
}
if (message_count == -1 && filter == MessageSearchFilter::UnreadReaction) {
message_count = d->unread_reaction_count;
}
if (message_count != -1 || return_local || dialog_type == DialogType::SecretChat ||
filter == MessageSearchFilter::FailedToSend) {
return promise.set_value(std::move(message_count));
}
} }
get_dialog_message_count_from_server(dialog_id, filter, std::move(promise)); get_dialog_message_count_from_server(dialog_id, saved_messages_topic_id, filter, std::move(promise));
} }
void MessagesManager::get_dialog_message_count_from_server(DialogId dialog_id, MessageSearchFilter filter, void MessagesManager::get_dialog_message_count_from_server(DialogId dialog_id,
Promise<int32> &&promise) { SavedMessagesTopicId saved_messages_topic_id,
LOG(INFO) << "Get number of messages in " << dialog_id << " filtered by " << filter << " from the server"; MessageSearchFilter filter, Promise<int32> &&promise) {
LOG(INFO) << "Get number of messages in " << dialog_id << " with " << saved_messages_topic_id << " filtered by "
<< filter << " from the server";
switch (dialog_id.get_type()) { switch (dialog_id.get_type()) {
case DialogType::User: case DialogType::User:
case DialogType::Chat: case DialogType::Chat:
case DialogType::Channel: case DialogType::Channel:
td_->create_handler<GetSearchCountersQuery>(std::move(promise))->send(dialog_id, filter); td_->create_handler<GetSearchCountersQuery>(std::move(promise))->send(dialog_id, saved_messages_topic_id, filter);
break; break;
case DialogType::None: case DialogType::None:
case DialogType::SecretChat: case DialogType::SecretChat:

View File

@ -180,8 +180,8 @@ class MessagesManager final : public Actor {
Promise<Unit> &&promise); Promise<Unit> &&promise);
void on_failed_dialog_messages_search(DialogId dialog_id, int64 random_id); void on_failed_dialog_messages_search(DialogId dialog_id, int64 random_id);
void on_get_dialog_message_count(DialogId dialog_id, MessageSearchFilter filter, int32 total_count, void on_get_dialog_message_count(DialogId dialog_id, SavedMessagesTopicId saved_messages_topic_id,
Promise<int32> &&promise); MessageSearchFilter filter, int32 total_count, Promise<int32> &&promise);
void on_get_messages_search_result(const string &query, int32 offset_date, DialogId offset_dialog_id, void on_get_messages_search_result(const string &query, int32 offset_date, DialogId offset_dialog_id,
MessageId offset_message_id, int32 limit, MessageSearchFilter filter, MessageId offset_message_id, int32 limit, MessageSearchFilter filter,
@ -743,8 +743,8 @@ class MessagesManager final : public Actor {
telegram_api::object_ptr<telegram_api::messages_searchResultsPositions> positions, telegram_api::object_ptr<telegram_api::messages_searchResultsPositions> positions,
Promise<td_api::object_ptr<td_api::messagePositions>> &&promise); Promise<td_api::object_ptr<td_api::messagePositions>> &&promise);
void get_dialog_message_count(DialogId dialog_id, MessageSearchFilter filter, bool return_local, void get_dialog_message_count(DialogId dialog_id, SavedMessagesTopicId saved_messages_topic_id,
Promise<int32> &&promise); MessageSearchFilter filter, bool return_local, Promise<int32> &&promise);
void get_dialog_message_position(MessageFullId message_full_id, MessageSearchFilter filter, void get_dialog_message_position(MessageFullId message_full_id, MessageSearchFilter filter,
MessageId top_thread_message_id, SavedMessagesTopicId saved_messages_topic_id, MessageId top_thread_message_id, SavedMessagesTopicId saved_messages_topic_id,
@ -1624,7 +1624,8 @@ class MessagesManager final : public Actor {
void delete_update_message_id(DialogId dialog_id, MessageId message_id); void delete_update_message_id(DialogId dialog_id, MessageId message_id);
void get_dialog_message_count_from_server(DialogId dialog_id, MessageSearchFilter filter, Promise<int32> &&promise); void get_dialog_message_count_from_server(DialogId dialog_id, SavedMessagesTopicId saved_messages_topic_id,
MessageSearchFilter filter, Promise<int32> &&promise);
MessageFullId on_get_message(MessageInfo &&message_info, const bool from_update, const bool is_channel_message, MessageFullId on_get_message(MessageInfo &&message_info, const bool from_update, const bool is_channel_message,
const char *source); const char *source);

View File

@ -5293,8 +5293,9 @@ void Td::on_request(uint64 id, const td_api::getChatMessageCount &request) {
promise.set_value(make_tl_object<td_api::count>(result.move_as_ok())); promise.set_value(make_tl_object<td_api::count>(result.move_as_ok()));
} }
}); });
messages_manager_->get_dialog_message_count(DialogId(request.chat_id_), get_message_search_filter(request.filter_), messages_manager_->get_dialog_message_count(
request.return_local_, std::move(query_promise)); DialogId(request.chat_id_), SavedMessagesTopicId(this, request.saved_messages_topic_),
get_message_search_filter(request.filter_), request.return_local_, std::move(query_promise));
} }
void Td::on_request(uint64 id, const td_api::getChatMessagePosition &request) { void Td::on_request(uint64 id, const td_api::getChatMessagePosition &request) {

View File

@ -2954,8 +2954,8 @@ class CliClient final : public Actor {
string filter; string filter;
bool return_local; bool return_local;
get_args(args, chat_id, filter, return_local); get_args(args, chat_id, filter, return_local);
send_request( send_request(td_api::make_object<td_api::getChatMessageCount>(chat_id, as_search_messages_filter(filter),
td_api::make_object<td_api::getChatMessageCount>(chat_id, as_search_messages_filter(filter), return_local)); get_saved_messages_topic(), return_local));
} else if (op == "gcmp") { } else if (op == "gcmp") {
ChatId chat_id; ChatId chat_id;
MessageId message_id; MessageId message_id;