Added initial support of fallback user photo to storage module.

This commit is contained in:
23rd 2022-12-19 13:01:32 +03:00 committed by John Preston
parent 6327d5ea38
commit b135a09e00
7 changed files with 106 additions and 4 deletions

View File

@ -8,10 +8,12 @@ https://github.com/telegramdesktop/tdesktop/blob/master/LEGAL
#include "data/data_user.h"
#include "storage/localstorage.h"
#include "storage/storage_user_photos.h"
#include "main/main_session.h"
#include "data/data_session.h"
#include "data/data_changes.h"
#include "data/data_peer_bot_command.h"
#include "data/data_photo.h"
#include "data/data_emoji_statuses.h"
#include "data/data_user_names.h"
#include "data/notify/data_notify_settings.h"
@ -380,6 +382,13 @@ void ApplyUserUpdate(not_null<UserData*> user, const MTPDuserFull &update) {
} else {
user->session().api().peerPhoto().unregisterNonPersonalPhoto(user);
}
if (const auto photo = update.vfallback_photo()) {
const auto data = user->owner().processPhoto(*photo);
user->session().storage().add(Storage::UserPhotosSetBack(
peerToUser(user->id),
data->id
));
}
user->setSettings(update.vsettings());
user->owner().notifySettings().apply(user, update.vnotify_settings());

View File

@ -237,3 +237,21 @@ rpl::producer<UserPhotosSlice> UserPhotosReversedViewer(
return std::move(slice);
});
}
std::optional<PhotoId> SyncUserFallbackPhotoViewer(not_null<UserData*> user) {
auto syncLifetime = rpl::lifetime();
auto result = std::optional<PhotoId>(std::nullopt);
constexpr auto kFallbackCount = 1;
user->session().storage().query(Storage::UserPhotosQuery(
Storage::UserPhotosKey(peerToUser(user->id), true),
kFallbackCount,
kFallbackCount
)) | rpl::start_with_next([&](Storage::UserPhotosResult &&slice) {
if (slice.photoIds.empty()) {
return;
}
result = slice.photoIds.front();
}, syncLifetime);
return result;
}

View File

@ -11,6 +11,8 @@ https://github.com/telegramdesktop/tdesktop/blob/master/LEGAL
#include "storage/storage_user_photos.h"
#include "base/weak_ptr.h"
class UserData;
namespace Main {
class Session;
} // namespace Main
@ -48,3 +50,6 @@ rpl::producer<UserPhotosSlice> UserPhotosReversedViewer(
UserPhotosSlice::Key key,
int limitBefore,
int limitAfter);
[[nodiscard]] std::optional<PhotoId> SyncUserFallbackPhotoViewer(
not_null<UserData*> user);

View File

@ -29,6 +29,7 @@ public:
rpl::producer<SharedMediaRemoveAll> sharedMediaAllRemoved() const;
rpl::producer<SharedMediaInvalidateBottom> sharedMediaBottomInvalidated() const;
void add(UserPhotosSetBack &&query);
void add(UserPhotosAddNew &&query);
void add(UserPhotosAddSlice &&query);
void remove(UserPhotosRemoveOne &&query);
@ -98,6 +99,10 @@ rpl::producer<SharedMediaInvalidateBottom> Facade::Impl::sharedMediaBottomInvali
return _sharedMedia.bottomInvalidated();
}
void Facade::Impl::add(UserPhotosSetBack &&query) {
return _userPhotos.add(std::move(query));
}
void Facade::Impl::add(UserPhotosAddNew &&query) {
return _userPhotos.add(std::move(query));
}
@ -181,6 +186,10 @@ rpl::producer<SharedMediaInvalidateBottom> Facade::sharedMediaBottomInvalidated(
return _impl->sharedMediaBottomInvalidated();
}
void Facade::add(UserPhotosSetBack &&query) {
return _impl->add(std::move(query));
}
void Facade::add(UserPhotosAddNew &&query) {
return _impl->add(std::move(query));
}

View File

@ -30,6 +30,7 @@ struct SharedMediaKey;
using SharedMediaResult = SparseIdsListResult;
struct SharedMediaSliceUpdate;
struct UserPhotosSetBack;
struct UserPhotosAddNew;
struct UserPhotosAddSlice;
struct UserPhotosRemoveOne;
@ -58,6 +59,7 @@ public:
rpl::producer<SharedMediaRemoveAll> sharedMediaAllRemoved() const;
rpl::producer<SharedMediaInvalidateBottom> sharedMediaBottomInvalidated() const;
void add(UserPhotosSetBack &&query);
void add(UserPhotosAddNew &&query);
void add(UserPhotosAddSlice &&query);
void remove(UserPhotosRemoveOne &&query);

View File

@ -9,12 +9,38 @@ https://github.com/telegramdesktop/tdesktop/blob/master/LEGAL
namespace Storage {
void UserPhotos::List::setBack(PhotoId photoId) {
if (_backPhotoId != photoId) {
detachBack();
_backPhotoId = photoId;
attachBack();
sendUpdate();
}
}
void UserPhotos::List::detachBack() {
if (_backPhotoId) {
removeOne(_backPhotoId);
}
}
void UserPhotos::List::attachBack() {
if (_backPhotoId) {
_photoIds.push_front(_backPhotoId);
if (_count) {
++*_count;
}
}
}
void UserPhotos::List::addNew(PhotoId photoId) {
if (!base::contains(_photoIds, photoId)) {
detachBack();
_photoIds.push_back(photoId);
if (_count) {
++*_count;
}
attachBack();
sendUpdate();
}
}
@ -22,6 +48,7 @@ void UserPhotos::List::addNew(PhotoId photoId) {
void UserPhotos::List::addSlice(
std::vector<PhotoId> &&photoIds,
int count) {
detachBack();
for (auto photoId : photoIds) {
if (!base::contains(_photoIds, photoId)) {
_photoIds.push_front(photoId);
@ -32,6 +59,7 @@ void UserPhotos::List::addSlice(
if ((_count && *_count < _photoIds.size()) || photoIds.empty()) {
_count = _photoIds.size();
}
attachBack();
sendUpdate();
}
@ -72,7 +100,7 @@ void UserPhotos::List::sendUpdate() {
rpl::producer<UserPhotosResult> UserPhotos::List::query(
UserPhotosQuery &&query) const {
return [this, query = std::move(query)](auto consumer) {
auto result = UserPhotosResult {};
auto result = UserPhotosResult();
result.count = _count;
auto position = ranges::find(_photoIds, query.key.photoId);
@ -91,6 +119,10 @@ rpl::producer<UserPhotosResult> UserPhotos::List::query(
result.skippedBefore = haveBefore - before;
result.skippedAfter = (haveEqualOrAfter - equalOrAfter);
consumer.put_next(std::move(result));
} else if (query.key.back && _backPhotoId) {
result.photoIds.push_front(_backPhotoId);
result.count = 1;
consumer.put_next(std::move(result));
} else if (_count) {
consumer.put_next(std::move(result));
}
@ -107,7 +139,8 @@ rpl::producer<UserPhotosSliceUpdate> UserPhotos::sliceUpdated() const {
return _sliceUpdated.events();
}
std::map<UserId, UserPhotos::List>::iterator UserPhotos::enforceLists(UserId user) {
std::map<UserId, UserPhotos::List>::iterator UserPhotos::enforceLists(
UserId user) {
auto result = _lists.find(user);
if (result != _lists.end()) {
return result;
@ -124,6 +157,11 @@ std::map<UserId, UserPhotos::List>::iterator UserPhotos::enforceLists(UserId use
return result;
}
void UserPhotos::add(UserPhotosSetBack &&query) {
auto userIt = enforceLists(query.userId);
userIt->second.setBack(query.photoId);
}
void UserPhotos::add(UserPhotosAddNew &&query) {
auto userIt = enforceLists(query.userId);
userIt->second.addNew(query.photoId);
@ -150,7 +188,8 @@ void UserPhotos::remove(UserPhotosRemoveAfter &&query) {
}
}
rpl::producer<UserPhotosResult> UserPhotos::query(UserPhotosQuery &&query) const {
rpl::producer<UserPhotosResult> UserPhotos::query(
UserPhotosQuery &&query) const {
auto userIt = _lists.find(query.key.userId);
if (userIt != _lists.end()) {
return userIt->second.query(std::move(query));

View File

@ -12,6 +12,16 @@ https://github.com/telegramdesktop/tdesktop/blob/master/LEGAL
namespace Storage {
struct UserPhotosSetBack {
UserPhotosSetBack(UserId userId, PhotoId photoId)
: userId(userId), photoId(photoId) {
}
UserId userId = 0;
PhotoId photoId = 0;
};
struct UserPhotosAddNew {
UserPhotosAddNew(UserId userId, PhotoId photoId)
: userId(userId), photoId(photoId) {
@ -71,10 +81,13 @@ struct UserPhotosKey {
: userId(userId)
, photoId(photoId) {
}
UserPhotosKey(UserId userId, bool back) : userId(userId), back(back) {
}
bool operator==(const UserPhotosKey &other) const {
return (userId == other.userId)
&& (photoId == other.photoId);
&& (photoId == other.photoId)
&& (back == other.back);
}
bool operator!=(const UserPhotosKey &other) const {
return !(*this == other);
@ -82,6 +95,7 @@ struct UserPhotosKey {
UserId userId = 0;
PhotoId photoId = 0;
bool back = false;
};
@ -125,6 +139,7 @@ struct UserPhotosSliceUpdate {
class UserPhotos {
public:
void add(UserPhotosSetBack &&query);
void add(UserPhotosAddNew &&query);
void add(UserPhotosAddSlice &&query);
void remove(UserPhotosRemoveOne &&query);
@ -136,6 +151,7 @@ public:
private:
class List {
public:
void setBack(PhotoId photoId);
void addNew(PhotoId photoId);
void addSlice(
std::vector<PhotoId> &&photoIds,
@ -152,10 +168,14 @@ private:
private:
void sendUpdate();
void detachBack();
void attachBack();
std::optional<int> _count;
std::deque<PhotoId> _photoIds;
PhotoId _backPhotoId = PhotoId(0);
rpl::event_stream<SliceUpdate> _sliceUpdated;
};