File reference improvements.
GitOrigin-RevId: 40d3ac6cde73503af544df464cc9ff569fb4016d
This commit is contained in:
parent
cc5eaa6b7e
commit
f54a0c3e70
|
@ -6,6 +6,7 @@
|
||||||
//
|
//
|
||||||
#include "td/telegram/FileReferenceManager.h"
|
#include "td/telegram/FileReferenceManager.h"
|
||||||
|
|
||||||
|
#include "td/telegram/files/FileManager.h"
|
||||||
#include "td/telegram/Global.h"
|
#include "td/telegram/Global.h"
|
||||||
#include "td/telegram/MessagesManager.h"
|
#include "td/telegram/MessagesManager.h"
|
||||||
|
|
||||||
|
@ -31,9 +32,6 @@ void FileReferenceManager::update_file_reference(FileId file_id, std::vector<Fil
|
||||||
MultiPromiseActorSafe mpas{"UpdateFileReferenceMultiPromiseActor"};
|
MultiPromiseActorSafe mpas{"UpdateFileReferenceMultiPromiseActor"};
|
||||||
mpas.add_promise(std::move(promise));
|
mpas.add_promise(std::move(promise));
|
||||||
auto lock = mpas.get_promise();
|
auto lock = mpas.get_promise();
|
||||||
SCOPE_EXIT {
|
|
||||||
lock.set_value(Unit());
|
|
||||||
};
|
|
||||||
for (auto source_id : sources) {
|
for (auto source_id : sources) {
|
||||||
auto it = to_full_message_id_.find(source_id);
|
auto it = to_full_message_id_.find(source_id);
|
||||||
auto new_promise = PromiseCreator::lambda([promise = mpas.get_promise(), file_id, source_id,
|
auto new_promise = PromiseCreator::lambda([promise = mpas.get_promise(), file_id, source_id,
|
||||||
|
@ -47,7 +45,7 @@ void FileReferenceManager::update_file_reference(FileId file_id, std::vector<Fil
|
||||||
promise.set_value(Unit());
|
promise.set_value(Unit());
|
||||||
});
|
});
|
||||||
if (it == to_full_message_id_.end()) {
|
if (it == to_full_message_id_.end()) {
|
||||||
new_promise.set_error(Status::Error("Unkonwn source id"));
|
new_promise.set_error(Status::Error("Unknown source id"));
|
||||||
continue;
|
continue;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -56,6 +54,7 @@ void FileReferenceManager::update_file_reference(FileId file_id, std::vector<Fil
|
||||||
send_closure_later(G()->messages_manager(), &MessagesManager::get_messages_from_server, std::move(message_ids),
|
send_closure_later(G()->messages_manager(), &MessagesManager::get_messages_from_server, std::move(message_ids),
|
||||||
std::move(new_promise), nullptr);
|
std::move(new_promise), nullptr);
|
||||||
}
|
}
|
||||||
|
lock.set_value(Unit());
|
||||||
}
|
}
|
||||||
|
|
||||||
} // namespace td
|
} // namespace td
|
||||||
|
|
|
@ -271,7 +271,7 @@ Result<std::pair<NetQueryPtr, bool>> FileDownloader::start_part(Part part, int32
|
||||||
Status FileDownloader::check_net_query(NetQueryPtr &net_query) {
|
Status FileDownloader::check_net_query(NetQueryPtr &net_query) {
|
||||||
if (net_query->is_error()) {
|
if (net_query->is_error()) {
|
||||||
auto error = net_query->move_as_error();
|
auto error = net_query->move_as_error();
|
||||||
if (begins_with(error.message(), "FILE_REFERENCE_")) {
|
if (error.code() == 400 && begins_with(error.message(), "FILE_REFERENCE_")) {
|
||||||
error = Status::Error(400, PSLICE()
|
error = Status::Error(400, PSLICE()
|
||||||
<< "FILE_REFERENCE_EXPIRED_BASE64" << base64_encode(remote_.get_file_reference()));
|
<< "FILE_REFERENCE_EXPIRED_BASE64" << base64_encode(remote_.get_file_reference()));
|
||||||
}
|
}
|
||||||
|
|
|
@ -553,7 +553,7 @@ class FullRemoteFileLocation {
|
||||||
bool has_file_reference() const {
|
bool has_file_reference() const {
|
||||||
return !file_reference_.empty();
|
return !file_reference_.empty();
|
||||||
}
|
}
|
||||||
string get_file_reference() const {
|
const string &get_file_reference() const {
|
||||||
return file_reference_;
|
return file_reference_;
|
||||||
}
|
}
|
||||||
string get_url() const {
|
string get_url() const {
|
||||||
|
|
|
@ -352,13 +352,16 @@ string FileNode::suggested_name() const {
|
||||||
bool FileView::has_local_location() const {
|
bool FileView::has_local_location() const {
|
||||||
return node_->local_.type() == LocalFileLocation::Type::Full;
|
return node_->local_.type() == LocalFileLocation::Type::Full;
|
||||||
}
|
}
|
||||||
|
|
||||||
const FullLocalFileLocation &FileView::local_location() const {
|
const FullLocalFileLocation &FileView::local_location() const {
|
||||||
CHECK(has_local_location());
|
CHECK(has_local_location());
|
||||||
return node_->local_.full();
|
return node_->local_.full();
|
||||||
}
|
}
|
||||||
|
|
||||||
bool FileView::has_remote_location() const {
|
bool FileView::has_remote_location() const {
|
||||||
return node_->remote_.type() == RemoteFileLocation::Type::Full;
|
return node_->remote_.type() == RemoteFileLocation::Type::Full;
|
||||||
}
|
}
|
||||||
|
|
||||||
bool FileView::has_active_remote_location() const {
|
bool FileView::has_active_remote_location() const {
|
||||||
if (!has_remote_location()) {
|
if (!has_remote_location()) {
|
||||||
return false;
|
return false;
|
||||||
|
@ -368,6 +371,7 @@ bool FileView::has_active_remote_location() const {
|
||||||
}
|
}
|
||||||
return remote_location().has_file_reference();
|
return remote_location().has_file_reference();
|
||||||
}
|
}
|
||||||
|
|
||||||
const FullRemoteFileLocation &FileView::remote_location() const {
|
const FullRemoteFileLocation &FileView::remote_location() const {
|
||||||
CHECK(has_remote_location());
|
CHECK(has_remote_location());
|
||||||
auto *remote = node_.get_remote();
|
auto *remote = node_.get_remote();
|
||||||
|
@ -376,9 +380,11 @@ const FullRemoteFileLocation &FileView::remote_location() const {
|
||||||
}
|
}
|
||||||
return node_->remote_.full();
|
return node_->remote_.full();
|
||||||
}
|
}
|
||||||
|
|
||||||
bool FileView::has_generate_location() const {
|
bool FileView::has_generate_location() const {
|
||||||
return node_->generate_ != nullptr;
|
return node_->generate_ != nullptr;
|
||||||
}
|
}
|
||||||
|
|
||||||
const FullGenerateFileLocation &FileView::generate_location() const {
|
const FullGenerateFileLocation &FileView::generate_location() const {
|
||||||
CHECK(has_generate_location());
|
CHECK(has_generate_location());
|
||||||
return *node_->generate_;
|
return *node_->generate_;
|
||||||
|
@ -989,12 +995,14 @@ static int merge_choose_remote_location(const RemoteFileLocation &x, int8 x_sour
|
||||||
return x.full().is_web(); // prefer non-web
|
return x.full().is_web(); // prefer non-web
|
||||||
}
|
}
|
||||||
auto x_ref = x.full().has_file_reference();
|
auto x_ref = x.full().has_file_reference();
|
||||||
auto y_ref = !y.full().has_file_reference();
|
auto y_ref = y.full().has_file_reference();
|
||||||
if (x_ref || y_ref) {
|
if (x_ref || y_ref) {
|
||||||
if (x_ref != y_ref) {
|
if (x_ref != y_ref) {
|
||||||
return !x_ref;
|
return !x_ref;
|
||||||
}
|
}
|
||||||
return x_source < y_source;
|
if (x.full().get_file_reference() != y.full().get_file_reference()) {
|
||||||
|
return x_source < y_source;
|
||||||
|
}
|
||||||
}
|
}
|
||||||
if (x.full().get_access_hash() != y.full().get_access_hash()) {
|
if (x.full().get_access_hash() != y.full().get_access_hash()) {
|
||||||
return x_source < y_source;
|
return x_source < y_source;
|
||||||
|
@ -1356,7 +1364,7 @@ void FileManager::add_file_source(FileId file_id, FileSourceId file_source_id) {
|
||||||
}
|
}
|
||||||
|
|
||||||
void FileManager::remove_file_source(FileId file_id, FileSourceId file_source_id) {
|
void FileManager::remove_file_source(FileId file_id, FileSourceId file_source_id) {
|
||||||
LOG(ERROR) << "Remove file source " << file_id, file_source_id;
|
LOG(ERROR) << "Remove file source " << file_id << " " << file_source_id;
|
||||||
auto node = get_file_node(file_id);
|
auto node = get_file_node(file_id);
|
||||||
if (!node) {
|
if (!node) {
|
||||||
return;
|
return;
|
||||||
|
@ -1752,7 +1760,7 @@ void FileManager::run_download(FileNodePtr node) {
|
||||||
|
|
||||||
// If file reference is needed
|
// If file reference is needed
|
||||||
if (!file_view.has_active_remote_location()) {
|
if (!file_view.has_active_remote_location()) {
|
||||||
LOG(INFO) << "run_download: Do not have valid file_reference " << file_id;
|
LOG(INFO) << "run_download: Do not have valid file_reference for file " << file_id;
|
||||||
QueryId id = queries_container_.create(Query{file_id, Query::DownloadWaitFileReferece});
|
QueryId id = queries_container_.create(Query{file_id, Query::DownloadWaitFileReferece});
|
||||||
node->download_id_ = id;
|
node->download_id_ = id;
|
||||||
if (node->file_source_ids_.empty()) {
|
if (node->file_source_ids_.empty()) {
|
||||||
|
@ -1760,23 +1768,23 @@ void FileManager::run_download(FileNodePtr node) {
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
if (!node->download_may_update_file_reference_) {
|
if (!node->download_may_update_file_reference_) {
|
||||||
on_error(id, Status::Error("Can't download file: have valid source id, but do not allowed to use id"));
|
on_error(id, Status::Error("Can't download file: have valid source id, but do not allowed to use it"));
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
node->download_may_update_file_reference_ = false;
|
node->download_may_update_file_reference_ = false;
|
||||||
|
|
||||||
send_closure(
|
send_closure(G()->file_reference_manager(), &FileReferenceManager::update_file_reference, file_id,
|
||||||
G()->file_reference_manager(), &FileReferenceManager::update_file_reference, file_id, node->file_source_ids_,
|
node->file_source_ids_,
|
||||||
PromiseCreator::lambda([id, actor_id = actor_id(this), file_id](Result<Unit> res) {
|
PromiseCreator::lambda([id, actor_id = actor_id(this), file_id](Result<Unit> res) {
|
||||||
Status error;
|
Status error;
|
||||||
if (res.is_ok()) {
|
if (res.is_ok()) {
|
||||||
error = td::Status::Error("FILE_DOWNLOAD_RESTART_WITH_FILE_REFERENCE");
|
error = Status::Error("FILE_DOWNLOAD_RESTART_WITH_FILE_REFERENCE");
|
||||||
} else {
|
} else {
|
||||||
error = res.move_as_error();
|
error = res.move_as_error();
|
||||||
}
|
}
|
||||||
LOG(INFO) << "run_download: Got result from FileSourceManager for file " << file_id << " : " << error;
|
LOG(INFO) << "run_download: Got result from FileSourceManager for file " << file_id << ": " << error;
|
||||||
send_closure(actor_id, &FileManager::on_error, id, std::move(error));
|
send_closure(actor_id, &FileManager::on_error, id, std::move(error));
|
||||||
}));
|
}));
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -2772,10 +2780,11 @@ void FileManager::on_error_impl(FileNodePtr node, FileManager::Query::Type type,
|
||||||
string file_reference;
|
string file_reference;
|
||||||
Slice prefix = "FILE_REFERENCE_EXPIRED_BASE64";
|
Slice prefix = "FILE_REFERENCE_EXPIRED_BASE64";
|
||||||
if (begins_with(status.message(), prefix)) {
|
if (begins_with(status.message(), prefix)) {
|
||||||
auto tmp = base64_decode(status.message().substr(prefix.size()));
|
auto r_file_reference = base64_decode(status.message().substr(prefix.size()));
|
||||||
LOG_IF(WARNING, tmp.is_error()) << "Can't decode file reference from error " << status << " " << tmp.error();
|
if (r_file_reference.is_ok()) {
|
||||||
if (tmp.is_ok()) {
|
file_reference = r_file_reference.move_as_ok();
|
||||||
file_reference = tmp.move_as_ok();
|
} else {
|
||||||
|
LOG(ERROR) << "Can't decode file reference from error " << status << ": " << r_file_reference.error();
|
||||||
}
|
}
|
||||||
} else {
|
} else {
|
||||||
LOG(ERROR) << "Unexpected error, file_reference will be deleted just in case " << status;
|
LOG(ERROR) << "Unexpected error, file_reference will be deleted just in case " << status;
|
||||||
|
|
Reference in New Issue
Block a user