mirror of
https://github.com/AyuGram/AyuGramDesktop.git
synced 2025-06-05 06:33:57 +02:00
Keep separate MTP::Config's for separate accounts.
This commit is contained in:
parent
63cdda2df7
commit
357caf8007
142 changed files with 1901 additions and 1263 deletions
|
@ -755,8 +755,6 @@ PRIVATE
|
||||||
mtproto/connection_tcp.cpp
|
mtproto/connection_tcp.cpp
|
||||||
mtproto/connection_tcp.h
|
mtproto/connection_tcp.h
|
||||||
mtproto/core_types.h
|
mtproto/core_types.h
|
||||||
mtproto/dc_options.cpp
|
|
||||||
mtproto/dc_options.h
|
|
||||||
mtproto/dedicated_file_loader.cpp
|
mtproto/dedicated_file_loader.cpp
|
||||||
mtproto/dedicated_file_loader.h
|
mtproto/dedicated_file_loader.h
|
||||||
mtproto/facade.cpp
|
mtproto/facade.cpp
|
||||||
|
@ -912,6 +910,8 @@ PRIVATE
|
||||||
storage/serialize_common.h
|
storage/serialize_common.h
|
||||||
storage/serialize_document.cpp
|
storage/serialize_document.cpp
|
||||||
storage/serialize_document.h
|
storage/serialize_document.h
|
||||||
|
storage/serialize_peer.cpp
|
||||||
|
storage/serialize_peer.h
|
||||||
storage/storage_account.cpp
|
storage/storage_account.cpp
|
||||||
storage/storage_account.h
|
storage/storage_account.h
|
||||||
storage/storage_accounts.cpp
|
storage/storage_accounts.cpp
|
||||||
|
|
|
@ -12,7 +12,7 @@ https://github.com/telegramdesktop/tdesktop/blob/master/LEGAL
|
||||||
namespace Api {
|
namespace Api {
|
||||||
|
|
||||||
SelfDestruct::SelfDestruct(not_null<ApiWrap*> api)
|
SelfDestruct::SelfDestruct(not_null<ApiWrap*> api)
|
||||||
: _api(api->instance()) {
|
: _api(&api->instance()) {
|
||||||
}
|
}
|
||||||
|
|
||||||
void SelfDestruct::reload() {
|
void SelfDestruct::reload() {
|
||||||
|
|
|
@ -21,7 +21,7 @@ constexpr auto kRefreshAppConfigTimeout = 3 * crl::time(1000);
|
||||||
|
|
||||||
SensitiveContent::SensitiveContent(not_null<ApiWrap*> api)
|
SensitiveContent::SensitiveContent(not_null<ApiWrap*> api)
|
||||||
: _session(&api->session())
|
: _session(&api->session())
|
||||||
, _api(api->instance())
|
, _api(&api->instance())
|
||||||
, _appConfigReloadTimer([=] { _session->account().appConfig().refresh(); }) {
|
, _appConfigReloadTimer([=] { _session->account().appConfig().refresh(); }) {
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
|
@ -11,7 +11,8 @@ https://github.com/telegramdesktop/tdesktop/blob/master/LEGAL
|
||||||
#include "main/main_session.h"
|
#include "main/main_session.h"
|
||||||
#include "main/main_account.h"
|
#include "main/main_account.h"
|
||||||
#include "mtproto/mtp_instance.h"
|
#include "mtproto/mtp_instance.h"
|
||||||
#include "mtproto/dc_options.h"
|
#include "mtproto/mtproto_config.h"
|
||||||
|
#include "mtproto/mtproto_dc_options.h"
|
||||||
#include "data/stickers/data_stickers.h"
|
#include "data/stickers/data_stickers.h"
|
||||||
#include "data/data_session.h"
|
#include "data/data_session.h"
|
||||||
#include "data/data_user.h"
|
#include "data/data_user.h"
|
||||||
|
@ -39,7 +40,6 @@ https://github.com/telegramdesktop/tdesktop/blob/master/LEGAL
|
||||||
#include "boxes/confirm_box.h"
|
#include "boxes/confirm_box.h"
|
||||||
#include "apiwrap.h"
|
#include "apiwrap.h"
|
||||||
#include "app.h" // App::formatPhone
|
#include "app.h" // App::formatPhone
|
||||||
#include "facades.h"
|
|
||||||
|
|
||||||
namespace Api {
|
namespace Api {
|
||||||
namespace {
|
namespace {
|
||||||
|
@ -340,7 +340,9 @@ void Updates::channelDifferenceDone(
|
||||||
channel->ptsSetRequesting(false);
|
channel->ptsSetRequesting(false);
|
||||||
|
|
||||||
if (!isFinal) {
|
if (!isFinal) {
|
||||||
MTP_LOG(0, ("getChannelDifference { good - after not final channelDifference was received }%1").arg(cTestMode() ? " TESTMODE" : ""));
|
MTP_LOG(0, ("getChannelDifference "
|
||||||
|
"{ good - after not final channelDifference was received }%1"
|
||||||
|
).arg(_session->mtp().isTestMode() ? " TESTMODE" : ""));
|
||||||
getChannelDifference(channel);
|
getChannelDifference(channel);
|
||||||
} else if (ranges::contains(
|
} else if (ranges::contains(
|
||||||
_activeChats,
|
_activeChats,
|
||||||
|
@ -410,7 +412,9 @@ void Updates::differenceDone(const MTPupdates_Difference &result) {
|
||||||
|
|
||||||
_ptsWaiter.setRequesting(false);
|
_ptsWaiter.setRequesting(false);
|
||||||
|
|
||||||
MTP_LOG(0, ("getDifference { good - after a slice of difference was received }%1").arg(cTestMode() ? " TESTMODE" : ""));
|
MTP_LOG(0, ("getDifference "
|
||||||
|
"{ good - after a slice of difference was received }%1"
|
||||||
|
).arg(_session->mtp().isTestMode() ? " TESTMODE" : ""));
|
||||||
getDifference();
|
getDifference();
|
||||||
} break;
|
} break;
|
||||||
case mtpc_updates_difference: {
|
case mtpc_updates_difference: {
|
||||||
|
@ -566,7 +570,9 @@ void Updates::getDifferenceAfterFail() {
|
||||||
wait = _getDifferenceTimeAfterFail - now;
|
wait = _getDifferenceTimeAfterFail - now;
|
||||||
} else {
|
} else {
|
||||||
_ptsWaiter.setRequesting(false);
|
_ptsWaiter.setRequesting(false);
|
||||||
MTP_LOG(0, ("getDifference { force - after get difference failed }%1").arg(cTestMode() ? " TESTMODE" : ""));
|
MTP_LOG(0, ("getDifference "
|
||||||
|
"{ force - after get difference failed }%1"
|
||||||
|
).arg(_session->mtp().isTestMode() ? " TESTMODE" : ""));
|
||||||
getDifference();
|
getDifference();
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
@ -650,7 +656,7 @@ void Updates::getChannelDifference(
|
||||||
}
|
}
|
||||||
|
|
||||||
void Updates::sendPing() {
|
void Updates::sendPing() {
|
||||||
_session->mtp()->ping();
|
_session->mtp().ping();
|
||||||
}
|
}
|
||||||
|
|
||||||
void Updates::addActiveChat(rpl::producer<PeerData*> chat) {
|
void Updates::addActiveChat(rpl::producer<PeerData*> chat) {
|
||||||
|
@ -680,9 +686,10 @@ void Updates::requestChannelRangeDifference(not_null<History*> history) {
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
|
|
||||||
MTP_LOG(0, ("getChannelDifference { good - "
|
MTP_LOG(0, ("getChannelDifference "
|
||||||
"after channelDifferenceTooLong was received, "
|
"{ good - after channelDifferenceTooLong was received, "
|
||||||
"validating history part }%1").arg(cTestMode() ? " TESTMODE" : ""));
|
"validating history part }%1"
|
||||||
|
).arg(_session->mtp().isTestMode() ? " TESTMODE" : ""));
|
||||||
channelRangeDifferenceSend(channel, range, channel->pts());
|
channelRangeDifferenceSend(channel, range, channel->pts());
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -752,10 +759,10 @@ void Updates::channelRangeDifferenceDone(
|
||||||
}
|
}
|
||||||
|
|
||||||
if (!isFinal && nextRequestPts) {
|
if (!isFinal && nextRequestPts) {
|
||||||
MTP_LOG(0, ("getChannelDifference { "
|
MTP_LOG(0, ("getChannelDifference "
|
||||||
"good - after not final channelDifference was received, "
|
"{ good - after not final channelDifference was received, "
|
||||||
"validating history part }%1"
|
"validating history part }%1"
|
||||||
).arg(cTestMode() ? " TESTMODE" : ""));
|
).arg(_session->mtp().isTestMode() ? " TESTMODE" : ""));
|
||||||
channelRangeDifferenceSend(channel, range, nextRequestPts);
|
channelRangeDifferenceSend(channel, range, nextRequestPts);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
@ -764,7 +771,7 @@ void Updates::mtpNewSessionCreated() {
|
||||||
Core::App().checkAutoLock();
|
Core::App().checkAutoLock();
|
||||||
_updatesSeq = 0;
|
_updatesSeq = 0;
|
||||||
MTP_LOG(0, ("getDifference { after new_session_created }%1"
|
MTP_LOG(0, ("getDifference { after new_session_created }%1"
|
||||||
).arg(cTestMode() ? " TESTMODE" : ""));
|
).arg(_session->mtp().isTestMode() ? " TESTMODE" : ""));
|
||||||
getDifference();
|
getDifference();
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -789,25 +796,26 @@ bool Updates::isIdle() const {
|
||||||
void Updates::updateOnline(bool gotOtherOffline) {
|
void Updates::updateOnline(bool gotOtherOffline) {
|
||||||
crl::on_main(&session(), [] { Core::App().checkAutoLock(); });
|
crl::on_main(&session(), [] { Core::App().checkAutoLock(); });
|
||||||
|
|
||||||
|
const auto &config = _session->serverConfig();
|
||||||
bool isOnline = Core::App().hasActiveWindow(&session());
|
bool isOnline = Core::App().hasActiveWindow(&session());
|
||||||
int updateIn = Global::OnlineUpdatePeriod();
|
int updateIn = config.onlineUpdatePeriod;
|
||||||
Assert(updateIn >= 0);
|
Assert(updateIn >= 0);
|
||||||
if (isOnline) {
|
if (isOnline) {
|
||||||
const auto idle = crl::now() - Core::App().lastNonIdleTime();
|
const auto idle = crl::now() - Core::App().lastNonIdleTime();
|
||||||
if (idle >= Global::OfflineIdleTimeout()) {
|
if (idle >= config.offlineIdleTimeout) {
|
||||||
isOnline = false;
|
isOnline = false;
|
||||||
if (!_isIdle) {
|
if (!_isIdle) {
|
||||||
_isIdle = true;
|
_isIdle = true;
|
||||||
_idleFinishTimer.callOnce(900);
|
_idleFinishTimer.callOnce(900);
|
||||||
}
|
}
|
||||||
} else {
|
} else {
|
||||||
updateIn = qMin(updateIn, int(Global::OfflineIdleTimeout() - idle));
|
updateIn = qMin(updateIn, int(config.offlineIdleTimeout - idle));
|
||||||
Assert(updateIn >= 0);
|
Assert(updateIn >= 0);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
auto ms = crl::now();
|
auto ms = crl::now();
|
||||||
if (isOnline != _lastWasOnline
|
if (isOnline != _lastWasOnline
|
||||||
|| (isOnline && _lastSetOnline + Global::OnlineUpdatePeriod() <= ms)
|
|| (isOnline && _lastSetOnline + config.onlineUpdatePeriod <= ms)
|
||||||
|| (isOnline && gotOtherOffline)) {
|
|| (isOnline && gotOtherOffline)) {
|
||||||
api().request(base::take(_onlineRequest)).cancel();
|
api().request(base::take(_onlineRequest)).cancel();
|
||||||
|
|
||||||
|
@ -828,7 +836,7 @@ void Updates::updateOnline(bool gotOtherOffline) {
|
||||||
}
|
}
|
||||||
|
|
||||||
const auto self = session().user();
|
const auto self = session().user();
|
||||||
self->onlineTill = base::unixtime::now() + (isOnline ? (Global::OnlineUpdatePeriod() / 1000) : -1);
|
self->onlineTill = base::unixtime::now() + (isOnline ? (config.onlineUpdatePeriod / 1000) : -1);
|
||||||
session().changes().peerUpdated(
|
session().changes().peerUpdated(
|
||||||
self,
|
self,
|
||||||
Data::PeerUpdate::Flag::OnlineStatus);
|
Data::PeerUpdate::Flag::OnlineStatus);
|
||||||
|
@ -838,7 +846,7 @@ void Updates::updateOnline(bool gotOtherOffline) {
|
||||||
|
|
||||||
_lastSetOnline = ms;
|
_lastSetOnline = ms;
|
||||||
} else if (isOnline) {
|
} else if (isOnline) {
|
||||||
updateIn = qMin(updateIn, int(_lastSetOnline + Global::OnlineUpdatePeriod() - ms));
|
updateIn = qMin(updateIn, int(_lastSetOnline + config.onlineUpdatePeriod - ms));
|
||||||
Assert(updateIn >= 0);
|
Assert(updateIn >= 0);
|
||||||
}
|
}
|
||||||
_onlineTimer.callOnce(updateIn);
|
_onlineTimer.callOnce(updateIn);
|
||||||
|
@ -846,7 +854,7 @@ void Updates::updateOnline(bool gotOtherOffline) {
|
||||||
|
|
||||||
void Updates::checkIdleFinish() {
|
void Updates::checkIdleFinish() {
|
||||||
if (crl::now() - Core::App().lastNonIdleTime()
|
if (crl::now() - Core::App().lastNonIdleTime()
|
||||||
< Global::OfflineIdleTimeout()) {
|
< _session->serverConfig().offlineIdleTimeout) {
|
||||||
_idleFinishTimer.cancel();
|
_idleFinishTimer.cancel();
|
||||||
_isIdle = false;
|
_isIdle = false;
|
||||||
updateOnline();
|
updateOnline();
|
||||||
|
@ -1153,7 +1161,9 @@ void Updates::applyUpdates(
|
||||||
|| (viaBotId && !session().data().userLoaded(viaBotId->v))
|
|| (viaBotId && !session().data().userLoaded(viaBotId->v))
|
||||||
|| (entities && !MentionUsersLoaded(&session(), *entities))
|
|| (entities && !MentionUsersLoaded(&session(), *entities))
|
||||||
|| (fwd && !ForwardedInfoDataLoaded(&session(), *fwd))) {
|
|| (fwd && !ForwardedInfoDataLoaded(&session(), *fwd))) {
|
||||||
MTP_LOG(0, ("getDifference { good - getting user for updateShortMessage }%1").arg(cTestMode() ? " TESTMODE" : ""));
|
MTP_LOG(0, ("getDifference "
|
||||||
|
"{ good - getting user for updateShortMessage }%1"
|
||||||
|
).arg(_session->mtp().isTestMode() ? " TESTMODE" : ""));
|
||||||
return getDifference();
|
return getDifference();
|
||||||
}
|
}
|
||||||
if (updateAndApply(d.vpts().v, d.vpts_count().v, updates)) {
|
if (updateAndApply(d.vpts().v, d.vpts_count().v, updates)) {
|
||||||
|
@ -1174,7 +1184,9 @@ void Updates::applyUpdates(
|
||||||
|| (viaBotId && !session().data().userLoaded(viaBotId->v))
|
|| (viaBotId && !session().data().userLoaded(viaBotId->v))
|
||||||
|| (entities && !MentionUsersLoaded(&session(), *entities))
|
|| (entities && !MentionUsersLoaded(&session(), *entities))
|
||||||
|| (fwd && !ForwardedInfoDataLoaded(&session(), *fwd))) {
|
|| (fwd && !ForwardedInfoDataLoaded(&session(), *fwd))) {
|
||||||
MTP_LOG(0, ("getDifference { good - getting user for updateShortChatMessage }%1").arg(cTestMode() ? " TESTMODE" : ""));
|
MTP_LOG(0, ("getDifference "
|
||||||
|
"{ good - getting user for updateShortChatMessage }%1"
|
||||||
|
).arg(_session->mtp().isTestMode() ? " TESTMODE" : ""));
|
||||||
if (chat && noFrom) {
|
if (chat && noFrom) {
|
||||||
session().api().requestFullPeer(chat);
|
session().api().requestFullPeer(chat);
|
||||||
}
|
}
|
||||||
|
@ -1232,7 +1244,9 @@ void Updates::applyUpdates(
|
||||||
} break;
|
} break;
|
||||||
|
|
||||||
case mtpc_updatesTooLong: {
|
case mtpc_updatesTooLong: {
|
||||||
MTP_LOG(0, ("getDifference { good - updatesTooLong received }%1").arg(cTestMode() ? " TESTMODE" : ""));
|
MTP_LOG(0, ("getDifference "
|
||||||
|
"{ good - updatesTooLong received }%1"
|
||||||
|
).arg(_session->mtp().isTestMode() ? " TESTMODE" : ""));
|
||||||
return getDifference();
|
return getDifference();
|
||||||
} break;
|
} break;
|
||||||
}
|
}
|
||||||
|
@ -1248,9 +1262,9 @@ void Updates::feedUpdate(const MTPUpdate &update) {
|
||||||
|
|
||||||
const auto isDataLoaded = AllDataLoadedForMessage(&session(), d.vmessage());
|
const auto isDataLoaded = AllDataLoadedForMessage(&session(), d.vmessage());
|
||||||
if (!requestingDifference() && isDataLoaded != DataIsLoadedResult::Ok) {
|
if (!requestingDifference() && isDataLoaded != DataIsLoadedResult::Ok) {
|
||||||
MTP_LOG(0, ("getDifference { good - "
|
MTP_LOG(0, ("getDifference "
|
||||||
"after not all data loaded in updateNewMessage }%1"
|
"{ good - after not all data loaded in updateNewMessage }%1"
|
||||||
).arg(cTestMode() ? " TESTMODE" : ""));
|
).arg(_session->mtp().isTestMode() ? " TESTMODE" : ""));
|
||||||
|
|
||||||
// This can be if this update was created by grouping
|
// This can be if this update was created by grouping
|
||||||
// some short message update into an updates vector.
|
// some short message update into an updates vector.
|
||||||
|
@ -1265,14 +1279,16 @@ void Updates::feedUpdate(const MTPUpdate &update) {
|
||||||
auto channel = session().data().channelLoaded(peerToChannel(PeerFromMessage(d.vmessage())));
|
auto channel = session().data().channelLoaded(peerToChannel(PeerFromMessage(d.vmessage())));
|
||||||
const auto isDataLoaded = AllDataLoadedForMessage(&session(), d.vmessage());
|
const auto isDataLoaded = AllDataLoadedForMessage(&session(), d.vmessage());
|
||||||
if (!requestingDifference() && (!channel || isDataLoaded != DataIsLoadedResult::Ok)) {
|
if (!requestingDifference() && (!channel || isDataLoaded != DataIsLoadedResult::Ok)) {
|
||||||
MTP_LOG(0, ("getDifference { good - "
|
MTP_LOG(0, ("getDifference "
|
||||||
"after not all data loaded in updateNewChannelMessage }%1"
|
"{ good - after not all data loaded in updateNewChannelMessage }%1"
|
||||||
).arg(cTestMode() ? " TESTMODE" : ""));
|
).arg(_session->mtp().isTestMode() ? " TESTMODE" : ""));
|
||||||
|
|
||||||
// Request last active supergroup participants if the 'from' user was not loaded yet.
|
// Request last active supergroup participants if the 'from' user was not loaded yet.
|
||||||
// This will optimize similar getDifference() calls for almost all next messages.
|
// This will optimize similar getDifference() calls for almost all next messages.
|
||||||
if (isDataLoaded == DataIsLoadedResult::FromNotLoaded && channel && channel->isMegagroup()) {
|
if (isDataLoaded == DataIsLoadedResult::FromNotLoaded && channel && channel->isMegagroup()) {
|
||||||
if (channel->mgInfo->lastParticipants.size() < Global::ChatSizeMax() && (channel->mgInfo->lastParticipants.empty() || channel->mgInfo->lastParticipants.size() < channel->membersCount())) {
|
if (channel->mgInfo->lastParticipants.size() < _session->serverConfig().chatSizeMax
|
||||||
|
&& (channel->mgInfo->lastParticipants.empty()
|
||||||
|
|| channel->mgInfo->lastParticipants.size() < channel->membersCount())) {
|
||||||
session().api().requestLastParticipants(channel);
|
session().api().requestLastParticipants(channel);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
@ -1657,11 +1673,11 @@ void Updates::feedUpdate(const MTPUpdate &update) {
|
||||||
|
|
||||||
case mtpc_updateDcOptions: {
|
case mtpc_updateDcOptions: {
|
||||||
auto &d = update.c_updateDcOptions();
|
auto &d = update.c_updateDcOptions();
|
||||||
Core::App().dcOptions()->addFromList(d.vdc_options());
|
session().mtp().dcOptions().addFromList(d.vdc_options());
|
||||||
} break;
|
} break;
|
||||||
|
|
||||||
case mtpc_updateConfig: {
|
case mtpc_updateConfig: {
|
||||||
session().mtp()->requestConfig();
|
session().mtp().requestConfig();
|
||||||
} break;
|
} break;
|
||||||
|
|
||||||
case mtpc_updateUserPhone: {
|
case mtpc_updateUserPhone: {
|
||||||
|
|
|
@ -43,6 +43,7 @@ https://github.com/telegramdesktop/tdesktop/blob/master/LEGAL
|
||||||
#include "mainwindow.h"
|
#include "mainwindow.h"
|
||||||
#include "mainwidget.h"
|
#include "mainwidget.h"
|
||||||
#include "boxes/add_contact_box.h"
|
#include "boxes/add_contact_box.h"
|
||||||
|
#include "mtproto/mtproto_config.h"
|
||||||
#include "history/history.h"
|
#include "history/history.h"
|
||||||
#include "history/history_message.h"
|
#include "history/history_message.h"
|
||||||
#include "history/history_item_components.h"
|
#include "history/history_item_components.h"
|
||||||
|
@ -231,7 +232,7 @@ bool ApiWrap::BlockedUsersSlice::operator!=(const BlockedUsersSlice &other) cons
|
||||||
}
|
}
|
||||||
|
|
||||||
ApiWrap::ApiWrap(not_null<Main::Session*> session)
|
ApiWrap::ApiWrap(not_null<Main::Session*> session)
|
||||||
: MTP::Sender(session->account().mtp())
|
: MTP::Sender(&session->account().mtp())
|
||||||
, _session(session)
|
, _session(session)
|
||||||
, _messageDataResolveDelayed([=] { resolveMessageDatas(); })
|
, _messageDataResolveDelayed([=] { resolveMessageDatas(); })
|
||||||
, _webPagesTimer([=] { resolveWebPages(); })
|
, _webPagesTimer([=] { resolveWebPages(); })
|
||||||
|
@ -572,10 +573,10 @@ void ApiWrap::sendMessageFail(
|
||||||
FullMsgId itemId) {
|
FullMsgId itemId) {
|
||||||
if (error.type() == qstr("PEER_FLOOD")) {
|
if (error.type() == qstr("PEER_FLOOD")) {
|
||||||
Ui::show(Box<InformBox>(
|
Ui::show(Box<InformBox>(
|
||||||
PeerFloodErrorText(PeerFloodType::Send)));
|
PeerFloodErrorText(&session(), PeerFloodType::Send)));
|
||||||
} else if (error.type() == qstr("USER_BANNED_IN_CHANNEL")) {
|
} else if (error.type() == qstr("USER_BANNED_IN_CHANNEL")) {
|
||||||
const auto link = textcmdLink(
|
const auto link = textcmdLink(
|
||||||
Core::App().createInternalLinkFull(qsl("spambot")),
|
session().createInternalLinkFull(qsl("spambot")),
|
||||||
tr::lng_cant_more_info(tr::now));
|
tr::lng_cant_more_info(tr::now));
|
||||||
Ui::show(Box<InformBox>(tr::lng_error_public_groups_denied(
|
Ui::show(Box<InformBox>(tr::lng_error_public_groups_denied(
|
||||||
tr::now,
|
tr::now,
|
||||||
|
@ -754,7 +755,7 @@ QString ApiWrap::exportDirectMessageLink(not_null<HistoryItem*> item) {
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
return Core::App().createInternalLinkFull(query);
|
return session().createInternalLinkFull(query);
|
||||||
};
|
};
|
||||||
const auto i = _unlikelyMessageLinks.find(itemId);
|
const auto i = _unlikelyMessageLinks.find(itemId);
|
||||||
const auto current = (i != end(_unlikelyMessageLinks))
|
const auto current = (i != end(_unlikelyMessageLinks))
|
||||||
|
@ -1450,7 +1451,7 @@ void ApiWrap::requestLastParticipants(not_null<ChannelData*> channel) {
|
||||||
channel->inputChannel,
|
channel->inputChannel,
|
||||||
MTP_channelParticipantsRecent(),
|
MTP_channelParticipantsRecent(),
|
||||||
MTP_int(offset),
|
MTP_int(offset),
|
||||||
MTP_int(Global::ChatSizeMax()),
|
MTP_int(_session->serverConfig().chatSizeMax),
|
||||||
MTP_int(participantsHash)
|
MTP_int(participantsHash)
|
||||||
)).done([=](const MTPchannels_ChannelParticipants &result) {
|
)).done([=](const MTPchannels_ChannelParticipants &result) {
|
||||||
_participantsRequests.remove(channel);
|
_participantsRequests.remove(channel);
|
||||||
|
@ -1480,7 +1481,7 @@ void ApiWrap::requestBots(not_null<ChannelData*> channel) {
|
||||||
channel->inputChannel,
|
channel->inputChannel,
|
||||||
MTP_channelParticipantsBots(),
|
MTP_channelParticipantsBots(),
|
||||||
MTP_int(offset),
|
MTP_int(offset),
|
||||||
MTP_int(Global::ChatSizeMax()),
|
MTP_int(_session->serverConfig().chatSizeMax),
|
||||||
MTP_int(participantsHash)
|
MTP_int(participantsHash)
|
||||||
)).done([this, channel](const MTPchannels_ChannelParticipants &result) {
|
)).done([this, channel](const MTPchannels_ChannelParticipants &result) {
|
||||||
_botsRequests.remove(channel);
|
_botsRequests.remove(channel);
|
||||||
|
@ -1510,7 +1511,7 @@ void ApiWrap::requestAdmins(not_null<ChannelData*> channel) {
|
||||||
channel->inputChannel,
|
channel->inputChannel,
|
||||||
MTP_channelParticipantsAdmins(),
|
MTP_channelParticipantsAdmins(),
|
||||||
MTP_int(offset),
|
MTP_int(offset),
|
||||||
MTP_int(Global::ChatSizeMax()),
|
MTP_int(_session->serverConfig().chatSizeMax),
|
||||||
MTP_int(participantsHash)
|
MTP_int(participantsHash)
|
||||||
)).done([this, channel](const MTPchannels_ChannelParticipants &result) {
|
)).done([this, channel](const MTPchannels_ChannelParticipants &result) {
|
||||||
_adminsRequests.remove(channel);
|
_adminsRequests.remove(channel);
|
||||||
|
@ -1820,7 +1821,7 @@ void ApiWrap::requestChannelMembersForAdd(
|
||||||
channel->inputChannel,
|
channel->inputChannel,
|
||||||
MTP_channelParticipantsRecent(),
|
MTP_channelParticipantsRecent(),
|
||||||
MTP_int(offset),
|
MTP_int(offset),
|
||||||
MTP_int(Global::ChatSizeMax()),
|
MTP_int(_session->serverConfig().chatSizeMax),
|
||||||
MTP_int(participantsHash)
|
MTP_int(participantsHash)
|
||||||
)).done([this](const MTPchannels_ChannelParticipants &result) {
|
)).done([this](const MTPchannels_ChannelParticipants &result) {
|
||||||
base::take(_channelMembersForAddRequestId);
|
base::take(_channelMembersForAddRequestId);
|
||||||
|
@ -5038,7 +5039,10 @@ FileLoadTo ApiWrap::fileLoadTaskOptions(const SendAction &action) const {
|
||||||
|
|
||||||
void ApiWrap::uploadPeerPhoto(not_null<PeerData*> peer, QImage &&image) {
|
void ApiWrap::uploadPeerPhoto(not_null<PeerData*> peer, QImage &&image) {
|
||||||
peer = peer->migrateToOrMe();
|
peer = peer->migrateToOrMe();
|
||||||
const auto ready = PreparePeerPhoto(instance()->mainDcId(), peer->id, std::move(image));
|
const auto ready = PreparePeerPhoto(
|
||||||
|
instance().mainDcId(),
|
||||||
|
peer->id,
|
||||||
|
std::move(image));
|
||||||
|
|
||||||
const auto fakeId = FullMsgId(
|
const auto fakeId = FullMsgId(
|
||||||
peerToChannel(peer->id),
|
peerToChannel(peer->id),
|
||||||
|
|
|
@ -118,9 +118,11 @@ style::InputField CreateBioFieldStyle() {
|
||||||
return result;
|
return result;
|
||||||
}
|
}
|
||||||
|
|
||||||
QString PeerFloodErrorText(PeerFloodType type) {
|
QString PeerFloodErrorText(
|
||||||
auto link = textcmdLink(
|
not_null<Main::Session*> session,
|
||||||
Core::App().createInternalLinkFull(qsl("spambot")),
|
PeerFloodType type) {
|
||||||
|
const auto link = textcmdLink(
|
||||||
|
session->createInternalLinkFull(qsl("spambot")),
|
||||||
tr::lng_cant_more_info(tr::now));
|
tr::lng_cant_more_info(tr::now));
|
||||||
if (type == PeerFloodType::InviteGroup) {
|
if (type == PeerFloodType::InviteGroup) {
|
||||||
return tr::lng_cant_invite_not_contact(tr::now, lt_more_info, link);
|
return tr::lng_cant_invite_not_contact(tr::now, lt_more_info, link);
|
||||||
|
@ -190,10 +192,10 @@ void ShowAddParticipantsError(
|
||||||
} else if (error == qstr("BOT_GROUPS_BLOCKED")) {
|
} else if (error == qstr("BOT_GROUPS_BLOCKED")) {
|
||||||
return tr::lng_error_cant_add_bot(tr::now);
|
return tr::lng_error_cant_add_bot(tr::now);
|
||||||
} else if (error == qstr("PEER_FLOOD")) {
|
} else if (error == qstr("PEER_FLOOD")) {
|
||||||
const auto isGroup = (chat->isChat() || chat->isMegagroup());
|
const auto type = (chat->isChat() || chat->isMegagroup())
|
||||||
return PeerFloodErrorText(isGroup
|
|
||||||
? PeerFloodType::InviteGroup
|
? PeerFloodType::InviteGroup
|
||||||
: PeerFloodType::InviteChannel);
|
: PeerFloodType::InviteChannel;
|
||||||
|
return PeerFloodErrorText(&chat->session(), type);
|
||||||
} else if (error == qstr("ADMINS_TOO_MUCH")) {
|
} else if (error == qstr("ADMINS_TOO_MUCH")) {
|
||||||
return ((chat->isChat() || chat->isMegagroup())
|
return ((chat->isChat() || chat->isMegagroup())
|
||||||
? tr::lng_error_admin_limit
|
? tr::lng_error_admin_limit
|
||||||
|
@ -453,7 +455,7 @@ GroupInfoBox::GroupInfoBox(
|
||||||
const QString &title,
|
const QString &title,
|
||||||
Fn<void(not_null<ChannelData*>)> channelDone)
|
Fn<void(not_null<ChannelData*>)> channelDone)
|
||||||
: _navigation(navigation)
|
: _navigation(navigation)
|
||||||
, _api(_navigation->session().mtp())
|
, _api(&_navigation->session().mtp())
|
||||||
, _type(type)
|
, _type(type)
|
||||||
, _initialTitle(title)
|
, _initialTitle(title)
|
||||||
, _channelDone(std::move(channelDone)) {
|
, _channelDone(std::move(channelDone)) {
|
||||||
|
@ -598,7 +600,9 @@ void GroupInfoBox::createGroup(
|
||||||
} else if (error.type() == qstr("PEER_FLOOD")) {
|
} else if (error.type() == qstr("PEER_FLOOD")) {
|
||||||
Ui::show(
|
Ui::show(
|
||||||
Box<InformBox>(
|
Box<InformBox>(
|
||||||
PeerFloodErrorText(PeerFloodType::InviteGroup)),
|
PeerFloodErrorText(
|
||||||
|
&_navigation->session(),
|
||||||
|
PeerFloodType::InviteGroup)),
|
||||||
Ui::LayerOption::KeepOther);
|
Ui::LayerOption::KeepOther);
|
||||||
} else if (error.type() == qstr("USER_RESTRICTED")) {
|
} else if (error.type() == qstr("USER_RESTRICTED")) {
|
||||||
Ui::show(
|
Ui::show(
|
||||||
|
@ -750,7 +754,7 @@ SetupChannelBox::SetupChannelBox(
|
||||||
bool existing)
|
bool existing)
|
||||||
: _navigation(navigation)
|
: _navigation(navigation)
|
||||||
, _channel(channel)
|
, _channel(channel)
|
||||||
, _api(_channel->session().mtp())
|
, _api(&_channel->session().mtp())
|
||||||
, _existing(existing)
|
, _existing(existing)
|
||||||
, _privacyGroup(
|
, _privacyGroup(
|
||||||
std::make_shared<Ui::RadioenumGroup<Privacy>>(Privacy::Public))
|
std::make_shared<Ui::RadioenumGroup<Privacy>>(Privacy::Public))
|
||||||
|
@ -790,7 +794,12 @@ SetupChannelBox::SetupChannelBox(
|
||||||
: tr::lng_create_private_channel_about)(tr::now),
|
: tr::lng_create_private_channel_about)(tr::now),
|
||||||
_defaultOptions,
|
_defaultOptions,
|
||||||
_aboutPublicWidth)
|
_aboutPublicWidth)
|
||||||
, _link(this, st::setupChannelLink, nullptr, channel->username, true) {
|
, _link(
|
||||||
|
this,
|
||||||
|
st::setupChannelLink,
|
||||||
|
nullptr,
|
||||||
|
channel->username,
|
||||||
|
channel->session().createInternalLink(QString())) {
|
||||||
}
|
}
|
||||||
|
|
||||||
void SetupChannelBox::prepare() {
|
void SetupChannelBox::prepare() {
|
||||||
|
@ -1168,7 +1177,7 @@ void SetupChannelBox::firstCheckFail(const RPCError &error) {
|
||||||
|
|
||||||
EditNameBox::EditNameBox(QWidget*, not_null<UserData*> user)
|
EditNameBox::EditNameBox(QWidget*, not_null<UserData*> user)
|
||||||
: _user(user)
|
: _user(user)
|
||||||
, _api(_user->session().mtp())
|
, _api(&_user->session().mtp())
|
||||||
, _first(this, st::defaultInputField, tr::lng_signup_firstname(), _user->firstName)
|
, _first(this, st::defaultInputField, tr::lng_signup_firstname(), _user->firstName)
|
||||||
, _last(this, st::defaultInputField, tr::lng_signup_lastname(), _user->lastName)
|
, _last(this, st::defaultInputField, tr::lng_signup_lastname(), _user->lastName)
|
||||||
, _invertOrder(langFirstNameGoesSecond()) {
|
, _invertOrder(langFirstNameGoesSecond()) {
|
||||||
|
@ -1292,7 +1301,7 @@ RevokePublicLinkBox::Inner::Inner(
|
||||||
Fn<void()> revokeCallback)
|
Fn<void()> revokeCallback)
|
||||||
: TWidget(parent)
|
: TWidget(parent)
|
||||||
, _session(session)
|
, _session(session)
|
||||||
, _api(_session->mtp())
|
, _api(&_session->mtp())
|
||||||
, _rowHeight(st::contactsPadding.top() + st::contactsPhotoSize + st::contactsPadding.bottom())
|
, _rowHeight(st::contactsPadding.top() + st::contactsPhotoSize + st::contactsPadding.bottom())
|
||||||
, _revokeWidth(st::normalFont->width(tr::lng_channels_too_much_public_revoke(tr::now)))
|
, _revokeWidth(st::normalFont->width(tr::lng_channels_too_much_public_revoke(tr::now)))
|
||||||
, _revokeCallback(std::move(revokeCallback)) {
|
, _revokeCallback(std::move(revokeCallback)) {
|
||||||
|
@ -1320,7 +1329,7 @@ RevokePublicLinkBox::Inner::Inner(
|
||||||
Ui::NameTextOptions());
|
Ui::NameTextOptions());
|
||||||
row.status.setText(
|
row.status.setText(
|
||||||
st::defaultTextStyle,
|
st::defaultTextStyle,
|
||||||
Core::App().createInternalLink(
|
_session->createInternalLink(
|
||||||
textcmdLink(1, peer->userName())),
|
textcmdLink(1, peer->userName())),
|
||||||
Ui::DialogTextOptions());
|
Ui::DialogTextOptions());
|
||||||
_rows.push_back(std::move(row));
|
_rows.push_back(std::move(row));
|
||||||
|
@ -1401,7 +1410,7 @@ void RevokePublicLinkBox::Inner::mouseReleaseEvent(QMouseEvent *e) {
|
||||||
auto text = text_method(
|
auto text = text_method(
|
||||||
tr::now,
|
tr::now,
|
||||||
lt_link,
|
lt_link,
|
||||||
Core::App().createInternalLink(pressed->userName()),
|
_session->createInternalLink(pressed->userName()),
|
||||||
lt_group,
|
lt_group,
|
||||||
pressed->name);
|
pressed->name);
|
||||||
auto confirmText = tr::lng_channels_too_much_public_revoke(tr::now);
|
auto confirmText = tr::lng_channels_too_much_public_revoke(tr::now);
|
||||||
|
|
|
@ -46,9 +46,11 @@ enum class PeerFloodType {
|
||||||
InviteChannel,
|
InviteChannel,
|
||||||
};
|
};
|
||||||
|
|
||||||
style::InputField CreateBioFieldStyle();
|
[[nodiscard]] style::InputField CreateBioFieldStyle();
|
||||||
|
|
||||||
QString PeerFloodErrorText(PeerFloodType type);
|
[[nodiscard]] QString PeerFloodErrorText(
|
||||||
|
not_null<Main::Session*> session,
|
||||||
|
PeerFloodType type);
|
||||||
void ShowAddParticipantsError(
|
void ShowAddParticipantsError(
|
||||||
const QString &error,
|
const QString &error,
|
||||||
not_null<PeerData*> chat,
|
not_null<PeerData*> chat,
|
||||||
|
|
|
@ -193,7 +193,7 @@ BackgroundBox::Inner::Inner(
|
||||||
not_null<Main::Session*> session)
|
not_null<Main::Session*> session)
|
||||||
: RpWidget(parent)
|
: RpWidget(parent)
|
||||||
, _session(session)
|
, _session(session)
|
||||||
, _api(_session->mtp())
|
, _api(&_session->mtp())
|
||||||
, _check(std::make_unique<Ui::RoundCheckbox>(st::overviewCheck, [=] { update(); })) {
|
, _check(std::make_unique<Ui::RoundCheckbox>(st::overviewCheck, [=] { update(); })) {
|
||||||
_check->setChecked(true, anim::type::instant);
|
_check->setChecked(true, anim::type::instant);
|
||||||
if (_session->data().wallpapers().empty()) {
|
if (_session->data().wallpapers().empty()) {
|
||||||
|
|
|
@ -514,7 +514,8 @@ void BackgroundPreviewBox::apply() {
|
||||||
}
|
}
|
||||||
|
|
||||||
void BackgroundPreviewBox::share() {
|
void BackgroundPreviewBox::share() {
|
||||||
QGuiApplication::clipboard()->setText(_paper.shareUrl());
|
QGuiApplication::clipboard()->setText(
|
||||||
|
_paper.shareUrl(&_controller->session()));
|
||||||
Ui::Toast::Show(tr::lng_background_link_copied(tr::now));
|
Ui::Toast::Show(tr::lng_background_link_copied(tr::now));
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
|
@ -140,7 +140,7 @@ ChangePhoneBox::EnterPhone::EnterPhone(
|
||||||
QWidget*,
|
QWidget*,
|
||||||
not_null<Main::Session*> session)
|
not_null<Main::Session*> session)
|
||||||
: _session(session)
|
: _session(session)
|
||||||
, _api(session->mtp()) {
|
, _api(&session->mtp()) {
|
||||||
}
|
}
|
||||||
|
|
||||||
void ChangePhoneBox::EnterPhone::prepare() {
|
void ChangePhoneBox::EnterPhone::prepare() {
|
||||||
|
@ -257,7 +257,7 @@ ChangePhoneBox::EnterCode::EnterCode(
|
||||||
int codeLength,
|
int codeLength,
|
||||||
int callTimeout)
|
int callTimeout)
|
||||||
: _session(session)
|
: _session(session)
|
||||||
, _api(session->mtp())
|
, _api(&session->mtp())
|
||||||
, _phone(phone)
|
, _phone(phone)
|
||||||
, _hash(hash)
|
, _hash(hash)
|
||||||
, _codeLength(codeLength)
|
, _codeLength(codeLength)
|
||||||
|
|
|
@ -36,7 +36,8 @@ https://github.com/telegramdesktop/tdesktop/blob/master/LEGAL
|
||||||
#include "data/data_changes.h"
|
#include "data/data_changes.h"
|
||||||
#include "base/unixtime.h"
|
#include "base/unixtime.h"
|
||||||
#include "main/main_session.h"
|
#include "main/main_session.h"
|
||||||
#include "facades.h"
|
#include "mtproto/mtproto_config.h"
|
||||||
|
#include "facades.h" // Ui::showChatsList
|
||||||
#include "app.h"
|
#include "app.h"
|
||||||
#include "styles/style_layers.h"
|
#include "styles/style_layers.h"
|
||||||
#include "styles/style_boxes.h"
|
#include "styles/style_boxes.h"
|
||||||
|
@ -351,7 +352,7 @@ MaxInviteBox::MaxInviteBox(QWidget*, not_null<ChannelData*> channel) : BoxConten
|
||||||
tr::lng_participant_invite_sorry(
|
tr::lng_participant_invite_sorry(
|
||||||
tr::now,
|
tr::now,
|
||||||
lt_count,
|
lt_count,
|
||||||
Global::ChatSizeMax()),
|
channel->session().serverConfig().chatSizeMax),
|
||||||
kInformBoxTextOptions,
|
kInformBoxTextOptions,
|
||||||
(st::boxWidth
|
(st::boxWidth
|
||||||
- st::boxPadding.left()
|
- st::boxPadding.left()
|
||||||
|
@ -433,7 +434,7 @@ PinMessageBox::PinMessageBox(
|
||||||
not_null<PeerData*> peer,
|
not_null<PeerData*> peer,
|
||||||
MsgId msgId)
|
MsgId msgId)
|
||||||
: _peer(peer)
|
: _peer(peer)
|
||||||
, _api(peer->session().mtp())
|
, _api(&peer->session().mtp())
|
||||||
, _msgId(msgId)
|
, _msgId(msgId)
|
||||||
, _text(this, tr::lng_pinned_pin_sure(tr::now), st::boxLabel) {
|
, _text(this, tr::lng_pinned_pin_sure(tr::now), st::boxLabel) {
|
||||||
}
|
}
|
||||||
|
|
|
@ -225,7 +225,7 @@ ConfirmPhoneBox::ConfirmPhoneBox(
|
||||||
const QString &phone,
|
const QString &phone,
|
||||||
const QString &hash)
|
const QString &hash)
|
||||||
: _session(session)
|
: _session(session)
|
||||||
, _api(session->mtp())
|
, _api(&session->mtp())
|
||||||
, _phone(phone)
|
, _phone(phone)
|
||||||
, _hash(hash)
|
, _hash(hash)
|
||||||
, _call([this] { sendCall(); }, [this] { update(); }) {
|
, _call([this] { sendCall(); }, [this] { update(); }) {
|
||||||
|
|
|
@ -1059,9 +1059,7 @@ void ProxiesBoxController::refreshChecker(Item &item) {
|
||||||
const auto type = (item.data.type == Type::Http)
|
const auto type = (item.data.type == Type::Http)
|
||||||
? Variants::Http
|
? Variants::Http
|
||||||
: Variants::Tcp;
|
: Variants::Tcp;
|
||||||
const auto mtproto = _account->mtp();
|
const auto mtproto = &_account->mtp();
|
||||||
Assert(mtproto != nullptr);
|
|
||||||
|
|
||||||
const auto dcId = mtproto->mainDcId();
|
const auto dcId = mtproto->mainDcId();
|
||||||
|
|
||||||
item.state = ItemState::Checking;
|
item.state = ItemState::Checking;
|
||||||
|
@ -1084,7 +1082,7 @@ void ProxiesBoxController::refreshChecker(Item &item) {
|
||||||
dcId);
|
dcId);
|
||||||
item.checkerv6 = nullptr;
|
item.checkerv6 = nullptr;
|
||||||
} else {
|
} else {
|
||||||
const auto options = mtproto->dcOptions()->lookup(
|
const auto options = mtproto->dcOptions().lookup(
|
||||||
dcId,
|
dcId,
|
||||||
MTP::DcType::Regular,
|
MTP::DcType::Regular,
|
||||||
true);
|
true);
|
||||||
|
@ -1376,9 +1374,7 @@ void ProxiesBoxController::setTryIPv6(bool enabled) {
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
Global::SetTryIPv6(enabled);
|
Global::SetTryIPv6(enabled);
|
||||||
if (const auto mtproto = _account->mtp()) {
|
_account->mtp().restart();
|
||||||
mtproto->restart();
|
|
||||||
}
|
|
||||||
Global::RefConnectionTypeChanged().notify();
|
Global::RefConnectionTypeChanged().notify();
|
||||||
saveDelayed();
|
saveDelayed();
|
||||||
}
|
}
|
||||||
|
@ -1410,8 +1406,7 @@ void ProxiesBoxController::updateView(const Item &item) {
|
||||||
if (!selected
|
if (!selected
|
||||||
|| (Global::ProxySettings() != ProxyData::Settings::Enabled)) {
|
|| (Global::ProxySettings() != ProxyData::Settings::Enabled)) {
|
||||||
return item.state;
|
return item.state;
|
||||||
} else if (_account->mtp()
|
} else if (_account->mtp().dcstate() == MTP::ConnectedState) {
|
||||||
&& _account->mtp()->dcstate() == MTP::ConnectedState) {
|
|
||||||
return ItemState::Online;
|
return ItemState::Online;
|
||||||
}
|
}
|
||||||
return ItemState::Connecting;
|
return ItemState::Connecting;
|
||||||
|
|
|
@ -37,6 +37,7 @@ https://github.com/telegramdesktop/tdesktop/blob/master/LEGAL
|
||||||
#include "media/streaming/media_streaming_loader_local.h"
|
#include "media/streaming/media_streaming_loader_local.h"
|
||||||
#include "storage/localimageloader.h"
|
#include "storage/localimageloader.h"
|
||||||
#include "storage/storage_media_prepare.h"
|
#include "storage/storage_media_prepare.h"
|
||||||
|
#include "mtproto/mtproto_config.h"
|
||||||
#include "ui/image/image.h"
|
#include "ui/image/image.h"
|
||||||
#include "ui/widgets/input_fields.h"
|
#include "ui/widgets/input_fields.h"
|
||||||
#include "ui/widgets/checkbox.h"
|
#include "ui/widgets/checkbox.h"
|
||||||
|
@ -46,7 +47,7 @@ https://github.com/telegramdesktop/tdesktop/blob/master/LEGAL
|
||||||
#include "window/window_session_controller.h"
|
#include "window/window_session_controller.h"
|
||||||
#include "confirm_box.h"
|
#include "confirm_box.h"
|
||||||
#include "apiwrap.h"
|
#include "apiwrap.h"
|
||||||
#include "facades.h"
|
#include "facades.h" // App::LambdaDelayed.
|
||||||
#include "app.h"
|
#include "app.h"
|
||||||
#include "styles/style_layers.h"
|
#include "styles/style_layers.h"
|
||||||
#include "styles/style_boxes.h"
|
#include "styles/style_boxes.h"
|
||||||
|
@ -67,7 +68,7 @@ EditCaptionBox::EditCaptionBox(
|
||||||
not_null<Window::SessionController*> controller,
|
not_null<Window::SessionController*> controller,
|
||||||
not_null<HistoryItem*> item)
|
not_null<HistoryItem*> item)
|
||||||
: _controller(controller)
|
: _controller(controller)
|
||||||
, _api(controller->session().mtp())
|
, _api(&controller->session().mtp())
|
||||||
, _msgId(item->fullId()) {
|
, _msgId(item->fullId()) {
|
||||||
Expects(item->media() != nullptr);
|
Expects(item->media() != nullptr);
|
||||||
Expects(item->media()->allowsEditCaption());
|
Expects(item->media()->allowsEditCaption());
|
||||||
|
@ -304,8 +305,10 @@ EditCaptionBox::EditCaptionBox(
|
||||||
Ui::InputField::Mode::MultiLine,
|
Ui::InputField::Mode::MultiLine,
|
||||||
tr::lng_photo_caption(),
|
tr::lng_photo_caption(),
|
||||||
editData);
|
editData);
|
||||||
_field->setMaxLength(Global::CaptionLengthMax());
|
_field->setMaxLength(
|
||||||
_field->setSubmitSettings(_controller->session().settings().sendSubmitWay());
|
_controller->session().serverConfig().captionLengthMax);
|
||||||
|
_field->setSubmitSettings(
|
||||||
|
_controller->session().settings().sendSubmitWay());
|
||||||
_field->setInstantReplaces(Ui::InstantReplaces::Default());
|
_field->setInstantReplaces(Ui::InstantReplaces::Default());
|
||||||
_field->setInstantReplacesEnabled(
|
_field->setInstantReplacesEnabled(
|
||||||
_controller->session().settings().replaceEmojiValue());
|
_controller->session().settings().replaceEmojiValue());
|
||||||
|
|
|
@ -50,7 +50,7 @@ PasscodeBox::PasscodeBox(
|
||||||
not_null<Main::Session*> session,
|
not_null<Main::Session*> session,
|
||||||
bool turningOff)
|
bool turningOff)
|
||||||
: _session(session)
|
: _session(session)
|
||||||
, _api(_session->mtp())
|
, _api(&_session->mtp())
|
||||||
, _turningOff(turningOff)
|
, _turningOff(turningOff)
|
||||||
, _about(st::boxWidth - st::boxPadding.left() * 1.5)
|
, _about(st::boxWidth - st::boxPadding.left() * 1.5)
|
||||||
, _oldPasscode(this, st::defaultInputField, tr::lng_passcode_enter_old())
|
, _oldPasscode(this, st::defaultInputField, tr::lng_passcode_enter_old())
|
||||||
|
@ -66,7 +66,7 @@ PasscodeBox::PasscodeBox(
|
||||||
not_null<Main::Session*> session,
|
not_null<Main::Session*> session,
|
||||||
const CloudFields &fields)
|
const CloudFields &fields)
|
||||||
: _session(session)
|
: _session(session)
|
||||||
, _api(_session->mtp())
|
, _api(&_session->mtp())
|
||||||
, _turningOff(fields.turningOff)
|
, _turningOff(fields.turningOff)
|
||||||
, _cloudPwd(true)
|
, _cloudPwd(true)
|
||||||
, _cloudFields(fields)
|
, _cloudFields(fields)
|
||||||
|
@ -929,7 +929,7 @@ RecoverBox::RecoverBox(
|
||||||
not_null<Main::Session*> session,
|
not_null<Main::Session*> session,
|
||||||
const QString &pattern,
|
const QString &pattern,
|
||||||
bool notEmptyPassport)
|
bool notEmptyPassport)
|
||||||
: _api(session->mtp())
|
: _api(&session->mtp())
|
||||||
, _pattern(st::normalFont->elided(tr::lng_signin_recover_hint(tr::now, lt_recover_email, pattern), st::boxWidth - st::boxPadding.left() * 1.5))
|
, _pattern(st::normalFont->elided(tr::lng_signin_recover_hint(tr::now, lt_recover_email, pattern), st::boxWidth - st::boxPadding.left() * 1.5))
|
||||||
, _notEmptyPassport(notEmptyPassport)
|
, _notEmptyPassport(notEmptyPassport)
|
||||||
, _recoverCode(this, st::defaultInputField, tr::lng_signin_code()) {
|
, _recoverCode(this, st::defaultInputField, tr::lng_signin_code()) {
|
||||||
|
|
|
@ -146,7 +146,7 @@ void PeerListRowWithLink::paintAction(
|
||||||
PeerListGlobalSearchController::PeerListGlobalSearchController(
|
PeerListGlobalSearchController::PeerListGlobalSearchController(
|
||||||
not_null<Window::SessionNavigation*> navigation)
|
not_null<Window::SessionNavigation*> navigation)
|
||||||
: _navigation(navigation)
|
: _navigation(navigation)
|
||||||
, _api(_navigation->session().mtp()) {
|
, _api(&_navigation->session().mtp()) {
|
||||||
_timer.setCallback([this] { searchOnServer(); });
|
_timer.setCallback([this] { searchOnServer(); });
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
|
@ -20,11 +20,12 @@ https://github.com/telegramdesktop/tdesktop/blob/master/LEGAL
|
||||||
#include "dialogs/dialogs_indexed_list.h"
|
#include "dialogs/dialogs_indexed_list.h"
|
||||||
#include "base/unixtime.h"
|
#include "base/unixtime.h"
|
||||||
#include "main/main_session.h"
|
#include "main/main_session.h"
|
||||||
|
#include "mtproto/mtproto_config.h"
|
||||||
#include "mainwidget.h"
|
#include "mainwidget.h"
|
||||||
#include "mainwindow.h"
|
#include "mainwindow.h"
|
||||||
#include "window/window_session_controller.h"
|
#include "window/window_session_controller.h"
|
||||||
#include "apiwrap.h"
|
#include "apiwrap.h"
|
||||||
#include "facades.h"
|
#include "facades.h" // Ui::showPeerHistory
|
||||||
#include "app.h"
|
#include "app.h"
|
||||||
|
|
||||||
namespace {
|
namespace {
|
||||||
|
@ -87,10 +88,11 @@ void AddParticipantsBoxController::subscribeToMigration() {
|
||||||
}
|
}
|
||||||
|
|
||||||
void AddParticipantsBoxController::rowClicked(not_null<PeerListRow*> row) {
|
void AddParticipantsBoxController::rowClicked(not_null<PeerListRow*> row) {
|
||||||
|
const auto &serverConfig = _peer->session().serverConfig();
|
||||||
auto count = fullCount();
|
auto count = fullCount();
|
||||||
auto limit = _peer && (_peer->isChat() || _peer->isMegagroup())
|
auto limit = _peer && (_peer->isChat() || _peer->isMegagroup())
|
||||||
? Global::MegagroupSizeMax()
|
? serverConfig.megagroupSizeMax
|
||||||
: Global::ChatSizeMax();
|
: serverConfig.chatSizeMax;
|
||||||
if (count < limit || row->checked()) {
|
if (count < limit || row->checked()) {
|
||||||
delegate()->peerListSetRowChecked(row, !row->checked());
|
delegate()->peerListSetRowChecked(row, !row->checked());
|
||||||
updateTitle();
|
updateTitle();
|
||||||
|
@ -100,8 +102,8 @@ void AddParticipantsBoxController::rowClicked(not_null<PeerListRow*> row) {
|
||||||
Box<MaxInviteBox>(_peer->asChannel()),
|
Box<MaxInviteBox>(_peer->asChannel()),
|
||||||
Ui::LayerOption::KeepOther);
|
Ui::LayerOption::KeepOther);
|
||||||
}
|
}
|
||||||
} else if (count >= Global::ChatSizeMax()
|
} else if (count >= serverConfig.chatSizeMax
|
||||||
&& count < Global::MegagroupSizeMax()) {
|
&& count < serverConfig.megagroupSizeMax) {
|
||||||
Ui::show(
|
Ui::show(
|
||||||
Box<InformBox>(tr::lng_profile_add_more_after_create(tr::now)),
|
Box<InformBox>(tr::lng_profile_add_more_after_create(tr::now)),
|
||||||
Ui::LayerOption::KeepOther);
|
Ui::LayerOption::KeepOther);
|
||||||
|
@ -166,7 +168,9 @@ void AddParticipantsBoxController::updateTitle() {
|
||||||
&& _peer->isChannel()
|
&& _peer->isChannel()
|
||||||
&& !_peer->isMegagroup())
|
&& !_peer->isMegagroup())
|
||||||
? QString()
|
? QString()
|
||||||
: qsl("%1 / %2").arg(fullCount()).arg(Global::MegagroupSizeMax());
|
: qsl("%1 / %2"
|
||||||
|
).arg(fullCount()
|
||||||
|
).arg(session().serverConfig().megagroupSizeMax);
|
||||||
delegate()->peerListSetTitle(tr::lng_profile_add_participant());
|
delegate()->peerListSetTitle(tr::lng_profile_add_participant());
|
||||||
delegate()->peerListSetAdditionalTitle(rpl::single(additional));
|
delegate()->peerListSetAdditionalTitle(rpl::single(additional));
|
||||||
}
|
}
|
||||||
|
@ -276,7 +280,7 @@ AddSpecialBoxController::AddSpecialBoxController(
|
||||||
peer,
|
peer,
|
||||||
&_additional))
|
&_additional))
|
||||||
, _peer(peer)
|
, _peer(peer)
|
||||||
, _api(_peer->session().mtp())
|
, _api(&_peer->session().mtp())
|
||||||
, _role(role)
|
, _role(role)
|
||||||
, _additional(peer, Role::Members)
|
, _additional(peer, Role::Members)
|
||||||
, _adminDoneCallback(std::move(adminDoneCallback))
|
, _adminDoneCallback(std::move(adminDoneCallback))
|
||||||
|
@ -829,7 +833,7 @@ AddSpecialBoxSearchController::AddSpecialBoxSearchController(
|
||||||
not_null<ParticipantsAdditionalData*> additional)
|
not_null<ParticipantsAdditionalData*> additional)
|
||||||
: _peer(peer)
|
: _peer(peer)
|
||||||
, _additional(additional)
|
, _additional(additional)
|
||||||
, _api(_peer->session().mtp())
|
, _api(&_peer->session().mtp())
|
||||||
, _timer([=] { searchOnServer(); }) {
|
, _timer([=] { searchOnServer(); }) {
|
||||||
subscribeToMigration();
|
subscribeToMigration();
|
||||||
}
|
}
|
||||||
|
|
|
@ -13,6 +13,7 @@ https://github.com/telegramdesktop/tdesktop/blob/master/LEGAL
|
||||||
#include "boxes/confirm_box.h"
|
#include "boxes/confirm_box.h"
|
||||||
#include "boxes/add_contact_box.h"
|
#include "boxes/add_contact_box.h"
|
||||||
#include "main/main_session.h"
|
#include "main/main_session.h"
|
||||||
|
#include "mtproto/mtproto_config.h"
|
||||||
#include "apiwrap.h"
|
#include "apiwrap.h"
|
||||||
#include "lang/lang_keys.h"
|
#include "lang/lang_keys.h"
|
||||||
#include "mainwidget.h"
|
#include "mainwidget.h"
|
||||||
|
@ -28,7 +29,6 @@ https://github.com/telegramdesktop/tdesktop/blob/master/LEGAL
|
||||||
#include "ui/ui_utility.h"
|
#include "ui/ui_utility.h"
|
||||||
#include "window/window_session_controller.h"
|
#include "window/window_session_controller.h"
|
||||||
#include "history/history.h"
|
#include "history/history.h"
|
||||||
#include "facades.h"
|
|
||||||
|
|
||||||
namespace {
|
namespace {
|
||||||
|
|
||||||
|
@ -707,7 +707,8 @@ void ParticipantsOnlineSorter::sort() {
|
||||||
const auto channel = _peer->asChannel();
|
const auto channel = _peer->asChannel();
|
||||||
if (channel
|
if (channel
|
||||||
&& (!channel->isMegagroup()
|
&& (!channel->isMegagroup()
|
||||||
|| channel->membersCount() > Global::ChatSizeMax())) {
|
|| (channel->membersCount()
|
||||||
|
> channel->session().serverConfig().chatSizeMax))) {
|
||||||
_onlineCount = 0;
|
_onlineCount = 0;
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
|
@ -752,7 +753,7 @@ ParticipantsBoxController::ParticipantsBoxController(
|
||||||
: PeerListController(CreateSearchController(peer, role, &_additional))
|
: PeerListController(CreateSearchController(peer, role, &_additional))
|
||||||
, _navigation(navigation)
|
, _navigation(navigation)
|
||||||
, _peer(peer)
|
, _peer(peer)
|
||||||
, _api(_peer->session().mtp())
|
, _api(&_peer->session().mtp())
|
||||||
, _role(role)
|
, _role(role)
|
||||||
, _additional(peer, _role) {
|
, _additional(peer, _role) {
|
||||||
subscribeToMigration();
|
subscribeToMigration();
|
||||||
|
@ -844,8 +845,9 @@ void ParticipantsBoxController::Start(
|
||||||
return chat
|
return chat
|
||||||
? chat->canAddMembers()
|
? chat->canAddMembers()
|
||||||
: (channel->canAddMembers()
|
: (channel->canAddMembers()
|
||||||
&& (channel->membersCount() < Global::ChatSizeMax()
|
&& (channel->isMegagroup()
|
||||||
|| channel->isMegagroup()));
|
|| (channel->membersCount()
|
||||||
|
< channel->session().serverConfig().chatSizeMax)));
|
||||||
case Role::Admins:
|
case Role::Admins:
|
||||||
return chat
|
return chat
|
||||||
? chat->canAddAdmins()
|
? chat->canAddAdmins()
|
||||||
|
@ -924,7 +926,8 @@ void ParticipantsBoxController::addNewParticipants() {
|
||||||
if (chat) {
|
if (chat) {
|
||||||
AddParticipantsBoxController::Start(_navigation, chat);
|
AddParticipantsBoxController::Start(_navigation, chat);
|
||||||
} else if (channel->isMegagroup()
|
} else if (channel->isMegagroup()
|
||||||
|| channel->membersCount() < Global::ChatSizeMax()) {
|
|| (channel->membersCount()
|
||||||
|
< channel->session().serverConfig().chatSizeMax)) {
|
||||||
const auto count = delegate()->peerListFullRowsCount();
|
const auto count = delegate()->peerListFullRowsCount();
|
||||||
auto already = std::vector<not_null<UserData*>>();
|
auto already = std::vector<not_null<UserData*>>();
|
||||||
already.reserve(count);
|
already.reserve(count);
|
||||||
|
@ -1887,7 +1890,7 @@ void ParticipantsBoxController::subscribeToCreatorChange(
|
||||||
channel->inputChannel,
|
channel->inputChannel,
|
||||||
MTP_channelParticipantsRecent(),
|
MTP_channelParticipantsRecent(),
|
||||||
MTP_int(0),
|
MTP_int(0),
|
||||||
MTP_int(Global::ChatSizeMax()),
|
MTP_int(channel->session().serverConfig().chatSizeMax),
|
||||||
MTP_int(0)
|
MTP_int(0)
|
||||||
)).done([=](const MTPchannels_ChannelParticipants &result) {
|
)).done([=](const MTPchannels_ChannelParticipants &result) {
|
||||||
if (channel->amCreator()) {
|
if (channel->amCreator()) {
|
||||||
|
@ -1922,7 +1925,7 @@ ParticipantsBoxSearchController::ParticipantsBoxSearchController(
|
||||||
: _channel(channel)
|
: _channel(channel)
|
||||||
, _role(role)
|
, _role(role)
|
||||||
, _additional(additional)
|
, _additional(additional)
|
||||||
, _api(_channel->session().mtp()) {
|
, _api(&_channel->session().mtp()) {
|
||||||
_timer.setCallback([=] { searchOnServer(); });
|
_timer.setCallback([=] { searchOnServer(); });
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
|
@ -355,7 +355,7 @@ Controller::Controller(
|
||||||
: _navigation(navigation)
|
: _navigation(navigation)
|
||||||
, _box(box)
|
, _box(box)
|
||||||
, _peer(peer)
|
, _peer(peer)
|
||||||
, _api(_peer->session().mtp())
|
, _api(&_peer->session().mtp())
|
||||||
, _isGroup(_peer->isChat() || _peer->isMegagroup()) {
|
, _isGroup(_peer->isChat() || _peer->isMegagroup()) {
|
||||||
_box->setTitle(_isGroup
|
_box->setTitle(_isGroup
|
||||||
? tr::lng_edit_group()
|
? tr::lng_edit_group()
|
||||||
|
|
|
@ -168,7 +168,7 @@ Controller::Controller(
|
||||||
std::optional<Privacy> privacySavedValue,
|
std::optional<Privacy> privacySavedValue,
|
||||||
std::optional<QString> usernameSavedValue)
|
std::optional<QString> usernameSavedValue)
|
||||||
: _peer(peer)
|
: _peer(peer)
|
||||||
, _api(_peer->session().mtp())
|
, _api(&_peer->session().mtp())
|
||||||
, _privacySavedValue(privacySavedValue)
|
, _privacySavedValue(privacySavedValue)
|
||||||
, _usernameSavedValue(usernameSavedValue)
|
, _usernameSavedValue(usernameSavedValue)
|
||||||
, _useLocationPhrases(useLocationPhrases)
|
, _useLocationPhrases(useLocationPhrases)
|
||||||
|
@ -335,7 +335,7 @@ object_ptr<Ui::RpWidget> Controller::createUsernameEdit() {
|
||||||
st::setupChannelLink,
|
st::setupChannelLink,
|
||||||
nullptr,
|
nullptr,
|
||||||
username,
|
username,
|
||||||
true));
|
_peer->session().createInternalLink(QString())));
|
||||||
_controls.usernameInput->heightValue(
|
_controls.usernameInput->heightValue(
|
||||||
) | rpl::start_with_next([placeholder](int height) {
|
) | rpl::start_with_next([placeholder](int height) {
|
||||||
placeholder->resize(placeholder->width(), height);
|
placeholder->resize(placeholder->width(), height);
|
||||||
|
|
|
@ -31,7 +31,7 @@ RateCallBox::RateCallBox(
|
||||||
uint64 callId,
|
uint64 callId,
|
||||||
uint64 callAccessHash)
|
uint64 callAccessHash)
|
||||||
: _session(session)
|
: _session(session)
|
||||||
, _api(_session->mtp())
|
, _api(&_session->mtp())
|
||||||
, _callId(callId)
|
, _callId(callId)
|
||||||
, _callAccessHash(callAccessHash) {
|
, _callAccessHash(callAccessHash) {
|
||||||
}
|
}
|
||||||
|
|
|
@ -28,12 +28,12 @@ constexpr auto kReportReasonLengthMax = 200;
|
||||||
|
|
||||||
ReportBox::ReportBox(QWidget*, not_null<PeerData*> peer)
|
ReportBox::ReportBox(QWidget*, not_null<PeerData*> peer)
|
||||||
: _peer(peer)
|
: _peer(peer)
|
||||||
, _api(_peer->session().mtp()) {
|
, _api(&_peer->session().mtp()) {
|
||||||
}
|
}
|
||||||
|
|
||||||
ReportBox::ReportBox(QWidget*, not_null<PeerData*> peer, MessageIdsList ids)
|
ReportBox::ReportBox(QWidget*, not_null<PeerData*> peer, MessageIdsList ids)
|
||||||
: _peer(peer)
|
: _peer(peer)
|
||||||
, _api(_peer->session().mtp())
|
, _api(&_peer->session().mtp())
|
||||||
, _ids(std::move(ids)) {
|
, _ids(std::move(ids)) {
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
|
@ -12,6 +12,7 @@ https://github.com/telegramdesktop/tdesktop/blob/master/LEGAL
|
||||||
#include "storage/localstorage.h"
|
#include "storage/localstorage.h"
|
||||||
#include "storage/storage_media_prepare.h"
|
#include "storage/storage_media_prepare.h"
|
||||||
#include "mainwidget.h"
|
#include "mainwidget.h"
|
||||||
|
#include "mtproto/mtproto_config.h"
|
||||||
#include "chat_helpers/message_field.h"
|
#include "chat_helpers/message_field.h"
|
||||||
#include "chat_helpers/emoji_suggestions_widget.h"
|
#include "chat_helpers/emoji_suggestions_widget.h"
|
||||||
#include "chat_helpers/tabbed_panel.h"
|
#include "chat_helpers/tabbed_panel.h"
|
||||||
|
@ -36,7 +37,7 @@ https://github.com/telegramdesktop/tdesktop/blob/master/LEGAL
|
||||||
#include "api/api_common.h"
|
#include "api/api_common.h"
|
||||||
#include "window/window_session_controller.h"
|
#include "window/window_session_controller.h"
|
||||||
#include "layout.h"
|
#include "layout.h"
|
||||||
#include "facades.h"
|
#include "facades.h" // App::LambdaDelayed.
|
||||||
#include "app.h"
|
#include "app.h"
|
||||||
#include "styles/style_history.h"
|
#include "styles/style_history.h"
|
||||||
#include "styles/style_layers.h"
|
#include "styles/style_layers.h"
|
||||||
|
@ -2041,8 +2042,10 @@ void SendFilesBox::applyAlbumOrder() {
|
||||||
}
|
}
|
||||||
|
|
||||||
void SendFilesBox::setupCaption() {
|
void SendFilesBox::setupCaption() {
|
||||||
_caption->setMaxLength(Global::CaptionLengthMax());
|
_caption->setMaxLength(
|
||||||
_caption->setSubmitSettings(_controller->session().settings().sendSubmitWay());
|
_controller->session().serverConfig().captionLengthMax);
|
||||||
|
_caption->setSubmitSettings(
|
||||||
|
_controller->session().settings().sendSubmitWay());
|
||||||
connect(_caption, &Ui::InputField::resized, [=] {
|
connect(_caption, &Ui::InputField::resized, [=] {
|
||||||
captionResized();
|
captionResized();
|
||||||
});
|
});
|
||||||
|
|
|
@ -77,7 +77,7 @@ private:
|
||||||
|
|
||||||
SessionsBox::SessionsBox(QWidget*, not_null<Main::Session*> session)
|
SessionsBox::SessionsBox(QWidget*, not_null<Main::Session*> session)
|
||||||
: _session(session)
|
: _session(session)
|
||||||
, _api(_session->mtp())
|
, _api(&_session->mtp())
|
||||||
, _shortPollTimer([=] { shortPollSessions(); }) {
|
, _shortPollTimer([=] { shortPollSessions(); }) {
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
|
@ -159,7 +159,7 @@ ShareBox::ShareBox(
|
||||||
SubmitCallback &&submitCallback,
|
SubmitCallback &&submitCallback,
|
||||||
FilterCallback &&filterCallback)
|
FilterCallback &&filterCallback)
|
||||||
: _navigation(navigation)
|
: _navigation(navigation)
|
||||||
, _api(_navigation->session().mtp())
|
, _api(&_navigation->session().mtp())
|
||||||
, _copyCallback(std::move(copyCallback))
|
, _copyCallback(std::move(copyCallback))
|
||||||
, _submitCallback(std::move(submitCallback))
|
, _submitCallback(std::move(submitCallback))
|
||||||
, _filterCallback(std::move(filterCallback))
|
, _filterCallback(std::move(filterCallback))
|
||||||
|
|
|
@ -190,7 +190,8 @@ void StickerSetBox::addStickers() {
|
||||||
}
|
}
|
||||||
|
|
||||||
void StickerSetBox::shareStickers() {
|
void StickerSetBox::shareStickers() {
|
||||||
auto url = Core::App().createInternalLinkFull(qsl("addstickers/") + _inner->shortName());
|
const auto url = _controller->session().createInternalLinkFull(
|
||||||
|
qsl("addstickers/") + _inner->shortName());
|
||||||
QGuiApplication::clipboard()->setText(url);
|
QGuiApplication::clipboard()->setText(url);
|
||||||
Ui::show(Box<InformBox>(tr::lng_stickers_copied(tr::now)));
|
Ui::show(Box<InformBox>(tr::lng_stickers_copied(tr::now)));
|
||||||
}
|
}
|
||||||
|
@ -229,7 +230,7 @@ StickerSetBox::Inner::Inner(
|
||||||
const MTPInputStickerSet &set)
|
const MTPInputStickerSet &set)
|
||||||
: RpWidget(parent)
|
: RpWidget(parent)
|
||||||
, _controller(controller)
|
, _controller(controller)
|
||||||
, _api(_controller->session().mtp())
|
, _api(&_controller->session().mtp())
|
||||||
, _input(set)
|
, _input(set)
|
||||||
, _previewTimer([=] { showPreview(); }) {
|
, _previewTimer([=] { showPreview(); }) {
|
||||||
set.match([&](const MTPDinputStickerSetID &data) {
|
set.match([&](const MTPDinputStickerSetID &data) {
|
||||||
|
|
|
@ -363,7 +363,7 @@ StickersBox::StickersBox(
|
||||||
not_null<Main::Session*> session,
|
not_null<Main::Session*> session,
|
||||||
Section section)
|
Section section)
|
||||||
: _session(session)
|
: _session(session)
|
||||||
, _api(session->mtp())
|
, _api(&session->mtp())
|
||||||
, _tabs(this, st::stickersTabs)
|
, _tabs(this, st::stickersTabs)
|
||||||
, _unreadBadge(
|
, _unreadBadge(
|
||||||
this,
|
this,
|
||||||
|
@ -377,7 +377,7 @@ StickersBox::StickersBox(
|
||||||
|
|
||||||
StickersBox::StickersBox(QWidget*, not_null<ChannelData*> megagroup)
|
StickersBox::StickersBox(QWidget*, not_null<ChannelData*> megagroup)
|
||||||
: _session(&megagroup->session())
|
: _session(&megagroup->session())
|
||||||
, _api(_session->mtp())
|
, _api(&_session->mtp())
|
||||||
, _section(Section::Installed)
|
, _section(Section::Installed)
|
||||||
, _installed(0, this, megagroup)
|
, _installed(0, this, megagroup)
|
||||||
, _megagroupSet(megagroup) {
|
, _megagroupSet(megagroup) {
|
||||||
|
@ -391,7 +391,7 @@ StickersBox::StickersBox(
|
||||||
not_null<Main::Session*> session,
|
not_null<Main::Session*> session,
|
||||||
const MTPVector<MTPStickerSetCovered> &attachedSets)
|
const MTPVector<MTPStickerSetCovered> &attachedSets)
|
||||||
: _session(session)
|
: _session(session)
|
||||||
, _api(session->mtp())
|
, _api(&session->mtp())
|
||||||
, _section(Section::Attached)
|
, _section(Section::Attached)
|
||||||
, _attached(0, this, session, Section::Attached)
|
, _attached(0, this, session, Section::Attached)
|
||||||
, _attachedSets(attachedSets) {
|
, _attachedSets(attachedSets) {
|
||||||
|
@ -928,7 +928,7 @@ StickersBox::Inner::Inner(
|
||||||
StickersBox::Section section)
|
StickersBox::Section section)
|
||||||
: RpWidget(parent)
|
: RpWidget(parent)
|
||||||
, _session(session)
|
, _session(session)
|
||||||
, _api(_session->mtp())
|
, _api(&_session->mtp())
|
||||||
, _section(section)
|
, _section(section)
|
||||||
, _rowHeight(st::contactsPadding.top() + st::contactsPhotoSize + st::contactsPadding.bottom())
|
, _rowHeight(st::contactsPadding.top() + st::contactsPhotoSize + st::contactsPadding.bottom())
|
||||||
, _shiftingAnimation([=](crl::time now) {
|
, _shiftingAnimation([=](crl::time now) {
|
||||||
|
@ -945,7 +945,7 @@ StickersBox::Inner::Inner(
|
||||||
StickersBox::Inner::Inner(QWidget *parent, not_null<ChannelData*> megagroup)
|
StickersBox::Inner::Inner(QWidget *parent, not_null<ChannelData*> megagroup)
|
||||||
: RpWidget(parent)
|
: RpWidget(parent)
|
||||||
, _session(&megagroup->session())
|
, _session(&megagroup->session())
|
||||||
, _api(_session->mtp())
|
, _api(&_session->mtp())
|
||||||
, _section(StickersBox::Section::Installed)
|
, _section(StickersBox::Section::Installed)
|
||||||
, _rowHeight(st::contactsPadding.top() + st::contactsPhotoSize + st::contactsPadding.bottom())
|
, _rowHeight(st::contactsPadding.top() + st::contactsPhotoSize + st::contactsPadding.bottom())
|
||||||
, _shiftingAnimation([=](crl::time now) {
|
, _shiftingAnimation([=](crl::time now) {
|
||||||
|
@ -954,10 +954,16 @@ StickersBox::Inner::Inner(QWidget *parent, not_null<ChannelData*> megagroup)
|
||||||
, _itemsTop(st::membersMarginTop)
|
, _itemsTop(st::membersMarginTop)
|
||||||
, _megagroupSet(megagroup)
|
, _megagroupSet(megagroup)
|
||||||
, _megagroupSetInput(_megagroupSet->mgInfo->stickerSet)
|
, _megagroupSetInput(_megagroupSet->mgInfo->stickerSet)
|
||||||
, _megagroupSetField(this, st::groupStickersField, rpl::single(qsl("stickerset")), QString(), true)
|
, _megagroupSetField(
|
||||||
|
this,
|
||||||
|
st::groupStickersField,
|
||||||
|
rpl::single(qsl("stickerset")),
|
||||||
|
QString(),
|
||||||
|
_session->createInternalLink(QString()))
|
||||||
, _megagroupDivider(this)
|
, _megagroupDivider(this)
|
||||||
, _megagroupSubTitle(this, tr::lng_stickers_group_from_your(tr::now), st::boxTitle) {
|
, _megagroupSubTitle(this, tr::lng_stickers_group_from_your(tr::now), st::boxTitle) {
|
||||||
_megagroupSetField->setLinkPlaceholder(Core::App().createInternalLink(qsl("addstickers/")));
|
_megagroupSetField->setLinkPlaceholder(
|
||||||
|
_session->createInternalLink(qsl("addstickers/")));
|
||||||
_megagroupSetField->setPlaceholderHidden(false);
|
_megagroupSetField->setPlaceholderHidden(false);
|
||||||
_megagroupSetAddressChangedTimer.setCallback([this] { handleMegagroupSetAddressChange(); });
|
_megagroupSetAddressChangedTimer.setCallback([this] { handleMegagroupSetAddressChange(); });
|
||||||
connect(
|
connect(
|
||||||
|
|
|
@ -31,13 +31,13 @@ constexpr auto kMinUsernameLength = 5;
|
||||||
|
|
||||||
UsernameBox::UsernameBox(QWidget*, not_null<Main::Session*> session)
|
UsernameBox::UsernameBox(QWidget*, not_null<Main::Session*> session)
|
||||||
: _session(session)
|
: _session(session)
|
||||||
, _api(_session->mtp())
|
, _api(&_session->mtp())
|
||||||
, _username(
|
, _username(
|
||||||
this,
|
this,
|
||||||
st::defaultInputField,
|
st::defaultInputField,
|
||||||
rpl::single(qsl("@username")),
|
rpl::single(qsl("@username")),
|
||||||
session->user()->username,
|
session->user()->username,
|
||||||
false)
|
QString())
|
||||||
, _link(this, QString(), st::boxLinkButton)
|
, _link(this, QString(), st::boxLinkButton)
|
||||||
, _about(st::boxWidth - st::usernamePadding.left())
|
, _about(st::boxWidth - st::usernamePadding.left())
|
||||||
, _checkTimer(this) {
|
, _checkTimer(this) {
|
||||||
|
@ -94,7 +94,8 @@ void UsernameBox::paintEvent(QPaintEvent *e) {
|
||||||
if (_link->isHidden()) {
|
if (_link->isHidden()) {
|
||||||
p.drawTextLeft(st::usernamePadding.left(), linky, width(), tr::lng_username_link_willbe(tr::now));
|
p.drawTextLeft(st::usernamePadding.left(), linky, width(), tr::lng_username_link_willbe(tr::now));
|
||||||
p.setPen(st::usernameDefaultFg);
|
p.setPen(st::usernameDefaultFg);
|
||||||
p.drawTextLeft(st::usernamePadding.left(), linky + st::usernameTextStyle.lineHeight + ((st::usernameTextStyle.lineHeight - st::boxTextFont->height) / 2), width(), Core::App().createInternalLinkFull(qsl("username")));
|
const auto link = _session->createInternalLinkFull(qsl("username"));
|
||||||
|
p.drawTextLeft(st::usernamePadding.left(), linky + st::usernameTextStyle.lineHeight + ((st::usernameTextStyle.lineHeight - st::boxTextFont->height) / 2), width(), link);
|
||||||
} else {
|
} else {
|
||||||
p.drawTextLeft(st::usernamePadding.left(), linky, width(), tr::lng_username_link(tr::now));
|
p.drawTextLeft(st::usernamePadding.left(), linky, width(), tr::lng_username_link(tr::now));
|
||||||
}
|
}
|
||||||
|
@ -179,7 +180,8 @@ void UsernameBox::changed() {
|
||||||
}
|
}
|
||||||
|
|
||||||
void UsernameBox::linkClick() {
|
void UsernameBox::linkClick() {
|
||||||
QGuiApplication::clipboard()->setText(Core::App().createInternalLinkFull(getName()));
|
QGuiApplication::clipboard()->setText(
|
||||||
|
_session->createInternalLinkFull(getName()));
|
||||||
Ui::Toast::Show(tr::lng_username_copied(tr::now));
|
Ui::Toast::Show(tr::lng_username_copied(tr::now));
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -251,7 +253,7 @@ QString UsernameBox::getName() const {
|
||||||
|
|
||||||
void UsernameBox::updateLinkText() {
|
void UsernameBox::updateLinkText() {
|
||||||
QString uname = getName();
|
QString uname = getName();
|
||||||
_link->setText(st::boxTextFont->elided(Core::App().createInternalLinkFull(uname), st::boxWidth - st::usernamePadding.left() - st::usernamePadding.right()));
|
_link->setText(st::boxTextFont->elided(_session->createInternalLinkFull(uname), st::boxWidth - st::usernamePadding.left() - st::usernamePadding.right()));
|
||||||
if (uname.isEmpty()) {
|
if (uname.isEmpty()) {
|
||||||
if (!_link->isHidden()) {
|
if (!_link->isHidden()) {
|
||||||
_link->hide();
|
_link->hide();
|
||||||
|
|
|
@ -216,7 +216,7 @@ void BoxController::Row::stopLastActionRipple() {
|
||||||
|
|
||||||
BoxController::BoxController(not_null<Window::SessionController*> window)
|
BoxController::BoxController(not_null<Window::SessionController*> window)
|
||||||
: _window(window)
|
: _window(window)
|
||||||
, _api(_window->session().mtp()) {
|
, _api(&_window->session().mtp()) {
|
||||||
}
|
}
|
||||||
|
|
||||||
Main::Session &BoxController::session() const {
|
Main::Session &BoxController::session() const {
|
||||||
|
|
|
@ -15,6 +15,7 @@ https://github.com/telegramdesktop/tdesktop/blob/master/LEGAL
|
||||||
#include "calls/calls_instance.h"
|
#include "calls/calls_instance.h"
|
||||||
#include "base/openssl_help.h"
|
#include "base/openssl_help.h"
|
||||||
#include "mtproto/mtproto_dh_utils.h"
|
#include "mtproto/mtproto_dh_utils.h"
|
||||||
|
#include "mtproto/mtproto_config.h"
|
||||||
#include "media/audio/media_audio_track.h"
|
#include "media/audio/media_audio_track.h"
|
||||||
#include "base/platform/base_platform_info.h"
|
#include "base/platform/base_platform_info.h"
|
||||||
#include "calls/calls_panel.h"
|
#include "calls/calls_panel.h"
|
||||||
|
@ -96,7 +97,7 @@ Call::Call(
|
||||||
Type type)
|
Type type)
|
||||||
: _delegate(delegate)
|
: _delegate(delegate)
|
||||||
, _user(user)
|
, _user(user)
|
||||||
, _api(_user->session().mtp())
|
, _api(&_user->session().mtp())
|
||||||
, _type(type) {
|
, _type(type) {
|
||||||
_discardByTimeoutTimer.setCallback([this] { hangup(); });
|
_discardByTimeoutTimer.setCallback([this] { hangup(); });
|
||||||
|
|
||||||
|
@ -193,7 +194,8 @@ void Call::startOutgoing() {
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
|
|
||||||
_discardByTimeoutTimer.callOnce(Global::CallReceiveTimeoutMs());
|
const auto &config = _user->session().serverConfig();
|
||||||
|
_discardByTimeoutTimer.callOnce(config.callReceiveTimeoutMs);
|
||||||
handleUpdate(phoneCall);
|
handleUpdate(phoneCall);
|
||||||
}).fail([this](const RPCError &error) {
|
}).fail([this](const RPCError &error) {
|
||||||
handleRequestError(error);
|
handleRequestError(error);
|
||||||
|
@ -382,7 +384,8 @@ bool Call::handleUpdate(const MTPPhoneCall &call) {
|
||||||
if (_type == Type::Outgoing
|
if (_type == Type::Outgoing
|
||||||
&& _state == State::Waiting
|
&& _state == State::Waiting
|
||||||
&& data.vreceive_date().value_or_empty() != 0) {
|
&& data.vreceive_date().value_or_empty() != 0) {
|
||||||
_discardByTimeoutTimer.callOnce(Global::CallRingTimeoutMs());
|
const auto &config = _user->session().serverConfig();
|
||||||
|
_discardByTimeoutTimer.callOnce(config.callRingTimeoutMs);
|
||||||
setState(State::Ringing);
|
setState(State::Ringing);
|
||||||
startWaitingTrack();
|
startWaitingTrack();
|
||||||
}
|
}
|
||||||
|
@ -534,6 +537,7 @@ void Call::createAndStartController(const MTPDphoneCall &call) {
|
||||||
}
|
}
|
||||||
|
|
||||||
const auto &protocol = call.vprotocol().c_phoneCallProtocol();
|
const auto &protocol = call.vprotocol().c_phoneCallProtocol();
|
||||||
|
const auto &serverConfig = _user->session().serverConfig();
|
||||||
|
|
||||||
TgVoipConfig config;
|
TgVoipConfig config;
|
||||||
config.dataSaving = TgVoipDataSaving::Never;
|
config.dataSaving = TgVoipDataSaving::Never;
|
||||||
|
@ -541,8 +545,8 @@ void Call::createAndStartController(const MTPDphoneCall &call) {
|
||||||
config.enableNS = true;
|
config.enableNS = true;
|
||||||
config.enableAGC = true;
|
config.enableAGC = true;
|
||||||
config.enableVolumeControl = true;
|
config.enableVolumeControl = true;
|
||||||
config.initializationTimeout = Global::CallConnectTimeoutMs() / 1000.;
|
config.initializationTimeout = serverConfig.callConnectTimeoutMs / 1000.;
|
||||||
config.receiveTimeout = Global::CallPacketTimeoutMs() / 1000.;
|
config.receiveTimeout = serverConfig.callPacketTimeoutMs / 1000.;
|
||||||
config.enableP2P = call.is_p2p_allowed();
|
config.enableP2P = call.is_p2p_allowed();
|
||||||
config.maxApiLayer = protocol.vmax_layer().v;
|
config.maxApiLayer = protocol.vmax_layer().v;
|
||||||
if (Logs::DebugEnabled()) {
|
if (Logs::DebugEnabled()) {
|
||||||
|
|
|
@ -21,8 +21,8 @@ https://github.com/telegramdesktop/tdesktop/blob/master/LEGAL
|
||||||
#include "platform/platform_specific.h"
|
#include "platform/platform_specific.h"
|
||||||
#include "base/unixtime.h"
|
#include "base/unixtime.h"
|
||||||
#include "mainwidget.h"
|
#include "mainwidget.h"
|
||||||
|
#include "mtproto/mtproto_config.h"
|
||||||
#include "boxes/rate_call_box.h"
|
#include "boxes/rate_call_box.h"
|
||||||
#include "facades.h"
|
|
||||||
#include "app.h"
|
#include "app.h"
|
||||||
|
|
||||||
namespace Calls {
|
namespace Calls {
|
||||||
|
@ -34,7 +34,7 @@ constexpr auto kServerConfigUpdateTimeoutMs = 24 * 3600 * crl::time(1000);
|
||||||
|
|
||||||
Instance::Instance(not_null<Main::Session*> session)
|
Instance::Instance(not_null<Main::Session*> session)
|
||||||
: _session(session)
|
: _session(session)
|
||||||
, _api(_session->mtp()) {
|
, _api(&_session->mtp()) {
|
||||||
}
|
}
|
||||||
|
|
||||||
void Instance::startOutgoingCall(not_null<UserData*> user) {
|
void Instance::startOutgoingCall(not_null<UserData*> user) {
|
||||||
|
@ -248,6 +248,7 @@ void Instance::handleCallUpdate(const MTPPhoneCall &call) {
|
||||||
} else if (user->isSelf()) {
|
} else if (user->isSelf()) {
|
||||||
LOG(("API Error: Self found in phoneCallRequested."));
|
LOG(("API Error: Self found in phoneCallRequested."));
|
||||||
}
|
}
|
||||||
|
const auto &config = _session->serverConfig();
|
||||||
if (alreadyInCall() || !user || user->isSelf()) {
|
if (alreadyInCall() || !user || user->isSelf()) {
|
||||||
_api.request(MTPphone_DiscardCall(
|
_api.request(MTPphone_DiscardCall(
|
||||||
MTP_flags(0),
|
MTP_flags(0),
|
||||||
|
@ -256,7 +257,7 @@ void Instance::handleCallUpdate(const MTPPhoneCall &call) {
|
||||||
MTP_phoneCallDiscardReasonBusy(),
|
MTP_phoneCallDiscardReasonBusy(),
|
||||||
MTP_long(0)
|
MTP_long(0)
|
||||||
)).send();
|
)).send();
|
||||||
} else if (phoneCall.vdate().v + (Global::CallRingTimeoutMs() / 1000)
|
} else if (phoneCall.vdate().v + (config.callRingTimeoutMs / 1000)
|
||||||
< base::unixtime::now()) {
|
< base::unixtime::now()) {
|
||||||
LOG(("Ignoring too old call."));
|
LOG(("Ignoring too old call."));
|
||||||
} else {
|
} else {
|
||||||
|
|
|
@ -134,7 +134,7 @@ GifsListWidget::GifsListWidget(
|
||||||
QWidget *parent,
|
QWidget *parent,
|
||||||
not_null<Window::SessionController*> controller)
|
not_null<Window::SessionController*> controller)
|
||||||
: Inner(parent, controller)
|
: Inner(parent, controller)
|
||||||
, _api(controller->session().mtp())
|
, _api(&controller->session().mtp())
|
||||||
, _section(Section::Gifs)
|
, _section(Section::Gifs)
|
||||||
, _updateInlineItems([=] { updateInlineItems(); })
|
, _updateInlineItems([=] { updateInlineItems(); })
|
||||||
, _previewTimer([=] { showPreview(); }) {
|
, _previewTimer([=] { showPreview(); }) {
|
||||||
|
|
|
@ -873,7 +873,7 @@ StickersListWidget::StickersListWidget(
|
||||||
QWidget *parent,
|
QWidget *parent,
|
||||||
not_null<Window::SessionController*> controller)
|
not_null<Window::SessionController*> controller)
|
||||||
: Inner(parent, controller)
|
: Inner(parent, controller)
|
||||||
, _api(controller->session().mtp())
|
, _api(&controller->session().mtp())
|
||||||
, _section(Section::Stickers)
|
, _section(Section::Stickers)
|
||||||
, _megagroupSetAbout(st::columnMinimalWidthThird - st::emojiScroll.width - st::emojiPanHeaderLeft)
|
, _megagroupSetAbout(st::columnMinimalWidthThird - st::emojiScroll.width - st::emojiPanHeaderLeft)
|
||||||
, _addText(tr::lng_stickers_featured_add(tr::now).toUpper())
|
, _addText(tr::lng_stickers_featured_add(tr::now).toUpper())
|
||||||
|
|
|
@ -39,7 +39,8 @@ https://github.com/telegramdesktop/tdesktop/blob/master/LEGAL
|
||||||
#include "main/main_accounts.h"
|
#include "main/main_accounts.h"
|
||||||
#include "main/main_session.h"
|
#include "main/main_session.h"
|
||||||
#include "media/view/media_view_overlay_widget.h"
|
#include "media/view/media_view_overlay_widget.h"
|
||||||
#include "mtproto/dc_options.h"
|
#include "mtproto/mtproto_dc_options.h"
|
||||||
|
#include "mtproto/mtproto_config.h"
|
||||||
#include "mtproto/mtp_instance.h"
|
#include "mtproto/mtp_instance.h"
|
||||||
#include "media/audio/media_audio.h"
|
#include "media/audio/media_audio.h"
|
||||||
#include "media/audio/media_audio_track.h"
|
#include "media/audio/media_audio_track.h"
|
||||||
|
@ -95,7 +96,8 @@ Application::Application(not_null<Launcher*> launcher)
|
||||||
, _private(std::make_unique<Private>())
|
, _private(std::make_unique<Private>())
|
||||||
, _databases(std::make_unique<Storage::Databases>())
|
, _databases(std::make_unique<Storage::Databases>())
|
||||||
, _animationsManager(std::make_unique<Ui::Animations::Manager>())
|
, _animationsManager(std::make_unique<Ui::Animations::Manager>())
|
||||||
, _dcOptions(std::make_unique<MTP::DcOptions>())
|
, _fallbackProductionConfig(
|
||||||
|
std::make_unique<MTP::Config>(MTP::Environment::Production))
|
||||||
, _accounts(std::make_unique<Main::Accounts>(cDataFile()))
|
, _accounts(std::make_unique<Main::Accounts>(cDataFile()))
|
||||||
, _langpack(std::make_unique<Lang::Instance>())
|
, _langpack(std::make_unique<Lang::Instance>())
|
||||||
, _langCloudManager(std::make_unique<Lang::CloudManager>(langpack()))
|
, _langCloudManager(std::make_unique<Lang::CloudManager>(langpack()))
|
||||||
|
@ -122,12 +124,8 @@ Application::Application(not_null<Launcher*> launcher)
|
||||||
}, _lifetime);
|
}, _lifetime);
|
||||||
|
|
||||||
accounts().activeValue(
|
accounts().activeValue(
|
||||||
) | rpl::map([=](Main::Account *account) {
|
) | rpl::filter(rpl::mappers::_1 != nullptr
|
||||||
return account ? account->mtpValue() : rpl::never<MTP::Instance*>();
|
) | rpl::take(1) | rpl::start_with_next([=] {
|
||||||
}) | rpl::flatten_latest(
|
|
||||||
) | rpl::filter([=](MTP::Instance *instance) {
|
|
||||||
return instance != nullptr;
|
|
||||||
}) | rpl::start_with_next([=] {
|
|
||||||
if (_window) {
|
if (_window) {
|
||||||
// Global::DesktopNotify is used in updateTrayMenu.
|
// Global::DesktopNotify is used in updateTrayMenu.
|
||||||
// This should be called when user settings are read.
|
// This should be called when user settings are read.
|
||||||
|
@ -149,14 +147,7 @@ Application::~Application() {
|
||||||
}
|
}
|
||||||
|
|
||||||
unlockTerms();
|
unlockTerms();
|
||||||
for (const auto &[index, account] : accounts().list()) {
|
accounts().finish();
|
||||||
if (account->sessionExists()) {
|
|
||||||
account->session().saveSettingsNowIfNeeded();
|
|
||||||
}
|
|
||||||
// Some MTP requests can be cancelled from data clearing.
|
|
||||||
account->destroySession();
|
|
||||||
account->clearMtp();
|
|
||||||
}
|
|
||||||
|
|
||||||
Local::finish();
|
Local::finish();
|
||||||
|
|
||||||
|
@ -269,7 +260,7 @@ void Application::run() {
|
||||||
_window->showSettings();
|
_window->showSettings();
|
||||||
}
|
}
|
||||||
|
|
||||||
_window->updateIsActive(Global::OnlineFocusTimeout());
|
_window->updateIsActiveFocus();
|
||||||
|
|
||||||
for (const auto &error : Shortcuts::Errors()) {
|
for (const auto &error : Shortcuts::Errors()) {
|
||||||
LOG(("Shortcuts Error: %1").arg(error));
|
LOG(("Shortcuts Error: %1").arg(error));
|
||||||
|
@ -399,6 +390,30 @@ void Application::saveSettingsDelayed(crl::time delay) {
|
||||||
_saveSettingsTimer.callOnce(delay);
|
_saveSettingsTimer.callOnce(delay);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
MTP::Config &Application::fallbackProductionConfig() const {
|
||||||
|
if (!_fallbackProductionConfig) {
|
||||||
|
_fallbackProductionConfig = std::make_unique<MTP::Config>(
|
||||||
|
MTP::Environment::Production);
|
||||||
|
}
|
||||||
|
return *_fallbackProductionConfig;
|
||||||
|
}
|
||||||
|
|
||||||
|
void Application::refreshFallbackProductionConfig(
|
||||||
|
const MTP::Config &config) {
|
||||||
|
if (config.environment() == MTP::Environment::Production) {
|
||||||
|
_fallbackProductionConfig = std::make_unique<MTP::Config>(config);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
void Application::constructFallbackProductionConfig(
|
||||||
|
const QByteArray &serialized) {
|
||||||
|
if (auto config = MTP::Config::FromSerialized(serialized)) {
|
||||||
|
if (config->environment() == MTP::Environment::Production) {
|
||||||
|
_fallbackProductionConfig = std::move(config);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
void Application::setCurrentProxy(
|
void Application::setCurrentProxy(
|
||||||
const MTP::ProxyData &proxy,
|
const MTP::ProxyData &proxy,
|
||||||
MTP::ProxyData::Settings settings) {
|
MTP::ProxyData::Settings settings) {
|
||||||
|
@ -436,18 +451,6 @@ void Application::badMtprotoConfigurationError() {
|
||||||
|
|
||||||
void Application::startLocalStorage() {
|
void Application::startLocalStorage() {
|
||||||
Local::start();
|
Local::start();
|
||||||
|
|
||||||
const auto writing = _lifetime.make_state<bool>(false);
|
|
||||||
_dcOptions->changed(
|
|
||||||
) | rpl::filter([=] {
|
|
||||||
return !*writing;
|
|
||||||
}) | rpl::start_with_next([=] {
|
|
||||||
*writing = true;
|
|
||||||
Ui::PostponeCall(this, [=] {
|
|
||||||
Local::writeSettings();
|
|
||||||
});
|
|
||||||
}, _lifetime);
|
|
||||||
|
|
||||||
_saveSettingsTimer.setCallback([=] { Local::writeSettings(); });
|
_saveSettingsTimer.setCallback([=] { Local::writeSettings(); });
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -498,13 +501,13 @@ void Application::stateChanged(Qt::ApplicationState state) {
|
||||||
void Application::handleAppActivated() {
|
void Application::handleAppActivated() {
|
||||||
checkLocalTime();
|
checkLocalTime();
|
||||||
if (_window) {
|
if (_window) {
|
||||||
_window->updateIsActive(Global::OnlineFocusTimeout());
|
_window->updateIsActiveFocus();
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
void Application::handleAppDeactivated() {
|
void Application::handleAppDeactivated() {
|
||||||
if (_window) {
|
if (_window) {
|
||||||
_window->updateIsActive(Global::OfflineBlurTimeout());
|
_window->updateIsActiveBlur();
|
||||||
}
|
}
|
||||||
Ui::Tooltip::Hide();
|
Ui::Tooltip::Hide();
|
||||||
}
|
}
|
||||||
|
@ -530,21 +533,6 @@ void Application::switchDebugMode() {
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
void Application::switchTestMode() {
|
|
||||||
if (cTestMode()) {
|
|
||||||
QFile(cWorkingDir() + qsl("tdata/withtestmode")).remove();
|
|
||||||
cSetTestMode(false);
|
|
||||||
} else {
|
|
||||||
QFile f(cWorkingDir() + qsl("tdata/withtestmode"));
|
|
||||||
if (f.open(QIODevice::WriteOnly)) {
|
|
||||||
f.write("1");
|
|
||||||
f.close();
|
|
||||||
}
|
|
||||||
cSetTestMode(true);
|
|
||||||
}
|
|
||||||
App::restart();
|
|
||||||
}
|
|
||||||
|
|
||||||
void Application::switchFreeType() {
|
void Application::switchFreeType() {
|
||||||
if (cUseFreeType()) {
|
if (cUseFreeType()) {
|
||||||
QFile(cWorkingDir() + qsl("tdata/withfreetype")).remove();
|
QFile(cWorkingDir() + qsl("tdata/withfreetype")).remove();
|
||||||
|
@ -613,45 +601,6 @@ bool Application::canApplyLangPackWithoutRestart() const {
|
||||||
return true;
|
return true;
|
||||||
}
|
}
|
||||||
|
|
||||||
void Application::setInternalLinkDomain(const QString &domain) const {
|
|
||||||
// This domain should start with 'http[s]://' and end with '/'.
|
|
||||||
// Like 'https://telegram.me/' or 'https://t.me/'.
|
|
||||||
auto validate = [](const auto &domain) {
|
|
||||||
const auto prefixes = {
|
|
||||||
qstr("https://"),
|
|
||||||
qstr("http://"),
|
|
||||||
};
|
|
||||||
for (const auto &prefix : prefixes) {
|
|
||||||
if (domain.startsWith(prefix, Qt::CaseInsensitive)) {
|
|
||||||
return domain.endsWith('/');
|
|
||||||
}
|
|
||||||
}
|
|
||||||
return false;
|
|
||||||
};
|
|
||||||
if (validate(domain) && domain != Global::InternalLinksDomain()) {
|
|
||||||
Global::SetInternalLinksDomain(domain);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
QString Application::createInternalLink(const QString &query) const {
|
|
||||||
auto result = createInternalLinkFull(query);
|
|
||||||
auto prefixes = {
|
|
||||||
qstr("https://"),
|
|
||||||
qstr("http://"),
|
|
||||||
};
|
|
||||||
for (auto &prefix : prefixes) {
|
|
||||||
if (result.startsWith(prefix, Qt::CaseInsensitive)) {
|
|
||||||
return result.mid(prefix.size());
|
|
||||||
}
|
|
||||||
}
|
|
||||||
LOG(("Warning: bad internal url '%1'").arg(result));
|
|
||||||
return result;
|
|
||||||
}
|
|
||||||
|
|
||||||
QString Application::createInternalLinkFull(const QString &query) const {
|
|
||||||
return Global::InternalLinksDomain() + query;
|
|
||||||
}
|
|
||||||
|
|
||||||
void Application::checkStartUrl() {
|
void Application::checkStartUrl() {
|
||||||
if (!cStartUrl().isEmpty() && !locked()) {
|
if (!cStartUrl().isEmpty() && !locked()) {
|
||||||
const auto url = cStartUrl();
|
const auto url = cStartUrl();
|
||||||
|
|
|
@ -49,7 +49,7 @@ class BoxContent;
|
||||||
} // namespace Ui
|
} // namespace Ui
|
||||||
|
|
||||||
namespace MTP {
|
namespace MTP {
|
||||||
class DcOptions;
|
class Config;
|
||||||
class Instance;
|
class Instance;
|
||||||
class AuthKey;
|
class AuthKey;
|
||||||
using AuthKeyPtr = std::shared_ptr<AuthKey>;
|
using AuthKeyPtr = std::shared_ptr<AuthKey>;
|
||||||
|
@ -82,6 +82,11 @@ struct LocalUrlHandler;
|
||||||
|
|
||||||
class Application final : public QObject, private base::Subscriber {
|
class Application final : public QObject, private base::Subscriber {
|
||||||
public:
|
public:
|
||||||
|
struct ProxyChange {
|
||||||
|
MTP::ProxyData was;
|
||||||
|
MTP::ProxyData now;
|
||||||
|
};
|
||||||
|
|
||||||
Application(not_null<Launcher*> launcher);
|
Application(not_null<Launcher*> launcher);
|
||||||
Application(const Application &other) = delete;
|
Application(const Application &other) = delete;
|
||||||
Application &operator=(const Application &other) = delete;
|
Application &operator=(const Application &other) = delete;
|
||||||
|
@ -132,14 +137,10 @@ public:
|
||||||
}
|
}
|
||||||
void saveSettingsDelayed(crl::time delay = kDefaultSaveDelay);
|
void saveSettingsDelayed(crl::time delay = kDefaultSaveDelay);
|
||||||
|
|
||||||
// Dc options and proxy.
|
// Fallback config and proxy.
|
||||||
[[nodiscard]] not_null<MTP::DcOptions*> dcOptions() {
|
[[nodiscard]] MTP::Config &fallbackProductionConfig() const;
|
||||||
return _dcOptions.get();
|
void refreshFallbackProductionConfig(const MTP::Config &config);
|
||||||
}
|
void constructFallbackProductionConfig(const QByteArray &serialized);
|
||||||
struct ProxyChange {
|
|
||||||
MTP::ProxyData was;
|
|
||||||
MTP::ProxyData now;
|
|
||||||
};
|
|
||||||
void setCurrentProxy(
|
void setCurrentProxy(
|
||||||
const MTP::ProxyData &proxy,
|
const MTP::ProxyData &proxy,
|
||||||
MTP::ProxyData::Settings settings);
|
MTP::ProxyData::Settings settings);
|
||||||
|
@ -183,9 +184,6 @@ public:
|
||||||
}
|
}
|
||||||
|
|
||||||
// Internal links.
|
// Internal links.
|
||||||
void setInternalLinkDomain(const QString &domain) const;
|
|
||||||
[[nodiscard]] QString createInternalLink(const QString &query) const;
|
|
||||||
[[nodiscard]] QString createInternalLinkFull(const QString &query) const;
|
|
||||||
void checkStartUrl();
|
void checkStartUrl();
|
||||||
bool openLocalUrl(const QString &url, QVariant context);
|
bool openLocalUrl(const QString &url, QVariant context);
|
||||||
bool openInternalUrl(const QString &url, QVariant context);
|
bool openInternalUrl(const QString &url, QVariant context);
|
||||||
|
@ -231,7 +229,6 @@ public:
|
||||||
void handleAppDeactivated();
|
void handleAppDeactivated();
|
||||||
|
|
||||||
void switchDebugMode();
|
void switchDebugMode();
|
||||||
void switchTestMode();
|
|
||||||
void switchFreeType();
|
void switchFreeType();
|
||||||
void writeInstallBetaVersionsSetting();
|
void writeInstallBetaVersionsSetting();
|
||||||
|
|
||||||
|
@ -284,7 +281,7 @@ private:
|
||||||
|
|
||||||
const std::unique_ptr<Storage::Databases> _databases;
|
const std::unique_ptr<Storage::Databases> _databases;
|
||||||
const std::unique_ptr<Ui::Animations::Manager> _animationsManager;
|
const std::unique_ptr<Ui::Animations::Manager> _animationsManager;
|
||||||
const std::unique_ptr<MTP::DcOptions> _dcOptions;
|
mutable std::unique_ptr<MTP::Config> _fallbackProductionConfig;
|
||||||
const std::unique_ptr<Main::Accounts> _accounts;
|
const std::unique_ptr<Main::Accounts> _accounts;
|
||||||
std::unique_ptr<Window::Controller> _window;
|
std::unique_ptr<Window::Controller> _window;
|
||||||
std::unique_ptr<Media::View::OverlayWidget> _mediaView;
|
std::unique_ptr<Media::View::OverlayWidget> _mediaView;
|
||||||
|
|
|
@ -97,12 +97,6 @@ void ComputeDebugMode() {
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
void ComputeTestMode() {
|
|
||||||
if (QFile::exists(cWorkingDir() + qsl("tdata/withtestmode"))) {
|
|
||||||
cSetTestMode(true);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
void ComputeExternalUpdater() {
|
void ComputeExternalUpdater() {
|
||||||
QFile file(qsl("/etc/tdesktop/externalupdater"));
|
QFile file(qsl("/etc/tdesktop/externalupdater"));
|
||||||
|
|
||||||
|
@ -350,7 +344,6 @@ int Launcher::exec() {
|
||||||
void Launcher::workingFolderReady() {
|
void Launcher::workingFolderReady() {
|
||||||
srand((unsigned int)time(nullptr));
|
srand((unsigned int)time(nullptr));
|
||||||
|
|
||||||
ComputeTestMode();
|
|
||||||
ComputeDebugMode();
|
ComputeDebugMode();
|
||||||
ComputeExternalUpdater();
|
ComputeExternalUpdater();
|
||||||
ComputeFreeType();
|
ComputeFreeType();
|
||||||
|
@ -476,7 +469,6 @@ void Launcher::processArguments() {
|
||||||
if (parseResult.contains("-externalupdater")) {
|
if (parseResult.contains("-externalupdater")) {
|
||||||
SetUpdaterDisabledAtStartup();
|
SetUpdaterDisabledAtStartup();
|
||||||
}
|
}
|
||||||
gTestMode = parseResult.contains("-testmode");
|
|
||||||
gUseFreeType = parseResult.contains("-freetype");
|
gUseFreeType = parseResult.contains("-freetype");
|
||||||
Logs::SetDebugEnabled(parseResult.contains("-debug"));
|
Logs::SetDebugEnabled(parseResult.contains("-debug"));
|
||||||
gManyInstance = parseResult.contains("-many");
|
gManyInstance = parseResult.contains("-many");
|
||||||
|
|
|
@ -20,9 +20,9 @@ https://github.com/telegramdesktop/tdesktop/blob/master/LEGAL
|
||||||
#include "main/main_account.h"
|
#include "main/main_account.h"
|
||||||
//#include "storage/storage_feed_messages.h" // #feed
|
//#include "storage/storage_feed_messages.h" // #feed
|
||||||
#include "main/main_session.h"
|
#include "main/main_session.h"
|
||||||
|
#include "mtproto/mtproto_config.h"
|
||||||
#include "apiwrap.h"
|
#include "apiwrap.h"
|
||||||
#include "mainwidget.h"
|
#include "mainwidget.h"
|
||||||
#include "facades.h"
|
|
||||||
#include "styles/style_dialogs.h"
|
#include "styles/style_dialogs.h"
|
||||||
|
|
||||||
namespace Data {
|
namespace Data {
|
||||||
|
@ -31,17 +31,6 @@ namespace {
|
||||||
constexpr auto kLoadedChatsMinCount = 20;
|
constexpr auto kLoadedChatsMinCount = 20;
|
||||||
constexpr auto kShowChatNamesCount = 8;
|
constexpr auto kShowChatNamesCount = 8;
|
||||||
|
|
||||||
rpl::producer<int> PinnedDialogsInFolderMaxValue(
|
|
||||||
not_null<Main::Session*> session) {
|
|
||||||
return rpl::single(
|
|
||||||
rpl::empty_value()
|
|
||||||
) | rpl::then(
|
|
||||||
session->account().configUpdates()
|
|
||||||
) | rpl::map([=] {
|
|
||||||
return Global::PinnedDialogsInFolderMax();
|
|
||||||
});
|
|
||||||
}
|
|
||||||
|
|
||||||
} // namespace
|
} // namespace
|
||||||
|
|
||||||
// #feed
|
// #feed
|
||||||
|
@ -60,7 +49,7 @@ Folder::Folder(not_null<Data::Session*> owner, FolderId id)
|
||||||
, _chatsList(
|
, _chatsList(
|
||||||
&owner->session(),
|
&owner->session(),
|
||||||
FilterId(),
|
FilterId(),
|
||||||
PinnedDialogsInFolderMaxValue(&owner->session()))
|
owner->session().serverConfig().pinnedDialogsInFolderMax.value())
|
||||||
, _name(tr::lng_archived_name(tr::now)) {
|
, _name(tr::lng_archived_name(tr::now)) {
|
||||||
indexNameParts();
|
indexNameParts();
|
||||||
|
|
||||||
|
|
|
@ -24,6 +24,7 @@ https://github.com/telegramdesktop/tdesktop/blob/master/LEGAL
|
||||||
#include "main/main_session.h"
|
#include "main/main_session.h"
|
||||||
#include "main/main_account.h"
|
#include "main/main_account.h"
|
||||||
#include "main/main_app_config.h"
|
#include "main/main_app_config.h"
|
||||||
|
#include "mtproto/mtproto_config.h"
|
||||||
#include "core/application.h"
|
#include "core/application.h"
|
||||||
#include "mainwindow.h"
|
#include "mainwindow.h"
|
||||||
#include "window/window_session_controller.h"
|
#include "window/window_session_controller.h"
|
||||||
|
@ -34,7 +35,7 @@ https://github.com/telegramdesktop/tdesktop/blob/master/LEGAL
|
||||||
#include "history/view/history_view_element.h"
|
#include "history/view/history_view_element.h"
|
||||||
#include "history/history_item.h"
|
#include "history/history_item.h"
|
||||||
#include "storage/file_download.h"
|
#include "storage/file_download.h"
|
||||||
#include "facades.h"
|
#include "facades.h" // Ui::showPeerProfile
|
||||||
#include "app.h"
|
#include "app.h"
|
||||||
|
|
||||||
namespace {
|
namespace {
|
||||||
|
@ -763,8 +764,8 @@ Data::RestrictionCheckResult PeerData::amRestricted(
|
||||||
bool PeerData::canRevokeFullHistory() const {
|
bool PeerData::canRevokeFullHistory() const {
|
||||||
return isUser()
|
return isUser()
|
||||||
&& !isSelf()
|
&& !isSelf()
|
||||||
&& Global::RevokePrivateInbox()
|
&& session().serverConfig().revokePrivateInbox
|
||||||
&& (Global::RevokePrivateTimeLimit() == 0x7FFFFFFF);
|
&& (session().serverConfig().revokePrivateTimeLimit == 0x7FFFFFFF);
|
||||||
}
|
}
|
||||||
|
|
||||||
bool PeerData::slowmodeApplied() const {
|
bool PeerData::slowmodeApplied() const {
|
||||||
|
|
|
@ -18,6 +18,7 @@ https://github.com/telegramdesktop/tdesktop/blob/master/LEGAL
|
||||||
#include "ui/image/image_location_factory.h" // Images::FromPhotoSize
|
#include "ui/image/image_location_factory.h" // Images::FromPhotoSize
|
||||||
#include "export/export_controller.h"
|
#include "export/export_controller.h"
|
||||||
#include "export/view/export_view_panel_controller.h"
|
#include "export/view/export_view_panel_controller.h"
|
||||||
|
#include "mtproto/mtproto_config.h"
|
||||||
#include "window/notifications_manager.h"
|
#include "window/notifications_manager.h"
|
||||||
#include "history/history.h"
|
#include "history/history.h"
|
||||||
#include "history/history_item_components.h"
|
#include "history/history_item_components.h"
|
||||||
|
@ -54,7 +55,7 @@ https://github.com/telegramdesktop/tdesktop/blob/master/LEGAL
|
||||||
#include "base/platform/base_platform_info.h"
|
#include "base/platform/base_platform_info.h"
|
||||||
#include "base/unixtime.h"
|
#include "base/unixtime.h"
|
||||||
#include "base/call_delayed.h"
|
#include "base/call_delayed.h"
|
||||||
#include "facades.h"
|
#include "facades.h" // Notify::switchInlineBotButtonReceived
|
||||||
#include "app.h"
|
#include "app.h"
|
||||||
#include "styles/style_boxes.h" // st::backgroundSize
|
#include "styles/style_boxes.h" // st::backgroundSize
|
||||||
|
|
||||||
|
@ -188,17 +189,6 @@ std::vector<UnavailableReason> ExtractUnavailableReasons(
|
||||||
return FindInlineThumbnail(data.vsizes().v);
|
return FindInlineThumbnail(data.vsizes().v);
|
||||||
}
|
}
|
||||||
|
|
||||||
[[nodiscard]] rpl::producer<int> PinnedDialogsCountMaxValue(
|
|
||||||
not_null<Main::Session*> session) {
|
|
||||||
return rpl::single(
|
|
||||||
rpl::empty_value()
|
|
||||||
) | rpl::then(
|
|
||||||
session->account().configUpdates()
|
|
||||||
) | rpl::map([=] {
|
|
||||||
return Global::PinnedDialogsCountMax();
|
|
||||||
});
|
|
||||||
}
|
|
||||||
|
|
||||||
} // namespace
|
} // namespace
|
||||||
|
|
||||||
Session::Session(not_null<Main::Session*> session)
|
Session::Session(not_null<Main::Session*> session)
|
||||||
|
@ -209,7 +199,10 @@ Session::Session(not_null<Main::Session*> session)
|
||||||
, _bigFileCache(Core::App().databases().get(
|
, _bigFileCache(Core::App().databases().get(
|
||||||
_session->local().cacheBigFilePath(),
|
_session->local().cacheBigFilePath(),
|
||||||
_session->local().cacheBigFileSettings()))
|
_session->local().cacheBigFileSettings()))
|
||||||
, _chatsList(session, FilterId(), PinnedDialogsCountMaxValue(session))
|
, _chatsList(
|
||||||
|
session,
|
||||||
|
FilterId(),
|
||||||
|
session->serverConfig().pinnedDialogsCountMax.value())
|
||||||
, _contactsList(Dialogs::SortMode::Name)
|
, _contactsList(Dialogs::SortMode::Name)
|
||||||
, _contactsNoChatsList(Dialogs::SortMode::Name)
|
, _contactsNoChatsList(Dialogs::SortMode::Name)
|
||||||
, _selfDestructTimer([=] { checkSelfDestructItems(); })
|
, _selfDestructTimer([=] { checkSelfDestructItems(); })
|
||||||
|
@ -929,7 +922,7 @@ void Session::startExport(const MTPInputPeer &singlePeer) {
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
_export = std::make_unique<Export::Controller>(
|
_export = std::make_unique<Export::Controller>(
|
||||||
session().mtp().get(),
|
&session().mtp(),
|
||||||
singlePeer);
|
singlePeer);
|
||||||
_exportPanel = std::make_unique<Export::View::PanelController>(
|
_exportPanel = std::make_unique<Export::View::PanelController>(
|
||||||
&session(),
|
&session(),
|
||||||
|
@ -1660,8 +1653,8 @@ int Session::pinnedChatsLimit(
|
||||||
FilterId filterId) const {
|
FilterId filterId) const {
|
||||||
if (!filterId) {
|
if (!filterId) {
|
||||||
return folder
|
return folder
|
||||||
? Global::PinnedDialogsInFolderMax()
|
? session().serverConfig().pinnedDialogsInFolderMax.current()
|
||||||
: Global::PinnedDialogsCountMax();
|
: session().serverConfig().pinnedDialogsCountMax.current();
|
||||||
}
|
}
|
||||||
const auto &list = chatsFilters().list();
|
const auto &list = chatsFilters().list();
|
||||||
const auto i = ranges::find(list, filterId, &Data::ChatFilter::id);
|
const auto i = ranges::find(list, filterId, &Data::ChatFilter::id);
|
||||||
|
|
|
@ -48,7 +48,7 @@ Storage::Cache::Key DocumentThumbCacheKey(int32 dcId, uint64 id) {
|
||||||
}
|
}
|
||||||
|
|
||||||
Storage::Cache::Key WebDocumentCacheKey(const WebFileLocation &location) {
|
Storage::Cache::Key WebDocumentCacheKey(const WebFileLocation &location) {
|
||||||
const auto CacheDcId = cTestMode() ? 2 : 4;
|
const auto CacheDcId = 4; // The default production value. Doesn't matter.
|
||||||
const auto dcId = uint64(CacheDcId) & 0xFFULL;
|
const auto dcId = uint64(CacheDcId) & 0xFFULL;
|
||||||
const auto &url = location.url();
|
const auto &url = location.url();
|
||||||
const auto hash = openssl::Sha256(bytes::make_span(url));
|
const auto hash = openssl::Sha256(bytes::make_span(url));
|
||||||
|
|
|
@ -154,11 +154,11 @@ bool WallPaper::hasShareUrl() const {
|
||||||
return !_slug.isEmpty();
|
return !_slug.isEmpty();
|
||||||
}
|
}
|
||||||
|
|
||||||
QString WallPaper::shareUrl() const {
|
QString WallPaper::shareUrl(not_null<Main::Session*> session) const {
|
||||||
if (!hasShareUrl()) {
|
if (!hasShareUrl()) {
|
||||||
return QString();
|
return QString();
|
||||||
}
|
}
|
||||||
const auto base = Core::App().createInternalLinkFull("bg/" + _slug);
|
const auto base = session->createInternalLinkFull("bg/" + _slug);
|
||||||
auto params = QStringList();
|
auto params = QStringList();
|
||||||
if (isPattern()) {
|
if (isPattern()) {
|
||||||
if (_backgroundColor) {
|
if (_backgroundColor) {
|
||||||
|
|
|
@ -35,7 +35,7 @@ public:
|
||||||
[[nodiscard]] bool isBlurred() const;
|
[[nodiscard]] bool isBlurred() const;
|
||||||
[[nodiscard]] int patternIntensity() const;
|
[[nodiscard]] int patternIntensity() const;
|
||||||
[[nodiscard]] bool hasShareUrl() const;
|
[[nodiscard]] bool hasShareUrl() const;
|
||||||
[[nodiscard]] QString shareUrl() const;
|
[[nodiscard]] QString shareUrl(not_null<Main::Session*> session) const;
|
||||||
|
|
||||||
void loadDocument() const;
|
void loadDocument() const;
|
||||||
void loadDocumentThumbnail() const;
|
void loadDocumentThumbnail() const;
|
||||||
|
|
|
@ -19,10 +19,10 @@ https://github.com/telegramdesktop/tdesktop/blob/master/LEGAL
|
||||||
#include "apiwrap.h"
|
#include "apiwrap.h"
|
||||||
#include "storage/storage_account.h"
|
#include "storage/storage_account.h"
|
||||||
#include "main/main_session.h"
|
#include "main/main_session.h"
|
||||||
|
#include "mtproto/mtproto_config.h"
|
||||||
#include "ui/toast/toast.h"
|
#include "ui/toast/toast.h"
|
||||||
#include "ui/image/image_location_factory.h"
|
#include "ui/image/image_location_factory.h"
|
||||||
#include "base/unixtime.h"
|
#include "base/unixtime.h"
|
||||||
#include "facades.h"
|
|
||||||
#include "styles/style_chat_helpers.h"
|
#include "styles/style_chat_helpers.h"
|
||||||
|
|
||||||
namespace Data {
|
namespace Data {
|
||||||
|
@ -142,7 +142,9 @@ void Stickers::incrementSticker(not_null<DocumentData*> document) {
|
||||||
break;
|
break;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
while (!recent.isEmpty() && set->stickers.size() + recent.size() > Global::StickersRecentLimit()) {
|
while (!recent.isEmpty()
|
||||||
|
&& (set->stickers.size() + recent.size()
|
||||||
|
> session().serverConfig().stickersRecentLimit)) {
|
||||||
writeOldRecent = true;
|
writeOldRecent = true;
|
||||||
recent.pop_back();
|
recent.pop_back();
|
||||||
}
|
}
|
||||||
|
@ -184,7 +186,7 @@ void Stickers::addSavedGif(not_null<DocumentData*> document) {
|
||||||
_savedGifs.remove(index);
|
_savedGifs.remove(index);
|
||||||
}
|
}
|
||||||
_savedGifs.push_front(document);
|
_savedGifs.push_front(document);
|
||||||
if (_savedGifs.size() > Global::SavedGifsLimit()) {
|
if (_savedGifs.size() > session().serverConfig().savedGifsLimit) {
|
||||||
_savedGifs.pop_back();
|
_savedGifs.pop_back();
|
||||||
}
|
}
|
||||||
session().local().writeSavedGifs();
|
session().local().writeSavedGifs();
|
||||||
|
@ -387,7 +389,7 @@ bool Stickers::isFaved(not_null<const DocumentData*> document) {
|
||||||
}
|
}
|
||||||
|
|
||||||
void Stickers::checkFavedLimit(StickersSet &set) {
|
void Stickers::checkFavedLimit(StickersSet &set) {
|
||||||
if (set.stickers.size() <= Global::StickersFavedLimit()) {
|
if (set.stickers.size() <= session().serverConfig().stickersFavedLimit) {
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
auto removing = set.stickers.back();
|
auto removing = set.stickers.back();
|
||||||
|
|
|
@ -12,6 +12,7 @@ https://github.com/telegramdesktop/tdesktop/blob/master/LEGAL
|
||||||
#include "ui/widgets/labels.h"
|
#include "ui/widgets/labels.h"
|
||||||
#include "ui/widgets/separate_panel.h"
|
#include "ui/widgets/separate_panel.h"
|
||||||
#include "ui/wrap/padding_wrap.h"
|
#include "ui/wrap/padding_wrap.h"
|
||||||
|
#include "mtproto/mtproto_config.h"
|
||||||
#include "boxes/confirm_box.h"
|
#include "boxes/confirm_box.h"
|
||||||
#include "lang/lang_keys.h"
|
#include "lang/lang_keys.h"
|
||||||
#include "storage/storage_account.h"
|
#include "storage/storage_account.h"
|
||||||
|
@ -20,7 +21,6 @@ https://github.com/telegramdesktop/tdesktop/blob/master/LEGAL
|
||||||
#include "data/data_session.h"
|
#include "data/data_session.h"
|
||||||
#include "base/platform/base_platform_info.h"
|
#include "base/platform/base_platform_info.h"
|
||||||
#include "base/unixtime.h"
|
#include "base/unixtime.h"
|
||||||
#include "facades.h"
|
|
||||||
#include "styles/style_export.h"
|
#include "styles/style_export.h"
|
||||||
#include "styles/style_layers.h"
|
#include "styles/style_layers.h"
|
||||||
|
|
||||||
|
@ -77,9 +77,9 @@ void SuggestBox::prepare() {
|
||||||
|
|
||||||
} // namespace
|
} // namespace
|
||||||
|
|
||||||
Environment PrepareEnvironment() {
|
Environment PrepareEnvironment(not_null<Main::Session*> session) {
|
||||||
auto result = Environment();
|
auto result = Environment();
|
||||||
result.internalLinksDomain = Global::InternalLinksDomain();
|
result.internalLinksDomain = session->serverConfig().internalLinksDomain;
|
||||||
result.aboutTelegram = tr::lng_export_about_telegram(tr::now).toUtf8();
|
result.aboutTelegram = tr::lng_export_about_telegram(tr::now).toUtf8();
|
||||||
result.aboutContacts = tr::lng_export_about_contacts(tr::now).toUtf8();
|
result.aboutContacts = tr::lng_export_about_contacts(tr::now).toUtf8();
|
||||||
result.aboutFrequent = tr::lng_export_about_frequent(tr::now).toUtf8();
|
result.aboutFrequent = tr::lng_export_about_frequent(tr::now).toUtf8();
|
||||||
|
@ -188,7 +188,7 @@ void PanelController::showSettings() {
|
||||||
settings->startClicks(
|
settings->startClicks(
|
||||||
) | rpl::start_with_next([=]() {
|
) | rpl::start_with_next([=]() {
|
||||||
showProgress();
|
showProgress();
|
||||||
_process->startExport(*_settings, PrepareEnvironment());
|
_process->startExport(*_settings, PrepareEnvironment(_session));
|
||||||
}, settings->lifetime());
|
}, settings->lifetime());
|
||||||
|
|
||||||
settings->cancelClicks(
|
settings->cancelClicks(
|
||||||
|
|
|
@ -22,12 +22,8 @@ class Session;
|
||||||
} // namespace Main
|
} // namespace Main
|
||||||
|
|
||||||
namespace Export {
|
namespace Export {
|
||||||
|
|
||||||
struct Environment;
|
|
||||||
|
|
||||||
namespace View {
|
namespace View {
|
||||||
|
|
||||||
Environment PrepareEnvironment();
|
|
||||||
QPointer<Ui::BoxContent> SuggestStart(not_null<Main::Session*> session);
|
QPointer<Ui::BoxContent> SuggestStart(not_null<Main::Session*> session);
|
||||||
void ClearSuggestStart(not_null<Main::Session*> session);
|
void ClearSuggestStart(not_null<Main::Session*> session);
|
||||||
bool IsDefaultPath(not_null<Main::Session*> session, const QString &path);
|
bool IsDefaultPath(not_null<Main::Session*> session, const QString &path);
|
||||||
|
|
|
@ -356,43 +356,6 @@ struct Data {
|
||||||
float64 VideoVolume = kDefaultVolume;
|
float64 VideoVolume = kDefaultVolume;
|
||||||
base::Observable<void> VideoVolumeChanged;
|
base::Observable<void> VideoVolumeChanged;
|
||||||
|
|
||||||
// config
|
|
||||||
int32 ChatSizeMax = 200;
|
|
||||||
int32 MegagroupSizeMax = 10000;
|
|
||||||
int32 ForwardedCountMax = 100;
|
|
||||||
int32 OnlineUpdatePeriod = 120000;
|
|
||||||
int32 OfflineBlurTimeout = 5000;
|
|
||||||
int32 OfflineIdleTimeout = 30000;
|
|
||||||
int32 OnlineFocusTimeout = 1000;
|
|
||||||
int32 OnlineCloudTimeout = 300000;
|
|
||||||
int32 NotifyCloudDelay = 30000;
|
|
||||||
int32 NotifyDefaultDelay = 1500;
|
|
||||||
int32 PushChatPeriod = 60000;
|
|
||||||
int32 PushChatLimit = 2;
|
|
||||||
int32 SavedGifsLimit = 200;
|
|
||||||
int32 EditTimeLimit = 172800;
|
|
||||||
int32 RevokeTimeLimit = 172800;
|
|
||||||
int32 RevokePrivateTimeLimit = 172800;
|
|
||||||
bool RevokePrivateInbox = false;
|
|
||||||
int32 StickersRecentLimit = 30;
|
|
||||||
int32 StickersFavedLimit = 5;
|
|
||||||
int32 PinnedDialogsCountMax = 5;
|
|
||||||
int32 PinnedDialogsInFolderMax = 100;
|
|
||||||
QString InternalLinksDomain = qsl("https://t.me/");
|
|
||||||
int32 ChannelsReadMediaPeriod = 86400 * 7;
|
|
||||||
int32 CallReceiveTimeoutMs = 20000;
|
|
||||||
int32 CallRingTimeoutMs = 90000;
|
|
||||||
int32 CallConnectTimeoutMs = 30000;
|
|
||||||
int32 CallPacketTimeoutMs = 10000;
|
|
||||||
int32 WebFileDcId = cTestMode() ? 2 : 4;
|
|
||||||
QString TxtDomainString = cTestMode()
|
|
||||||
? qsl("tapv3.stel.com")
|
|
||||||
: qsl("apv3.stel.com");
|
|
||||||
bool PhoneCallsEnabled = true;
|
|
||||||
bool BlockedMode = false;
|
|
||||||
int32 CaptionLengthMax = 1024;
|
|
||||||
base::Observable<void> PhoneCallsEnabledChanged;
|
|
||||||
|
|
||||||
HiddenPinnedMessagesMap HiddenPinnedMessages;
|
HiddenPinnedMessagesMap HiddenPinnedMessages;
|
||||||
|
|
||||||
bool AskDownloadPath = false;
|
bool AskDownloadPath = false;
|
||||||
|
@ -475,41 +438,6 @@ DefineRefVar(Global, base::Observable<void>, SongVolumeChanged);
|
||||||
DefineVar(Global, float64, VideoVolume);
|
DefineVar(Global, float64, VideoVolume);
|
||||||
DefineRefVar(Global, base::Observable<void>, VideoVolumeChanged);
|
DefineRefVar(Global, base::Observable<void>, VideoVolumeChanged);
|
||||||
|
|
||||||
// config
|
|
||||||
DefineVar(Global, int32, ChatSizeMax);
|
|
||||||
DefineVar(Global, int32, MegagroupSizeMax);
|
|
||||||
DefineVar(Global, int32, ForwardedCountMax);
|
|
||||||
DefineVar(Global, int32, OnlineUpdatePeriod);
|
|
||||||
DefineVar(Global, int32, OfflineBlurTimeout);
|
|
||||||
DefineVar(Global, int32, OfflineIdleTimeout);
|
|
||||||
DefineVar(Global, int32, OnlineFocusTimeout);
|
|
||||||
DefineVar(Global, int32, OnlineCloudTimeout);
|
|
||||||
DefineVar(Global, int32, NotifyCloudDelay);
|
|
||||||
DefineVar(Global, int32, NotifyDefaultDelay);
|
|
||||||
DefineVar(Global, int32, PushChatPeriod);
|
|
||||||
DefineVar(Global, int32, PushChatLimit);
|
|
||||||
DefineVar(Global, int32, SavedGifsLimit);
|
|
||||||
DefineVar(Global, int32, EditTimeLimit);
|
|
||||||
DefineVar(Global, int32, RevokeTimeLimit);
|
|
||||||
DefineVar(Global, int32, RevokePrivateTimeLimit);
|
|
||||||
DefineVar(Global, bool, RevokePrivateInbox);
|
|
||||||
DefineVar(Global, int32, StickersRecentLimit);
|
|
||||||
DefineVar(Global, int32, StickersFavedLimit);
|
|
||||||
DefineVar(Global, int32, PinnedDialogsCountMax);
|
|
||||||
DefineVar(Global, int32, PinnedDialogsInFolderMax);
|
|
||||||
DefineVar(Global, QString, InternalLinksDomain);
|
|
||||||
DefineVar(Global, int32, ChannelsReadMediaPeriod);
|
|
||||||
DefineVar(Global, int32, CallReceiveTimeoutMs);
|
|
||||||
DefineVar(Global, int32, CallRingTimeoutMs);
|
|
||||||
DefineVar(Global, int32, CallConnectTimeoutMs);
|
|
||||||
DefineVar(Global, int32, CallPacketTimeoutMs);
|
|
||||||
DefineVar(Global, int32, WebFileDcId);
|
|
||||||
DefineVar(Global, QString, TxtDomainString);
|
|
||||||
DefineVar(Global, bool, PhoneCallsEnabled);
|
|
||||||
DefineVar(Global, bool, BlockedMode);
|
|
||||||
DefineVar(Global, int32, CaptionLengthMax);
|
|
||||||
DefineRefVar(Global, base::Observable<void>, PhoneCallsEnabledChanged);
|
|
||||||
|
|
||||||
DefineVar(Global, HiddenPinnedMessagesMap, HiddenPinnedMessages);
|
DefineVar(Global, HiddenPinnedMessagesMap, HiddenPinnedMessages);
|
||||||
|
|
||||||
DefineVar(Global, bool, AskDownloadPath);
|
DefineVar(Global, bool, AskDownloadPath);
|
||||||
|
|
|
@ -166,41 +166,6 @@ DeclareRefVar(base::Observable<void>, SongVolumeChanged);
|
||||||
DeclareVar(float64, VideoVolume);
|
DeclareVar(float64, VideoVolume);
|
||||||
DeclareRefVar(base::Observable<void>, VideoVolumeChanged);
|
DeclareRefVar(base::Observable<void>, VideoVolumeChanged);
|
||||||
|
|
||||||
// config
|
|
||||||
DeclareVar(int32, ChatSizeMax);
|
|
||||||
DeclareVar(int32, MegagroupSizeMax);
|
|
||||||
DeclareVar(int32, ForwardedCountMax);
|
|
||||||
DeclareVar(int32, OnlineUpdatePeriod);
|
|
||||||
DeclareVar(int32, OfflineBlurTimeout);
|
|
||||||
DeclareVar(int32, OfflineIdleTimeout);
|
|
||||||
DeclareVar(int32, OnlineFocusTimeout); // not from config
|
|
||||||
DeclareVar(int32, OnlineCloudTimeout);
|
|
||||||
DeclareVar(int32, NotifyCloudDelay);
|
|
||||||
DeclareVar(int32, NotifyDefaultDelay);
|
|
||||||
DeclareVar(int32, PushChatPeriod);
|
|
||||||
DeclareVar(int32, PushChatLimit);
|
|
||||||
DeclareVar(int32, SavedGifsLimit);
|
|
||||||
DeclareVar(int32, EditTimeLimit);
|
|
||||||
DeclareVar(int32, RevokeTimeLimit);
|
|
||||||
DeclareVar(int32, RevokePrivateTimeLimit);
|
|
||||||
DeclareVar(bool, RevokePrivateInbox);
|
|
||||||
DeclareVar(int32, StickersRecentLimit);
|
|
||||||
DeclareVar(int32, StickersFavedLimit);
|
|
||||||
DeclareVar(int32, PinnedDialogsCountMax);
|
|
||||||
DeclareVar(int32, PinnedDialogsInFolderMax);
|
|
||||||
DeclareVar(QString, InternalLinksDomain);
|
|
||||||
DeclareVar(int32, ChannelsReadMediaPeriod);
|
|
||||||
DeclareVar(int32, CallReceiveTimeoutMs);
|
|
||||||
DeclareVar(int32, CallRingTimeoutMs);
|
|
||||||
DeclareVar(int32, CallConnectTimeoutMs);
|
|
||||||
DeclareVar(int32, CallPacketTimeoutMs);
|
|
||||||
DeclareVar(int32, WebFileDcId);
|
|
||||||
DeclareVar(QString, TxtDomainString);
|
|
||||||
DeclareVar(bool, PhoneCallsEnabled);
|
|
||||||
DeclareVar(bool, BlockedMode);
|
|
||||||
DeclareVar(int32, CaptionLengthMax);
|
|
||||||
DeclareRefVar(base::Observable<void>, PhoneCallsEnabledChanged);
|
|
||||||
|
|
||||||
typedef QMap<PeerId, MsgId> HiddenPinnedMessagesMap;
|
typedef QMap<PeerId, MsgId> HiddenPinnedMessagesMap;
|
||||||
DeclareVar(HiddenPinnedMessagesMap, HiddenPinnedMessages);
|
DeclareVar(HiddenPinnedMessagesMap, HiddenPinnedMessages);
|
||||||
|
|
||||||
|
|
|
@ -229,7 +229,7 @@ InnerWidget::InnerWidget(
|
||||||
, _controller(controller)
|
, _controller(controller)
|
||||||
, _channel(channel)
|
, _channel(channel)
|
||||||
, _history(channel->owner().history(channel))
|
, _history(channel->owner().history(channel))
|
||||||
, _api(_channel->session().mtp())
|
, _api(&_channel->session().mtp())
|
||||||
, _scrollDateCheck([=] { scrollDateCheck(); })
|
, _scrollDateCheck([=] { scrollDateCheck(); })
|
||||||
, _emptyText(
|
, _emptyText(
|
||||||
st::historyAdminLogEmptyWidth
|
st::historyAdminLogEmptyWidth
|
||||||
|
|
|
@ -472,7 +472,11 @@ void GenerateItems(
|
||||||
auto bodyClientFlags = MTPDmessage_ClientFlag::f_admin_log_entry;
|
auto bodyClientFlags = MTPDmessage_ClientFlag::f_admin_log_entry;
|
||||||
auto bodyReplyTo = 0;
|
auto bodyReplyTo = 0;
|
||||||
auto bodyViaBotId = 0;
|
auto bodyViaBotId = 0;
|
||||||
auto newLink = newValue.isEmpty() ? TextWithEntities() : PrepareText(Core::App().createInternalLinkFull(newValue), QString());
|
auto newLink = newValue.isEmpty()
|
||||||
|
? TextWithEntities()
|
||||||
|
: PrepareText(
|
||||||
|
history->session().createInternalLinkFull(newValue),
|
||||||
|
QString());
|
||||||
auto body = history->makeMessage(
|
auto body = history->makeMessage(
|
||||||
history->nextNonHistoryEntryId(),
|
history->nextNonHistoryEntryId(),
|
||||||
bodyFlags,
|
bodyFlags,
|
||||||
|
@ -484,7 +488,9 @@ void GenerateItems(
|
||||||
QString(),
|
QString(),
|
||||||
newLink);
|
newLink);
|
||||||
if (!oldValue.isEmpty()) {
|
if (!oldValue.isEmpty()) {
|
||||||
auto oldLink = PrepareText(Core::App().createInternalLinkFull(oldValue), QString());
|
auto oldLink = PrepareText(
|
||||||
|
history->session().createInternalLinkFull(oldValue),
|
||||||
|
QString());
|
||||||
body->addLogEntryOriginal(id, tr::lng_admin_log_previous_link(tr::now), oldLink);
|
body->addLogEntryOriginal(id, tr::lng_admin_log_previous_link(tr::now), oldLink);
|
||||||
}
|
}
|
||||||
addPart(body);
|
addPart(body);
|
||||||
|
|
|
@ -17,6 +17,7 @@ https://github.com/telegramdesktop/tdesktop/blob/master/LEGAL
|
||||||
#include "history/history_service.h"
|
#include "history/history_service.h"
|
||||||
#include "history/history_message.h"
|
#include "history/history_message.h"
|
||||||
#include "history/history.h"
|
#include "history/history.h"
|
||||||
|
#include "mtproto/mtproto_config.h"
|
||||||
#include "media/clip/media_clip_reader.h"
|
#include "media/clip/media_clip_reader.h"
|
||||||
#include "ui/effects/ripple_animation.h"
|
#include "ui/effects/ripple_animation.h"
|
||||||
#include "ui/text/text_isolated_emoji.h"
|
#include "ui/text/text_isolated_emoji.h"
|
||||||
|
@ -42,7 +43,6 @@ https://github.com/telegramdesktop/tdesktop/blob/master/LEGAL
|
||||||
#include "data/data_channel.h"
|
#include "data/data_channel.h"
|
||||||
#include "data/data_chat.h"
|
#include "data/data_chat.h"
|
||||||
#include "data/data_user.h"
|
#include "data/data_user.h"
|
||||||
#include "facades.h"
|
|
||||||
#include "styles/style_dialogs.h"
|
#include "styles/style_dialogs.h"
|
||||||
#include "styles/style_history.h"
|
#include "styles/style_history.h"
|
||||||
|
|
||||||
|
@ -289,7 +289,8 @@ void HistoryItem::finishEditionToEmpty() {
|
||||||
bool HistoryItem::hasUnreadMediaFlag() const {
|
bool HistoryItem::hasUnreadMediaFlag() const {
|
||||||
if (_history->peer->isChannel()) {
|
if (_history->peer->isChannel()) {
|
||||||
const auto passed = base::unixtime::now() - date();
|
const auto passed = base::unixtime::now() - date();
|
||||||
if (passed >= Global::ChannelsReadMediaPeriod()) {
|
const auto &config = _history->session().serverConfig();
|
||||||
|
if (passed >= config.channelsReadMediaPeriod) {
|
||||||
return false;
|
return false;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
@ -566,12 +567,13 @@ bool HistoryItem::canDelete() const {
|
||||||
|
|
||||||
bool HistoryItem::canDeleteForEveryone(TimeId now) const {
|
bool HistoryItem::canDeleteForEveryone(TimeId now) const {
|
||||||
const auto peer = history()->peer;
|
const auto peer = history()->peer;
|
||||||
|
const auto &config = history()->session().serverConfig();
|
||||||
const auto messageToMyself = peer->isSelf();
|
const auto messageToMyself = peer->isSelf();
|
||||||
const auto messageTooOld = messageToMyself
|
const auto messageTooOld = messageToMyself
|
||||||
? false
|
? false
|
||||||
: peer->isUser()
|
: peer->isUser()
|
||||||
? (now - date() >= Global::RevokePrivateTimeLimit())
|
? (now - date() >= config.revokePrivateTimeLimit)
|
||||||
: (now - date() >= Global::RevokeTimeLimit());
|
: (now - date() >= config.revokeTimeLimit);
|
||||||
if (id < 0 || messageToMyself || messageTooOld || isPost()) {
|
if (id < 0 || messageToMyself || messageTooOld || isPost()) {
|
||||||
return false;
|
return false;
|
||||||
}
|
}
|
||||||
|
@ -599,7 +601,7 @@ bool HistoryItem::canDeleteForEveryone(TimeId now) const {
|
||||||
return false;
|
return false;
|
||||||
}
|
}
|
||||||
} else if (peer->isUser()) {
|
} else if (peer->isUser()) {
|
||||||
return Global::RevokePrivateInbox();
|
return config.revokePrivateInbox;
|
||||||
} else {
|
} else {
|
||||||
return false;
|
return false;
|
||||||
}
|
}
|
||||||
|
|
|
@ -33,6 +33,7 @@ https://github.com/telegramdesktop/tdesktop/blob/master/LEGAL
|
||||||
#include "window/notifications_manager.h"
|
#include "window/notifications_manager.h"
|
||||||
#include "window/window_session_controller.h"
|
#include "window/window_session_controller.h"
|
||||||
#include "storage/storage_shared_media.h"
|
#include "storage/storage_shared_media.h"
|
||||||
|
#include "mtproto/mtproto_config.h"
|
||||||
#include "data/data_session.h"
|
#include "data/data_session.h"
|
||||||
#include "data/data_changes.h"
|
#include "data/data_changes.h"
|
||||||
#include "data/data_game.h"
|
#include "data/data_game.h"
|
||||||
|
@ -40,7 +41,7 @@ https://github.com/telegramdesktop/tdesktop/blob/master/LEGAL
|
||||||
#include "data/data_channel.h"
|
#include "data/data_channel.h"
|
||||||
#include "data/data_user.h"
|
#include "data/data_user.h"
|
||||||
#include "data/data_histories.h"
|
#include "data/data_histories.h"
|
||||||
#include "facades.h"
|
#include "facades.h" // Notify::replyMarkupUpdated
|
||||||
#include "app.h"
|
#include "app.h"
|
||||||
#include "styles/style_dialogs.h"
|
#include "styles/style_dialogs.h"
|
||||||
#include "styles/style_widgets.h"
|
#include "styles/style_widgets.h"
|
||||||
|
@ -208,6 +209,7 @@ void FastShareMessage(not_null<HistoryItem*> item) {
|
||||||
};
|
};
|
||||||
const auto history = item->history();
|
const auto history = item->history();
|
||||||
const auto owner = &history->owner();
|
const auto owner = &history->owner();
|
||||||
|
const auto session = &history->session();
|
||||||
const auto data = std::make_shared<ShareData>(
|
const auto data = std::make_shared<ShareData>(
|
||||||
history->peer,
|
history->peer,
|
||||||
owner->itemOrItsGroup(item));
|
owner->itemOrItsGroup(item));
|
||||||
|
@ -220,13 +222,11 @@ void FastShareMessage(not_null<HistoryItem*> item) {
|
||||||
auto copyCallback = [=]() {
|
auto copyCallback = [=]() {
|
||||||
if (const auto item = owner->message(data->msgIds[0])) {
|
if (const auto item = owner->message(data->msgIds[0])) {
|
||||||
if (item->hasDirectLink()) {
|
if (item->hasDirectLink()) {
|
||||||
HistoryView::CopyPostLink(
|
HistoryView::CopyPostLink(session, item->fullId());
|
||||||
&item->history()->session(),
|
|
||||||
item->fullId());
|
|
||||||
} else if (const auto bot = item->getMessageBot()) {
|
} else if (const auto bot = item->getMessageBot()) {
|
||||||
if (const auto media = item->media()) {
|
if (const auto media = item->media()) {
|
||||||
if (const auto game = media->game()) {
|
if (const auto game = media->game()) {
|
||||||
const auto link = Core::App().createInternalLinkFull(
|
const auto link = session->createInternalLinkFull(
|
||||||
bot->username
|
bot->username
|
||||||
+ qsl("?game=")
|
+ qsl("?game=")
|
||||||
+ game->shortName);
|
+ game->shortName);
|
||||||
|
@ -782,7 +782,7 @@ bool HistoryMessage::allowsSendNow() const {
|
||||||
|
|
||||||
bool HistoryMessage::isTooOldForEdit(TimeId now) const {
|
bool HistoryMessage::isTooOldForEdit(TimeId now) const {
|
||||||
return !_history->peer->canEditMessagesIndefinitely()
|
return !_history->peer->canEditMessagesIndefinitely()
|
||||||
&& (now - date() >= Global::EditTimeLimit());
|
&& (now - date() >= _history->session().serverConfig().editTimeLimit);
|
||||||
}
|
}
|
||||||
|
|
||||||
bool HistoryMessage::allowsEdit(TimeId now) const {
|
bool HistoryMessage::allowsEdit(TimeId now) const {
|
||||||
|
|
|
@ -65,6 +65,7 @@ https://github.com/telegramdesktop/tdesktop/blob/master/LEGAL
|
||||||
#include "chat_helpers/bot_keyboard.h"
|
#include "chat_helpers/bot_keyboard.h"
|
||||||
#include "chat_helpers/message_field.h"
|
#include "chat_helpers/message_field.h"
|
||||||
#include "platform/platform_specific.h"
|
#include "platform/platform_specific.h"
|
||||||
|
#include "mtproto/mtproto_config.h"
|
||||||
#include "lang/lang_keys.h"
|
#include "lang/lang_keys.h"
|
||||||
#include "mainwidget.h"
|
#include "mainwidget.h"
|
||||||
#include "mainwindow.h"
|
#include "mainwindow.h"
|
||||||
|
@ -6756,7 +6757,7 @@ void HistoryWidget::paintEditHeader(Painter &p, const QRect &rect, int left, int
|
||||||
QString editTimeLeftText;
|
QString editTimeLeftText;
|
||||||
int updateIn = -1;
|
int updateIn = -1;
|
||||||
auto timeSinceMessage = ItemDateTime(_replyEditMsg).msecsTo(QDateTime::currentDateTime());
|
auto timeSinceMessage = ItemDateTime(_replyEditMsg).msecsTo(QDateTime::currentDateTime());
|
||||||
auto editTimeLeft = (Global::EditTimeLimit() * 1000LL) - timeSinceMessage;
|
auto editTimeLeft = (session().serverConfig().editTimeLimit * 1000LL) - timeSinceMessage;
|
||||||
if (editTimeLeft < 2) {
|
if (editTimeLeft < 2) {
|
||||||
editTimeLeftText = qsl("0:00");
|
editTimeLeftText = qsl("0:00");
|
||||||
} else if (editTimeLeft > kDisplayEditTimeWarningMs) {
|
} else if (editTimeLeft > kDisplayEditTimeWarningMs) {
|
||||||
|
|
|
@ -18,6 +18,7 @@ https://github.com/telegramdesktop/tdesktop/blob/master/LEGAL
|
||||||
#include "mainwidget.h"
|
#include "mainwidget.h"
|
||||||
#include "mainwindow.h"
|
#include "mainwindow.h"
|
||||||
#include "main/main_session.h"
|
#include "main/main_session.h"
|
||||||
|
#include "mtproto/mtproto_config.h"
|
||||||
#include "lang/lang_keys.h"
|
#include "lang/lang_keys.h"
|
||||||
#include "core/shortcuts.h"
|
#include "core/shortcuts.h"
|
||||||
#include "ui/widgets/buttons.h"
|
#include "ui/widgets/buttons.h"
|
||||||
|
@ -129,9 +130,10 @@ TopBarWidget::TopBarWidget(
|
||||||
}
|
}
|
||||||
}, lifetime());
|
}, lifetime());
|
||||||
|
|
||||||
subscribe(Global::RefPhoneCallsEnabledChanged(), [this] {
|
session().serverConfig().phoneCallsEnabled.changes(
|
||||||
|
) | rpl::start_with_next([=] {
|
||||||
updateControlsVisibility();
|
updateControlsVisibility();
|
||||||
});
|
}, lifetime());
|
||||||
|
|
||||||
rpl::combine(
|
rpl::combine(
|
||||||
session().settings().thirdSectionInfoEnabledValue(),
|
session().settings().thirdSectionInfoEnabledValue(),
|
||||||
|
@ -156,8 +158,8 @@ Main::Session &TopBarWidget::session() const {
|
||||||
}
|
}
|
||||||
|
|
||||||
void TopBarWidget::updateConnectingState() {
|
void TopBarWidget::updateConnectingState() {
|
||||||
const auto mtp = _controller->session().mtp()->dcstate();
|
const auto state = _controller->session().mtp().dcstate();
|
||||||
if (mtp == MTP::ConnectedState) {
|
if (state == MTP::ConnectedState) {
|
||||||
if (_connecting) {
|
if (_connecting) {
|
||||||
_connecting = nullptr;
|
_connecting = nullptr;
|
||||||
update();
|
update();
|
||||||
|
@ -640,7 +642,8 @@ void TopBarWidget::updateControlsVisibility() {
|
||||||
const auto callsEnabled = [&] {
|
const auto callsEnabled = [&] {
|
||||||
if (const auto peer = _activeChat.peer()) {
|
if (const auto peer = _activeChat.peer()) {
|
||||||
if (const auto user = peer->asUser()) {
|
if (const auto user = peer->asUser()) {
|
||||||
return Global::PhoneCallsEnabled() && user->hasCalls();
|
return session().serverConfig().phoneCallsEnabled.current()
|
||||||
|
&& user->hasCalls();
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
return false;
|
return false;
|
||||||
|
@ -663,7 +666,9 @@ void TopBarWidget::updateMembersShowArea() {
|
||||||
return chat->amIn();
|
return chat->amIn();
|
||||||
}
|
}
|
||||||
if (auto megagroup = peer->asMegagroup()) {
|
if (auto megagroup = peer->asMegagroup()) {
|
||||||
return megagroup->canViewMembers() && (megagroup->membersCount() < Global::ChatSizeMax());
|
return megagroup->canViewMembers()
|
||||||
|
&& (megagroup->membersCount()
|
||||||
|
< megagroup->session().serverConfig().chatSizeMax);
|
||||||
}
|
}
|
||||||
return false;
|
return false;
|
||||||
}();
|
}();
|
||||||
|
@ -846,7 +851,10 @@ void TopBarWidget::updateOnlineDisplay() {
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
} else if (const auto channel = _activeChat.peer()->asChannel()) {
|
} else if (const auto channel = _activeChat.peer()->asChannel()) {
|
||||||
if (channel->isMegagroup() && channel->membersCount() > 0 && channel->membersCount() <= Global::ChatSizeMax()) {
|
if (channel->isMegagroup()
|
||||||
|
&& (channel->membersCount() > 0)
|
||||||
|
&& (channel->membersCount()
|
||||||
|
<= channel->session().serverConfig().chatSizeMax)) {
|
||||||
if (channel->lastParticipantsRequestNeeded()) {
|
if (channel->lastParticipantsRequestNeeded()) {
|
||||||
session().api().requestLastParticipants(channel);
|
session().api().requestLastParticipants(channel);
|
||||||
}
|
}
|
||||||
|
|
|
@ -68,7 +68,7 @@ ListController::ListController(
|
||||||
not_null<UserData*> user)
|
not_null<UserData*> user)
|
||||||
: PeerListController()
|
: PeerListController()
|
||||||
, _controller(controller)
|
, _controller(controller)
|
||||||
, _api(_controller->session().mtp())
|
, _api(&_controller->session().mtp())
|
||||||
, _user(user) {
|
, _user(user) {
|
||||||
_controller->setSearchEnabledByContent(false);
|
_controller->setSearchEnabledByContent(false);
|
||||||
}
|
}
|
||||||
|
|
|
@ -28,12 +28,12 @@ https://github.com/telegramdesktop/tdesktop/blob/master/LEGAL
|
||||||
#include "boxes/peer_list_box.h"
|
#include "boxes/peer_list_box.h"
|
||||||
#include "boxes/confirm_box.h"
|
#include "boxes/confirm_box.h"
|
||||||
#include "main/main_session.h"
|
#include "main/main_session.h"
|
||||||
|
#include "mtproto/mtproto_config.h"
|
||||||
#include "data/data_session.h"
|
#include "data/data_session.h"
|
||||||
#include "data/data_changes.h"
|
#include "data/data_changes.h"
|
||||||
#include "data/data_user.h"
|
#include "data/data_user.h"
|
||||||
#include "mainwidget.h"
|
#include "mainwidget.h"
|
||||||
#include "lang/lang_keys.h"
|
#include "lang/lang_keys.h"
|
||||||
#include "facades.h"
|
|
||||||
#include "styles/style_info.h"
|
#include "styles/style_info.h"
|
||||||
#include "styles/style_profile.h"
|
#include "styles/style_profile.h"
|
||||||
|
|
||||||
|
@ -479,7 +479,9 @@ void WrapWidget::addProfileCallsButton() {
|
||||||
|
|
||||||
const auto peer = key().peer();
|
const auto peer = key().peer();
|
||||||
const auto user = peer ? peer->asUser() : nullptr;
|
const auto user = peer ? peer->asUser() : nullptr;
|
||||||
if (!user || user->isSelf() || !Global::PhoneCallsEnabled()) {
|
if (!user
|
||||||
|
|| user->isSelf()
|
||||||
|
|| !user->session().serverConfig().phoneCallsEnabled.current()) {
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
|
@ -232,7 +232,7 @@ ListController::ListController(
|
||||||
, _poll(poll)
|
, _poll(poll)
|
||||||
, _context(context)
|
, _context(context)
|
||||||
, _option(option)
|
, _option(option)
|
||||||
, _api(_session->mtp()) {
|
, _api(&_session->mtp()) {
|
||||||
const auto i = ranges::find(poll->answers, option, &PollAnswer::option);
|
const auto i = ranges::find(poll->answers, option, &PollAnswer::option);
|
||||||
Assert(i != poll->answers.end());
|
Assert(i != poll->answers.end());
|
||||||
_fullCount = i->votes;
|
_fullCount = i->votes;
|
||||||
|
|
|
@ -301,7 +301,7 @@ object_ptr<Ui::RpWidget> DetailsFiller::setupInfo() {
|
||||||
std::move(linkText),
|
std::move(linkText),
|
||||||
QString());
|
QString());
|
||||||
link->setClickHandlerFilter([peer = _peer](auto&&...) {
|
link->setClickHandlerFilter([peer = _peer](auto&&...) {
|
||||||
const auto link = Core::App().createInternalLinkFull(
|
const auto link = peer->session().createInternalLinkFull(
|
||||||
peer->userName());
|
peer->userName());
|
||||||
if (!link.isEmpty()) {
|
if (!link.isEmpty()) {
|
||||||
QGuiApplication::clipboard()->setText(link);
|
QGuiApplication::clipboard()->setText(link);
|
||||||
|
|
|
@ -133,10 +133,10 @@ rpl::producer<TextWithEntities> AboutValue(not_null<PeerData*> peer) {
|
||||||
rpl::producer<QString> LinkValue(not_null<PeerData*> peer) {
|
rpl::producer<QString> LinkValue(not_null<PeerData*> peer) {
|
||||||
return PlainUsernameValue(
|
return PlainUsernameValue(
|
||||||
peer
|
peer
|
||||||
) | rpl::map([](QString &&username) {
|
) | rpl::map([=](QString &&username) {
|
||||||
return username.isEmpty()
|
return username.isEmpty()
|
||||||
? QString()
|
? QString()
|
||||||
: Core::App().createInternalLinkFull(username);
|
: peer->session().createInternalLinkFull(username);
|
||||||
});
|
});
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
|
@ -746,7 +746,7 @@ Widget::Widget(
|
||||||
not_null<Window::SessionController*> controller)
|
not_null<Window::SessionController*> controller)
|
||||||
: RpWidget(parent)
|
: RpWidget(parent)
|
||||||
, _controller(controller)
|
, _controller(controller)
|
||||||
, _api(_controller->session().mtp())
|
, _api(&_controller->session().mtp())
|
||||||
, _contentMaxHeight(st::emojiPanMaxHeight)
|
, _contentMaxHeight(st::emojiPanMaxHeight)
|
||||||
, _contentHeight(_contentMaxHeight)
|
, _contentHeight(_contentMaxHeight)
|
||||||
, _scroll(this, st::inlineBotsScroll) {
|
, _scroll(this, st::inlineBotsScroll) {
|
||||||
|
|
|
@ -211,9 +211,9 @@ void CodeWidget::finished() {
|
||||||
}
|
}
|
||||||
|
|
||||||
void CodeWidget::cancelled() {
|
void CodeWidget::cancelled() {
|
||||||
api()->request(base::take(_sentRequest)).cancel();
|
api().request(base::take(_sentRequest)).cancel();
|
||||||
api()->request(base::take(_callRequestId)).cancel();
|
api().request(base::take(_callRequestId)).cancel();
|
||||||
api()->request(MTPauth_CancelCode(
|
api().request(MTPauth_CancelCode(
|
||||||
MTP_string(getData()->phone),
|
MTP_string(getData()->phone),
|
||||||
MTP_bytes(getData()->phoneHash)
|
MTP_bytes(getData()->phoneHash)
|
||||||
)).send();
|
)).send();
|
||||||
|
@ -224,12 +224,12 @@ void CodeWidget::stopCheck() {
|
||||||
}
|
}
|
||||||
|
|
||||||
void CodeWidget::checkRequest() {
|
void CodeWidget::checkRequest() {
|
||||||
auto status = api()->instance()->state(_sentRequest);
|
auto status = api().instance().state(_sentRequest);
|
||||||
if (status < 0) {
|
if (status < 0) {
|
||||||
auto leftms = -status;
|
auto leftms = -status;
|
||||||
if (leftms >= 1000) {
|
if (leftms >= 1000) {
|
||||||
if (_sentRequest) {
|
if (_sentRequest) {
|
||||||
api()->request(base::take(_sentRequest)).cancel();
|
api().request(base::take(_sentRequest)).cancel();
|
||||||
_sentCode.clear();
|
_sentCode.clear();
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
@ -282,7 +282,7 @@ void CodeWidget::codeSubmitFail(const RPCError &error) {
|
||||||
showCodeError(tr::lng_bad_code());
|
showCodeError(tr::lng_bad_code());
|
||||||
} else if (err == qstr("SESSION_PASSWORD_NEEDED")) {
|
} else if (err == qstr("SESSION_PASSWORD_NEEDED")) {
|
||||||
_checkRequestTimer.callEach(1000);
|
_checkRequestTimer.callEach(1000);
|
||||||
_sentRequest = api()->request(MTPaccount_GetPassword(
|
_sentRequest = api().request(MTPaccount_GetPassword(
|
||||||
)).done([=](const MTPaccount_Password &result) {
|
)).done([=](const MTPaccount_Password &result) {
|
||||||
gotPassword(result);
|
gotPassword(result);
|
||||||
}).fail([=](const RPCError &error) {
|
}).fail([=](const RPCError &error) {
|
||||||
|
@ -305,7 +305,7 @@ void CodeWidget::sendCall() {
|
||||||
if (--_callTimeout <= 0) {
|
if (--_callTimeout <= 0) {
|
||||||
_callStatus = CallStatus::Calling;
|
_callStatus = CallStatus::Calling;
|
||||||
_callTimer.cancel();
|
_callTimer.cancel();
|
||||||
_callRequestId = api()->request(MTPauth_ResendCode(
|
_callRequestId = api().request(MTPauth_ResendCode(
|
||||||
MTP_string(getData()->phone),
|
MTP_string(getData()->phone),
|
||||||
MTP_bytes(getData()->phoneHash)
|
MTP_bytes(getData()->phoneHash)
|
||||||
)).done([=](const MTPauth_SentCode &result) {
|
)).done([=](const MTPauth_SentCode &result) {
|
||||||
|
@ -383,7 +383,7 @@ void CodeWidget::submit() {
|
||||||
getData()->hasRecovery = false;
|
getData()->hasRecovery = false;
|
||||||
getData()->pwdHint = QString();
|
getData()->pwdHint = QString();
|
||||||
getData()->pwdNotEmptyPassport = false;
|
getData()->pwdNotEmptyPassport = false;
|
||||||
_sentRequest = api()->request(MTPauth_SignIn(
|
_sentRequest = api().request(MTPauth_SignIn(
|
||||||
MTP_string(getData()->phone),
|
MTP_string(getData()->phone),
|
||||||
MTP_bytes(getData()->phoneHash),
|
MTP_bytes(getData()->phoneHash),
|
||||||
MTP_string(_sentCode)
|
MTP_string(_sentCode)
|
||||||
|
@ -398,7 +398,7 @@ void CodeWidget::noTelegramCode() {
|
||||||
if (_noTelegramCodeRequestId) {
|
if (_noTelegramCodeRequestId) {
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
_noTelegramCodeRequestId = api()->request(MTPauth_ResendCode(
|
_noTelegramCodeRequestId = api().request(MTPauth_ResendCode(
|
||||||
MTP_string(getData()->phone),
|
MTP_string(getData()->phone),
|
||||||
MTP_bytes(getData()->phoneHash)
|
MTP_bytes(getData()->phoneHash)
|
||||||
)).done([=](const MTPauth_SentCode &result) {
|
)).done([=](const MTPauth_SentCode &result) {
|
||||||
|
|
|
@ -114,7 +114,7 @@ void PasswordCheckWidget::activate() {
|
||||||
}
|
}
|
||||||
|
|
||||||
void PasswordCheckWidget::cancelled() {
|
void PasswordCheckWidget::cancelled() {
|
||||||
api()->request(base::take(_sentRequest)).cancel();
|
api().request(base::take(_sentRequest)).cancel();
|
||||||
}
|
}
|
||||||
|
|
||||||
void PasswordCheckWidget::pwdSubmitDone(bool recover, const MTPauth_Authorization &result) {
|
void PasswordCheckWidget::pwdSubmitDone(bool recover, const MTPauth_Authorization &result) {
|
||||||
|
@ -181,8 +181,8 @@ void PasswordCheckWidget::checkPasswordHash() {
|
||||||
}
|
}
|
||||||
|
|
||||||
void PasswordCheckWidget::requestPasswordData() {
|
void PasswordCheckWidget::requestPasswordData() {
|
||||||
api()->request(base::take(_sentRequest)).cancel();
|
api().request(base::take(_sentRequest)).cancel();
|
||||||
_sentRequest = api()->request(
|
_sentRequest = api().request(
|
||||||
MTPaccount_GetPassword()
|
MTPaccount_GetPassword()
|
||||||
).done([=](const MTPaccount_Password &result) {
|
).done([=](const MTPaccount_Password &result) {
|
||||||
_sentRequest = 0;
|
_sentRequest = 0;
|
||||||
|
@ -204,7 +204,7 @@ void PasswordCheckWidget::passwordChecked() {
|
||||||
return serverError();
|
return serverError();
|
||||||
}
|
}
|
||||||
_request.id = 0;
|
_request.id = 0;
|
||||||
_sentRequest = api()->request(
|
_sentRequest = api().request(
|
||||||
MTPauth_CheckPassword(check.result)
|
MTPauth_CheckPassword(check.result)
|
||||||
).done([=](const MTPauth_Authorization &result) {
|
).done([=](const MTPauth_Authorization &result) {
|
||||||
pwdSubmitDone(false, result);
|
pwdSubmitDone(false, result);
|
||||||
|
@ -266,7 +266,7 @@ void PasswordCheckWidget::recoverStartFail(const RPCError &error) {
|
||||||
void PasswordCheckWidget::toRecover() {
|
void PasswordCheckWidget::toRecover() {
|
||||||
if (_hasRecovery) {
|
if (_hasRecovery) {
|
||||||
if (_sentRequest) {
|
if (_sentRequest) {
|
||||||
api()->request(base::take(_sentRequest)).cancel();
|
api().request(base::take(_sentRequest)).cancel();
|
||||||
}
|
}
|
||||||
hideError();
|
hideError();
|
||||||
_toRecover->hide();
|
_toRecover->hide();
|
||||||
|
@ -278,7 +278,7 @@ void PasswordCheckWidget::toRecover() {
|
||||||
_codeField->setFocus();
|
_codeField->setFocus();
|
||||||
updateDescriptionText();
|
updateDescriptionText();
|
||||||
if (_emailPattern.isEmpty()) {
|
if (_emailPattern.isEmpty()) {
|
||||||
api()->request(
|
api().request(
|
||||||
MTPauth_RequestPasswordRecovery()
|
MTPauth_RequestPasswordRecovery()
|
||||||
).done([=](const MTPauth_PasswordRecovery &result) {
|
).done([=](const MTPauth_PasswordRecovery &result) {
|
||||||
recoverStarted(result);
|
recoverStarted(result);
|
||||||
|
@ -301,7 +301,7 @@ void PasswordCheckWidget::toPassword() {
|
||||||
|
|
||||||
void PasswordCheckWidget::showReset() {
|
void PasswordCheckWidget::showReset() {
|
||||||
if (_sentRequest) {
|
if (_sentRequest) {
|
||||||
api()->request(base::take(_sentRequest)).cancel();
|
api().request(base::take(_sentRequest)).cancel();
|
||||||
}
|
}
|
||||||
_toRecover->show();
|
_toRecover->show();
|
||||||
_toPassword->hide();
|
_toPassword->hide();
|
||||||
|
@ -334,7 +334,7 @@ void PasswordCheckWidget::submit() {
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
const auto send = crl::guard(this, [=] {
|
const auto send = crl::guard(this, [=] {
|
||||||
_sentRequest = api()->request(
|
_sentRequest = api().request(
|
||||||
MTPauth_RecoverPassword(MTP_string(code))
|
MTPauth_RecoverPassword(MTP_string(code))
|
||||||
).done([=](const MTPauth_Authorization &result) {
|
).done([=](const MTPauth_Authorization &result) {
|
||||||
pwdSubmitDone(true, result);
|
pwdSubmitDone(true, result);
|
||||||
|
|
|
@ -141,8 +141,8 @@ void PhoneWidget::submit() {
|
||||||
_checkRequestTimer.callEach(1000);
|
_checkRequestTimer.callEach(1000);
|
||||||
|
|
||||||
_sentPhone = phone;
|
_sentPhone = phone;
|
||||||
api()->instance()->setUserPhone(_sentPhone);
|
api().instance().setUserPhone(_sentPhone);
|
||||||
_sentRequest = api()->request(MTPauth_SendCode(
|
_sentRequest = api().request(MTPauth_SendCode(
|
||||||
MTP_string(_sentPhone),
|
MTP_string(_sentPhone),
|
||||||
MTP_int(ApiId),
|
MTP_int(ApiId),
|
||||||
MTP_string(ApiHash),
|
MTP_string(ApiHash),
|
||||||
|
@ -159,11 +159,11 @@ void PhoneWidget::stopCheck() {
|
||||||
}
|
}
|
||||||
|
|
||||||
void PhoneWidget::checkRequest() {
|
void PhoneWidget::checkRequest() {
|
||||||
auto status = api()->instance()->state(_sentRequest);
|
auto status = api().instance().state(_sentRequest);
|
||||||
if (status < 0) {
|
if (status < 0) {
|
||||||
auto leftms = -status;
|
auto leftms = -status;
|
||||||
if (leftms >= 1000) {
|
if (leftms >= 1000) {
|
||||||
api()->request(base::take(_sentRequest)).cancel();
|
api().request(base::take(_sentRequest)).cancel();
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
if (!_sentRequest && status == MTP::RequestSent) {
|
if (!_sentRequest && status == MTP::RequestSent) {
|
||||||
|
@ -246,7 +246,7 @@ void PhoneWidget::finished() {
|
||||||
}
|
}
|
||||||
|
|
||||||
void PhoneWidget::cancelled() {
|
void PhoneWidget::cancelled() {
|
||||||
api()->request(base::take(_sentRequest)).cancel();
|
api().request(base::take(_sentRequest)).cancel();
|
||||||
}
|
}
|
||||||
|
|
||||||
} // namespace details
|
} // namespace details
|
||||||
|
|
|
@ -308,7 +308,7 @@ void QrWidget::refreshCode() {
|
||||||
if (_requestId) {
|
if (_requestId) {
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
_requestId = api()->request(MTPauth_ExportLoginToken(
|
_requestId = api().request(MTPauth_ExportLoginToken(
|
||||||
MTP_int(ApiId),
|
MTP_int(ApiId),
|
||||||
MTP_string(ApiHash),
|
MTP_string(ApiHash),
|
||||||
MTP_vector<MTPint>(0)
|
MTP_vector<MTPint>(0)
|
||||||
|
@ -356,8 +356,8 @@ void QrWidget::showToken(const QByteArray &token) {
|
||||||
void QrWidget::importTo(MTP::DcId dcId, const QByteArray &token) {
|
void QrWidget::importTo(MTP::DcId dcId, const QByteArray &token) {
|
||||||
Expects(_requestId != 0);
|
Expects(_requestId != 0);
|
||||||
|
|
||||||
api()->instance()->setMainDcId(dcId);
|
api().instance().setMainDcId(dcId);
|
||||||
_requestId = api()->request(MTPauth_ImportLoginToken(
|
_requestId = api().request(MTPauth_ImportLoginToken(
|
||||||
MTP_bytes(token)
|
MTP_bytes(token)
|
||||||
)).done([=](const MTPauth_LoginToken &result) {
|
)).done([=](const MTPauth_LoginToken &result) {
|
||||||
handleTokenResult(result);
|
handleTokenResult(result);
|
||||||
|
@ -382,7 +382,7 @@ void QrWidget::done(const MTPauth_Authorization &authorization) {
|
||||||
}
|
}
|
||||||
|
|
||||||
void QrWidget::sendCheckPasswordRequest() {
|
void QrWidget::sendCheckPasswordRequest() {
|
||||||
_requestId = api()->request(MTPaccount_GetPassword(
|
_requestId = api().request(MTPaccount_GetPassword(
|
||||||
)).done([=](const MTPaccount_Password &result) {
|
)).done([=](const MTPaccount_Password &result) {
|
||||||
result.match([&](const MTPDaccount_password &data) {
|
result.match([&](const MTPDaccount_password &data) {
|
||||||
getData()->pwdRequest = Core::ParseCloudPasswordCheckRequest(
|
getData()->pwdRequest = Core::ParseCloudPasswordCheckRequest(
|
||||||
|
@ -426,7 +426,7 @@ void QrWidget::finished() {
|
||||||
}
|
}
|
||||||
|
|
||||||
void QrWidget::cancelled() {
|
void QrWidget::cancelled() {
|
||||||
api()->request(base::take(_requestId)).cancel();
|
api().request(base::take(_requestId)).cancel();
|
||||||
}
|
}
|
||||||
|
|
||||||
} // namespace details
|
} // namespace details
|
||||||
|
|
|
@ -101,7 +101,7 @@ void SignupWidget::activate() {
|
||||||
}
|
}
|
||||||
|
|
||||||
void SignupWidget::cancelled() {
|
void SignupWidget::cancelled() {
|
||||||
api()->request(base::take(_sentRequest)).cancel();
|
api().request(base::take(_sentRequest)).cancel();
|
||||||
}
|
}
|
||||||
|
|
||||||
void SignupWidget::nameSubmitDone(const MTPauth_Authorization &result) {
|
void SignupWidget::nameSubmitDone(const MTPauth_Authorization &result) {
|
||||||
|
@ -181,7 +181,7 @@ void SignupWidget::submit() {
|
||||||
|
|
||||||
_firstName = _first->getLastText().trimmed();
|
_firstName = _first->getLastText().trimmed();
|
||||||
_lastName = _last->getLastText().trimmed();
|
_lastName = _last->getLastText().trimmed();
|
||||||
_sentRequest = api()->request(MTPauth_SignUp(
|
_sentRequest = api().request(MTPauth_SignUp(
|
||||||
MTP_string(getData()->phone),
|
MTP_string(getData()->phone),
|
||||||
MTP_bytes(getData()->phoneHash),
|
MTP_bytes(getData()->phoneHash),
|
||||||
MTP_string(_firstName),
|
MTP_string(_firstName),
|
||||||
|
|
|
@ -98,11 +98,11 @@ Step::Step(
|
||||||
|
|
||||||
Step::~Step() = default;
|
Step::~Step() = default;
|
||||||
|
|
||||||
not_null<MTP::Sender*> Step::api() const {
|
MTP::Sender &Step::api() const {
|
||||||
if (!_api) {
|
if (!_api) {
|
||||||
_api.emplace(_account->mtp());
|
_api.emplace(&_account->mtp());
|
||||||
}
|
}
|
||||||
return &*_api;
|
return *_api;
|
||||||
}
|
}
|
||||||
|
|
||||||
void Step::apiClear() {
|
void Step::apiClear() {
|
||||||
|
|
|
@ -45,7 +45,7 @@ public:
|
||||||
|
|
||||||
// It should not be called in StartWidget, in other steps it should be
|
// It should not be called in StartWidget, in other steps it should be
|
||||||
// present and not changing.
|
// present and not changing.
|
||||||
[[nodiscard]] not_null<MTP::Sender*> api() const;
|
[[nodiscard]] MTP::Sender &api() const;
|
||||||
void apiClear();
|
void apiClear();
|
||||||
|
|
||||||
virtual void finishInit() {
|
virtual void finishInit() {
|
||||||
|
|
|
@ -24,7 +24,7 @@ https://github.com/telegramdesktop/tdesktop/blob/master/LEGAL
|
||||||
#include "ui/wrap/fade_wrap.h"
|
#include "ui/wrap/fade_wrap.h"
|
||||||
#include "core/update_checker.h"
|
#include "core/update_checker.h"
|
||||||
#include "core/application.h"
|
#include "core/application.h"
|
||||||
#include "mtproto/dc_options.h"
|
#include "mtproto/mtproto_dc_options.h"
|
||||||
#include "window/window_slide_animation.h"
|
#include "window/window_slide_animation.h"
|
||||||
#include "window/window_connecting_widget.h"
|
#include "window/window_connecting_widget.h"
|
||||||
#include "base/platform/base_platform_info.h"
|
#include "base/platform/base_platform_info.h"
|
||||||
|
@ -64,14 +64,11 @@ Widget::Widget(QWidget *parent, not_null<Main::Account*> account)
|
||||||
getData()->country = Platform::SystemCountry();
|
getData()->country = Platform::SystemCountry();
|
||||||
|
|
||||||
_account->mtpValue(
|
_account->mtpValue(
|
||||||
) | rpl::start_with_next([=](MTP::Instance *instance) {
|
) | rpl::start_with_next([=](not_null<MTP::Instance*> instance) {
|
||||||
if (instance) {
|
_api.emplace(instance);
|
||||||
_api.emplace(instance);
|
createLanguageLink();
|
||||||
createLanguageLink();
|
|
||||||
} else {
|
|
||||||
_api.reset();
|
|
||||||
}
|
|
||||||
}, lifetime());
|
}, lifetime());
|
||||||
|
|
||||||
subscribe(Lang::CurrentCloudManager().firstLanguageSuggestion(), [=] {
|
subscribe(Lang::CurrentCloudManager().firstLanguageSuggestion(), [=] {
|
||||||
createLanguageLink();
|
createLanguageLink();
|
||||||
});
|
});
|
||||||
|
@ -141,9 +138,9 @@ void Widget::handleUpdates(const MTPUpdates &updates) {
|
||||||
|
|
||||||
void Widget::handleUpdate(const MTPUpdate &update) {
|
void Widget::handleUpdate(const MTPUpdate &update) {
|
||||||
update.match([&](const MTPDupdateDcOptions &data) {
|
update.match([&](const MTPDupdateDcOptions &data) {
|
||||||
Core::App().dcOptions()->addFromList(data.vdc_options());
|
_account->mtp().dcOptions().addFromList(data.vdc_options());
|
||||||
}, [&](const MTPDupdateConfig &data) {
|
}, [&](const MTPDupdateConfig &data) {
|
||||||
_account->mtp()->requestConfig();
|
_account->mtp().requestConfig();
|
||||||
}, [&](const MTPDupdateServiceNotification &data) {
|
}, [&](const MTPDupdateServiceNotification &data) {
|
||||||
const auto text = TextWithEntities{
|
const auto text = TextWithEntities{
|
||||||
qs(data.vmessage()),
|
qs(data.vmessage()),
|
||||||
|
|
|
@ -160,15 +160,16 @@ CloudManager::CloudManager(Instance &langpack)
|
||||||
: _langpack(langpack) {
|
: _langpack(langpack) {
|
||||||
Core::App().accounts().activeValue(
|
Core::App().accounts().activeValue(
|
||||||
) | rpl::map([=](Main::Account *account) {
|
) | rpl::map([=](Main::Account *account) {
|
||||||
return account ? account->mtpValue() : rpl::never<MTP::Instance*>();
|
if (!account) {
|
||||||
}) | rpl::flatten_latest(
|
|
||||||
) | rpl::start_with_next([=](MTP::Instance *instance) {
|
|
||||||
if (instance) {
|
|
||||||
_api.emplace(instance);
|
|
||||||
resendRequests();
|
|
||||||
} else {
|
|
||||||
_api.reset();
|
_api.reset();
|
||||||
}
|
}
|
||||||
|
return account
|
||||||
|
? account->mtpValue()
|
||||||
|
: rpl::never<not_null<MTP::Instance*>>();
|
||||||
|
}) | rpl::flatten_latest(
|
||||||
|
) | rpl::start_with_next([=](not_null<MTP::Instance*> instance) {
|
||||||
|
_api.emplace(instance);
|
||||||
|
resendRequests();
|
||||||
}, _lifetime);
|
}, _lifetime);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -604,7 +605,7 @@ void CloudManager::switchLangPackId(const Language &data) {
|
||||||
void CloudManager::changeIdAndReInitConnection(const Language &data) {
|
void CloudManager::changeIdAndReInitConnection(const Language &data) {
|
||||||
_langpack.switchToId(data);
|
_langpack.switchToId(data);
|
||||||
if (_api) {
|
if (_api) {
|
||||||
const auto mtproto = _api->instance();
|
const auto mtproto = &_api->instance();
|
||||||
mtproto->reInitConnection(mtproto->mainDcId());
|
mtproto->reInitConnection(mtproto->mainDcId());
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
|
@ -414,16 +414,11 @@ void start(not_null<Core::Launcher*> launcher) {
|
||||||
LogsData = nullptr;
|
LogsData = nullptr;
|
||||||
}
|
}
|
||||||
|
|
||||||
LOG(("Launched version: %1, "
|
LOG(("Launched version: %1, install beta: %2, alpha: %3, debug mode: %4"
|
||||||
"install beta: %2, "
|
|
||||||
"alpha: %3, "
|
|
||||||
"debug mode: %4, "
|
|
||||||
"test dc: %5"
|
|
||||||
).arg(AppVersion
|
).arg(AppVersion
|
||||||
).arg(Logs::b(cInstallBetaVersion())
|
).arg(Logs::b(cInstallBetaVersion())
|
||||||
).arg(cAlphaVersion()
|
).arg(cAlphaVersion()
|
||||||
).arg(Logs::b(DebugEnabled())
|
).arg(Logs::b(DebugEnabled())));
|
||||||
).arg(Logs::b(cTestMode())));
|
|
||||||
LOG(("Executable dir: %1, name: %2").arg(cExeDir()).arg(cExeName()));
|
LOG(("Executable dir: %1, name: %2").arg(cExeDir()).arg(cExeName()));
|
||||||
LOG(("Initial working dir: %1").arg(initialWorkingDir));
|
LOG(("Initial working dir: %1").arg(initialWorkingDir));
|
||||||
LOG(("Working dir: %1").arg(cWorkingDir()));
|
LOG(("Working dir: %1").arg(cWorkingDir()));
|
||||||
|
|
|
@ -13,12 +13,16 @@ https://github.com/telegramdesktop/tdesktop/blob/master/LEGAL
|
||||||
#include "storage/storage_account.h"
|
#include "storage/storage_account.h"
|
||||||
#include "storage/storage_accounts.h" // Storage::StartResult.
|
#include "storage/storage_accounts.h" // Storage::StartResult.
|
||||||
#include "storage/serialize_common.h"
|
#include "storage/serialize_common.h"
|
||||||
|
#include "storage/serialize_peer.h"
|
||||||
#include "storage/localstorage.h"
|
#include "storage/localstorage.h"
|
||||||
#include "data/data_session.h"
|
#include "data/data_session.h"
|
||||||
#include "data/data_user.h"
|
#include "data/data_user.h"
|
||||||
#include "data/data_changes.h"
|
#include "data/data_changes.h"
|
||||||
#include "window/window_controller.h"
|
#include "window/window_controller.h"
|
||||||
#include "media/audio/media_audio.h"
|
#include "media/audio/media_audio.h"
|
||||||
|
#include "mtproto/mtproto_config.h"
|
||||||
|
#include "mtproto/mtproto_dc_options.h"
|
||||||
|
#include "mtproto/mtp_instance.h"
|
||||||
#include "ui/image/image.h"
|
#include "ui/image/image.h"
|
||||||
#include "mainwidget.h"
|
#include "mainwidget.h"
|
||||||
#include "api/api_updates.h"
|
#include "api/api_updates.h"
|
||||||
|
@ -46,7 +50,14 @@ Account::Account(const QString &dataName, int index)
|
||||||
ComposeDataString(dataName, index))) {
|
ComposeDataString(dataName, index))) {
|
||||||
}
|
}
|
||||||
|
|
||||||
Account::~Account() = default;
|
Account::~Account() {
|
||||||
|
if (sessionExists()) {
|
||||||
|
session().saveSettingsNowIfNeeded();
|
||||||
|
}
|
||||||
|
destroySession();
|
||||||
|
_mtpValue.reset(nullptr);
|
||||||
|
base::take(_mtp);
|
||||||
|
}
|
||||||
|
|
||||||
[[nodiscard]] Storage::StartResult Account::legacyStart(
|
[[nodiscard]] Storage::StartResult Account::legacyStart(
|
||||||
const QByteArray &passcode) {
|
const QByteArray &passcode) {
|
||||||
|
@ -54,22 +65,27 @@ Account::~Account() = default;
|
||||||
|
|
||||||
const auto result = _local->legacyStart(passcode);
|
const auto result = _local->legacyStart(passcode);
|
||||||
if (result == Storage::StartResult::Success) {
|
if (result == Storage::StartResult::Success) {
|
||||||
finishStarting();
|
finishStarting(nullptr);
|
||||||
}
|
}
|
||||||
return result;
|
return result;
|
||||||
}
|
}
|
||||||
|
|
||||||
void Account::start(std::shared_ptr<MTP::AuthKey> localKey) {
|
void Account::start(std::shared_ptr<MTP::AuthKey> localKey) {
|
||||||
_local->start(std::move(localKey));
|
finishStarting(_local->start(std::move(localKey)));
|
||||||
finishStarting();
|
|
||||||
}
|
}
|
||||||
|
|
||||||
void Account::startAdded(std::shared_ptr<MTP::AuthKey> localKey) {
|
void Account::startAdded(
|
||||||
|
std::shared_ptr<MTP::AuthKey> localKey,
|
||||||
|
std::unique_ptr<MTP::Config> config) {
|
||||||
_local->startAdded(std::move(localKey));
|
_local->startAdded(std::move(localKey));
|
||||||
finishStarting();
|
finishStarting(std::move(config));
|
||||||
}
|
}
|
||||||
|
|
||||||
void Account::finishStarting() {
|
void Account::finishStarting(std::unique_ptr<MTP::Config> config) {
|
||||||
|
startMtp(config
|
||||||
|
? std::move(config)
|
||||||
|
: std::make_unique<MTP::Config>(
|
||||||
|
Core::App().fallbackProductionConfig()));
|
||||||
_appConfig = std::make_unique<AppConfig>(this);
|
_appConfig = std::make_unique<AppConfig>(this);
|
||||||
watchProxyChanges();
|
watchProxyChanges();
|
||||||
watchSessionChanges();
|
watchSessionChanges();
|
||||||
|
@ -195,12 +211,10 @@ rpl::producer<Session*> Account::sessionChanges() const {
|
||||||
return _sessionValue.changes();
|
return _sessionValue.changes();
|
||||||
}
|
}
|
||||||
|
|
||||||
rpl::producer<MTP::Instance*> Account::mtpValue() const {
|
rpl::producer<not_null<MTP::Instance*>> Account::mtpValue() const {
|
||||||
return _mtpValue.value();
|
return _mtpValue.value() | rpl::map([](MTP::Instance *instance) {
|
||||||
}
|
return not_null{ instance };
|
||||||
|
});
|
||||||
rpl::producer<MTP::Instance*> Account::mtpChanges() const {
|
|
||||||
return _mtpValue.changes();
|
|
||||||
}
|
}
|
||||||
|
|
||||||
rpl::producer<MTPUpdates> Account::mtpUpdates() const {
|
rpl::producer<MTPUpdates> Account::mtpUpdates() const {
|
||||||
|
@ -214,14 +228,14 @@ rpl::producer<> Account::mtpNewSessionCreated() const {
|
||||||
void Account::setLegacyMtpMainDcId(MTP::DcId mainDcId) {
|
void Account::setLegacyMtpMainDcId(MTP::DcId mainDcId) {
|
||||||
Expects(!_mtp);
|
Expects(!_mtp);
|
||||||
|
|
||||||
_mtpConfig.mainDcId = mainDcId;
|
_mtpFields.mainDcId = mainDcId;
|
||||||
}
|
}
|
||||||
|
|
||||||
void Account::setLegacyMtpKey(std::shared_ptr<MTP::AuthKey> key) {
|
void Account::setLegacyMtpKey(std::shared_ptr<MTP::AuthKey> key) {
|
||||||
Expects(!_mtp);
|
Expects(!_mtp);
|
||||||
Expects(key != nullptr);
|
Expects(key != nullptr);
|
||||||
|
|
||||||
_mtpConfig.keys.push_back(std::move(key));
|
_mtpFields.keys.push_back(std::move(key));
|
||||||
}
|
}
|
||||||
|
|
||||||
QByteArray Account::serializeMtpAuthorization() const {
|
QByteArray Account::serializeMtpAuthorization() const {
|
||||||
|
@ -270,9 +284,9 @@ QByteArray Account::serializeMtpAuthorization() const {
|
||||||
: MTP::AuthKeysList();
|
: MTP::AuthKeysList();
|
||||||
return serialize(_mtp->mainDcId(), keys, keysToDestroy);
|
return serialize(_mtp->mainDcId(), keys, keysToDestroy);
|
||||||
}
|
}
|
||||||
const auto &keys = _mtpConfig.keys;
|
const auto &keys = _mtpFields.keys;
|
||||||
const auto &keysToDestroy = _mtpKeysToDestroy;
|
const auto &keysToDestroy = _mtpKeysToDestroy;
|
||||||
return serialize(_mtpConfig.mainDcId, keys, keysToDestroy);
|
return serialize(_mtpFields.mainDcId, keys, keysToDestroy);
|
||||||
}
|
}
|
||||||
|
|
||||||
void Account::setSessionUserId(UserId userId) {
|
void Account::setSessionUserId(UserId userId) {
|
||||||
|
@ -319,9 +333,9 @@ void Account::setMtpAuthorization(const QByteArray &serialized) {
|
||||||
}
|
}
|
||||||
|
|
||||||
setSessionUserId(userId);
|
setSessionUserId(userId);
|
||||||
_mtpConfig.mainDcId = mainDcId;
|
_mtpFields.mainDcId = mainDcId;
|
||||||
|
|
||||||
const auto readKeys = [&stream](auto &keys) {
|
const auto readKeys = [&](auto &keys) {
|
||||||
const auto count = Serialize::read<qint32>(stream);
|
const auto count = Serialize::read<qint32>(stream);
|
||||||
if (stream.status() != QDataStream::Ok) {
|
if (stream.status() != QDataStream::Ok) {
|
||||||
LOG(("MTP Error: "
|
LOG(("MTP Error: "
|
||||||
|
@ -340,29 +354,53 @@ void Account::setMtpAuthorization(const QByteArray &serialized) {
|
||||||
keys.push_back(std::make_shared<MTP::AuthKey>(MTP::AuthKey::Type::ReadFromFile, dcId, keyData));
|
keys.push_back(std::make_shared<MTP::AuthKey>(MTP::AuthKey::Type::ReadFromFile, dcId, keyData));
|
||||||
}
|
}
|
||||||
};
|
};
|
||||||
readKeys(_mtpConfig.keys);
|
readKeys(_mtpFields.keys);
|
||||||
readKeys(_mtpKeysToDestroy);
|
readKeys(_mtpKeysToDestroy);
|
||||||
LOG(("MTP Info: "
|
LOG(("MTP Info: "
|
||||||
"read keys, current: %1, to destroy: %2"
|
"read keys, current: %1, to destroy: %2"
|
||||||
).arg(_mtpConfig.keys.size()
|
).arg(_mtpFields.keys.size()
|
||||||
).arg(_mtpKeysToDestroy.size()));
|
).arg(_mtpKeysToDestroy.size()));
|
||||||
}
|
}
|
||||||
|
|
||||||
void Account::startMtp() {
|
void Account::startMtp(std::unique_ptr<MTP::Config> config) {
|
||||||
Expects(!_mtp);
|
Expects(!_mtp);
|
||||||
|
|
||||||
auto config = base::take(_mtpConfig);
|
auto fields = base::take(_mtpFields);
|
||||||
config.deviceModel = Core::App().launcher()->deviceModel();
|
fields.config = std::move(config);
|
||||||
config.systemVersion = Core::App().launcher()->systemVersion();
|
fields.deviceModel = Core::App().launcher()->deviceModel();
|
||||||
|
fields.systemVersion = Core::App().launcher()->systemVersion();
|
||||||
_mtp = std::make_unique<MTP::Instance>(
|
_mtp = std::make_unique<MTP::Instance>(
|
||||||
Core::App().dcOptions(),
|
|
||||||
MTP::Instance::Mode::Normal,
|
MTP::Instance::Mode::Normal,
|
||||||
std::move(config));
|
std::move(fields));
|
||||||
|
|
||||||
|
const auto writingKeys = _mtp->lifetime().make_state<bool>(false);
|
||||||
_mtp->writeKeysRequests(
|
_mtp->writeKeysRequests(
|
||||||
) | rpl::start_with_next([=] {
|
) | rpl::filter([=] {
|
||||||
local().writeMtpData();
|
return !*writingKeys;
|
||||||
|
}) | rpl::start_with_next([=] {
|
||||||
|
*writingKeys = true;
|
||||||
|
Ui::PostponeCall(_mtp.get(), [=] {
|
||||||
|
local().writeMtpData();
|
||||||
|
*writingKeys = false;
|
||||||
|
});
|
||||||
}, _mtp->lifetime());
|
}, _mtp->lifetime());
|
||||||
_mtpConfig.mainDcId = _mtp->mainDcId();
|
|
||||||
|
const auto writingConfig = _lifetime.make_state<bool>(false);
|
||||||
|
rpl::merge(
|
||||||
|
_mtp->config().updates(),
|
||||||
|
_mtp->dcOptions().changed(
|
||||||
|
) | rpl::map([] { return rpl::empty_value(); })
|
||||||
|
) | rpl::filter([=] {
|
||||||
|
return !*writingConfig;
|
||||||
|
}) | rpl::start_with_next([=] {
|
||||||
|
*writingConfig = true;
|
||||||
|
Ui::PostponeCall(_mtp.get(), [=] {
|
||||||
|
local().writeMtpConfig();
|
||||||
|
*writingConfig = false;
|
||||||
|
});
|
||||||
|
}, _lifetime);
|
||||||
|
|
||||||
|
_mtpFields.mainDcId = _mtp->mainDcId();
|
||||||
|
|
||||||
_mtp->setUpdatesHandler(::rpcDone([=](
|
_mtp->setUpdatesHandler(::rpcDone([=](
|
||||||
const mtpPrime *from,
|
const mtpPrime *from,
|
||||||
|
@ -466,6 +504,8 @@ void Account::loggedOut() {
|
||||||
}
|
}
|
||||||
|
|
||||||
void Account::destroyMtpKeys(MTP::AuthKeysList &&keys) {
|
void Account::destroyMtpKeys(MTP::AuthKeysList &&keys) {
|
||||||
|
Expects(_mtp != nullptr);
|
||||||
|
|
||||||
if (keys.empty()) {
|
if (keys.empty()) {
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
|
@ -474,15 +514,16 @@ void Account::destroyMtpKeys(MTP::AuthKeysList &&keys) {
|
||||||
local().writeMtpData();
|
local().writeMtpData();
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
auto destroyConfig = MTP::Instance::Config();
|
auto destroyFields = MTP::Instance::Fields();
|
||||||
destroyConfig.mainDcId = MTP::Instance::Config::kNoneMainDc;
|
|
||||||
destroyConfig.keys = std::move(keys);
|
destroyFields.mainDcId = MTP::Instance::Fields::kNoneMainDc;
|
||||||
destroyConfig.deviceModel = Core::App().launcher()->deviceModel();
|
destroyFields.config = std::make_unique<MTP::Config>(_mtp->config());
|
||||||
destroyConfig.systemVersion = Core::App().launcher()->systemVersion();
|
destroyFields.keys = std::move(keys);
|
||||||
|
destroyFields.deviceModel = Core::App().launcher()->deviceModel();
|
||||||
|
destroyFields.systemVersion = Core::App().launcher()->systemVersion();
|
||||||
_mtpForKeysDestroy = std::make_unique<MTP::Instance>(
|
_mtpForKeysDestroy = std::make_unique<MTP::Instance>(
|
||||||
Core::App().dcOptions(),
|
|
||||||
MTP::Instance::Mode::KeysDestroyer,
|
MTP::Instance::Mode::KeysDestroyer,
|
||||||
std::move(destroyConfig));
|
std::move(destroyFields));
|
||||||
_mtpForKeysDestroy->writeKeysRequests(
|
_mtpForKeysDestroy->writeKeysRequests(
|
||||||
) | rpl::start_with_next([=] {
|
) | rpl::start_with_next([=] {
|
||||||
local().writeMtpData();
|
local().writeMtpData();
|
||||||
|
@ -501,8 +542,8 @@ void Account::suggestMainDcId(MTP::DcId mainDcId) {
|
||||||
Expects(_mtp != nullptr);
|
Expects(_mtp != nullptr);
|
||||||
|
|
||||||
_mtp->suggestMainDcId(mainDcId);
|
_mtp->suggestMainDcId(mainDcId);
|
||||||
if (_mtpConfig.mainDcId != MTP::Instance::Config::kNotSetMainDc) {
|
if (_mtpFields.mainDcId != MTP::Instance::Fields::kNotSetMainDc) {
|
||||||
_mtpConfig.mainDcId = mainDcId;
|
_mtpFields.mainDcId = mainDcId;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -521,25 +562,15 @@ void Account::destroyStaleAuthorizationKeys() {
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
void Account::configUpdated() {
|
|
||||||
_configUpdates.fire({});
|
|
||||||
}
|
|
||||||
|
|
||||||
rpl::producer<> Account::configUpdates() const {
|
|
||||||
return _configUpdates.events();
|
|
||||||
}
|
|
||||||
|
|
||||||
void Account::resetAuthorizationKeys() {
|
void Account::resetAuthorizationKeys() {
|
||||||
_mtpValue = nullptr;
|
Expects(_mtp != nullptr);
|
||||||
_mtp = nullptr;
|
|
||||||
startMtp();
|
{
|
||||||
|
const auto old = base::take(_mtp);
|
||||||
|
auto config = std::make_unique<MTP::Config>(old->config());
|
||||||
|
startMtp(std::move(config));
|
||||||
|
}
|
||||||
local().writeMtpData();
|
local().writeMtpData();
|
||||||
}
|
}
|
||||||
|
|
||||||
void Account::clearMtp() {
|
|
||||||
_mtpValue = nullptr;
|
|
||||||
_mtp = nullptr;
|
|
||||||
_mtpForKeysDestroy = nullptr;
|
|
||||||
}
|
|
||||||
|
|
||||||
} // namespace Main
|
} // namespace Main
|
||||||
|
|
|
@ -18,6 +18,7 @@ enum class StartResult : uchar;
|
||||||
|
|
||||||
namespace MTP {
|
namespace MTP {
|
||||||
class AuthKey;
|
class AuthKey;
|
||||||
|
class Config;
|
||||||
} // namespace MTP
|
} // namespace MTP
|
||||||
|
|
||||||
namespace Main {
|
namespace Main {
|
||||||
|
@ -37,7 +38,9 @@ public:
|
||||||
[[nodiscard]] Storage::StartResult legacyStart(
|
[[nodiscard]] Storage::StartResult legacyStart(
|
||||||
const QByteArray &passcode);
|
const QByteArray &passcode);
|
||||||
void start(std::shared_ptr<MTP::AuthKey> localKey);
|
void start(std::shared_ptr<MTP::AuthKey> localKey);
|
||||||
void startAdded(std::shared_ptr<MTP::AuthKey> localKey);
|
void startAdded(
|
||||||
|
std::shared_ptr<MTP::AuthKey> localKey,
|
||||||
|
std::unique_ptr<MTP::Config> config);
|
||||||
|
|
||||||
[[nodiscard]] UserId willHaveUserId() const;
|
[[nodiscard]] UserId willHaveUserId() const;
|
||||||
void createSession(const MTPUser &user);
|
void createSession(const MTPUser &user);
|
||||||
|
@ -67,11 +70,10 @@ public:
|
||||||
[[nodiscard]] rpl::producer<Session*> sessionValue() const;
|
[[nodiscard]] rpl::producer<Session*> sessionValue() const;
|
||||||
[[nodiscard]] rpl::producer<Session*> sessionChanges() const;
|
[[nodiscard]] rpl::producer<Session*> sessionChanges() const;
|
||||||
|
|
||||||
[[nodiscard]] MTP::Instance *mtp() const {
|
[[nodiscard]] MTP::Instance &mtp() const {
|
||||||
return _mtp.get();
|
return *_mtp;
|
||||||
}
|
}
|
||||||
[[nodiscard]] rpl::producer<MTP::Instance*> mtpValue() const;
|
[[nodiscard]] rpl::producer<not_null<MTP::Instance*>> mtpValue() const;
|
||||||
[[nodiscard]] rpl::producer<MTP::Instance*> mtpChanges() const;
|
|
||||||
|
|
||||||
// Set from legacy storage.
|
// Set from legacy storage.
|
||||||
void setLegacyMtpMainDcId(MTP::DcId mainDcId);
|
void setLegacyMtpMainDcId(MTP::DcId mainDcId);
|
||||||
|
@ -89,24 +91,21 @@ public:
|
||||||
[[nodiscard]] QByteArray serializeMtpAuthorization() const;
|
[[nodiscard]] QByteArray serializeMtpAuthorization() const;
|
||||||
void setMtpAuthorization(const QByteArray &serialized);
|
void setMtpAuthorization(const QByteArray &serialized);
|
||||||
|
|
||||||
void startMtp();
|
|
||||||
void suggestMainDcId(MTP::DcId mainDcId);
|
void suggestMainDcId(MTP::DcId mainDcId);
|
||||||
void destroyStaleAuthorizationKeys();
|
void destroyStaleAuthorizationKeys();
|
||||||
void configUpdated();
|
|
||||||
[[nodiscard]] rpl::producer<> configUpdates() const;
|
|
||||||
void clearMtp();
|
|
||||||
|
|
||||||
rpl::lifetime &lifetime() {
|
[[nodiscard]] rpl::lifetime &lifetime() {
|
||||||
return _lifetime;
|
return _lifetime;
|
||||||
}
|
}
|
||||||
|
|
||||||
private:
|
private:
|
||||||
|
void startMtp(std::unique_ptr<MTP::Config> config);
|
||||||
void createSession(
|
void createSession(
|
||||||
const MTPUser &user,
|
const MTPUser &user,
|
||||||
QByteArray serialized,
|
QByteArray serialized,
|
||||||
int streamVersion,
|
int streamVersion,
|
||||||
Settings &&settings);
|
Settings &&settings);
|
||||||
void finishStarting();
|
void finishStarting(std::unique_ptr<MTP::Config> config);
|
||||||
void watchProxyChanges();
|
void watchProxyChanges();
|
||||||
void watchSessionChanges();
|
void watchSessionChanges();
|
||||||
bool checkForUpdates(const mtpPrime *from, const mtpPrime *end);
|
bool checkForUpdates(const mtpPrime *from, const mtpPrime *end);
|
||||||
|
@ -124,7 +123,6 @@ private:
|
||||||
std::unique_ptr<MTP::Instance> _mtpForKeysDestroy;
|
std::unique_ptr<MTP::Instance> _mtpForKeysDestroy;
|
||||||
rpl::event_stream<MTPUpdates> _mtpUpdates;
|
rpl::event_stream<MTPUpdates> _mtpUpdates;
|
||||||
rpl::event_stream<> _mtpNewSessionCreated;
|
rpl::event_stream<> _mtpNewSessionCreated;
|
||||||
rpl::event_stream<> _configUpdates;
|
|
||||||
|
|
||||||
std::unique_ptr<AppConfig> _appConfig;
|
std::unique_ptr<AppConfig> _appConfig;
|
||||||
|
|
||||||
|
@ -135,7 +133,7 @@ private:
|
||||||
QByteArray _sessionUserSerialized;
|
QByteArray _sessionUserSerialized;
|
||||||
int32 _sessionUserStreamVersion = 0;
|
int32 _sessionUserStreamVersion = 0;
|
||||||
std::unique_ptr<Settings> _storedSettings;
|
std::unique_ptr<Settings> _storedSettings;
|
||||||
MTP::Instance::Config _mtpConfig;
|
MTP::Instance::Fields _mtpFields;
|
||||||
MTP::AuthKeysList _mtpKeysToDestroy;
|
MTP::AuthKeysList _mtpKeysToDestroy;
|
||||||
bool _loggingOut = false;
|
bool _loggingOut = false;
|
||||||
|
|
||||||
|
|
|
@ -11,6 +11,8 @@ https://github.com/telegramdesktop/tdesktop/blob/master/LEGAL
|
||||||
#include "core/shortcuts.h"
|
#include "core/shortcuts.h"
|
||||||
#include "main/main_account.h"
|
#include "main/main_account.h"
|
||||||
#include "main/main_session.h"
|
#include "main/main_session.h"
|
||||||
|
#include "mtproto/mtproto_config.h"
|
||||||
|
#include "mtproto/mtproto_dc_options.h"
|
||||||
#include "storage/storage_accounts.h"
|
#include "storage/storage_accounts.h"
|
||||||
#include "storage/localstorage.h"
|
#include "storage/localstorage.h"
|
||||||
#include "facades.h"
|
#include "facades.h"
|
||||||
|
@ -43,6 +45,12 @@ Storage::StartResult Accounts::start(const QByteArray &passcode) {
|
||||||
return result;
|
return result;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
void Accounts::finish() {
|
||||||
|
_activeIndex = -1;
|
||||||
|
_active = nullptr;
|
||||||
|
base::take(_accounts);
|
||||||
|
}
|
||||||
|
|
||||||
void Accounts::accountAddedInStorage(
|
void Accounts::accountAddedInStorage(
|
||||||
int index,
|
int index,
|
||||||
std::unique_ptr<Account> account) {
|
std::unique_ptr<Account> account) {
|
||||||
|
@ -115,7 +123,28 @@ rpl::producer<Session*> Accounts::activeSessionValue() const {
|
||||||
return rpl::single(current) | rpl::then(_activeSessions.events());
|
return rpl::single(current) | rpl::then(_activeSessions.events());
|
||||||
}
|
}
|
||||||
|
|
||||||
int Accounts::add() {
|
int Accounts::add(MTP::Environment environment) {
|
||||||
|
Expects(_active.current() != nullptr);
|
||||||
|
|
||||||
|
static const auto cloneConfig = [](const MTP::Config &config) {
|
||||||
|
return std::make_unique<MTP::Config>(config);
|
||||||
|
};
|
||||||
|
static const auto accountConfig = [](not_null<Account*> account) {
|
||||||
|
return cloneConfig(account->mtp().config());
|
||||||
|
};
|
||||||
|
auto config = [&] {
|
||||||
|
if (_active.current()->mtp().environment() == environment) {
|
||||||
|
return accountConfig(_active.current());
|
||||||
|
}
|
||||||
|
for (const auto &[index, account] : list()) {
|
||||||
|
if (account->mtp().environment() == environment) {
|
||||||
|
return accountConfig(account.get());
|
||||||
|
}
|
||||||
|
}
|
||||||
|
return (environment == MTP::Environment::Production)
|
||||||
|
? cloneConfig(Core::App().fallbackProductionConfig())
|
||||||
|
: std::make_unique<MTP::Config>(environment);
|
||||||
|
}();
|
||||||
auto index = 0;
|
auto index = 0;
|
||||||
while (_accounts.contains(index)) {
|
while (_accounts.contains(index)) {
|
||||||
++index;
|
++index;
|
||||||
|
@ -124,17 +153,16 @@ int Accounts::add() {
|
||||||
index,
|
index,
|
||||||
std::make_unique<Account>(_dataName, index)
|
std::make_unique<Account>(_dataName, index)
|
||||||
).first->second.get();
|
).first->second.get();
|
||||||
_local->startAdded(account);
|
_local->startAdded(account, std::move(config));
|
||||||
watchSession(account);
|
watchSession(account);
|
||||||
return index;
|
return index;
|
||||||
}
|
}
|
||||||
|
|
||||||
void Accounts::watchSession(not_null<Account*> account) {
|
void Accounts::watchSession(not_null<Account*> account) {
|
||||||
account->startMtp();
|
|
||||||
account->sessionChanges(
|
account->sessionChanges(
|
||||||
) | rpl::filter([=](Session *session) {
|
) | rpl::filter([=](Session *session) {
|
||||||
return !session; // removeRedundantAccounts may remove passcode lock.
|
return !session; // removeRedundantAccounts may remove passcode lock.
|
||||||
}) | rpl::start_with_next([=](Session *session) {
|
}) | rpl::start_with_next([=] {
|
||||||
if (account == _active.current()) {
|
if (account == _active.current()) {
|
||||||
activateAuthedAccount();
|
activateAuthedAccount();
|
||||||
}
|
}
|
||||||
|
@ -183,6 +211,7 @@ void Accounts::removeRedundantAccounts() {
|
||||||
++i;
|
++i;
|
||||||
continue;
|
continue;
|
||||||
}
|
}
|
||||||
|
checkForLastProductionConfig(i->second.get());
|
||||||
i = _accounts.erase(i);
|
i = _accounts.erase(i);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -191,6 +220,21 @@ void Accounts::removeRedundantAccounts() {
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
void Accounts::checkForLastProductionConfig(
|
||||||
|
not_null<Main::Account*> account) {
|
||||||
|
const auto mtp = &account->mtp();
|
||||||
|
if (mtp->environment() != MTP::Environment::Production) {
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
for (const auto &[index, other] : _accounts) {
|
||||||
|
if (other.get() != account
|
||||||
|
&& other->mtp().environment() == MTP::Environment::Production) {
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
Core::App().refreshFallbackProductionConfig(mtp->config());
|
||||||
|
}
|
||||||
|
|
||||||
void Accounts::activate(int index) {
|
void Accounts::activate(int index) {
|
||||||
Expects(_accounts.contains(index));
|
Expects(_accounts.contains(index));
|
||||||
|
|
||||||
|
|
|
@ -12,6 +12,10 @@ class Accounts;
|
||||||
enum class StartResult : uchar;
|
enum class StartResult : uchar;
|
||||||
} // namespace Storage
|
} // namespace Storage
|
||||||
|
|
||||||
|
namespace MTP {
|
||||||
|
enum class Environment : uchar;
|
||||||
|
} // namespace MTP
|
||||||
|
|
||||||
namespace Main {
|
namespace Main {
|
||||||
|
|
||||||
class Account;
|
class Account;
|
||||||
|
@ -25,6 +29,7 @@ public:
|
||||||
[[nodiscard]] bool started() const;
|
[[nodiscard]] bool started() const;
|
||||||
[[nodiscard]] Storage::StartResult start(const QByteArray &passcode);
|
[[nodiscard]] Storage::StartResult start(const QByteArray &passcode);
|
||||||
void resetWithForgottenPasscode();
|
void resetWithForgottenPasscode();
|
||||||
|
void finish();
|
||||||
|
|
||||||
[[nodiscard]] Storage::Accounts &local() const {
|
[[nodiscard]] Storage::Accounts &local() const {
|
||||||
return *_local;
|
return *_local;
|
||||||
|
@ -42,7 +47,7 @@ public:
|
||||||
[[nodiscard]] rpl::producer<Session*> activeSessionValue() const;
|
[[nodiscard]] rpl::producer<Session*> activeSessionValue() const;
|
||||||
[[nodiscard]] rpl::producer<Session*> activeSessionChanges() const;
|
[[nodiscard]] rpl::producer<Session*> activeSessionChanges() const;
|
||||||
|
|
||||||
[[nodiscard]] int add();
|
[[nodiscard]] int add(MTP::Environment environment);
|
||||||
void activate(int index);
|
void activate(int index);
|
||||||
|
|
||||||
// Interface for Storage::Accounts.
|
// Interface for Storage::Accounts.
|
||||||
|
@ -55,6 +60,7 @@ private:
|
||||||
void removeRedundantAccounts();
|
void removeRedundantAccounts();
|
||||||
void watchSession(not_null<Account*> account);
|
void watchSession(not_null<Account*> account);
|
||||||
void scheduleWriteAccounts();
|
void scheduleWriteAccounts();
|
||||||
|
void checkForLastProductionConfig(not_null<Main::Account*> account);
|
||||||
|
|
||||||
const QString _dataName;
|
const QString _dataName;
|
||||||
const std::unique_ptr<Storage::Accounts> _local;
|
const std::unique_ptr<Storage::Accounts> _local;
|
||||||
|
|
|
@ -20,14 +20,9 @@ constexpr auto kRefreshTimeout = 3600 * crl::time(1000);
|
||||||
|
|
||||||
AppConfig::AppConfig(not_null<Account*> account) : _account(account) {
|
AppConfig::AppConfig(not_null<Account*> account) : _account(account) {
|
||||||
account->mtpValue(
|
account->mtpValue(
|
||||||
) | rpl::start_with_next([=](MTP::Instance *instance) {
|
) | rpl::start_with_next([=](not_null<MTP::Instance*> instance) {
|
||||||
if (instance) {
|
_api.emplace(instance);
|
||||||
_api.emplace(instance);
|
refresh();
|
||||||
refresh();
|
|
||||||
} else {
|
|
||||||
_api.reset();
|
|
||||||
_requestId = 0;
|
|
||||||
}
|
|
||||||
}, _lifetime);
|
}, _lifetime);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
|
@ -12,6 +12,7 @@ https://github.com/telegramdesktop/tdesktop/blob/master/LEGAL
|
||||||
#include "core/application.h"
|
#include "core/application.h"
|
||||||
#include "core/changelogs.h"
|
#include "core/changelogs.h"
|
||||||
#include "main/main_account.h"
|
#include "main/main_account.h"
|
||||||
|
#include "mtproto/mtproto_config.h"
|
||||||
#include "chat_helpers/stickers_emoji_pack.h"
|
#include "chat_helpers/stickers_emoji_pack.h"
|
||||||
#include "chat_helpers/stickers_dice_pack.h"
|
#include "chat_helpers/stickers_dice_pack.h"
|
||||||
#include "storage/file_download.h"
|
#include "storage/file_download.h"
|
||||||
|
@ -40,6 +41,25 @@ namespace {
|
||||||
|
|
||||||
constexpr auto kLegacyCallsPeerToPeerNobody = 4;
|
constexpr auto kLegacyCallsPeerToPeerNobody = 4;
|
||||||
|
|
||||||
|
[[nodiscard]] QString ValidatedInternalLinksDomain(
|
||||||
|
not_null<const Main::Session*> session) {
|
||||||
|
// This domain should start with 'http[s]://' and end with '/'.
|
||||||
|
// Like 'https://telegram.me/' or 'https://t.me/'.
|
||||||
|
const auto &domain = session->serverConfig().internalLinksDomain;
|
||||||
|
const auto prefixes = {
|
||||||
|
qstr("https://"),
|
||||||
|
qstr("http://"),
|
||||||
|
};
|
||||||
|
for (const auto &prefix : prefixes) {
|
||||||
|
if (domain.startsWith(prefix, Qt::CaseInsensitive)) {
|
||||||
|
return domain.endsWith('/')
|
||||||
|
? domain
|
||||||
|
: MTP::ConfigFields().internalLinksDomain;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
return MTP::ConfigFields().internalLinksDomain;
|
||||||
|
}
|
||||||
|
|
||||||
} // namespace
|
} // namespace
|
||||||
|
|
||||||
Session::Session(
|
Session::Session(
|
||||||
|
@ -75,7 +95,7 @@ Session::Session(
|
||||||
_api->requestTermsUpdate();
|
_api->requestTermsUpdate();
|
||||||
_api->requestFullPeer(_user);
|
_api->requestFullPeer(_user);
|
||||||
|
|
||||||
_api->instance()->setUserPhone(_user->phone());
|
_api->instance().setUserPhone(_user->phone());
|
||||||
|
|
||||||
crl::on_main(this, [=] {
|
crl::on_main(this, [=] {
|
||||||
using Flag = Data::PeerUpdate::Flag;
|
using Flag = Data::PeerUpdate::Flag;
|
||||||
|
@ -91,9 +111,9 @@ Session::Session(
|
||||||
|
|
||||||
if (update.flags & Flag::PhoneNumber) {
|
if (update.flags & Flag::PhoneNumber) {
|
||||||
const auto phone = _user->phone();
|
const auto phone = _user->phone();
|
||||||
_api->instance()->setUserPhone(phone);
|
_api->instance().setUserPhone(phone);
|
||||||
if (!phone.isEmpty()) {
|
if (!phone.isEmpty()) {
|
||||||
_api->instance()->requestConfig();
|
_api->instance().requestConfig();
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}, _lifetime);
|
}, _lifetime);
|
||||||
|
@ -156,19 +176,42 @@ void Session::saveSettingsDelayed(crl::time delay) {
|
||||||
}
|
}
|
||||||
|
|
||||||
MTP::DcId Session::mainDcId() const {
|
MTP::DcId Session::mainDcId() const {
|
||||||
return _account->mtp()->mainDcId();
|
return _account->mtp().mainDcId();
|
||||||
}
|
}
|
||||||
|
|
||||||
not_null<MTP::Instance*> Session::mtp() const {
|
MTP::Instance &Session::mtp() const {
|
||||||
return _account->mtp();
|
return _account->mtp();
|
||||||
}
|
}
|
||||||
|
|
||||||
|
const MTP::ConfigFields &Session::serverConfig() const {
|
||||||
|
return _account->mtp().configValues();
|
||||||
|
}
|
||||||
|
|
||||||
void Session::termsDeleteNow() {
|
void Session::termsDeleteNow() {
|
||||||
api().request(MTPaccount_DeleteAccount(
|
api().request(MTPaccount_DeleteAccount(
|
||||||
MTP_string("Decline ToS update")
|
MTP_string("Decline ToS update")
|
||||||
)).send();
|
)).send();
|
||||||
}
|
}
|
||||||
|
|
||||||
|
QString Session::createInternalLink(const QString &query) const {
|
||||||
|
auto result = createInternalLinkFull(query);
|
||||||
|
auto prefixes = {
|
||||||
|
qstr("https://"),
|
||||||
|
qstr("http://"),
|
||||||
|
};
|
||||||
|
for (auto &prefix : prefixes) {
|
||||||
|
if (result.startsWith(prefix, Qt::CaseInsensitive)) {
|
||||||
|
return result.mid(prefix.size());
|
||||||
|
}
|
||||||
|
}
|
||||||
|
LOG(("Warning: bad internal url '%1'").arg(result));
|
||||||
|
return result;
|
||||||
|
}
|
||||||
|
|
||||||
|
QString Session::createInternalLinkFull(const QString &query) const {
|
||||||
|
return ValidatedInternalLinksDomain(this) + query;
|
||||||
|
}
|
||||||
|
|
||||||
bool Session::supportMode() const {
|
bool Session::supportMode() const {
|
||||||
return (_supportHelper != nullptr);
|
return (_supportHelper != nullptr);
|
||||||
}
|
}
|
||||||
|
|
|
@ -21,6 +21,7 @@ class Updates;
|
||||||
|
|
||||||
namespace MTP {
|
namespace MTP {
|
||||||
class Instance;
|
class Instance;
|
||||||
|
struct ConfigFields;
|
||||||
} // namespace MTP
|
} // namespace MTP
|
||||||
|
|
||||||
namespace Support {
|
namespace Support {
|
||||||
|
@ -127,7 +128,8 @@ public:
|
||||||
// Shortcuts.
|
// Shortcuts.
|
||||||
[[nodiscard]] base::Observable<void> &downloaderTaskFinished();
|
[[nodiscard]] base::Observable<void> &downloaderTaskFinished();
|
||||||
[[nodiscard]] MTP::DcId mainDcId() const;
|
[[nodiscard]] MTP::DcId mainDcId() const;
|
||||||
[[nodiscard]] not_null<MTP::Instance*> mtp() const;
|
[[nodiscard]] MTP::Instance &mtp() const;
|
||||||
|
[[nodiscard]] const MTP::ConfigFields &serverConfig() const;
|
||||||
[[nodiscard]] ApiWrap &api() {
|
[[nodiscard]] ApiWrap &api() {
|
||||||
return *_api;
|
return *_api;
|
||||||
}
|
}
|
||||||
|
@ -138,6 +140,10 @@ public:
|
||||||
|
|
||||||
void termsDeleteNow();
|
void termsDeleteNow();
|
||||||
|
|
||||||
|
void setInternalLinkDomain(const QString &domain) const;
|
||||||
|
[[nodiscard]] QString createInternalLink(const QString &query) const;
|
||||||
|
[[nodiscard]] QString createInternalLinkFull(const QString &query) const;
|
||||||
|
|
||||||
[[nodiscard]] rpl::lifetime &lifetime() {
|
[[nodiscard]] rpl::lifetime &lifetime() {
|
||||||
return _lifetime;
|
return _lifetime;
|
||||||
}
|
}
|
||||||
|
|
|
@ -85,7 +85,7 @@ https://github.com/telegramdesktop/tdesktop/blob/master/LEGAL
|
||||||
#include "window/window_session_controller.h"
|
#include "window/window_session_controller.h"
|
||||||
#include "window/themes/window_theme.h"
|
#include "window/themes/window_theme.h"
|
||||||
#include "window/window_history_hider.h"
|
#include "window/window_history_hider.h"
|
||||||
#include "mtproto/dc_options.h"
|
#include "mtproto/mtproto_dc_options.h"
|
||||||
#include "core/file_utilities.h"
|
#include "core/file_utilities.h"
|
||||||
#include "core/update_checker.h"
|
#include "core/update_checker.h"
|
||||||
#include "core/shortcuts.h"
|
#include "core/shortcuts.h"
|
||||||
|
|
|
@ -516,7 +516,7 @@ bool MainWindow::doWeMarkAsRead() {
|
||||||
if (!_main || Ui::isLayerShown()) {
|
if (!_main || Ui::isLayerShown()) {
|
||||||
return false;
|
return false;
|
||||||
}
|
}
|
||||||
updateIsActive(0);
|
updateIsActive();
|
||||||
return isActive() && _main->doWeMarkAsRead();
|
return isActive() && _main->doWeMarkAsRead();
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -609,7 +609,7 @@ void MainWindow::updateTrayMenu(bool force) {
|
||||||
auto minimizeAction = actions.at(1);
|
auto minimizeAction = actions.at(1);
|
||||||
minimizeAction->setEnabled(isVisible());
|
minimizeAction->setEnabled(isVisible());
|
||||||
} else {
|
} else {
|
||||||
updateIsActive(0);
|
updateIsActive();
|
||||||
auto active = Platform::IsWayland() ? isVisible() : isActive();
|
auto active = Platform::IsWayland() ? isVisible() : isActive();
|
||||||
auto toggleAction = actions.at(0);
|
auto toggleAction = actions.at(0);
|
||||||
disconnect(toggleAction, SIGNAL(triggered(bool)), this, SLOT(minimizeToTray()));
|
disconnect(toggleAction, SIGNAL(triggered(bool)), this, SLOT(minimizeToTray()));
|
||||||
|
@ -705,7 +705,7 @@ void MainWindow::activate() {
|
||||||
setVisible(true);
|
setVisible(true);
|
||||||
psActivateProcess();
|
psActivateProcess();
|
||||||
activateWindow();
|
activateWindow();
|
||||||
updateIsActive(Global::OnlineFocusTimeout());
|
controller().updateIsActiveFocus();
|
||||||
if (wasHidden) {
|
if (wasHidden) {
|
||||||
if (_main) {
|
if (_main) {
|
||||||
_main->windowShown();
|
_main->windowShown();
|
||||||
|
@ -743,7 +743,7 @@ void MainWindow::showFromTray(QSystemTrayIcon::ActivationReason reason) {
|
||||||
|
|
||||||
void MainWindow::handleTrayIconActication(
|
void MainWindow::handleTrayIconActication(
|
||||||
QSystemTrayIcon::ActivationReason reason) {
|
QSystemTrayIcon::ActivationReason reason) {
|
||||||
updateIsActive(0);
|
updateIsActive();
|
||||||
if (Platform::IsMac() && isActive()) {
|
if (Platform::IsMac() && isActive()) {
|
||||||
if (trayIcon && !trayIcon->contextMenu()) {
|
if (trayIcon && !trayIcon->contextMenu()) {
|
||||||
showFromTray(reason);
|
showFromTray(reason);
|
||||||
|
|
|
@ -27,7 +27,7 @@ LoaderMtproto::LoaderMtproto(
|
||||||
Data::FileOrigin origin)
|
Data::FileOrigin origin)
|
||||||
: DownloadMtprotoTask(owner, location, origin)
|
: DownloadMtprotoTask(owner, location, origin)
|
||||||
, _size(size)
|
, _size(size)
|
||||||
, _api(api().instance()) {
|
, _api(&api().instance()) {
|
||||||
}
|
}
|
||||||
|
|
||||||
Storage::Cache::Key LoaderMtproto::baseCacheKey() const {
|
Storage::Cache::Key LoaderMtproto::baseCacheKey() const {
|
||||||
|
|
|
@ -2462,6 +2462,7 @@ void OverlayWidget::initThemePreview() {
|
||||||
return result;
|
return result;
|
||||||
}();
|
}();
|
||||||
|
|
||||||
|
const auto weakSession = base::make_weak(&_document->session());
|
||||||
const auto path = _document->location().name();
|
const auto path = _document->location().name();
|
||||||
const auto id = _themePreviewId = rand_value<uint64>();
|
const auto id = _themePreviewId = rand_value<uint64>();
|
||||||
const auto weak = Ui::MakeWeak(this);
|
const auto weak = Ui::MakeWeak(this);
|
||||||
|
@ -2473,7 +2474,8 @@ void OverlayWidget::initThemePreview() {
|
||||||
std::move(data),
|
std::move(data),
|
||||||
Window::Theme::PreviewType::Extended);
|
Window::Theme::PreviewType::Extended);
|
||||||
crl::on_main(weak, [=, result = std::move(preview)]() mutable {
|
crl::on_main(weak, [=, result = std::move(preview)]() mutable {
|
||||||
if (id != _themePreviewId) {
|
const auto session = weakSession.get();
|
||||||
|
if (id != _themePreviewId || !session) {
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
_themePreviewId = 0;
|
_themePreviewId = 0;
|
||||||
|
@ -2509,7 +2511,7 @@ void OverlayWidget::initThemePreview() {
|
||||||
_themeShare->show();
|
_themeShare->show();
|
||||||
_themeShare->setClickedCallback([=] {
|
_themeShare->setClickedCallback([=] {
|
||||||
QGuiApplication::clipboard()->setText(
|
QGuiApplication::clipboard()->setText(
|
||||||
Core::App().createInternalLinkFull("addtheme/" + slug));
|
session->createInternalLinkFull("addtheme/" + slug));
|
||||||
Ui::Toast::Show(
|
Ui::Toast::Show(
|
||||||
this,
|
this,
|
||||||
tr::lng_background_link_copied(tr::now));
|
tr::lng_background_link_copied(tr::now));
|
||||||
|
|
|
@ -9,7 +9,8 @@ https://github.com/telegramdesktop/tdesktop/blob/master/LEGAL
|
||||||
|
|
||||||
#include "mtproto/special_config_request.h"
|
#include "mtproto/special_config_request.h"
|
||||||
#include "mtproto/facade.h"
|
#include "mtproto/facade.h"
|
||||||
#include "mtproto/dc_options.h"
|
#include "mtproto/mtproto_dc_options.h"
|
||||||
|
#include "mtproto/mtproto_config.h"
|
||||||
#include "mtproto/mtp_instance.h"
|
#include "mtproto/mtp_instance.h"
|
||||||
#include "facades.h"
|
#include "facades.h"
|
||||||
|
|
||||||
|
@ -40,7 +41,7 @@ void ConfigLoader::load() {
|
||||||
sendRequest(_instance->mainDcId());
|
sendRequest(_instance->mainDcId());
|
||||||
_enumDCTimer.callOnce(kEnumerateDcTimeout);
|
_enumDCTimer.callOnce(kEnumerateDcTimeout);
|
||||||
} else {
|
} else {
|
||||||
auto ids = _instance->dcOptions()->configEnumDcIds();
|
auto ids = _instance->dcOptions().configEnumDcIds();
|
||||||
Assert(!ids.empty());
|
Assert(!ids.empty());
|
||||||
_enumCurrent = ids.front();
|
_enumCurrent = ids.front();
|
||||||
enumerate();
|
enumerate();
|
||||||
|
@ -87,7 +88,7 @@ void ConfigLoader::enumerate() {
|
||||||
if (!_enumCurrent) {
|
if (!_enumCurrent) {
|
||||||
_enumCurrent = _instance->mainDcId();
|
_enumCurrent = _instance->mainDcId();
|
||||||
}
|
}
|
||||||
auto ids = _instance->dcOptions()->configEnumDcIds();
|
auto ids = _instance->dcOptions().configEnumDcIds();
|
||||||
Assert(!ids.empty());
|
Assert(!ids.empty());
|
||||||
|
|
||||||
auto i = std::find(ids.cbegin(), ids.cend(), _enumCurrent);
|
auto i = std::find(ids.cbegin(), ids.cend(), _enumCurrent);
|
||||||
|
@ -135,7 +136,7 @@ void ConfigLoader::createSpecialLoader() {
|
||||||
} else {
|
} else {
|
||||||
addSpecialEndpoint(dcId, ip, port, secret);
|
addSpecialEndpoint(dcId, ip, port, secret);
|
||||||
}
|
}
|
||||||
}, _phone);
|
}, _instance->configValues().txtDomainString, _phone);
|
||||||
}
|
}
|
||||||
|
|
||||||
void ConfigLoader::addSpecialEndpoint(
|
void ConfigLoader::addSpecialEndpoint(
|
||||||
|
@ -180,7 +181,7 @@ void ConfigLoader::sendSpecialRequest() {
|
||||||
using Flag = MTPDdcOption::Flag;
|
using Flag = MTPDdcOption::Flag;
|
||||||
const auto flags = Flag::f_tcpo_only
|
const auto flags = Flag::f_tcpo_only
|
||||||
| (endpoint->secret.empty() ? Flag(0) : Flag::f_secret);
|
| (endpoint->secret.empty() ? Flag(0) : Flag::f_secret);
|
||||||
_instance->dcOptions()->constructAddOne(
|
_instance->dcOptions().constructAddOne(
|
||||||
_specialEnumCurrent,
|
_specialEnumCurrent,
|
||||||
flags,
|
flags,
|
||||||
endpoint->ip,
|
endpoint->ip,
|
||||||
|
@ -212,7 +213,7 @@ void ConfigLoader::specialConfigLoaded(const MTPConfig &result) {
|
||||||
|
|
||||||
// We use special config only for dc options.
|
// We use special config only for dc options.
|
||||||
// For everything else we wait for normal config from main dc.
|
// For everything else we wait for normal config from main dc.
|
||||||
_instance->dcOptions()->setFromList(data.vdc_options());
|
_instance->dcOptions().setFromList(data.vdc_options());
|
||||||
}
|
}
|
||||||
|
|
||||||
} // namespace details
|
} // namespace details
|
||||||
|
|
|
@ -7,7 +7,7 @@ https://github.com/telegramdesktop/tdesktop/blob/master/LEGAL
|
||||||
*/
|
*/
|
||||||
#pragma once
|
#pragma once
|
||||||
|
|
||||||
#include "mtproto/dc_options.h"
|
#include "mtproto/mtproto_dc_options.h"
|
||||||
#include "mtproto/mtproto_proxy_data.h"
|
#include "mtproto/mtproto_proxy_data.h"
|
||||||
#include "base/bytes.h"
|
#include "base/bytes.h"
|
||||||
|
|
||||||
|
|
|
@ -84,7 +84,7 @@ std::optional<DedicatedLoader::File> ParseFile(
|
||||||
|
|
||||||
WeakInstance::WeakInstance(base::weak_ptr<Main::Session> session)
|
WeakInstance::WeakInstance(base::weak_ptr<Main::Session> session)
|
||||||
: _session(session)
|
: _session(session)
|
||||||
, _instance(_session ? _session->account().mtp() : nullptr) {
|
, _instance(_session ? &_session->account().mtp() : nullptr) {
|
||||||
if (!valid()) {
|
if (!valid()) {
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
|
|
|
@ -9,7 +9,7 @@ https://github.com/telegramdesktop/tdesktop/blob/master/LEGAL
|
||||||
|
|
||||||
#include "mtproto/facade.h"
|
#include "mtproto/facade.h"
|
||||||
#include "mtproto/mtproto_auth_key.h"
|
#include "mtproto/mtproto_auth_key.h"
|
||||||
#include "mtproto/dc_options.h"
|
#include "mtproto/mtproto_dc_options.h"
|
||||||
#include "mtproto/mtp_instance.h"
|
#include "mtproto/mtp_instance.h"
|
||||||
#include "mtproto/special_config_request.h"
|
#include "mtproto/special_config_request.h"
|
||||||
|
|
||||||
|
|
|
@ -294,7 +294,7 @@ void DomainResolver::performRequest(
|
||||||
request.setRawHeader("Host", host.toLatin1());
|
request.setRawHeader("Host", host.toLatin1());
|
||||||
}
|
}
|
||||||
} break;
|
} break;
|
||||||
default: Unexpected("Type in SpecialConfigRequest::performRequest.");
|
default: Unexpected("Type in DomainResolver::performRequest.");
|
||||||
}
|
}
|
||||||
request.setUrl(url);
|
request.setUrl(url);
|
||||||
request.setRawHeader("User-Agent", DnsUserAgent());
|
request.setRawHeader("User-Agent", DnsUserAgent());
|
||||||
|
|
|
@ -63,17 +63,17 @@ inline bool isCdnDc(MTPDdcOption::Flags flags) {
|
||||||
|
|
||||||
inline bool isTemporaryDcId(ShiftedDcId shiftedDcId) {
|
inline bool isTemporaryDcId(ShiftedDcId shiftedDcId) {
|
||||||
auto dcId = BareDcId(shiftedDcId);
|
auto dcId = BareDcId(shiftedDcId);
|
||||||
return (dcId >= Instance::Config::kTemporaryMainDc);
|
return (dcId >= Instance::Fields::kTemporaryMainDc);
|
||||||
}
|
}
|
||||||
|
|
||||||
inline DcId getRealIdFromTemporaryDcId(ShiftedDcId shiftedDcId) {
|
inline DcId getRealIdFromTemporaryDcId(ShiftedDcId shiftedDcId) {
|
||||||
auto dcId = BareDcId(shiftedDcId);
|
auto dcId = BareDcId(shiftedDcId);
|
||||||
return (dcId >= Instance::Config::kTemporaryMainDc) ? (dcId - Instance::Config::kTemporaryMainDc) : 0;
|
return (dcId >= Instance::Fields::kTemporaryMainDc) ? (dcId - Instance::Fields::kTemporaryMainDc) : 0;
|
||||||
}
|
}
|
||||||
|
|
||||||
inline DcId getTemporaryIdFromRealDcId(ShiftedDcId shiftedDcId) {
|
inline DcId getTemporaryIdFromRealDcId(ShiftedDcId shiftedDcId) {
|
||||||
auto dcId = BareDcId(shiftedDcId);
|
auto dcId = BareDcId(shiftedDcId);
|
||||||
return (dcId < Instance::Config::kTemporaryMainDc) ? (dcId + Instance::Config::kTemporaryMainDc) : 0;
|
return (dcId < Instance::Fields::kTemporaryMainDc) ? (dcId + Instance::Fields::kTemporaryMainDc) : 0;
|
||||||
}
|
}
|
||||||
|
|
||||||
namespace details {
|
namespace details {
|
||||||
|
|
|
@ -11,7 +11,8 @@ https://github.com/telegramdesktop/tdesktop/blob/master/LEGAL
|
||||||
#include "mtproto/details/mtproto_rsa_public_key.h"
|
#include "mtproto/details/mtproto_rsa_public_key.h"
|
||||||
#include "mtproto/special_config_request.h"
|
#include "mtproto/special_config_request.h"
|
||||||
#include "mtproto/session.h"
|
#include "mtproto/session.h"
|
||||||
#include "mtproto/dc_options.h"
|
#include "mtproto/mtproto_config.h"
|
||||||
|
#include "mtproto/mtproto_dc_options.h"
|
||||||
#include "mtproto/config_loader.h"
|
#include "mtproto/config_loader.h"
|
||||||
#include "mtproto/sender.h"
|
#include "mtproto/sender.h"
|
||||||
#include "storage/localstorage.h"
|
#include "storage/localstorage.h"
|
||||||
|
@ -53,9 +54,18 @@ int GetNextRequestId() {
|
||||||
|
|
||||||
class Instance::Private : private Sender {
|
class Instance::Private : private Sender {
|
||||||
public:
|
public:
|
||||||
Private(not_null<Instance*> instance, not_null<DcOptions*> options, Instance::Mode mode);
|
Private(
|
||||||
|
not_null<Instance*> instance,
|
||||||
|
Instance::Mode mode,
|
||||||
|
Fields &&fields);
|
||||||
|
|
||||||
void start(Config &&config);
|
void start();
|
||||||
|
|
||||||
|
[[nodiscard]] Config &config() const;
|
||||||
|
[[nodiscard]] const ConfigFields &configValues() const;
|
||||||
|
[[nodiscard]] DcOptions &dcOptions() const;
|
||||||
|
[[nodiscard]] Environment environment() const;
|
||||||
|
[[nodiscard]] bool isTestMode() const;
|
||||||
|
|
||||||
void resolveProxyDomain(const QString &host);
|
void resolveProxyDomain(const QString &host);
|
||||||
void setGoodProxyDomain(const QString &host, const QString &ip);
|
void setGoodProxyDomain(const QString &host, const QString &ip);
|
||||||
|
@ -72,8 +82,6 @@ public:
|
||||||
void addKeysForDestroy(AuthKeysList &&keys);
|
void addKeysForDestroy(AuthKeysList &&keys);
|
||||||
[[nodiscard]] rpl::producer<> allKeysDestroyed() const;
|
[[nodiscard]] rpl::producer<> allKeysDestroyed() const;
|
||||||
|
|
||||||
[[nodiscard]] not_null<DcOptions*> dcOptions();
|
|
||||||
|
|
||||||
// Thread safe.
|
// Thread safe.
|
||||||
[[nodiscard]] QString deviceModel() const;
|
[[nodiscard]] QString deviceModel() const;
|
||||||
[[nodiscard]] QString systemVersion() const;
|
[[nodiscard]] QString systemVersion() const;
|
||||||
|
@ -195,8 +203,8 @@ private:
|
||||||
void checkDelayedRequests();
|
void checkDelayedRequests();
|
||||||
|
|
||||||
const not_null<Instance*> _instance;
|
const not_null<Instance*> _instance;
|
||||||
const not_null<DcOptions*> _dcOptions;
|
|
||||||
const Instance::Mode _mode = Instance::Mode::Normal;
|
const Instance::Mode _mode = Instance::Mode::Normal;
|
||||||
|
const std::unique_ptr<Config> _config;
|
||||||
|
|
||||||
std::unique_ptr<QThread> _mainSessionThread;
|
std::unique_ptr<QThread> _mainSessionThread;
|
||||||
std::unique_ptr<QThread> _otherSessionsThread;
|
std::unique_ptr<QThread> _otherSessionsThread;
|
||||||
|
@ -205,7 +213,7 @@ private:
|
||||||
QString _deviceModel;
|
QString _deviceModel;
|
||||||
QString _systemVersion;
|
QString _systemVersion;
|
||||||
|
|
||||||
DcId _mainDcId = Config::kDefaultMainDc;
|
DcId _mainDcId = Fields::kDefaultMainDc;
|
||||||
bool _mainDcIdForced = false;
|
bool _mainDcIdForced = false;
|
||||||
base::flat_map<DcId, std::unique_ptr<Dcenter>> _dcenters;
|
base::flat_map<DcId, std::unique_ptr<Dcenter>> _dcenters;
|
||||||
std::vector<std::unique_ptr<Dcenter>> _dcentersToDestroy;
|
std::vector<std::unique_ptr<Dcenter>> _dcentersToDestroy;
|
||||||
|
@ -261,27 +269,36 @@ private:
|
||||||
|
|
||||||
};
|
};
|
||||||
|
|
||||||
|
Instance::Fields::Fields() = default;
|
||||||
|
|
||||||
|
Instance::Fields::Fields(Fields &&other) = default;
|
||||||
|
|
||||||
|
auto Instance::Fields::operator=(Fields &&other) -> Fields & = default;
|
||||||
|
|
||||||
|
Instance::Fields::~Fields() = default;
|
||||||
|
|
||||||
Instance::Private::Private(
|
Instance::Private::Private(
|
||||||
not_null<Instance*> instance,
|
not_null<Instance*> instance,
|
||||||
not_null<DcOptions*> options,
|
Instance::Mode mode,
|
||||||
Instance::Mode mode)
|
Fields &&fields)
|
||||||
: Sender(instance)
|
: Sender(instance)
|
||||||
, _instance(instance)
|
, _instance(instance)
|
||||||
, _dcOptions(options)
|
, _mode(mode)
|
||||||
, _mode(mode) {
|
, _config(std::move(fields.config)) {
|
||||||
|
Expects(_config != nullptr);
|
||||||
|
|
||||||
const auto idealThreadPoolSize = QThread::idealThreadCount();
|
const auto idealThreadPoolSize = QThread::idealThreadCount();
|
||||||
_fileSessionThreads.resize(2 * std::max(idealThreadPoolSize / 2, 1));
|
_fileSessionThreads.resize(2 * std::max(idealThreadPoolSize / 2, 1));
|
||||||
|
|
||||||
details::unpaused(
|
details::unpaused(
|
||||||
) | rpl::start_with_next([=] {
|
) | rpl::start_with_next([=] {
|
||||||
unpaused();
|
unpaused();
|
||||||
}, _lifetime);
|
}, _lifetime);
|
||||||
}
|
|
||||||
|
|
||||||
void Instance::Private::start(Config &&config) {
|
_deviceModel = std::move(fields.deviceModel);
|
||||||
_deviceModel = std::move(config.deviceModel);
|
_systemVersion = std::move(fields.systemVersion);
|
||||||
_systemVersion = std::move(config.systemVersion);
|
|
||||||
|
|
||||||
for (auto &key : config.keys) {
|
for (auto &key : fields.keys) {
|
||||||
auto dcId = key->dcId();
|
auto dcId = key->dcId();
|
||||||
auto shiftedDcId = dcId;
|
auto shiftedDcId = dcId;
|
||||||
if (isKeysDestroyer()) {
|
if (isKeysDestroyer()) {
|
||||||
|
@ -297,22 +314,24 @@ void Instance::Private::start(Config &&config) {
|
||||||
addDc(shiftedDcId, std::move(key));
|
addDc(shiftedDcId, std::move(key));
|
||||||
}
|
}
|
||||||
|
|
||||||
if (config.mainDcId != Config::kNotSetMainDc) {
|
if (fields.mainDcId != Fields::kNotSetMainDc) {
|
||||||
_mainDcId = config.mainDcId;
|
_mainDcId = fields.mainDcId;
|
||||||
_mainDcIdForced = true;
|
_mainDcIdForced = true;
|
||||||
}
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
void Instance::Private::start() {
|
||||||
if (isKeysDestroyer()) {
|
if (isKeysDestroyer()) {
|
||||||
for (const auto &[shiftedDcId, dc] : _dcenters) {
|
for (const auto &[shiftedDcId, dc] : _dcenters) {
|
||||||
startSession(shiftedDcId);
|
startSession(shiftedDcId);
|
||||||
}
|
}
|
||||||
} else if (_mainDcId != Config::kNoneMainDc) {
|
} else if (_mainDcId != Fields::kNoneMainDc) {
|
||||||
_mainSession = startSession(_mainDcId);
|
_mainSession = startSession(_mainDcId);
|
||||||
}
|
}
|
||||||
|
|
||||||
_checkDelayedTimer.setCallback([this] { checkDelayedRequests(); });
|
_checkDelayedTimer.setCallback([this] { checkDelayedRequests(); });
|
||||||
|
|
||||||
Assert((_mainDcId == Config::kNoneMainDc) == isKeysDestroyer());
|
Assert((_mainDcId == Fields::kNoneMainDc) == isKeysDestroyer());
|
||||||
requestConfig();
|
requestConfig();
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -418,7 +437,8 @@ void Instance::Private::setMainDcId(DcId mainDcId) {
|
||||||
}
|
}
|
||||||
|
|
||||||
DcId Instance::Private::mainDcId() const {
|
DcId Instance::Private::mainDcId() const {
|
||||||
Expects(_mainDcId != Config::kNoneMainDc);
|
Expects(_mainDcId != Fields::kNoneMainDc);
|
||||||
|
|
||||||
return _mainDcId;
|
return _mainDcId;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -457,7 +477,7 @@ void Instance::Private::syncHttpUnixtime() {
|
||||||
InvokeQueued(_instance, [=] {
|
InvokeQueued(_instance, [=] {
|
||||||
_httpUnixtimeLoader = nullptr;
|
_httpUnixtimeLoader = nullptr;
|
||||||
});
|
});
|
||||||
});
|
}, configValues().txtDomainString);
|
||||||
}
|
}
|
||||||
|
|
||||||
void Instance::Private::restartedByTimeout(ShiftedDcId shiftedDcId) {
|
void Instance::Private::restartedByTimeout(ShiftedDcId shiftedDcId) {
|
||||||
|
@ -469,7 +489,7 @@ rpl::producer<ShiftedDcId> Instance::Private::restartsByTimeout() const {
|
||||||
}
|
}
|
||||||
|
|
||||||
void Instance::Private::requestConfigIfOld() {
|
void Instance::Private::requestConfigIfOld() {
|
||||||
const auto timeout = Global::BlockedMode()
|
const auto timeout = _config->values().blockedMode
|
||||||
? kConfigBecomesOldForBlockedIn
|
? kConfigBecomesOldForBlockedIn
|
||||||
: kConfigBecomesOldIn;
|
: kConfigBecomesOldIn;
|
||||||
if (crl::now() - _lastConfigLoadedTime >= timeout) {
|
if (crl::now() - _lastConfigLoadedTime >= timeout) {
|
||||||
|
@ -490,7 +510,7 @@ void Instance::Private::requestConfigIfExpired() {
|
||||||
}
|
}
|
||||||
|
|
||||||
void Instance::Private::requestCDNConfig() {
|
void Instance::Private::requestCDNConfig() {
|
||||||
if (_cdnConfigLoadRequestId || _mainDcId == Config::kNoneMainDc) {
|
if (_cdnConfigLoadRequestId || _mainDcId == Fields::kNoneMainDc) {
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
_cdnConfigLoadRequestId = request(
|
_cdnConfigLoadRequestId = request(
|
||||||
|
@ -498,7 +518,7 @@ void Instance::Private::requestCDNConfig() {
|
||||||
).done([this](const MTPCdnConfig &result) {
|
).done([this](const MTPCdnConfig &result) {
|
||||||
_cdnConfigLoadRequestId = 0;
|
_cdnConfigLoadRequestId = 0;
|
||||||
result.match([&](const MTPDcdnConfig &data) {
|
result.match([&](const MTPDcdnConfig &data) {
|
||||||
dcOptions()->setCDNConfig(data);
|
dcOptions().setCDNConfig(data);
|
||||||
});
|
});
|
||||||
Local::writeSettings();
|
Local::writeSettings();
|
||||||
}).send();
|
}).send();
|
||||||
|
@ -642,7 +662,7 @@ void Instance::Private::logoutGuestDcs() {
|
||||||
dcIds.push_back(key.first);
|
dcIds.push_back(key.first);
|
||||||
}
|
}
|
||||||
for (const auto dcId : dcIds) {
|
for (const auto dcId : dcIds) {
|
||||||
if (dcId == mainDcId() || dcOptions()->dcType(dcId) == DcType::Cdn) {
|
if (dcId == mainDcId() || dcOptions().dcType(dcId) == DcType::Cdn) {
|
||||||
continue;
|
continue;
|
||||||
}
|
}
|
||||||
const auto shiftedDcId = MTP::logoutDcId(dcId);
|
const auto shiftedDcId = MTP::logoutDcId(dcId);
|
||||||
|
@ -784,8 +804,24 @@ rpl::producer<> Instance::Private::writeKeysRequests() const {
|
||||||
return _writeKeysRequests.events();
|
return _writeKeysRequests.events();
|
||||||
}
|
}
|
||||||
|
|
||||||
not_null<DcOptions*> Instance::Private::dcOptions() {
|
Config &Instance::Private::config() const {
|
||||||
return _dcOptions;
|
return *_config;
|
||||||
|
}
|
||||||
|
|
||||||
|
const ConfigFields &Instance::Private::configValues() const {
|
||||||
|
return _config->values();
|
||||||
|
}
|
||||||
|
|
||||||
|
DcOptions &Instance::Private::dcOptions() const {
|
||||||
|
return _config->dcOptions();
|
||||||
|
}
|
||||||
|
|
||||||
|
Environment Instance::Private::environment() const {
|
||||||
|
return _config->environment();
|
||||||
|
}
|
||||||
|
|
||||||
|
bool Instance::Private::isTestMode() const {
|
||||||
|
return _config->isTestMode();
|
||||||
}
|
}
|
||||||
|
|
||||||
QString Instance::Private::deviceModel() const {
|
QString Instance::Private::deviceModel() const {
|
||||||
|
@ -809,58 +845,13 @@ void Instance::Private::configLoadDone(const MTPConfig &result) {
|
||||||
_lastConfigLoadedTime = crl::now();
|
_lastConfigLoadedTime = crl::now();
|
||||||
|
|
||||||
const auto &data = result.c_config();
|
const auto &data = result.c_config();
|
||||||
DEBUG_LOG(("MTP Info: got config, chat_size_max: %1, date: %2, test_mode: %3, this_dc: %4, dc_options.length: %5").arg(data.vchat_size_max().v).arg(data.vdate().v).arg(mtpIsTrue(data.vtest_mode())).arg(data.vthis_dc().v).arg(data.vdc_options().v.size()));
|
_config->apply(data);
|
||||||
if (data.vdc_options().v.empty()) {
|
|
||||||
LOG(("MTP Error: config with empty dc_options received!"));
|
|
||||||
} else {
|
|
||||||
_dcOptions->setFromList(data.vdc_options());
|
|
||||||
}
|
|
||||||
|
|
||||||
Global::SetChatSizeMax(data.vchat_size_max().v);
|
|
||||||
Global::SetMegagroupSizeMax(data.vmegagroup_size_max().v);
|
|
||||||
Global::SetForwardedCountMax(data.vforwarded_count_max().v);
|
|
||||||
Global::SetOnlineUpdatePeriod(data.vonline_update_period_ms().v);
|
|
||||||
Global::SetOfflineBlurTimeout(data.voffline_blur_timeout_ms().v);
|
|
||||||
Global::SetOfflineIdleTimeout(data.voffline_idle_timeout_ms().v);
|
|
||||||
Global::SetOnlineCloudTimeout(data.vonline_cloud_timeout_ms().v);
|
|
||||||
Global::SetNotifyCloudDelay(data.vnotify_cloud_delay_ms().v);
|
|
||||||
Global::SetNotifyDefaultDelay(data.vnotify_default_delay_ms().v);
|
|
||||||
Global::SetPushChatPeriod(data.vpush_chat_period_ms().v);
|
|
||||||
Global::SetPushChatLimit(data.vpush_chat_limit().v);
|
|
||||||
Global::SetSavedGifsLimit(data.vsaved_gifs_limit().v);
|
|
||||||
Global::SetEditTimeLimit(data.vedit_time_limit().v);
|
|
||||||
Global::SetRevokeTimeLimit(data.vrevoke_time_limit().v);
|
|
||||||
Global::SetRevokePrivateTimeLimit(data.vrevoke_pm_time_limit().v);
|
|
||||||
Global::SetRevokePrivateInbox(data.is_revoke_pm_inbox());
|
|
||||||
Global::SetStickersRecentLimit(data.vstickers_recent_limit().v);
|
|
||||||
Global::SetStickersFavedLimit(data.vstickers_faved_limit().v);
|
|
||||||
Global::SetPinnedDialogsCountMax(
|
|
||||||
std::max(data.vpinned_dialogs_count_max().v, 1));
|
|
||||||
Global::SetPinnedDialogsInFolderMax(
|
|
||||||
std::max(data.vpinned_infolder_count_max().v, 1));
|
|
||||||
Core::App().setInternalLinkDomain(qs(data.vme_url_prefix()));
|
|
||||||
Global::SetChannelsReadMediaPeriod(data.vchannels_read_media_period().v);
|
|
||||||
Global::SetWebFileDcId(data.vwebfile_dc_id().v);
|
|
||||||
Global::SetTxtDomainString(qs(data.vdc_txt_domain_name()));
|
|
||||||
Global::SetCallReceiveTimeoutMs(data.vcall_receive_timeout_ms().v);
|
|
||||||
Global::SetCallRingTimeoutMs(data.vcall_ring_timeout_ms().v);
|
|
||||||
Global::SetCallConnectTimeoutMs(data.vcall_connect_timeout_ms().v);
|
|
||||||
Global::SetCallPacketTimeoutMs(data.vcall_packet_timeout_ms().v);
|
|
||||||
if (Global::PhoneCallsEnabled() != data.is_phonecalls_enabled()) {
|
|
||||||
Global::SetPhoneCallsEnabled(data.is_phonecalls_enabled());
|
|
||||||
Global::RefPhoneCallsEnabledChanged().notify();
|
|
||||||
}
|
|
||||||
Global::SetBlockedMode(data.is_blocked_mode());
|
|
||||||
Global::SetCaptionLengthMax(data.vcaption_length_max().v);
|
|
||||||
|
|
||||||
const auto lang = qs(data.vsuggested_lang_code().value_or_empty());
|
const auto lang = qs(data.vsuggested_lang_code().value_or_empty());
|
||||||
Lang::CurrentCloudManager().setSuggestedLanguage(lang);
|
Lang::CurrentCloudManager().setSuggestedLanguage(lang);
|
||||||
Lang::CurrentCloudManager().setCurrentVersions(
|
Lang::CurrentCloudManager().setCurrentVersions(
|
||||||
data.vlang_pack_version().value_or_empty(),
|
data.vlang_pack_version().value_or_empty(),
|
||||||
data.vbase_lang_pack_version().value_or_empty());
|
data.vbase_lang_pack_version().value_or_empty());
|
||||||
|
|
||||||
Core::App().activeAccount().configUpdated(); // #TODO multi
|
|
||||||
|
|
||||||
if (const auto prefix = data.vautoupdate_url_prefix()) {
|
if (const auto prefix = data.vautoupdate_url_prefix()) {
|
||||||
Local::writeAutoupdatePrefix(qs(*prefix));
|
Local::writeAutoupdatePrefix(qs(*prefix));
|
||||||
}
|
}
|
||||||
|
@ -1520,7 +1511,7 @@ not_null<QThread*> Instance::Private::getThreadForDc(
|
||||||
void Instance::Private::scheduleKeyDestroy(ShiftedDcId shiftedDcId) {
|
void Instance::Private::scheduleKeyDestroy(ShiftedDcId shiftedDcId) {
|
||||||
Expects(isKeysDestroyer());
|
Expects(isKeysDestroyer());
|
||||||
|
|
||||||
if (dcOptions()->dcType(shiftedDcId) == DcType::Cdn) {
|
if (dcOptions().dcType(shiftedDcId) == DcType::Cdn) {
|
||||||
performKeyDestroy(shiftedDcId);
|
performKeyDestroy(shiftedDcId);
|
||||||
} else {
|
} else {
|
||||||
_instance->send(MTPauth_LogOut(), rpcDone([=](const MTPBool &) {
|
_instance->send(MTPauth_LogOut(), rpcDone([=](const MTPBool &) {
|
||||||
|
@ -1643,10 +1634,10 @@ void Instance::Private::prepareToDestroy() {
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
Instance::Instance(not_null<DcOptions*> options, Mode mode, Config &&config)
|
Instance::Instance(Mode mode, Fields &&fields)
|
||||||
: QObject()
|
: QObject()
|
||||||
, _private(std::make_unique<Private>(this, options, mode)) {
|
, _private(std::make_unique<Private>(this, mode, std::move(fields))) {
|
||||||
_private->start(std::move(config));
|
_private->start();
|
||||||
}
|
}
|
||||||
|
|
||||||
void Instance::resolveProxyDomain(const QString &host) {
|
void Instance::resolveProxyDomain(const QString &host) {
|
||||||
|
@ -1787,10 +1778,26 @@ void Instance::addKeysForDestroy(AuthKeysList &&keys) {
|
||||||
_private->addKeysForDestroy(std::move(keys));
|
_private->addKeysForDestroy(std::move(keys));
|
||||||
}
|
}
|
||||||
|
|
||||||
not_null<DcOptions*> Instance::dcOptions() {
|
Config &Instance::config() const {
|
||||||
|
return _private->config();
|
||||||
|
}
|
||||||
|
|
||||||
|
const ConfigFields &Instance::configValues() const {
|
||||||
|
return _private->configValues();
|
||||||
|
}
|
||||||
|
|
||||||
|
DcOptions &Instance::dcOptions() const {
|
||||||
return _private->dcOptions();
|
return _private->dcOptions();
|
||||||
}
|
}
|
||||||
|
|
||||||
|
Environment Instance::environment() const {
|
||||||
|
return _private->environment();
|
||||||
|
}
|
||||||
|
|
||||||
|
bool Instance::isTestMode() const {
|
||||||
|
return _private->isTestMode();
|
||||||
|
}
|
||||||
|
|
||||||
QString Instance::deviceModel() const {
|
QString Instance::deviceModel() const {
|
||||||
return _private->deviceModel();
|
return _private->deviceModel();
|
||||||
}
|
}
|
||||||
|
|
|
@ -21,20 +21,29 @@ class Session;
|
||||||
} // namespace details
|
} // namespace details
|
||||||
|
|
||||||
class DcOptions;
|
class DcOptions;
|
||||||
|
class Config;
|
||||||
|
struct ConfigFields;
|
||||||
class AuthKey;
|
class AuthKey;
|
||||||
using AuthKeyPtr = std::shared_ptr<AuthKey>;
|
using AuthKeyPtr = std::shared_ptr<AuthKey>;
|
||||||
using AuthKeysList = std::vector<AuthKeyPtr>;
|
using AuthKeysList = std::vector<AuthKeyPtr>;
|
||||||
|
enum class Environment : uchar;
|
||||||
|
|
||||||
class Instance : public QObject {
|
class Instance : public QObject {
|
||||||
Q_OBJECT
|
Q_OBJECT
|
||||||
|
|
||||||
public:
|
public:
|
||||||
struct Config {
|
struct Fields {
|
||||||
|
Fields();
|
||||||
|
Fields(Fields &&other);
|
||||||
|
Fields &operator=(Fields &&other);
|
||||||
|
~Fields();
|
||||||
|
|
||||||
static constexpr auto kNoneMainDc = -1;
|
static constexpr auto kNoneMainDc = -1;
|
||||||
static constexpr auto kNotSetMainDc = 0;
|
static constexpr auto kNotSetMainDc = 0;
|
||||||
static constexpr auto kDefaultMainDc = 2;
|
static constexpr auto kDefaultMainDc = 2;
|
||||||
static constexpr auto kTemporaryMainDc = 1000;
|
static constexpr auto kTemporaryMainDc = 1000;
|
||||||
|
|
||||||
|
std::unique_ptr<Config> config;
|
||||||
DcId mainDcId = kNotSetMainDc;
|
DcId mainDcId = kNotSetMainDc;
|
||||||
AuthKeysList keys;
|
AuthKeysList keys;
|
||||||
QString deviceModel;
|
QString deviceModel;
|
||||||
|
@ -46,7 +55,7 @@ public:
|
||||||
KeysDestroyer,
|
KeysDestroyer,
|
||||||
};
|
};
|
||||||
|
|
||||||
Instance(not_null<DcOptions*> options, Mode mode, Config &&config);
|
Instance(Mode mode, Fields &&fields);
|
||||||
Instance(const Instance &other) = delete;
|
Instance(const Instance &other) = delete;
|
||||||
Instance &operator=(const Instance &other) = delete;
|
Instance &operator=(const Instance &other) = delete;
|
||||||
~Instance();
|
~Instance();
|
||||||
|
@ -64,6 +73,11 @@ public:
|
||||||
[[nodiscard]] rpl::producer<> allKeysDestroyed() const;
|
[[nodiscard]] rpl::producer<> allKeysDestroyed() const;
|
||||||
|
|
||||||
// Thread-safe.
|
// Thread-safe.
|
||||||
|
[[nodiscard]] Config &config() const;
|
||||||
|
[[nodiscard]] const ConfigFields &configValues() const;
|
||||||
|
[[nodiscard]] DcOptions &dcOptions() const;
|
||||||
|
[[nodiscard]] Environment environment() const;
|
||||||
|
[[nodiscard]] bool isTestMode() const;
|
||||||
[[nodiscard]] QString deviceModel() const;
|
[[nodiscard]] QString deviceModel() const;
|
||||||
[[nodiscard]] QString systemVersion() const;
|
[[nodiscard]] QString systemVersion() const;
|
||||||
|
|
||||||
|
@ -74,8 +88,6 @@ public:
|
||||||
[[nodiscard]] AuthKeysList getKeysForWrite() const;
|
[[nodiscard]] AuthKeysList getKeysForWrite() const;
|
||||||
void addKeysForDestroy(AuthKeysList &&keys);
|
void addKeysForDestroy(AuthKeysList &&keys);
|
||||||
|
|
||||||
[[nodiscard]] not_null<DcOptions*> dcOptions();
|
|
||||||
|
|
||||||
void restart();
|
void restart();
|
||||||
void restart(ShiftedDcId shiftedDcId);
|
void restart(ShiftedDcId shiftedDcId);
|
||||||
int32 dcstate(ShiftedDcId shiftedDcId = 0);
|
int32 dcstate(ShiftedDcId shiftedDcId = 0);
|
||||||
|
|
259
Telegram/SourceFiles/mtproto/mtproto_config.cpp
Normal file
259
Telegram/SourceFiles/mtproto/mtproto_config.cpp
Normal file
|
@ -0,0 +1,259 @@
|
||||||
|
/*
|
||||||
|
This file is part of Telegram Desktop,
|
||||||
|
the official desktop application for the Telegram messaging service.
|
||||||
|
|
||||||
|
For license and copyright information please follow this link:
|
||||||
|
https://github.com/telegramdesktop/tdesktop/blob/master/LEGAL
|
||||||
|
*/
|
||||||
|
#include "mtproto/mtproto_config.h"
|
||||||
|
|
||||||
|
#include "storage/serialize_common.h"
|
||||||
|
#include "mtproto/type_utils.h"
|
||||||
|
#include "logs.h"
|
||||||
|
|
||||||
|
namespace MTP {
|
||||||
|
namespace {
|
||||||
|
|
||||||
|
constexpr auto kVersion = 1;
|
||||||
|
|
||||||
|
}
|
||||||
|
Config::Config(Environment environment) : _dcOptions(environment) {
|
||||||
|
_fields.webFileDcId = _dcOptions.isTestMode() ? 2 : 4;
|
||||||
|
_fields.txtDomainString = _dcOptions.isTestMode()
|
||||||
|
? u"tapv3.stel.com"_q
|
||||||
|
: u"apv3.stel.com"_q;
|
||||||
|
}
|
||||||
|
|
||||||
|
Config::Config(const Config &other)
|
||||||
|
: _dcOptions(other.dcOptions())
|
||||||
|
, _fields(other._fields) {
|
||||||
|
}
|
||||||
|
|
||||||
|
QByteArray Config::serialize() const {
|
||||||
|
auto options = _dcOptions.serialize();
|
||||||
|
auto size = sizeof(qint32) * 2; // version + environment
|
||||||
|
size += Serialize::bytearraySize(options);
|
||||||
|
size += 28 * sizeof(qint32);
|
||||||
|
size += Serialize::stringSize(_fields.internalLinksDomain);
|
||||||
|
size += Serialize::stringSize(_fields.txtDomainString);
|
||||||
|
|
||||||
|
auto result = QByteArray();
|
||||||
|
result.reserve(size);
|
||||||
|
{
|
||||||
|
QDataStream stream(&result, QIODevice::WriteOnly);
|
||||||
|
stream.setVersion(QDataStream::Qt_5_1);
|
||||||
|
stream
|
||||||
|
<< qint32(kVersion)
|
||||||
|
<< qint32(_dcOptions.isTestMode()
|
||||||
|
? Environment::Test
|
||||||
|
: Environment::Production)
|
||||||
|
<< options
|
||||||
|
<< qint32(_fields.chatSizeMax)
|
||||||
|
<< qint32(_fields.megagroupSizeMax)
|
||||||
|
<< qint32(_fields.forwardedCountMax)
|
||||||
|
<< qint32(_fields.onlineUpdatePeriod)
|
||||||
|
<< qint32(_fields.offlineBlurTimeout)
|
||||||
|
<< qint32(_fields.offlineIdleTimeout)
|
||||||
|
<< qint32(_fields.onlineFocusTimeout)
|
||||||
|
<< qint32(_fields.onlineCloudTimeout)
|
||||||
|
<< qint32(_fields.notifyCloudDelay)
|
||||||
|
<< qint32(_fields.notifyDefaultDelay)
|
||||||
|
<< qint32(_fields.savedGifsLimit)
|
||||||
|
<< qint32(_fields.editTimeLimit)
|
||||||
|
<< qint32(_fields.revokeTimeLimit)
|
||||||
|
<< qint32(_fields.revokePrivateTimeLimit)
|
||||||
|
<< qint32(_fields.revokePrivateInbox ? 1 : 0)
|
||||||
|
<< qint32(_fields.stickersRecentLimit)
|
||||||
|
<< qint32(_fields.stickersFavedLimit)
|
||||||
|
<< qint32(_fields.pinnedDialogsCountMax.current())
|
||||||
|
<< qint32(_fields.pinnedDialogsInFolderMax.current())
|
||||||
|
<< _fields.internalLinksDomain
|
||||||
|
<< qint32(_fields.channelsReadMediaPeriod)
|
||||||
|
<< qint32(_fields.callReceiveTimeoutMs)
|
||||||
|
<< qint32(_fields.callRingTimeoutMs)
|
||||||
|
<< qint32(_fields.callConnectTimeoutMs)
|
||||||
|
<< qint32(_fields.callPacketTimeoutMs)
|
||||||
|
<< qint32(_fields.webFileDcId)
|
||||||
|
<< _fields.txtDomainString
|
||||||
|
<< qint32(_fields.phoneCallsEnabled.current() ? 1 : 0)
|
||||||
|
<< qint32(_fields.blockedMode ? 1 : 0)
|
||||||
|
<< qint32(_fields.captionLengthMax);
|
||||||
|
}
|
||||||
|
return result;
|
||||||
|
}
|
||||||
|
|
||||||
|
std::unique_ptr<Config> Config::FromSerialized(const QByteArray &serialized) {
|
||||||
|
auto result = std::unique_ptr<Config>();
|
||||||
|
auto raw = result.get();
|
||||||
|
|
||||||
|
QDataStream stream(serialized);
|
||||||
|
stream.setVersion(QDataStream::Qt_5_1);
|
||||||
|
|
||||||
|
auto version = qint32();
|
||||||
|
stream >> version;
|
||||||
|
if (version != kVersion) {
|
||||||
|
return result;
|
||||||
|
}
|
||||||
|
auto environment = qint32();
|
||||||
|
stream >> environment;
|
||||||
|
switch (environment) {
|
||||||
|
case qint32(Environment::Test):
|
||||||
|
result = std::make_unique<Config>(Environment::Test);
|
||||||
|
break;
|
||||||
|
case qint32(Environment::Production):
|
||||||
|
result = std::make_unique<Config>(Environment::Production);
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
if (!(raw = result.get())) {
|
||||||
|
return result;
|
||||||
|
}
|
||||||
|
|
||||||
|
auto dcOptionsSerialized = QByteArray();
|
||||||
|
const auto read = [&](auto &field) {
|
||||||
|
using Type = std::decay_t<decltype(field)>();
|
||||||
|
if constexpr (std::is_same_v<Type, int>
|
||||||
|
|| std::is_same_v<Type, rpl::variable<int>>) {
|
||||||
|
auto value = qint32();
|
||||||
|
stream >> value;
|
||||||
|
field = value;
|
||||||
|
} else if constexpr (std::is_same_v<Type, bool>
|
||||||
|
|| std::is_same_v<Type, rpl::variable<bool>>) {
|
||||||
|
auto value = qint32();
|
||||||
|
stream >> value;
|
||||||
|
field = (value == 1);
|
||||||
|
} else if constexpr (std::is_same_v<Type, QByteArray>
|
||||||
|
|| std::is_same_v<Type, QString>) {
|
||||||
|
static_assert(false_(field), "Bad read() call.");
|
||||||
|
}
|
||||||
|
};
|
||||||
|
|
||||||
|
read(dcOptionsSerialized);
|
||||||
|
read(raw->_fields.chatSizeMax);
|
||||||
|
read(raw->_fields.megagroupSizeMax);
|
||||||
|
read(raw->_fields.forwardedCountMax);
|
||||||
|
read(raw->_fields.onlineUpdatePeriod);
|
||||||
|
read(raw->_fields.offlineBlurTimeout);
|
||||||
|
read(raw->_fields.offlineIdleTimeout);
|
||||||
|
read(raw->_fields.onlineFocusTimeout);
|
||||||
|
read(raw->_fields.onlineCloudTimeout);
|
||||||
|
read(raw->_fields.notifyCloudDelay);
|
||||||
|
read(raw->_fields.notifyDefaultDelay);
|
||||||
|
read(raw->_fields.savedGifsLimit);
|
||||||
|
read(raw->_fields.editTimeLimit);
|
||||||
|
read(raw->_fields.revokeTimeLimit);
|
||||||
|
read(raw->_fields.revokePrivateTimeLimit);
|
||||||
|
read(raw->_fields.revokePrivateInbox);
|
||||||
|
read(raw->_fields.stickersRecentLimit);
|
||||||
|
read(raw->_fields.stickersFavedLimit);
|
||||||
|
read(raw->_fields.pinnedDialogsCountMax);
|
||||||
|
read(raw->_fields.pinnedDialogsInFolderMax);
|
||||||
|
read(raw->_fields.internalLinksDomain);
|
||||||
|
read(raw->_fields.channelsReadMediaPeriod);
|
||||||
|
read(raw->_fields.callReceiveTimeoutMs);
|
||||||
|
read(raw->_fields.callRingTimeoutMs);
|
||||||
|
read(raw->_fields.callConnectTimeoutMs);
|
||||||
|
read(raw->_fields.callPacketTimeoutMs);
|
||||||
|
read(raw->_fields.webFileDcId);
|
||||||
|
read(raw->_fields.txtDomainString);
|
||||||
|
read(raw->_fields.phoneCallsEnabled);
|
||||||
|
read(raw->_fields.blockedMode);
|
||||||
|
read(raw->_fields.captionLengthMax);
|
||||||
|
|
||||||
|
if (stream.status() != QDataStream::Ok
|
||||||
|
|| !raw->_dcOptions.constructFromSerialized(dcOptionsSerialized)) {
|
||||||
|
return nullptr;
|
||||||
|
}
|
||||||
|
return result;
|
||||||
|
}
|
||||||
|
|
||||||
|
const ConfigFields &Config::values() const {
|
||||||
|
return _fields;
|
||||||
|
}
|
||||||
|
|
||||||
|
void Config::apply(const MTPDconfig &data) {
|
||||||
|
if (mtpIsTrue(data.vtest_mode()) != _dcOptions.isTestMode()) {
|
||||||
|
LOG(("MTP Error: config with wrong test mode field received!"));
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
|
||||||
|
DEBUG_LOG(("MTP Info: got config, "
|
||||||
|
"chat_size_max: %1, "
|
||||||
|
"date: %2, "
|
||||||
|
"test_mode: %3, "
|
||||||
|
"this_dc: %4, "
|
||||||
|
"dc_options.length: %5"
|
||||||
|
).arg(data.vchat_size_max().v
|
||||||
|
).arg(data.vdate().v
|
||||||
|
).arg(mtpIsTrue(data.vtest_mode())
|
||||||
|
).arg(data.vthis_dc().v
|
||||||
|
).arg(data.vdc_options().v.size()));
|
||||||
|
|
||||||
|
_fields.chatSizeMax = data.vchat_size_max().v;
|
||||||
|
_fields.megagroupSizeMax = data.vmegagroup_size_max().v;
|
||||||
|
_fields.forwardedCountMax = data.vforwarded_count_max().v;
|
||||||
|
_fields.onlineUpdatePeriod = data.vonline_update_period_ms().v;
|
||||||
|
_fields.offlineBlurTimeout = data.voffline_blur_timeout_ms().v;
|
||||||
|
_fields.offlineIdleTimeout = data.voffline_idle_timeout_ms().v;
|
||||||
|
_fields.onlineCloudTimeout = data.vonline_cloud_timeout_ms().v;
|
||||||
|
_fields.notifyCloudDelay = data.vnotify_cloud_delay_ms().v;
|
||||||
|
_fields.notifyDefaultDelay = data.vnotify_default_delay_ms().v;
|
||||||
|
_fields.savedGifsLimit = data.vsaved_gifs_limit().v;
|
||||||
|
_fields.editTimeLimit = data.vedit_time_limit().v;
|
||||||
|
_fields.revokeTimeLimit = data.vrevoke_time_limit().v;
|
||||||
|
_fields.revokePrivateTimeLimit = data.vrevoke_pm_time_limit().v;
|
||||||
|
_fields.revokePrivateInbox = data.is_revoke_pm_inbox();
|
||||||
|
_fields.stickersRecentLimit = data.vstickers_recent_limit().v;
|
||||||
|
_fields.stickersFavedLimit = data.vstickers_faved_limit().v;
|
||||||
|
_fields.pinnedDialogsCountMax =
|
||||||
|
std::max(data.vpinned_dialogs_count_max().v, 1);
|
||||||
|
_fields.pinnedDialogsInFolderMax =
|
||||||
|
std::max(data.vpinned_infolder_count_max().v, 1);
|
||||||
|
_fields.internalLinksDomain = qs(data.vme_url_prefix());
|
||||||
|
_fields.channelsReadMediaPeriod = data.vchannels_read_media_period().v;
|
||||||
|
_fields.webFileDcId = data.vwebfile_dc_id().v;
|
||||||
|
_fields.callReceiveTimeoutMs = data.vcall_receive_timeout_ms().v;
|
||||||
|
_fields.callRingTimeoutMs = data.vcall_ring_timeout_ms().v;
|
||||||
|
_fields.callConnectTimeoutMs = data.vcall_connect_timeout_ms().v;
|
||||||
|
_fields.callPacketTimeoutMs = data.vcall_packet_timeout_ms().v;
|
||||||
|
_fields.phoneCallsEnabled = data.is_phonecalls_enabled();
|
||||||
|
_fields.blockedMode = data.is_blocked_mode();
|
||||||
|
_fields.captionLengthMax = data.vcaption_length_max().v;
|
||||||
|
|
||||||
|
if (data.vdc_options().v.empty()) {
|
||||||
|
LOG(("MTP Error: config with empty dc_options received!"));
|
||||||
|
} else {
|
||||||
|
dcOptions().setFromList(data.vdc_options());
|
||||||
|
}
|
||||||
|
|
||||||
|
_updates.fire({});
|
||||||
|
}
|
||||||
|
|
||||||
|
rpl::producer<> Config::updates() const {
|
||||||
|
return _updates.events();
|
||||||
|
}
|
||||||
|
|
||||||
|
void Config::setChatSizeMax(int value) {
|
||||||
|
_fields.chatSizeMax = value;
|
||||||
|
}
|
||||||
|
|
||||||
|
void Config::setSavedGifsLimit(int value) {
|
||||||
|
_fields.savedGifsLimit = value;
|
||||||
|
}
|
||||||
|
|
||||||
|
void Config::setStickersRecentLimit(int value) {
|
||||||
|
_fields.stickersRecentLimit = value;
|
||||||
|
}
|
||||||
|
|
||||||
|
void Config::setStickersFavedLimit(int value) {
|
||||||
|
_fields.stickersFavedLimit = value;
|
||||||
|
}
|
||||||
|
|
||||||
|
void Config::setMegagroupSizeMax(int value) {
|
||||||
|
_fields.megagroupSizeMax = value;
|
||||||
|
}
|
||||||
|
|
||||||
|
void Config::setTxtDomainString(const QString &value) {
|
||||||
|
_fields.txtDomainString = value;
|
||||||
|
}
|
||||||
|
|
||||||
|
} // namespace MTP
|
93
Telegram/SourceFiles/mtproto/mtproto_config.h
Normal file
93
Telegram/SourceFiles/mtproto/mtproto_config.h
Normal file
|
@ -0,0 +1,93 @@
|
||||||
|
/*
|
||||||
|
This file is part of Telegram Desktop,
|
||||||
|
the official desktop application for the Telegram messaging service.
|
||||||
|
|
||||||
|
For license and copyright information please follow this link:
|
||||||
|
https://github.com/telegramdesktop/tdesktop/blob/master/LEGAL
|
||||||
|
*/
|
||||||
|
#pragma once
|
||||||
|
|
||||||
|
#include "mtproto/mtproto_dc_options.h"
|
||||||
|
|
||||||
|
namespace MTP {
|
||||||
|
|
||||||
|
struct ConfigFields {
|
||||||
|
int chatSizeMax = 200;
|
||||||
|
int megagroupSizeMax = 10000;
|
||||||
|
int forwardedCountMax = 100;
|
||||||
|
int onlineUpdatePeriod = 120000;
|
||||||
|
int offlineBlurTimeout = 5000;
|
||||||
|
int offlineIdleTimeout = 30000;
|
||||||
|
int onlineFocusTimeout = 1000; // Not from the server config.
|
||||||
|
int onlineCloudTimeout = 300000;
|
||||||
|
int notifyCloudDelay = 30000;
|
||||||
|
int notifyDefaultDelay = 1500;
|
||||||
|
int savedGifsLimit = 200;
|
||||||
|
int editTimeLimit = 172800;
|
||||||
|
int revokeTimeLimit = 172800;
|
||||||
|
int revokePrivateTimeLimit = 172800;
|
||||||
|
bool revokePrivateInbox = false;
|
||||||
|
int stickersRecentLimit = 30;
|
||||||
|
int stickersFavedLimit = 5;
|
||||||
|
rpl::variable<int> pinnedDialogsCountMax = 5;
|
||||||
|
rpl::variable<int> pinnedDialogsInFolderMax = 100;
|
||||||
|
QString internalLinksDomain = u"https://t.me/"_q;
|
||||||
|
int channelsReadMediaPeriod = 86400 * 7;
|
||||||
|
int callReceiveTimeoutMs = 20000;
|
||||||
|
int callRingTimeoutMs = 90000;
|
||||||
|
int callConnectTimeoutMs = 30000;
|
||||||
|
int callPacketTimeoutMs = 10000;
|
||||||
|
int webFileDcId = 4;
|
||||||
|
QString txtDomainString;
|
||||||
|
rpl::variable<bool> phoneCallsEnabled = true;
|
||||||
|
bool blockedMode = false;
|
||||||
|
int captionLengthMax = 1024;
|
||||||
|
};
|
||||||
|
|
||||||
|
class Config final {
|
||||||
|
struct PrivateTag {
|
||||||
|
};
|
||||||
|
|
||||||
|
public:
|
||||||
|
explicit Config(Environment environment);
|
||||||
|
Config(const Config &other);
|
||||||
|
|
||||||
|
[[nodiscard]] QByteArray serialize() const;
|
||||||
|
[[nodiscard]] static std::unique_ptr<Config> FromSerialized(
|
||||||
|
const QByteArray &serialized);
|
||||||
|
|
||||||
|
[[nodiscard]] DcOptions &dcOptions() {
|
||||||
|
return _dcOptions;
|
||||||
|
}
|
||||||
|
[[nodiscard]] const DcOptions &dcOptions() const {
|
||||||
|
return _dcOptions;
|
||||||
|
}
|
||||||
|
[[nodiscard]] MTP::Environment environment() const {
|
||||||
|
return _dcOptions.environment();
|
||||||
|
}
|
||||||
|
[[nodiscard]] bool isTestMode() const {
|
||||||
|
return _dcOptions.isTestMode();
|
||||||
|
}
|
||||||
|
|
||||||
|
void apply(const MTPDconfig &data);
|
||||||
|
|
||||||
|
[[nodiscard]] const ConfigFields &values() const;
|
||||||
|
[[nodiscard]] rpl::producer<> updates() const;
|
||||||
|
|
||||||
|
// Set from legacy local stored values.
|
||||||
|
void setChatSizeMax(int value);
|
||||||
|
void setSavedGifsLimit(int value);
|
||||||
|
void setStickersRecentLimit(int value);
|
||||||
|
void setStickersFavedLimit(int value);
|
||||||
|
void setMegagroupSizeMax(int value);
|
||||||
|
void setTxtDomainString(const QString &value);
|
||||||
|
|
||||||
|
private:
|
||||||
|
DcOptions _dcOptions;
|
||||||
|
ConfigFields _fields;
|
||||||
|
|
||||||
|
rpl::event_stream<> _updates;
|
||||||
|
|
||||||
|
};
|
||||||
|
|
||||||
|
} // namespace MTP
|
|
@ -5,13 +5,16 @@ the official desktop application for the Telegram messaging service.
|
||||||
For license and copyright information please follow this link:
|
For license and copyright information please follow this link:
|
||||||
https://github.com/telegramdesktop/tdesktop/blob/master/LEGAL
|
https://github.com/telegramdesktop/tdesktop/blob/master/LEGAL
|
||||||
*/
|
*/
|
||||||
#include "mtproto/dc_options.h"
|
#include "mtproto/mtproto_dc_options.h"
|
||||||
|
|
||||||
#include "mtproto/details/mtproto_rsa_public_key.h"
|
#include "mtproto/details/mtproto_rsa_public_key.h"
|
||||||
#include "mtproto/facade.h"
|
#include "mtproto/facade.h"
|
||||||
#include "mtproto/connection_tcp.h"
|
#include "mtproto/connection_tcp.h"
|
||||||
#include "storage/serialize_common.h"
|
#include "storage/serialize_common.h"
|
||||||
|
|
||||||
|
#include <QtCore/QFile>
|
||||||
|
#include <QtCore/QRegularExpression>
|
||||||
|
|
||||||
namespace MTP {
|
namespace MTP {
|
||||||
namespace {
|
namespace {
|
||||||
|
|
||||||
|
@ -136,10 +139,20 @@ private:
|
||||||
|
|
||||||
};
|
};
|
||||||
|
|
||||||
DcOptions::DcOptions() {
|
DcOptions::DcOptions(Environment environment)
|
||||||
|
: _environment(environment) {
|
||||||
constructFromBuiltIn();
|
constructFromBuiltIn();
|
||||||
}
|
}
|
||||||
|
|
||||||
|
DcOptions::DcOptions(const DcOptions &other)
|
||||||
|
: _environment(other._environment)
|
||||||
|
, _data(other._data)
|
||||||
|
, _cdnDcIds(other._cdnDcIds)
|
||||||
|
, _publicKeys(other._publicKeys)
|
||||||
|
, _cdnPublicKeys(other._cdnPublicKeys)
|
||||||
|
, _immutable(other._immutable) {
|
||||||
|
}
|
||||||
|
|
||||||
DcOptions::~DcOptions() = default;
|
DcOptions::~DcOptions() = default;
|
||||||
|
|
||||||
bool DcOptions::ValidateSecret(bytes::const_span secret) {
|
bool DcOptions::ValidateSecret(bytes::const_span secret) {
|
||||||
|
@ -163,13 +176,21 @@ void DcOptions::readBuiltInPublicKeys() {
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
Environment DcOptions::environment() const {
|
||||||
|
return _environment;
|
||||||
|
}
|
||||||
|
|
||||||
|
bool DcOptions::isTestMode() const {
|
||||||
|
return (_environment != Environment::Production);
|
||||||
|
}
|
||||||
|
|
||||||
void DcOptions::constructFromBuiltIn() {
|
void DcOptions::constructFromBuiltIn() {
|
||||||
WriteLocker lock(this);
|
WriteLocker lock(this);
|
||||||
_data.clear();
|
_data.clear();
|
||||||
|
|
||||||
readBuiltInPublicKeys();
|
readBuiltInPublicKeys();
|
||||||
|
|
||||||
const auto list = cTestMode()
|
const auto list = isTestMode()
|
||||||
? gsl::make_span(kBuiltInDcsTest)
|
? gsl::make_span(kBuiltInDcsTest)
|
||||||
: gsl::make_span(kBuiltInDcs).subspan(0);
|
: gsl::make_span(kBuiltInDcs).subspan(0);
|
||||||
for (const auto &entry : list) {
|
for (const auto &entry : list) {
|
||||||
|
@ -181,7 +202,7 @@ void DcOptions::constructFromBuiltIn() {
|
||||||
).arg(entry.port));
|
).arg(entry.port));
|
||||||
}
|
}
|
||||||
|
|
||||||
const auto listv6 = cTestMode()
|
const auto listv6 = isTestMode()
|
||||||
? gsl::make_span(kBuiltInDcsIPv6Test)
|
? gsl::make_span(kBuiltInDcsIPv6Test)
|
||||||
: gsl::make_span(kBuiltInDcsIPv6).subspan(0);
|
: gsl::make_span(kBuiltInDcsIPv6).subspan(0);
|
||||||
for (const auto &entry : listv6) {
|
for (const auto &entry : listv6) {
|
||||||
|
@ -204,7 +225,7 @@ void DcOptions::processFromList(
|
||||||
|
|
||||||
auto data = [&] {
|
auto data = [&] {
|
||||||
if (overwrite) {
|
if (overwrite) {
|
||||||
return std::map<DcId, std::vector<Endpoint>>();
|
return base::flat_map<DcId, std::vector<Endpoint>>();
|
||||||
}
|
}
|
||||||
ReadLocker lock(this);
|
ReadLocker lock(this);
|
||||||
return _data;
|
return _data;
|
||||||
|
@ -313,7 +334,7 @@ bool DcOptions::applyOneGuarded(
|
||||||
}
|
}
|
||||||
|
|
||||||
bool DcOptions::ApplyOneOption(
|
bool DcOptions::ApplyOneOption(
|
||||||
std::map<DcId, std::vector<Endpoint>> &data,
|
base::flat_map<DcId, std::vector<Endpoint>> &data,
|
||||||
DcId dcId,
|
DcId dcId,
|
||||||
Flags flags,
|
Flags flags,
|
||||||
const std::string &ip,
|
const std::string &ip,
|
||||||
|
@ -336,8 +357,8 @@ bool DcOptions::ApplyOneOption(
|
||||||
}
|
}
|
||||||
|
|
||||||
std::vector<DcId> DcOptions::CountOptionsDifference(
|
std::vector<DcId> DcOptions::CountOptionsDifference(
|
||||||
const std::map<DcId, std::vector<Endpoint>> &a,
|
const base::flat_map<DcId, std::vector<Endpoint>> &a,
|
||||||
const std::map<DcId, std::vector<Endpoint>> &b) {
|
const base::flat_map<DcId, std::vector<Endpoint>> &b) {
|
||||||
auto result = std::vector<DcId>();
|
auto result = std::vector<DcId>();
|
||||||
const auto find = [](
|
const auto find = [](
|
||||||
const std::vector<Endpoint> &where,
|
const std::vector<Endpoint> &where,
|
||||||
|
@ -389,7 +410,7 @@ std::vector<DcId> DcOptions::CountOptionsDifference(
|
||||||
QByteArray DcOptions::serialize() const {
|
QByteArray DcOptions::serialize() const {
|
||||||
if (_immutable) {
|
if (_immutable) {
|
||||||
// Don't write the overriden options to our settings.
|
// Don't write the overriden options to our settings.
|
||||||
return DcOptions().serialize();
|
return DcOptions(_environment).serialize();
|
||||||
}
|
}
|
||||||
|
|
||||||
ReadLocker lock(this);
|
ReadLocker lock(this);
|
||||||
|
@ -477,7 +498,7 @@ QByteArray DcOptions::serialize() const {
|
||||||
return result;
|
return result;
|
||||||
}
|
}
|
||||||
|
|
||||||
void DcOptions::constructFromSerialized(const QByteArray &serialized) {
|
bool DcOptions::constructFromSerialized(const QByteArray &serialized) {
|
||||||
QDataStream stream(serialized);
|
QDataStream stream(serialized);
|
||||||
stream.setVersion(QDataStream::Qt_5_1);
|
stream.setVersion(QDataStream::Qt_5_1);
|
||||||
|
|
||||||
|
@ -493,7 +514,7 @@ void DcOptions::constructFromSerialized(const QByteArray &serialized) {
|
||||||
}
|
}
|
||||||
if (stream.status() != QDataStream::Ok) {
|
if (stream.status() != QDataStream::Ok) {
|
||||||
LOG(("MTP Error: Bad data for DcOptions::constructFromSerialized()"));
|
LOG(("MTP Error: Bad data for DcOptions::constructFromSerialized()"));
|
||||||
return;
|
return false;
|
||||||
}
|
}
|
||||||
|
|
||||||
WriteLocker lock(this);
|
WriteLocker lock(this);
|
||||||
|
@ -506,7 +527,7 @@ void DcOptions::constructFromSerialized(const QByteArray &serialized) {
|
||||||
constexpr auto kMaxIpSize = 45;
|
constexpr auto kMaxIpSize = 45;
|
||||||
if (ipSize <= 0 || ipSize > kMaxIpSize) {
|
if (ipSize <= 0 || ipSize > kMaxIpSize) {
|
||||||
LOG(("MTP Error: Bad data inside DcOptions::constructFromSerialized()"));
|
LOG(("MTP Error: Bad data inside DcOptions::constructFromSerialized()"));
|
||||||
return;
|
return false;
|
||||||
}
|
}
|
||||||
|
|
||||||
auto ip = std::string(ipSize, ' ');
|
auto ip = std::string(ipSize, ' ');
|
||||||
|
@ -519,7 +540,7 @@ void DcOptions::constructFromSerialized(const QByteArray &serialized) {
|
||||||
stream >> secretSize;
|
stream >> secretSize;
|
||||||
if (secretSize < 0 || secretSize > kMaxSecretSize) {
|
if (secretSize < 0 || secretSize > kMaxSecretSize) {
|
||||||
LOG(("MTP Error: Bad data inside DcOptions::constructFromSerialized()"));
|
LOG(("MTP Error: Bad data inside DcOptions::constructFromSerialized()"));
|
||||||
return;
|
return false;
|
||||||
} else if (secretSize > 0) {
|
} else if (secretSize > 0) {
|
||||||
secret.resize(secretSize);
|
secret.resize(secretSize);
|
||||||
stream.readRawData(
|
stream.readRawData(
|
||||||
|
@ -530,7 +551,7 @@ void DcOptions::constructFromSerialized(const QByteArray &serialized) {
|
||||||
|
|
||||||
if (stream.status() != QDataStream::Ok) {
|
if (stream.status() != QDataStream::Ok) {
|
||||||
LOG(("MTP Error: Bad data inside DcOptions::constructFromSerialized()"));
|
LOG(("MTP Error: Bad data inside DcOptions::constructFromSerialized()"));
|
||||||
return;
|
return false;
|
||||||
}
|
}
|
||||||
|
|
||||||
applyOneGuarded(
|
applyOneGuarded(
|
||||||
|
@ -547,7 +568,7 @@ void DcOptions::constructFromSerialized(const QByteArray &serialized) {
|
||||||
stream >> count;
|
stream >> count;
|
||||||
if (stream.status() != QDataStream::Ok) {
|
if (stream.status() != QDataStream::Ok) {
|
||||||
LOG(("MTP Error: Bad data for CDN config in DcOptions::constructFromSerialized()"));
|
LOG(("MTP Error: Bad data for CDN config in DcOptions::constructFromSerialized()"));
|
||||||
return;
|
return false;
|
||||||
}
|
}
|
||||||
|
|
||||||
for (auto i = 0; i != count; ++i) {
|
for (auto i = 0; i != count; ++i) {
|
||||||
|
@ -556,7 +577,7 @@ void DcOptions::constructFromSerialized(const QByteArray &serialized) {
|
||||||
stream >> dcId >> Serialize::bytes(n) >> Serialize::bytes(e);
|
stream >> dcId >> Serialize::bytes(n) >> Serialize::bytes(e);
|
||||||
if (stream.status() != QDataStream::Ok) {
|
if (stream.status() != QDataStream::Ok) {
|
||||||
LOG(("MTP Error: Bad data for CDN config inside DcOptions::constructFromSerialized()"));
|
LOG(("MTP Error: Bad data for CDN config inside DcOptions::constructFromSerialized()"));
|
||||||
return;
|
return false;
|
||||||
}
|
}
|
||||||
|
|
||||||
auto key = RSAPublicKey(n, e);
|
auto key = RSAPublicKey(n, e);
|
||||||
|
@ -564,9 +585,11 @@ void DcOptions::constructFromSerialized(const QByteArray &serialized) {
|
||||||
_cdnPublicKeys[dcId].emplace(key.fingerprint(), std::move(key));
|
_cdnPublicKeys[dcId].emplace(key.fingerprint(), std::move(key));
|
||||||
} else {
|
} else {
|
||||||
LOG(("MTP Error: Could not read valid CDN public key."));
|
LOG(("MTP Error: Could not read valid CDN public key."));
|
||||||
|
return false;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
return true;
|
||||||
}
|
}
|
||||||
|
|
||||||
rpl::producer<DcId> DcOptions::changed() const {
|
rpl::producer<DcId> DcOptions::changed() const {
|
||||||
|
@ -640,7 +663,8 @@ bool DcOptions::hasCDNKeysForDc(DcId dcId) const {
|
||||||
RSAPublicKey DcOptions::getDcRSAKey(
|
RSAPublicKey DcOptions::getDcRSAKey(
|
||||||
DcId dcId,
|
DcId dcId,
|
||||||
const QVector<MTPlong> &fingerprints) const {
|
const QVector<MTPlong> &fingerprints) const {
|
||||||
const auto findKey = [&](const std::map<uint64, RSAPublicKey> &keys) {
|
const auto findKey = [&](
|
||||||
|
const base::flat_map<uint64, RSAPublicKey> &keys) {
|
||||||
for (const auto &fingerprint : fingerprints) {
|
for (const auto &fingerprint : fingerprints) {
|
||||||
const auto it = keys.find(static_cast<uint64>(fingerprint.v));
|
const auto it = keys.find(static_cast<uint64>(fingerprint.v));
|
||||||
if (it != keys.cend()) {
|
if (it != keys.cend()) {
|
|
@ -27,6 +27,12 @@ enum class DcType {
|
||||||
MediaCluster,
|
MediaCluster,
|
||||||
Cdn,
|
Cdn,
|
||||||
};
|
};
|
||||||
|
|
||||||
|
enum class Environment : uchar {
|
||||||
|
Production,
|
||||||
|
Test,
|
||||||
|
};
|
||||||
|
|
||||||
class DcOptions {
|
class DcOptions {
|
||||||
public:
|
public:
|
||||||
using Flag = MTPDdcOption::Flag;
|
using Flag = MTPDdcOption::Flag;
|
||||||
|
@ -53,13 +59,17 @@ public:
|
||||||
|
|
||||||
};
|
};
|
||||||
|
|
||||||
DcOptions();
|
explicit DcOptions(Environment environment);
|
||||||
|
DcOptions(const DcOptions &other);
|
||||||
~DcOptions();
|
~DcOptions();
|
||||||
|
|
||||||
[[nodiscard]] static bool ValidateSecret(bytes::const_span secret);
|
[[nodiscard]] static bool ValidateSecret(bytes::const_span secret);
|
||||||
|
|
||||||
|
[[nodiscard]] Environment environment() const;
|
||||||
|
[[nodiscard]] bool isTestMode() const;
|
||||||
|
|
||||||
// construct methods don't notify "changed" subscribers.
|
// construct methods don't notify "changed" subscribers.
|
||||||
void constructFromSerialized(const QByteArray &serialized);
|
bool constructFromSerialized(const QByteArray &serialized);
|
||||||
void constructFromBuiltIn();
|
void constructFromBuiltIn();
|
||||||
void constructAddOne(
|
void constructAddOne(
|
||||||
int id,
|
int id,
|
||||||
|
@ -114,15 +124,15 @@ private:
|
||||||
int port,
|
int port,
|
||||||
const bytes::vector &secret);
|
const bytes::vector &secret);
|
||||||
static bool ApplyOneOption(
|
static bool ApplyOneOption(
|
||||||
std::map<DcId, std::vector<Endpoint>> &data,
|
base::flat_map<DcId, std::vector<Endpoint>> &data,
|
||||||
DcId dcId,
|
DcId dcId,
|
||||||
Flags flags,
|
Flags flags,
|
||||||
const std::string &ip,
|
const std::string &ip,
|
||||||
int port,
|
int port,
|
||||||
const bytes::vector &secret);
|
const bytes::vector &secret);
|
||||||
static std::vector<DcId> CountOptionsDifference(
|
static std::vector<DcId> CountOptionsDifference(
|
||||||
const std::map<DcId, std::vector<Endpoint>> &a,
|
const base::flat_map<DcId, std::vector<Endpoint>> &a,
|
||||||
const std::map<DcId, std::vector<Endpoint>> &b);
|
const base::flat_map<DcId, std::vector<Endpoint>> &b);
|
||||||
static void FilterIfHasWithFlag(Variants &variants, Flag flag);
|
static void FilterIfHasWithFlag(Variants &variants, Flag flag);
|
||||||
|
|
||||||
[[nodiscard]] bool hasMediaOnlyOptionsFor(DcId dcId) const;
|
[[nodiscard]] bool hasMediaOnlyOptionsFor(DcId dcId) const;
|
||||||
|
@ -138,10 +148,13 @@ private:
|
||||||
class ReadLocker;
|
class ReadLocker;
|
||||||
friend class ReadLocker;
|
friend class ReadLocker;
|
||||||
|
|
||||||
std::map<DcId, std::vector<Endpoint>> _data;
|
const Environment _environment = Environment();
|
||||||
std::set<DcId> _cdnDcIds;
|
base::flat_map<DcId, std::vector<Endpoint>> _data;
|
||||||
std::map<uint64, details::RSAPublicKey> _publicKeys;
|
base::flat_set<DcId> _cdnDcIds;
|
||||||
std::map<DcId, std::map<uint64, details::RSAPublicKey>> _cdnPublicKeys;
|
base::flat_map<uint64, details::RSAPublicKey> _publicKeys;
|
||||||
|
base::flat_map<
|
||||||
|
DcId,
|
||||||
|
base::flat_map<uint64, details::RSAPublicKey>> _cdnPublicKeys;
|
||||||
mutable QReadWriteLock _useThroughLockers;
|
mutable QReadWriteLock _useThroughLockers;
|
||||||
|
|
||||||
rpl::event_stream<DcId> _changed;
|
rpl::event_stream<DcId> _changed;
|
|
@ -10,10 +10,14 @@ https://github.com/telegramdesktop/tdesktop/blob/master/LEGAL
|
||||||
#include <QtNetwork/QNetworkProxy>
|
#include <QtNetwork/QNetworkProxy>
|
||||||
#include <QtNetwork/QTcpSocket>
|
#include <QtNetwork/QTcpSocket>
|
||||||
|
|
||||||
|
#include <range/v3/all.hpp>
|
||||||
|
|
||||||
#include <rpl/rpl.h>
|
#include <rpl/rpl.h>
|
||||||
#include <crl/crl.h>
|
#include <crl/crl.h>
|
||||||
|
|
||||||
#include "base/bytes.h"
|
#include "base/bytes.h"
|
||||||
|
#include "base/flat_map.h"
|
||||||
|
#include "base/flat_set.h"
|
||||||
|
|
||||||
#include "logs.h"
|
#include "logs.h"
|
||||||
#include "scheme.h"
|
#include "scheme.h"
|
||||||
|
|
|
@ -196,8 +196,8 @@ public:
|
||||||
: _instance(instance) {
|
: _instance(instance) {
|
||||||
}
|
}
|
||||||
|
|
||||||
[[nodiscard]] not_null<Instance*> instance() const {
|
[[nodiscard]] Instance &instance() const {
|
||||||
return _instance;
|
return *_instance;
|
||||||
}
|
}
|
||||||
|
|
||||||
template <typename Request>
|
template <typename Request>
|
||||||
|
@ -247,7 +247,7 @@ public:
|
||||||
}
|
}
|
||||||
|
|
||||||
mtpRequestId send() {
|
mtpRequestId send() {
|
||||||
const auto id = sender()->instance()->send(
|
const auto id = sender()->_instance->send(
|
||||||
_request,
|
_request,
|
||||||
takeOnDone(),
|
takeOnDone(),
|
||||||
takeOnFail(),
|
takeOnFail(),
|
||||||
|
@ -376,7 +376,7 @@ private:
|
||||||
};
|
};
|
||||||
|
|
||||||
template <typename Request>
|
template <typename Request>
|
||||||
friend class SpecialRequestBuilder;
|
friend class SpecificRequestBuilder;
|
||||||
friend class RequestBuilder;
|
friend class RequestBuilder;
|
||||||
friend class RequestWrap;
|
friend class RequestWrap;
|
||||||
friend class SentRequestWrap;
|
friend class SentRequestWrap;
|
||||||
|
|
|
@ -195,7 +195,7 @@ void Session::watchDcKeyChanges() {
|
||||||
}
|
}
|
||||||
|
|
||||||
void Session::watchDcOptionsChanges() {
|
void Session::watchDcOptionsChanges() {
|
||||||
_instance->dcOptions()->changed(
|
_instance->dcOptions().changed(
|
||||||
) | rpl::filter([=](DcId dcId) {
|
) | rpl::filter([=](DcId dcId) {
|
||||||
return (BareDcId(_shiftedDcId) == dcId) && (_private != nullptr);
|
return (BareDcId(_shiftedDcId) == dcId) && (_private != nullptr);
|
||||||
}) | rpl::start_with_next([=] {
|
}) | rpl::start_with_next([=] {
|
||||||
|
@ -204,8 +204,8 @@ void Session::watchDcOptionsChanges() {
|
||||||
});
|
});
|
||||||
}, _lifetime);
|
}, _lifetime);
|
||||||
|
|
||||||
if (_instance->dcOptions()->dcType(_shiftedDcId) == DcType::Cdn) {
|
if (_instance->dcOptions().dcType(_shiftedDcId) == DcType::Cdn) {
|
||||||
_instance->dcOptions()->cdnConfigChanged(
|
_instance->dcOptions().cdnConfigChanged(
|
||||||
) | rpl::filter([=] {
|
) | rpl::filter([=] {
|
||||||
return (_private != nullptr);
|
return (_private != nullptr);
|
||||||
}) | rpl::start_with_next([=] {
|
}) | rpl::start_with_next([=] {
|
||||||
|
|
|
@ -13,7 +13,7 @@ https://github.com/telegramdesktop/tdesktop/blob/master/LEGAL
|
||||||
#include "mtproto/details/mtproto_rsa_public_key.h"
|
#include "mtproto/details/mtproto_rsa_public_key.h"
|
||||||
#include "mtproto/session.h"
|
#include "mtproto/session.h"
|
||||||
#include "mtproto/mtproto_rpc_sender.h"
|
#include "mtproto/mtproto_rpc_sender.h"
|
||||||
#include "mtproto/dc_options.h"
|
#include "mtproto/mtproto_dc_options.h"
|
||||||
#include "mtproto/connection_abstract.h"
|
#include "mtproto/connection_abstract.h"
|
||||||
#include "base/openssl_help.h"
|
#include "base/openssl_help.h"
|
||||||
#include "base/qthelp_url.h"
|
#include "base/qthelp_url.h"
|
||||||
|
@ -117,7 +117,7 @@ SessionPrivate::SessionPrivate(
|
||||||
: QObject(nullptr)
|
: QObject(nullptr)
|
||||||
, _instance(instance)
|
, _instance(instance)
|
||||||
, _shiftedDcId(shiftedDcId)
|
, _shiftedDcId(shiftedDcId)
|
||||||
, _realDcType(_instance->dcOptions()->dcType(_shiftedDcId))
|
, _realDcType(_instance->dcOptions().dcType(_shiftedDcId))
|
||||||
, _currentDcType(_realDcType)
|
, _currentDcType(_realDcType)
|
||||||
, _state(DisconnectedState)
|
, _state(DisconnectedState)
|
||||||
, _retryTimer(thread, [=] { retryByTimer(); })
|
, _retryTimer(thread, [=] { retryByTimer(); })
|
||||||
|
@ -203,7 +203,7 @@ int16 SessionPrivate::getProtocolDcId() const {
|
||||||
const auto simpleDcId = isTemporaryDcId(dcId)
|
const auto simpleDcId = isTemporaryDcId(dcId)
|
||||||
? getRealIdFromTemporaryDcId(dcId)
|
? getRealIdFromTemporaryDcId(dcId)
|
||||||
: dcId;
|
: dcId;
|
||||||
const auto testedDcId = cTestMode()
|
const auto testedDcId = _instance->isTestMode()
|
||||||
? (kTestModeDcIdShift + simpleDcId)
|
? (kTestModeDcIdShift + simpleDcId)
|
||||||
: simpleDcId;
|
: simpleDcId;
|
||||||
return (_currentDcType == DcType::MediaCluster)
|
return (_currentDcType == DcType::MediaCluster)
|
||||||
|
@ -374,7 +374,7 @@ uint32 SessionPrivate::nextRequestSeqNumber(bool needAck) {
|
||||||
}
|
}
|
||||||
|
|
||||||
bool SessionPrivate::realDcTypeChanged() {
|
bool SessionPrivate::realDcTypeChanged() {
|
||||||
const auto now = _instance->dcOptions()->dcType(_shiftedDcId);
|
const auto now = _instance->dcOptions().dcType(_shiftedDcId);
|
||||||
if (_realDcType == now) {
|
if (_realDcType == now) {
|
||||||
return false;
|
return false;
|
||||||
}
|
}
|
||||||
|
@ -936,7 +936,7 @@ void SessionPrivate::connectToServer(bool afterConfig) {
|
||||||
|
|
||||||
_currentDcType = tryAcquireKeyCreation();
|
_currentDcType = tryAcquireKeyCreation();
|
||||||
if (_currentDcType == DcType::Cdn && !_instance->isKeysDestroyer()) {
|
if (_currentDcType == DcType::Cdn && !_instance->isKeysDestroyer()) {
|
||||||
if (!_instance->dcOptions()->hasCDNKeysForDc(bareDc)) {
|
if (!_instance->dcOptions().hasCDNKeysForDc(bareDc)) {
|
||||||
requestCDNConfig();
|
requestCDNConfig();
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
|
@ -947,7 +947,7 @@ void SessionPrivate::connectToServer(bool afterConfig) {
|
||||||
} else {
|
} else {
|
||||||
using Variants = DcOptions::Variants;
|
using Variants = DcOptions::Variants;
|
||||||
const auto special = (_currentDcType == DcType::Temporary);
|
const auto special = (_currentDcType == DcType::Temporary);
|
||||||
const auto variants = _instance->dcOptions()->lookup(
|
const auto variants = _instance->dcOptions().lookup(
|
||||||
bareDc,
|
bareDc,
|
||||||
_currentDcType,
|
_currentDcType,
|
||||||
_options->proxy.type != ProxyData::Type::None);
|
_options->proxy.type != ProxyData::Type::None);
|
||||||
|
@ -2366,7 +2366,7 @@ void SessionPrivate::applyAuthKey(AuthKeyPtr &&encryptionKey) {
|
||||||
BareDcId(_shiftedDcId),
|
BareDcId(_shiftedDcId),
|
||||||
getProtocolDcId(),
|
getProtocolDcId(),
|
||||||
_connection.get(),
|
_connection.get(),
|
||||||
_instance->dcOptions());
|
&_instance->dcOptions());
|
||||||
} else {
|
} else {
|
||||||
DEBUG_LOG(("AuthKey Info: No key in updateAuthKey(), "
|
DEBUG_LOG(("AuthKey Info: No key in updateAuthKey(), "
|
||||||
"but someone is creating already, waiting."));
|
"but someone is creating already, waiting."));
|
||||||
|
|
|
@ -10,7 +10,7 @@ https://github.com/telegramdesktop/tdesktop/blob/master/LEGAL
|
||||||
#include "mtproto/details/mtproto_received_ids_manager.h"
|
#include "mtproto/details/mtproto_received_ids_manager.h"
|
||||||
#include "mtproto/details/mtproto_serialized_request.h"
|
#include "mtproto/details/mtproto_serialized_request.h"
|
||||||
#include "mtproto/mtproto_auth_key.h"
|
#include "mtproto/mtproto_auth_key.h"
|
||||||
#include "mtproto/dc_options.h"
|
#include "mtproto/mtproto_dc_options.h"
|
||||||
#include "mtproto/connection_abstract.h"
|
#include "mtproto/connection_abstract.h"
|
||||||
#include "mtproto/facade.h"
|
#include "mtproto/facade.h"
|
||||||
#include "base/openssl_help.h"
|
#include "base/openssl_help.h"
|
||||||
|
|
|
@ -8,7 +8,7 @@ https://github.com/telegramdesktop/tdesktop/blob/master/LEGAL
|
||||||
#include "mtproto/special_config_request.h"
|
#include "mtproto/special_config_request.h"
|
||||||
|
|
||||||
#include "mtproto/details/mtproto_rsa_public_key.h"
|
#include "mtproto/details/mtproto_rsa_public_key.h"
|
||||||
#include "mtproto/dc_options.h"
|
#include "mtproto/mtproto_dc_options.h"
|
||||||
#include "mtproto/mtproto_auth_key.h"
|
#include "mtproto/mtproto_auth_key.h"
|
||||||
#include "base/unixtime.h"
|
#include "base/unixtime.h"
|
||||||
#include "base/openssl_help.h"
|
#include "base/openssl_help.h"
|
||||||
|
@ -189,9 +189,11 @@ SpecialConfigRequest::SpecialConfigRequest(
|
||||||
int port,
|
int port,
|
||||||
bytes::const_span secret)> callback,
|
bytes::const_span secret)> callback,
|
||||||
Fn<void()> timeDoneCallback,
|
Fn<void()> timeDoneCallback,
|
||||||
|
const QString &domainString,
|
||||||
const QString &phone)
|
const QString &phone)
|
||||||
: _callback(std::move(callback))
|
: _callback(std::move(callback))
|
||||||
, _timeDoneCallback(std::move(timeDoneCallback))
|
, _timeDoneCallback(std::move(timeDoneCallback))
|
||||||
|
, _domainString(domainString)
|
||||||
, _phone(phone) {
|
, _phone(phone) {
|
||||||
Expects((_callback == nullptr) != (_timeDoneCallback == nullptr));
|
Expects((_callback == nullptr) != (_timeDoneCallback == nullptr));
|
||||||
|
|
||||||
|
@ -251,12 +253,19 @@ SpecialConfigRequest::SpecialConfigRequest(
|
||||||
const std::string &ip,
|
const std::string &ip,
|
||||||
int port,
|
int port,
|
||||||
bytes::const_span secret)> callback,
|
bytes::const_span secret)> callback,
|
||||||
|
const QString &domainString,
|
||||||
const QString &phone)
|
const QString &phone)
|
||||||
: SpecialConfigRequest(std::move(callback), nullptr, phone) {
|
: SpecialConfigRequest(std::move(callback), nullptr, domainString, phone) {
|
||||||
}
|
}
|
||||||
|
|
||||||
SpecialConfigRequest::SpecialConfigRequest(Fn<void()> timeDoneCallback)
|
SpecialConfigRequest::SpecialConfigRequest(
|
||||||
: SpecialConfigRequest(nullptr, std::move(timeDoneCallback), QString()) {
|
Fn<void()> timeDoneCallback,
|
||||||
|
const QString &domainString)
|
||||||
|
: SpecialConfigRequest(
|
||||||
|
nullptr,
|
||||||
|
std::move(timeDoneCallback),
|
||||||
|
domainString,
|
||||||
|
QString()) {
|
||||||
}
|
}
|
||||||
|
|
||||||
void SpecialConfigRequest::sendNextRequest() {
|
void SpecialConfigRequest::sendNextRequest() {
|
||||||
|
@ -283,7 +292,7 @@ void SpecialConfigRequest::performRequest(const Attempt &attempt) {
|
||||||
url.setHost(attempt.data);
|
url.setHost(attempt.data);
|
||||||
url.setPath(qsl("/dns-query"));
|
url.setPath(qsl("/dns-query"));
|
||||||
url.setQuery(qsl("name=%1&type=16&random_padding=%2"
|
url.setQuery(qsl("name=%1&type=16&random_padding=%2"
|
||||||
).arg(Global::TxtDomainString()
|
).arg(_domainString
|
||||||
).arg(GenerateDnsRandomPadding()));
|
).arg(GenerateDnsRandomPadding()));
|
||||||
request.setRawHeader("accept", "application/dns-json");
|
request.setRawHeader("accept", "application/dns-json");
|
||||||
} break;
|
} break;
|
||||||
|
@ -291,7 +300,7 @@ void SpecialConfigRequest::performRequest(const Attempt &attempt) {
|
||||||
url.setHost(attempt.data);
|
url.setHost(attempt.data);
|
||||||
url.setPath(qsl("/resolve"));
|
url.setPath(qsl("/resolve"));
|
||||||
url.setQuery(qsl("name=%1&type=ANY&random_padding=%2"
|
url.setQuery(qsl("name=%1&type=ANY&random_padding=%2"
|
||||||
).arg(Global::TxtDomainString()
|
).arg(_domainString
|
||||||
).arg(GenerateDnsRandomPadding()));
|
).arg(GenerateDnsRandomPadding()));
|
||||||
if (!attempt.host.isEmpty()) {
|
if (!attempt.host.isEmpty()) {
|
||||||
const auto host = attempt.host + ".google.com";
|
const auto host = attempt.host + ".google.com";
|
||||||
|
|
|
@ -25,8 +25,11 @@ public:
|
||||||
const std::string &ip,
|
const std::string &ip,
|
||||||
int port,
|
int port,
|
||||||
bytes::const_span secret)> callback,
|
bytes::const_span secret)> callback,
|
||||||
|
const QString &domainString,
|
||||||
const QString &phone);
|
const QString &phone);
|
||||||
explicit SpecialConfigRequest(Fn<void()> timeDoneCallback);
|
SpecialConfigRequest(
|
||||||
|
Fn<void()> timeDoneCallback,
|
||||||
|
const QString &domainString);
|
||||||
|
|
||||||
private:
|
private:
|
||||||
enum class Type {
|
enum class Type {
|
||||||
|
@ -49,6 +52,7 @@ private:
|
||||||
int port,
|
int port,
|
||||||
bytes::const_span secret)> callback,
|
bytes::const_span secret)> callback,
|
||||||
Fn<void()> timeDoneCallback,
|
Fn<void()> timeDoneCallback,
|
||||||
|
const QString &domainString,
|
||||||
const QString &phone);
|
const QString &phone);
|
||||||
|
|
||||||
void sendNextRequest();
|
void sendNextRequest();
|
||||||
|
@ -65,6 +69,7 @@ private:
|
||||||
int port,
|
int port,
|
||||||
bytes::const_span secret)> _callback;
|
bytes::const_span secret)> _callback;
|
||||||
Fn<void()> _timeDoneCallback;
|
Fn<void()> _timeDoneCallback;
|
||||||
|
QString _domainString;
|
||||||
QString _phone;
|
QString _phone;
|
||||||
MTPhelp_ConfigSimple _simpleConfig;
|
MTPhelp_ConfigSimple _simpleConfig;
|
||||||
|
|
||||||
|
|
|
@ -624,7 +624,7 @@ FormController::FormController(
|
||||||
not_null<Window::SessionController*> controller,
|
not_null<Window::SessionController*> controller,
|
||||||
const FormRequest &request)
|
const FormRequest &request)
|
||||||
: _controller(controller)
|
: _controller(controller)
|
||||||
, _api(_controller->session().mtp())
|
, _api(&_controller->session().mtp())
|
||||||
, _request(PreprocessRequest(request))
|
, _request(PreprocessRequest(request))
|
||||||
, _shortPollTimer([=] { reloadPassword(); })
|
, _shortPollTimer([=] { reloadPassword(); })
|
||||||
, _view(std::make_unique<PanelController>(this)) {
|
, _view(std::make_unique<PanelController>(this)) {
|
||||||
|
|
Some files were not shown because too many files have changed in this diff Show more
Loading…
Add table
Reference in a new issue