diff --git a/td/generate/scheme/td_api.tl b/td/generate/scheme/td_api.tl index 4cf9507a..1c76c681 100644 --- a/td/generate/scheme/td_api.tl +++ b/td/generate/scheme/td_api.tl @@ -3608,6 +3608,9 @@ getBackgrounds = Backgrounds; //@description Constructs persistent URL for a background @name Background name @type Background type getBackgroundUrl name:string type:BackgroundType = HttpUrl; +//@description Searches for a background by its name @name The name of the background +searchBackground name:string = Background; + //@description Returns information about the current localization target. This is an offline request if only_local is true. Can be called before authorization @only_local If true, returns only locally available information without sending network requests getLocalizationTargetInfo only_local:Bool = LocalizationTargetInfo; diff --git a/td/generate/scheme/td_api.tlo b/td/generate/scheme/td_api.tlo index 90c0f889..7e25d254 100644 Binary files a/td/generate/scheme/td_api.tlo and b/td/generate/scheme/td_api.tlo differ diff --git a/td/telegram/BackgroundManager.cpp b/td/telegram/BackgroundManager.cpp index b916d5b9..7c14e78c 100644 --- a/td/telegram/BackgroundManager.cpp +++ b/td/telegram/BackgroundManager.cpp @@ -26,6 +26,38 @@ namespace td { +class GetBackgroundQuery : public Td::ResultHandler { + Promise promise_; + BackgroundId background_id_; + + public: + explicit GetBackgroundQuery(Promise &&promise) : promise_(std::move(promise)) { + } + + void send(BackgroundId background_id, telegram_api::object_ptr &&input_wallpaper) { + background_id_ = background_id; + LOG(INFO) << "Load " << background_id << " from server: " << to_string(input_wallpaper); + send_query( + G()->net_query_creator().create(create_storer(telegram_api::account_getWallPaper(std::move(input_wallpaper))))); + } + + void on_result(uint64 id, BufferSlice packet) override { + auto result_ptr = fetch_result(packet); + if (result_ptr.is_error()) { + return on_error(id, result_ptr.move_as_error()); + } + + td->background_manager_->on_get_background(background_id_, result_ptr.move_as_ok()); + + promise_.set_value(Unit()); + } + + void on_error(uint64 id, Status status) override { + LOG(INFO) << "Receive error for getBackground: " << status; + promise_.set_error(std::move(status)); + } +}; + class GetBackgroundsQuery : public Td::ResultHandler { Promise> promise_; @@ -156,6 +188,27 @@ Result BackgroundManager::get_background_url(const string &name, } } +void BackgroundManager::reload_background(BackgroundId background_id, + telegram_api::object_ptr &&input_wallpaper, + Promise &&promise) const { + if (G()->close_flag()) { + return promise.set_error(Status::Error(500, "Request aborted")); + } + td_->create_handler(std::move(promise))->send(background_id, std::move(input_wallpaper)); +} + +BackgroundId BackgroundManager::search_background(const string &name, Promise &&promise) { + auto it = name_to_background_id_.find(name); + if (it != name_to_background_id_.end()) { + promise.set_value(Unit()); + return it->second; + } + + reload_background(BackgroundId(), telegram_api::make_object(name), + std::move(promise)); + return BackgroundId(); +} + BackgroundManager::Background *BackgroundManager::add_background(BackgroundId background_id) { CHECK(background_id.is_valid()); return &backgrounds_[background_id]; @@ -202,7 +255,8 @@ BackgroundManager::BackgroundType BackgroundManager::get_background_type( } } -BackgroundId BackgroundManager::on_get_background(telegram_api::object_ptr wallpaper) { +BackgroundId BackgroundManager::on_get_background(BackgroundId expected_background_id, + telegram_api::object_ptr wallpaper) { CHECK(wallpaper != nullptr); auto id = BackgroundId(wallpaper->id_); @@ -210,6 +264,9 @@ BackgroundId BackgroundManager::on_get_background(telegram_api::object_ptrdocument_->get_id(); if (document_id == telegram_api::documentEmpty::ID) { @@ -233,12 +290,20 @@ BackgroundId BackgroundManager::on_get_background(telegram_api::object_ptrid = id; background->access_hash = wallpaper->access_hash_; - background->name = std::move(wallpaper->slug_); background->file_id = document.file_id; background->is_creator = (flags & telegram_api::wallPaper::CREATOR_MASK) != 0; background->is_default = (flags & telegram_api::wallPaper::DEFAULT_MASK) != 0; background->is_dark = (flags & telegram_api::wallPaper::DARK_MASK) != 0; background->type = get_background_type(is_pattern, std::move(wallpaper->settings_)); + if (background->name != wallpaper->slug_) { + if (!background->name.empty()) { + LOG(ERROR) << "Background name has changed from " << background->name << " to " << wallpaper->slug_; + name_to_background_id_.erase(background->name); + } + + background->name = std::move(wallpaper->slug_); + name_to_background_id_.emplace(background->name, id); + } return id; } @@ -270,7 +335,7 @@ void BackgroundManager::on_get_backgrounds(Result(wallpapers_ptr); for (auto &wallpaper : wallpapers->wallpapers_) { - auto background_id = on_get_background(std::move(wallpaper)); + auto background_id = on_get_background(BackgroundId(), std::move(wallpaper)); if (background_id.is_valid()) { installed_backgrounds_.push_back(background_id); } diff --git a/td/telegram/BackgroundManager.h b/td/telegram/BackgroundManager.h index 68676aea..41fe4223 100644 --- a/td/telegram/BackgroundManager.h +++ b/td/telegram/BackgroundManager.h @@ -34,10 +34,15 @@ class BackgroundManager : public Actor { Result get_background_url(const string &name, td_api::object_ptr background_type) const; + BackgroundId search_background(const string &name, Promise &&promise); + td_api::object_ptr get_background_object(BackgroundId background_id) const; td_api::object_ptr get_backgrounds_object() const; + BackgroundId on_get_background(BackgroundId expected_background_id, + telegram_api::object_ptr wallpaper); + private: struct BackgroundType { enum class Type : int32 { Wallpaper, Pattern, Solid }; @@ -71,6 +76,10 @@ class BackgroundManager : public Actor { void tear_down() override; + void reload_background(BackgroundId background_id, + telegram_api::object_ptr &&input_wallpaper, + Promise &&promise) const; + Background *add_background(BackgroundId background_id); const Background *get_background(BackgroundId background_id) const; @@ -80,14 +89,14 @@ class BackgroundManager : public Actor { static BackgroundType get_background_type(bool is_pattern, telegram_api::object_ptr settings); - BackgroundId on_get_background(telegram_api::object_ptr wallpaper); - void on_get_backgrounds(Result> result); static td_api::object_ptr get_background_type_object(const BackgroundType &type); std::unordered_map backgrounds_; // id -> Background + std::unordered_map name_to_background_id_; + vector installed_backgrounds_; vector> pending_get_backgrounds_queries_; diff --git a/td/telegram/Td.cpp b/td/telegram/Td.cpp index 5a2aea74..df6cd0f8 100644 --- a/td/telegram/Td.cpp +++ b/td/telegram/Td.cpp @@ -2899,6 +2899,25 @@ class GetBackgroundsRequest : public RequestOnceActor { } }; +class SearchBackgroundRequest : public RequestActor<> { + string name_; + + BackgroundId background_id_; + + void do_run(Promise &&promise) override { + background_id_ = td->background_manager_->search_background(name_, std::move(promise)); + } + + void do_send_result() override { + send_result(td->background_manager_->get_background_object(background_id_)); + } + + public: + SearchBackgroundRequest(ActorShared td, uint64 request_id, string &&name) + : RequestActor(std::move(td), request_id), name_(std::move(name)) { + } +}; + class GetRecentlyVisitedTMeUrlsRequest : public RequestActor> { string referrer_; @@ -6955,6 +6974,12 @@ void Td::on_request(uint64 id, td_api::getBackgroundUrl &request) { send_closure(actor_id(this), &Td::send_result, id, td_api::make_object(r_url.ok())); } +void Td::on_request(uint64 id, td_api::searchBackground &request) { + CHECK_IS_USER(); + CLEAN_INPUT_STRING(request.name_); + CREATE_REQUEST(SearchBackgroundRequest, std::move(request.name_)); +} + void Td::on_request(uint64 id, td_api::getRecentlyVisitedTMeUrls &request) { CHECK_IS_USER(); CLEAN_INPUT_STRING(request.referrer_); diff --git a/td/telegram/Td.h b/td/telegram/Td.h index 643efd48..8baae63a 100644 --- a/td/telegram/Td.h +++ b/td/telegram/Td.h @@ -926,6 +926,8 @@ class Td final : public NetQueryCallback { void on_request(uint64 id, td_api::getBackgroundUrl &request); + void on_request(uint64 id, td_api::searchBackground &request); + void on_request(uint64 id, td_api::getRecentlyVisitedTMeUrls &request); void on_request(uint64 id, td_api::setBotUpdatesStatus &request); diff --git a/td/telegram/cli.cpp b/td/telegram/cli.cpp index f88e53b6..099ac438 100644 --- a/td/telegram/cli.cpp +++ b/td/telegram/cli.cpp @@ -1980,6 +1980,8 @@ class CliClient final : public Actor { send_get_background_url(td_api::make_object(-1)); send_get_background_url(td_api::make_object(0xABCDEF)); send_get_background_url(td_api::make_object(0x1000000)); + } else if (op == "sbg") { + send_request(td_api::make_object(args)); } else if (op == "gccode") { send_request(td_api::make_object()); } else if (op == "git") {