Add td_api::getChatBoostLinkInfo.

This commit is contained in:
levlam 2023-09-15 19:07:18 +03:00
parent 069f8607df
commit 469be958f2
10 changed files with 198 additions and 1 deletions

View File

@ -579,6 +579,7 @@ set(TDLIB_SOURCE
td/telegram/DialogAction.h
td/telegram/DialogActionBar.h
td/telegram/DialogAdministrator.h
td/telegram/DialogBoostLinkInfo.h
td/telegram/DialogDate.h
td/telegram/DialogDb.h
td/telegram/DialogEventLog.h

View File

@ -5227,6 +5227,11 @@ messageLinkInfo is_public:Bool chat_id:int53 message_thread_id:int53 message:mes
//@description Contains an HTTPS link to boost a chat @link The link @is_public True, if the link will work for non-members of the chat
chatBoostLink link:string is_public:Bool = ChatBoostLink;
//@description Contains information about a link to boost a a chat
//@is_public True, if the link will work for non-members of the chat
//@chat_id Identifier of the chat to which the link points; 0 if the chat isn't found
chatBoostLinkInfo is_public:Bool chat_id:int53 = ChatBoostLinkInfo;
//@class BlockList @description Describes a type of a block list
@ -7696,6 +7701,9 @@ boostChat chat_id:int53 = Ok;
//@description Returns an HTTPS link to boost the specified channel chat @chat_id Identifier of the chat
getChatBoostLink chat_id:int53 = ChatBoostLink;
//@description Returns information about a link to boost a chat. Can be called for any internal link of the type internalLinkTypeChatBoost @url The link to boost a chat
getChatBoostLinkInfo url:string = ChatBoostLinkInfo;
//@description Returns information about a bot that can be added to attachment or side menu @bot_user_id Bot's user identifier
getAttachmentMenuBot bot_user_id:int53 = AttachmentMenuBot;

View File

@ -0,0 +1,21 @@
//
// Copyright Aliaksei Levin (levlam@telegram.org), Arseny Smirnov (arseny30@gmail.com) 2014-2023
//
// Distributed under the Boost Software License, Version 1.0. (See accompanying
// file LICENSE_1_0.txt or copy at http://www.boost.org/LICENSE_1_0.txt)
//
#pragma once
#include "td/telegram/ChannelId.h"
#include "td/utils/common.h"
namespace td {
struct DialogBoostLinkInfo {
string username;
// or
ChannelId channel_id;
};
} // namespace td

View File

@ -2686,6 +2686,105 @@ Result<CustomEmojiId> LinkManager::get_link_custom_emoji_id(Slice url) {
return Status::Error(400, "Custom emoji URL must have an emoji identifier");
}
Result<DialogBoostLinkInfo> LinkManager::get_dialog_boost_link_info(Slice url) {
if (url.empty()) {
return Status::Error("URL must be non-empty");
}
auto link_info = get_link_info(url);
if (link_info.type_ != LinkType::Tg && link_info.type_ != LinkType::TMe) {
return Status::Error("Invalid chat boost link URL");
}
url = link_info.query_;
Slice username;
Slice channel_id_slice;
if (link_info.type_ == LinkType::Tg) {
// boost?domain=username
// boost?channel=123456789
if (!begins_with(url, "boost")) {
return Status::Error("Wrong chat boost link URL");
}
url = url.substr(5);
if (begins_with(url, "/")) {
url = url.substr(1);
}
if (!begins_with(url, "?")) {
return Status::Error("Wrong chat boost link URL");
}
url = url.substr(1);
auto args = full_split(url, '&');
for (auto arg : args) {
auto key_value = split(arg, '=');
if (key_value.first == "domain") {
username = key_value.second;
} else if (key_value.first == "channel") {
channel_id_slice = key_value.second;
}
}
} else {
// /username?boost
// /c/123456789?boost
CHECK(!url.empty() && url[0] == '/');
url.remove_prefix(1);
size_t username_end_pos = 0;
while (username_end_pos < url.size() && url[username_end_pos] != '/' && url[username_end_pos] != '?' &&
url[username_end_pos] != '#') {
username_end_pos++;
}
username = url.substr(0, username_end_pos);
url = url.substr(username_end_pos);
if (!url.empty() && url[0] == '/') {
url = url.substr(1);
}
if (username == "c") {
username = Slice();
size_t channel_id_end_pos = 0;
while (channel_id_end_pos < url.size() && url[channel_id_end_pos] != '/' && url[channel_id_end_pos] != '?' &&
url[channel_id_end_pos] != '#') {
channel_id_end_pos++;
}
channel_id_slice = url.substr(0, channel_id_end_pos);
url = url.substr(channel_id_end_pos);
}
bool is_boost = false;
auto query_pos = url.find('?');
if (query_pos != Slice::npos) {
auto args = full_split(url.substr(query_pos + 1), '&');
for (auto arg : args) {
auto key_value = split(arg, '=');
if (key_value.first == "boost") {
is_boost = true;
}
}
}
if (!is_boost) {
return Status::Error("Wrong chat boost link URL");
}
}
ChannelId channel_id;
if (username.empty()) {
auto r_channel_id = to_integer_safe<int64>(channel_id_slice);
if (r_channel_id.is_error() || !ChannelId(r_channel_id.ok()).is_valid()) {
return Status::Error("Wrong channel ID");
}
channel_id = ChannelId(r_channel_id.ok());
}
DialogBoostLinkInfo info;
info.username = username.str();
info.channel_id = channel_id;
LOG(INFO) << "Have link to boost chat @" << info.username << '/' << channel_id.get();
return std::move(info);
}
Result<MessageLinkInfo> LinkManager::get_message_link_info(Slice url) {
if (url.empty()) {
return Status::Error("URL must be non-empty");
@ -2885,7 +2984,7 @@ Result<MessageLinkInfo> LinkManager::get_message_link_info(Slice url) {
info.media_timestamp = is_media_timestamp_invalid ? 0 : media_timestamp;
info.is_single = is_single;
info.for_comment = for_comment;
LOG(INFO) << "Have link to " << info.message_id << " in chat @" << info.username << "/" << channel_id.get();
LOG(INFO) << "Have link to " << info.message_id << " in chat @" << info.username << '/' << channel_id.get();
return std::move(info);
}

View File

@ -7,6 +7,7 @@
#pragma once
#include "td/telegram/CustomEmojiId.h"
#include "td/telegram/DialogBoostLinkInfo.h"
#include "td/telegram/FullMessageId.h"
#include "td/telegram/MessageLinkInfo.h"
#include "td/telegram/td_api.h"
@ -107,6 +108,8 @@ class LinkManager final : public Actor {
static Result<CustomEmojiId> get_link_custom_emoji_id(Slice url);
static Result<DialogBoostLinkInfo> get_dialog_boost_link_info(Slice url);
static Result<MessageLinkInfo> get_message_link_info(Slice url);
private:

View File

@ -3016,6 +3016,29 @@ Result<std::pair<string, bool>> StoryManager::get_dialog_boost_link(DialogId dia
return std::make_pair(sb.as_cslice().str(), is_public);
}
void StoryManager::get_dialog_boost_link_info(Slice url, Promise<DialogBoostLinkInfo> &&promise) {
auto r_dialog_boost_link_info = LinkManager::get_dialog_boost_link_info(url);
if (r_dialog_boost_link_info.is_error()) {
return promise.set_error(Status::Error(400, r_dialog_boost_link_info.error().message()));
}
auto info = r_dialog_boost_link_info.move_as_ok();
auto query_promise = PromiseCreator::lambda(
[info, promise = std::move(promise)](Result<DialogId> &&result) mutable { promise.set_value(std::move(info)); });
td_->messages_manager_->resolve_dialog(info.username, info.channel_id, std::move(query_promise));
}
td_api::object_ptr<td_api::chatBoostLinkInfo> StoryManager::get_chat_boost_link_info_object(
const DialogBoostLinkInfo &info) const {
CHECK(info.username.empty() == info.channel_id.is_valid());
bool is_public = !info.username.empty();
DialogId dialog_id =
is_public ? td_->messages_manager_->resolve_dialog_username(info.username) : DialogId(info.channel_id);
return td_api::make_object<td_api::chatBoostLinkInfo>(
is_public, td_->messages_manager_->get_chat_id_object(dialog_id, "chatBoostLinkInfo"));
}
bool StoryManager::have_story(StoryFullId story_full_id) const {
return get_story(story_full_id) != nullptr;
}

View File

@ -7,6 +7,7 @@
#pragma once
#include "td/telegram/ChannelId.h"
#include "td/telegram/DialogBoostLinkInfo.h"
#include "td/telegram/DialogDate.h"
#include "td/telegram/DialogId.h"
#include "td/telegram/files/FileId.h"
@ -278,6 +279,10 @@ class StoryManager final : public Actor {
Result<std::pair<string, bool>> get_dialog_boost_link(DialogId dialog_id);
void get_dialog_boost_link_info(Slice url, Promise<DialogBoostLinkInfo> &&promise);
td_api::object_ptr<td_api::chatBoostLinkInfo> get_chat_boost_link_info_object(const DialogBoostLinkInfo &info) const;
void remove_story_notifications_by_story_ids(DialogId dialog_id, const vector<StoryId> &story_ids);
StoryId on_get_story(DialogId owner_dialog_id, telegram_api::object_ptr<telegram_api::StoryItem> &&story_item_ptr);

View File

@ -32,6 +32,7 @@
#include "td/telegram/CustomEmojiId.h"
#include "td/telegram/DeviceTokenManager.h"
#include "td/telegram/DialogAction.h"
#include "td/telegram/DialogBoostLinkInfo.h"
#include "td/telegram/DialogEventLog.h"
#include "td/telegram/DialogFilter.h"
#include "td/telegram/DialogFilterId.h"
@ -1128,6 +1129,33 @@ class GetMessageLinkInfoRequest final : public RequestActor<MessageLinkInfo> {
}
};
class GetDialogBoostLinkInfoRequest final : public RequestActor<DialogBoostLinkInfo> {
string url_;
DialogBoostLinkInfo dialog_boost_link_info_;
void do_run(Promise<DialogBoostLinkInfo> &&promise) final {
if (get_tries() < 2) {
promise.set_value(std::move(dialog_boost_link_info_));
return;
}
td_->story_manager_->get_dialog_boost_link_info(url_, std::move(promise));
}
void do_set_result(DialogBoostLinkInfo &&result) final {
dialog_boost_link_info_ = std::move(result);
}
void do_send_result() final {
send_result(td_->story_manager_->get_chat_boost_link_info_object(dialog_boost_link_info_));
}
public:
GetDialogBoostLinkInfoRequest(ActorShared<Td> td, uint64 request_id, string url)
: RequestActor(std::move(td), request_id), url_(std::move(url)) {
}
};
class EditMessageTextRequest final : public RequestOnceActor {
FullMessageId full_message_id_;
tl_object_ptr<td_api::ReplyMarkup> reply_markup_;
@ -6614,6 +6642,11 @@ void Td::on_request(uint64 id, const td_api::getChatBoostLink &request) {
}
}
void Td::on_request(uint64 id, td_api::getChatBoostLinkInfo &request) {
CLEAN_INPUT_STRING(request.url_);
CREATE_REQUEST(GetDialogBoostLinkInfoRequest, std::move(request.url_));
}
void Td::on_request(uint64 id, const td_api::getAttachmentMenuBot &request) {
CHECK_IS_USER();
CREATE_REQUEST_PROMISE();

View File

@ -1048,6 +1048,8 @@ class Td final : public Actor {
void on_request(uint64 id, const td_api::getChatBoostLink &request);
void on_request(uint64 id, td_api::getChatBoostLinkInfo &request);
void on_request(uint64 id, const td_api::getAttachmentMenuBot &request);
void on_request(uint64 id, const td_api::toggleBotIsAddedToAttachmentMenu &request);

View File

@ -4306,6 +4306,8 @@ class CliClient final : public Actor {
ChatId chat_id;
get_args(args, chat_id);
send_request(td_api::make_object<td_api::getChatBoostLink>(chat_id));
} else if (op == "gcbli") {
send_request(td_api::make_object<td_api::getChatBoostLinkInfo>(args));
} else if (op == "gamb") {
UserId user_id;
get_args(args, user_id);