Add td_api::internalLinkTypeChatFilterInvite.
This commit is contained in:
parent
49b9ea2ec1
commit
02a2e23cac
@ -4641,6 +4641,9 @@ internalLinkTypeBotStartInGroup bot_username:string start_parameter:string admin
|
|||||||
//@description The link is a link to the change phone number section of the app
|
//@description The link is a link to the change phone number section of the app
|
||||||
internalLinkTypeChangePhoneNumber = InternalLinkType;
|
internalLinkTypeChangePhoneNumber = InternalLinkType;
|
||||||
|
|
||||||
|
//@description The link is an invite link to a chat filter. Call checkChatFilterInviteLink with the given invite link to process the link @invite_link Internal representation of the invite link
|
||||||
|
internalLinkTypeChatFilterInvite invite_link:string = InternalLinkType;
|
||||||
|
|
||||||
//@description The link is a chat invite link. Call checkChatInviteLink with the given invite link to process the link @invite_link Internal representation of the invite link
|
//@description The link is a chat invite link. Call checkChatInviteLink with the given invite link to process the link @invite_link Internal representation of the invite link
|
||||||
internalLinkTypeChatInvite invite_link:string = InternalLinkType;
|
internalLinkTypeChatInvite invite_link:string = InternalLinkType;
|
||||||
|
|
||||||
|
@ -71,12 +71,12 @@ static string get_url_query_hash(bool is_tg, const HttpUrlQuery &url_query) {
|
|||||||
const auto &path = url_query.path_;
|
const auto &path = url_query.path_;
|
||||||
if (is_tg) {
|
if (is_tg) {
|
||||||
if (path.size() == 1 && path[0] == "join" && !url_query.get_arg("invite").empty()) {
|
if (path.size() == 1 && path[0] == "join" && !url_query.get_arg("invite").empty()) {
|
||||||
// join?invite=abcdef
|
// join?invite=<hash>
|
||||||
return url_query.get_arg("invite").str();
|
return url_query.get_arg("invite").str();
|
||||||
}
|
}
|
||||||
} else {
|
} else {
|
||||||
if (path.size() >= 2 && path[0] == "joinchat" && !path[1].empty()) {
|
if (path.size() >= 2 && path[0] == "joinchat" && !path[1].empty()) {
|
||||||
// /joinchat/<link>
|
// /joinchat/<hash>
|
||||||
return path[1];
|
return path[1];
|
||||||
}
|
}
|
||||||
if (!path.empty() && path[0].size() >= 2 && (path[0][0] == ' ' || path[0][0] == '+')) {
|
if (!path.empty() && path[0].size() >= 2 && (path[0][0] == ' ' || path[0][0] == '+')) {
|
||||||
@ -87,6 +87,22 @@ static string get_url_query_hash(bool is_tg, const HttpUrlQuery &url_query) {
|
|||||||
return string();
|
return string();
|
||||||
}
|
}
|
||||||
|
|
||||||
|
static string get_url_query_slug(bool is_tg, const HttpUrlQuery &url_query) {
|
||||||
|
const auto &path = url_query.path_;
|
||||||
|
if (is_tg) {
|
||||||
|
if (path.size() == 1 && path[0] == "list" && !url_query.get_arg("slug").empty()) {
|
||||||
|
// list?slug=<hash>
|
||||||
|
return url_query.get_arg("slug").str();
|
||||||
|
}
|
||||||
|
} else {
|
||||||
|
if (path.size() >= 2 && path[0] == "list" && !path[1].empty()) {
|
||||||
|
// /list/<hash>
|
||||||
|
return path[1];
|
||||||
|
}
|
||||||
|
}
|
||||||
|
return string();
|
||||||
|
}
|
||||||
|
|
||||||
static AdministratorRights get_administrator_rights(Slice rights, bool for_channel) {
|
static AdministratorRights get_administrator_rights(Slice rights, bool for_channel) {
|
||||||
bool can_manage_dialog = false;
|
bool can_manage_dialog = false;
|
||||||
bool can_change_info = false;
|
bool can_change_info = false;
|
||||||
@ -350,6 +366,18 @@ class LinkManager::InternalLinkDefaultMessageAutoDeleteTimerSettings final : pub
|
|||||||
}
|
}
|
||||||
};
|
};
|
||||||
|
|
||||||
|
class LinkManager::InternalLinkDialogFilterInvite final : public InternalLink {
|
||||||
|
string url_;
|
||||||
|
|
||||||
|
td_api::object_ptr<td_api::InternalLinkType> get_internal_link_type_object() const final {
|
||||||
|
return td_api::make_object<td_api::internalLinkTypeChatFilterInvite>(url_);
|
||||||
|
}
|
||||||
|
|
||||||
|
public:
|
||||||
|
explicit InternalLinkDialogFilterInvite(string url) : url_(std::move(url)) {
|
||||||
|
}
|
||||||
|
};
|
||||||
|
|
||||||
class LinkManager::InternalLinkDialogInvite final : public InternalLink {
|
class LinkManager::InternalLinkDialogInvite final : public InternalLink {
|
||||||
string url_;
|
string url_;
|
||||||
|
|
||||||
@ -989,8 +1017,9 @@ LinkManager::LinkInfo LinkManager::get_link_info(Slice link) {
|
|||||||
Slice subdomain(&host[0], host.size() - 5);
|
Slice subdomain(&host[0], host.size() - 5);
|
||||||
if (is_valid_username(subdomain) && subdomain != "addemoji" && subdomain != "addstickers" &&
|
if (is_valid_username(subdomain) && subdomain != "addemoji" && subdomain != "addstickers" &&
|
||||||
subdomain != "addtheme" && subdomain != "auth" && subdomain != "confirmphone" && subdomain != "invoice" &&
|
subdomain != "addtheme" && subdomain != "auth" && subdomain != "confirmphone" && subdomain != "invoice" &&
|
||||||
subdomain != "joinchat" && subdomain != "login" && subdomain != "proxy" && subdomain != "setlanguage" &&
|
subdomain != "joinchat" && subdomain != "list" && subdomain != "login" && subdomain != "proxy" &&
|
||||||
subdomain != "share" && subdomain != "socks" && subdomain != "web" && subdomain != "k" && subdomain != "z") {
|
subdomain != "setlanguage" && subdomain != "share" && subdomain != "socks" && subdomain != "web" &&
|
||||||
|
subdomain != "k" && subdomain != "z") {
|
||||||
result.type_ = LinkType::TMe;
|
result.type_ = LinkType::TMe;
|
||||||
result.query_ = PSTRING() << '/' << subdomain << http_url.query_;
|
result.query_ = PSTRING() << '/' << subdomain << http_url.query_;
|
||||||
return result;
|
return result;
|
||||||
@ -1260,12 +1289,20 @@ unique_ptr<LinkManager::InternalLink> LinkManager::parse_tg_link_query(Slice que
|
|||||||
}
|
}
|
||||||
// settings
|
// settings
|
||||||
return td::make_unique<InternalLinkSettings>();
|
return td::make_unique<InternalLinkSettings>();
|
||||||
|
} else if (path.size() == 1 && path[0] == "list") {
|
||||||
|
// list?slug=<hash>
|
||||||
|
if (has_arg("slug")) {
|
||||||
|
auto slug = get_url_query_slug(true, url_query);
|
||||||
|
if (!slug.empty() && is_base64url_characters(slug)) {
|
||||||
|
return td::make_unique<InternalLinkDialogFilterInvite>(PSTRING() << "tg:list?slug=" << slug);
|
||||||
|
}
|
||||||
|
}
|
||||||
} else if (path.size() == 1 && path[0] == "join") {
|
} else if (path.size() == 1 && path[0] == "join") {
|
||||||
// join?invite=<hash>
|
// join?invite=<hash>
|
||||||
if (has_arg("invite")) {
|
if (has_arg("invite")) {
|
||||||
auto invite_hash = get_url_query_hash(true, url_query);
|
auto invite_hash = get_url_query_hash(true, url_query);
|
||||||
if (!invite_hash.empty() && !is_valid_phone_number(invite_hash) && is_base64url_characters(invite_hash)) {
|
if (!invite_hash.empty() && !is_valid_phone_number(invite_hash) && is_base64url_characters(invite_hash)) {
|
||||||
return td::make_unique<InternalLinkDialogInvite>(PSTRING() << "tg:join?invite=" << url_encode(invite_hash));
|
return td::make_unique<InternalLinkDialogInvite>(PSTRING() << "tg:join?invite=" << invite_hash);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
} else if (path.size() == 1 && (path[0] == "addstickers" || path[0] == "addemoji")) {
|
} else if (path.size() == 1 && (path[0] == "addstickers" || path[0] == "addemoji")) {
|
||||||
@ -1392,12 +1429,20 @@ unique_ptr<LinkManager::InternalLink> LinkManager::parse_t_me_link_query(Slice q
|
|||||||
// /login/<code>
|
// /login/<code>
|
||||||
return td::make_unique<InternalLinkAuthenticationCode>(path[1]);
|
return td::make_unique<InternalLinkAuthenticationCode>(path[1]);
|
||||||
}
|
}
|
||||||
|
} else if (path[0] == "list") {
|
||||||
|
if (path.size() >= 2 && !path[1].empty()) {
|
||||||
|
auto slug = get_url_query_slug(false, url_query);
|
||||||
|
if (!slug.empty() && is_base64url_characters(slug)) {
|
||||||
|
// /list/<slug>
|
||||||
|
return td::make_unique<InternalLinkDialogFilterInvite>(PSTRING() << "tg:list?slug=" << slug);
|
||||||
|
}
|
||||||
|
}
|
||||||
} else if (path[0] == "joinchat") {
|
} else if (path[0] == "joinchat") {
|
||||||
if (path.size() >= 2 && !path[1].empty()) {
|
if (path.size() >= 2 && !path[1].empty()) {
|
||||||
auto invite_hash = get_url_query_hash(false, url_query);
|
auto invite_hash = get_url_query_hash(false, url_query);
|
||||||
if (!invite_hash.empty() && !is_valid_phone_number(invite_hash) && is_base64url_characters(invite_hash)) {
|
if (!invite_hash.empty() && !is_valid_phone_number(invite_hash) && is_base64url_characters(invite_hash)) {
|
||||||
// /joinchat/<link>
|
// /joinchat/<hash>
|
||||||
return td::make_unique<InternalLinkDialogInvite>(PSTRING() << "tg:join?invite=" << url_encode(invite_hash));
|
return td::make_unique<InternalLinkDialogInvite>(PSTRING() << "tg:join?invite=" << invite_hash);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
} else if (path[0][0] == ' ' || path[0][0] == '+') {
|
} else if (path[0][0] == ' ' || path[0][0] == '+') {
|
||||||
@ -1415,7 +1460,7 @@ unique_ptr<LinkManager::InternalLink> LinkManager::parse_t_me_link_query(Slice q
|
|||||||
return std::move(user_link);
|
return std::move(user_link);
|
||||||
} else if (!invite_hash.empty() && is_base64url_characters(invite_hash)) {
|
} else if (!invite_hash.empty() && is_base64url_characters(invite_hash)) {
|
||||||
// /+<link>
|
// /+<link>
|
||||||
return td::make_unique<InternalLinkDialogInvite>(PSTRING() << "tg:join?invite=" << url_encode(invite_hash));
|
return td::make_unique<InternalLinkDialogInvite>(PSTRING() << "tg:join?invite=" << invite_hash);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
} else if (path[0] == "contact") {
|
} else if (path[0] == "contact") {
|
||||||
@ -1832,6 +1877,14 @@ Result<string> LinkManager::get_internal_link_impl(const td_api::InternalLinkTyp
|
|||||||
return Status::Error("HTTP link is unavailable for the link type");
|
return Status::Error("HTTP link is unavailable for the link type");
|
||||||
}
|
}
|
||||||
return "tg://settings/change_number";
|
return "tg://settings/change_number";
|
||||||
|
case td_api::internalLinkTypeChatFilterInvite::ID: {
|
||||||
|
auto link = static_cast<const td_api::internalLinkTypeChatFilterInvite *>(type_ptr);
|
||||||
|
auto slug = get_dialog_filter_invite_link_slug(link->invite_link_);
|
||||||
|
if (slug.empty()) {
|
||||||
|
return Status::Error(400, "Invalid invite link specified");
|
||||||
|
}
|
||||||
|
return get_dialog_filter_invite_link(slug, is_internal);
|
||||||
|
}
|
||||||
case td_api::internalLinkTypeChatInvite::ID: {
|
case td_api::internalLinkTypeChatInvite::ID: {
|
||||||
auto link = static_cast<const td_api::internalLinkTypeChatInvite *>(type_ptr);
|
auto link = static_cast<const td_api::internalLinkTypeChatInvite *>(type_ptr);
|
||||||
auto invite_hash = get_dialog_invite_link_hash(link->invite_link_);
|
auto invite_hash = get_dialog_invite_link_hash(link->invite_link_);
|
||||||
@ -2267,6 +2320,30 @@ Result<string> LinkManager::get_background_url(const string &name,
|
|||||||
return url;
|
return url;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
string LinkManager::get_dialog_filter_invite_link_slug(Slice invite_link) {
|
||||||
|
auto link_info = get_link_info(invite_link);
|
||||||
|
if (link_info.type_ != LinkType::Tg && link_info.type_ != LinkType::TMe) {
|
||||||
|
return string();
|
||||||
|
}
|
||||||
|
const auto url_query = parse_url_query(link_info.query_);
|
||||||
|
auto slug = get_url_query_slug(link_info.type_ == LinkType::Tg, url_query);
|
||||||
|
if (!is_base64url_characters(slug)) {
|
||||||
|
return string();
|
||||||
|
}
|
||||||
|
return slug;
|
||||||
|
}
|
||||||
|
|
||||||
|
string LinkManager::get_dialog_filter_invite_link(Slice slug, bool is_internal) {
|
||||||
|
if (!is_base64url_characters(slug)) {
|
||||||
|
return string();
|
||||||
|
}
|
||||||
|
if (is_internal) {
|
||||||
|
return PSTRING() << "tg:list?slug=" << slug;
|
||||||
|
} else {
|
||||||
|
return PSTRING() << get_t_me_url() << "list/" << slug;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
string LinkManager::get_dialog_invite_link_hash(Slice invite_link) {
|
string LinkManager::get_dialog_invite_link_hash(Slice invite_link) {
|
||||||
auto link_info = get_link_info(invite_link);
|
auto link_info = get_link_info(invite_link);
|
||||||
if (link_info.type_ != LinkType::Tg && link_info.type_ != LinkType::TMe) {
|
if (link_info.type_ != LinkType::Tg && link_info.type_ != LinkType::TMe) {
|
||||||
|
@ -83,6 +83,10 @@ class LinkManager final : public Actor {
|
|||||||
static Result<string> get_background_url(const string &name,
|
static Result<string> get_background_url(const string &name,
|
||||||
td_api::object_ptr<td_api::BackgroundType> background_type);
|
td_api::object_ptr<td_api::BackgroundType> background_type);
|
||||||
|
|
||||||
|
static string get_dialog_filter_invite_link_slug(Slice invite_link);
|
||||||
|
|
||||||
|
static string get_dialog_filter_invite_link(Slice slug, bool is_internal);
|
||||||
|
|
||||||
static string get_dialog_invite_link_hash(Slice invite_link);
|
static string get_dialog_invite_link_hash(Slice invite_link);
|
||||||
|
|
||||||
static string get_dialog_invite_link(Slice hash, bool is_internal);
|
static string get_dialog_invite_link(Slice hash, bool is_internal);
|
||||||
@ -120,6 +124,7 @@ class LinkManager final : public Actor {
|
|||||||
class InternalLinkChangePhoneNumber;
|
class InternalLinkChangePhoneNumber;
|
||||||
class InternalLinkConfirmPhone;
|
class InternalLinkConfirmPhone;
|
||||||
class InternalLinkDefaultMessageAutoDeleteTimerSettings;
|
class InternalLinkDefaultMessageAutoDeleteTimerSettings;
|
||||||
|
class InternalLinkDialogFilterInvite;
|
||||||
class InternalLinkDialogInvite;
|
class InternalLinkDialogInvite;
|
||||||
class InternalLinkEditProfileSettings;
|
class InternalLinkEditProfileSettings;
|
||||||
class InternalLinkFilterSettings;
|
class InternalLinkFilterSettings;
|
||||||
|
@ -218,6 +218,10 @@ static auto change_phone_number() {
|
|||||||
return td::td_api::make_object<td::td_api::internalLinkTypeChangePhoneNumber>();
|
return td::td_api::make_object<td::td_api::internalLinkTypeChangePhoneNumber>();
|
||||||
}
|
}
|
||||||
|
|
||||||
|
static auto chat_filter_invite(const td::string &slug) {
|
||||||
|
return td::td_api::make_object<td::td_api::internalLinkTypeChatFilterInvite>("tg:list?slug=" + slug);
|
||||||
|
}
|
||||||
|
|
||||||
static auto chat_invite(const td::string &hash) {
|
static auto chat_invite(const td::string &hash) {
|
||||||
return td::td_api::make_object<td::td_api::internalLinkTypeChatInvite>("tg:join?invite=" + hash);
|
return td::td_api::make_object<td::td_api::internalLinkTypeChatInvite>("tg:join?invite=" + hash);
|
||||||
}
|
}
|
||||||
@ -703,6 +707,24 @@ TEST(Link, parse_internal_link_part2) {
|
|||||||
parse_internal_link("t.me/+123456?attach=bot&startattach=1",
|
parse_internal_link("t.me/+123456?attach=bot&startattach=1",
|
||||||
attachment_menu_bot(nullptr, user_phone_number("123456"), "bot", "1"));
|
attachment_menu_bot(nullptr, user_phone_number("123456"), "bot", "1"));
|
||||||
|
|
||||||
|
parse_internal_link("t.me/list?invite=abcdef", nullptr);
|
||||||
|
parse_internal_link("t.me/list", nullptr);
|
||||||
|
parse_internal_link("t.me/list/", nullptr);
|
||||||
|
parse_internal_link("t.me/list//abcdef", nullptr);
|
||||||
|
parse_internal_link("t.me/list?/abcdef", nullptr);
|
||||||
|
parse_internal_link("t.me/list/?abcdef", nullptr);
|
||||||
|
parse_internal_link("t.me/list/#abcdef", nullptr);
|
||||||
|
parse_internal_link("t.me/list/abacaba", chat_filter_invite("abacaba"));
|
||||||
|
parse_internal_link("t.me/list/aba%20aba", nullptr);
|
||||||
|
parse_internal_link("t.me/list/aba%30aba", chat_filter_invite("aba0aba"));
|
||||||
|
parse_internal_link("t.me/list/123456a", chat_filter_invite("123456a"));
|
||||||
|
parse_internal_link("t.me/list/12345678901", chat_filter_invite("12345678901"));
|
||||||
|
parse_internal_link("t.me/list/123456", chat_filter_invite("123456"));
|
||||||
|
parse_internal_link("t.me/list/123456/123123/12/31/a/s//21w/?asdas#test", chat_filter_invite("123456"));
|
||||||
|
parse_internal_link("t.me/list/12345678901a", chat_filter_invite("12345678901a"));
|
||||||
|
parse_internal_link("t.me/list/123456a", chat_filter_invite("123456a"));
|
||||||
|
parse_internal_link("t.me/list/123456a/123123/12/31/a/s//21w/?asdas#test", chat_filter_invite("123456a"));
|
||||||
|
|
||||||
parse_internal_link("t.me/contact/startattach/adasd", user_token("startattach"));
|
parse_internal_link("t.me/contact/startattach/adasd", user_token("startattach"));
|
||||||
parse_internal_link("t.me/contact/startattach", user_token("startattach"));
|
parse_internal_link("t.me/contact/startattach", user_token("startattach"));
|
||||||
parse_internal_link("t.me/contact/startattach=1", user_token("startattach=1"));
|
parse_internal_link("t.me/contact/startattach=1", user_token("startattach=1"));
|
||||||
@ -714,6 +736,11 @@ TEST(Link, parse_internal_link_part2) {
|
|||||||
parse_internal_link("tg://join?invite=abc%30def", chat_invite("abc0def"));
|
parse_internal_link("tg://join?invite=abc%30def", chat_invite("abc0def"));
|
||||||
parse_internal_link("tg:join?invite=", unknown_deep_link("tg://join?invite="));
|
parse_internal_link("tg:join?invite=", unknown_deep_link("tg://join?invite="));
|
||||||
|
|
||||||
|
parse_internal_link("tg:list?slug=abcdef", chat_filter_invite("abcdef"));
|
||||||
|
parse_internal_link("tg:list?slug=abc%20def", unknown_deep_link("tg://list?slug=abc%20def"));
|
||||||
|
parse_internal_link("tg://list?slug=abc%30def", chat_filter_invite("abc0def"));
|
||||||
|
parse_internal_link("tg:list?slug=", unknown_deep_link("tg://list?slug="));
|
||||||
|
|
||||||
parse_internal_link("t.me/addstickers?set=abcdef", nullptr);
|
parse_internal_link("t.me/addstickers?set=abcdef", nullptr);
|
||||||
parse_internal_link("t.me/addstickers", nullptr);
|
parse_internal_link("t.me/addstickers", nullptr);
|
||||||
parse_internal_link("t.me/addstickers/", nullptr);
|
parse_internal_link("t.me/addstickers/", nullptr);
|
||||||
@ -1142,6 +1169,7 @@ TEST(Link, parse_internal_link_part4) {
|
|||||||
parse_internal_link("confirmphone.t.me", nullptr);
|
parse_internal_link("confirmphone.t.me", nullptr);
|
||||||
parse_internal_link("invoice.t.me", nullptr);
|
parse_internal_link("invoice.t.me", nullptr);
|
||||||
parse_internal_link("joinchat.t.me", nullptr);
|
parse_internal_link("joinchat.t.me", nullptr);
|
||||||
|
parse_internal_link("list.t.me", nullptr);
|
||||||
parse_internal_link("login.t.me", nullptr);
|
parse_internal_link("login.t.me", nullptr);
|
||||||
parse_internal_link("proxy.t.me", nullptr);
|
parse_internal_link("proxy.t.me", nullptr);
|
||||||
parse_internal_link("setlanguage.t.me", nullptr);
|
parse_internal_link("setlanguage.t.me", nullptr);
|
||||||
|
Loading…
Reference in New Issue
Block a user