diff --git a/src/lib/appManagers/apiUpdatesManager.ts b/src/lib/appManagers/apiUpdatesManager.ts index 7b370e20..b40e6357 100644 --- a/src/lib/appManagers/apiUpdatesManager.ts +++ b/src/lib/appManagers/apiUpdatesManager.ts @@ -247,7 +247,7 @@ export class ApiUpdatesManager { const promise = apiManager.invokeApi('updates.getDifference', { pts: updatesState.pts, - pts_total_limit: first && false ? 1200 : undefined, + pts_total_limit: first/* && false */ ? 50/* 1200 */ : undefined, date: updatesState.date, qts: -1 }, { @@ -307,6 +307,7 @@ export class ApiUpdatesManager { this.channelStates = {}; + this.log.warn('getDifference:', differenceResult._); rootScope.dispatchEvent('state_cleared'); } @@ -645,6 +646,7 @@ export class ApiUpdatesManager { /* state.seq = 1; state.pts = state.pts - 15; state.date = 1; */ + // state.pts -= 100; Object.assign(this.updatesState, state); diff --git a/src/lib/appManagers/appChatsManager.ts b/src/lib/appManagers/appChatsManager.ts index f5916ae6..54fe05c9 100644 --- a/src/lib/appManagers/appChatsManager.ts +++ b/src/lib/appManagers/appChatsManager.ts @@ -34,7 +34,8 @@ export class AppChatsManager { //private megagroups: {[id: number]: true}; constructor() { - this.clear(); + this.chats = this.storage.getCache(); + this.clear(true); rootScope.addMultipleEventsListeners({ /* updateChannel: (update) => { @@ -62,7 +63,6 @@ export class AppChatsManager { appStateManager.getState().then((state) => { const chats = appStateManager.storagesResults.chats; if(chats.length) { - this.chats = {}; for(let i = 0, length = chats.length; i < length; ++i) { const chat = chats[i]; if(chat) { @@ -91,20 +91,22 @@ export class AppChatsManager { }); } - public clear() { - if(this.chats) { - for(const chatId in this.chats) { - if(!appStateManager.isPeerNeeded(-+chatId)) { + public clear(init = false) { + if(!init) { + const chats = appStateManager.storagesResults.chats; + for(const _chatId in this.chats) { + const chatId = +_chatId; + if(!chatId) continue; + if(!appStateManager.isPeerNeeded(-chatId)) { /* const chat = this.chats[chatId]; if(chat.username) { delete this.usernames[cleanUsername(chat.username)]; } */ - - delete this.chats[chatId]; + + chats.findAndSplice((chat) => chat.id === chatId); + this.storage.delete(chatId); } } - } else { - this.chats = {}; } } diff --git a/src/lib/appManagers/appDialogsManager.ts b/src/lib/appManagers/appDialogsManager.ts index 3bca0038..f324e39d 100644 --- a/src/lib/appManagers/appDialogsManager.ts +++ b/src/lib/appManagers/appDialogsManager.ts @@ -21,7 +21,7 @@ import appPeersManager from './appPeersManager'; import appImManager from "./appImManager"; import appMessagesManager, { Dialog } from "./appMessagesManager"; import {MyDialogFilter as DialogFilter} from "../storages/filters"; -import appStateManager from "./appStateManager"; +import appStateManager, { AppStateManager, State } from "./appStateManager"; import appUsersManager from "./appUsersManager"; import Button from "../../components/button"; import SetTransition from "../../components/singleTransition"; @@ -328,7 +328,33 @@ export class AppDialogsManager { rootScope.addEventListener('state_cleared', () => { appUsersManager.clear(); appChatsManager.clear(); + + const filtersStorage = appMessagesManager.filtersStorage; + const filters = filtersStorage.filters; + for(const filterId in filters) { // delete filters + rootScope.dispatchEvent('updateDialogFilter', { + _: 'updateDialogFilter', + id: +filterId, + }); + } + appMessagesManager.clear(); + + /* const clearPromises: Promise[] = []; + for(const name in appStateManager.storagesResults) { + const results = appStateManager.storagesResults[name as keyof AppStateManager['storages']]; + const storage = appStateManager.storages[name as keyof AppStateManager['storages']]; + results.length = 0; + clearPromises.push(storage.clear()); + } */ + + this.validateForFilter(); + Promise.all([ + appStateManager.getState(), + //Promise.all(clearPromises) + ]).then(([state]) => { + this.onStateLoaded(state); + }); }); const foldersScrollable = new ScrollableX(this.folders.menuScrollContainer); @@ -356,28 +382,8 @@ export class AppDialogsManager { //selectTab(0); (this.folders.menu.firstElementChild as HTMLElement).click(); appMessagesManager.construct(); - appStateManager.getState().then(async(state) => { - appNotificationsManager.getNotifyPeerTypeSettings(); - - const renderFiltersPromise = appMessagesManager.filtersStorage.getDialogFilters().then((filters) => { - for(const filter of filters) { - this.addFilter(filter); - } - }); - - if(state.filters && Object.keys(state.filters).length) { - await renderFiltersPromise; - if(this.showFiltersPromise) { - await this.showFiltersPromise; - } - } - - if(appStateManager.storagesResults.dialogs.length) { - appDraftsManager.getAllDrafts(); - appDraftsManager.addMissedDialogs(); - } - - return this.loadDialogs(); + appStateManager.getState().then((state) => { + return this.onStateLoaded(state); }).then(() => { //return; @@ -407,6 +413,29 @@ export class AppDialogsManager { }, 200); } + private async onStateLoaded(state: State) { + appNotificationsManager.getNotifyPeerTypeSettings(); + + const renderFiltersPromise = appMessagesManager.filtersStorage.getDialogFilters().then((filters) => { + for(const filter of filters) { + this.addFilter(filter); + } + }); + + if(state.filters && Object.keys(state.filters).length) { + await renderFiltersPromise; + if(this.showFiltersPromise) { + await this.showFiltersPromise; + } + } + + if(appStateManager.storagesResults.dialogs.length) { + appDraftsManager.addMissedDialogs(); + } + + return this.loadDialogs(); + } + private getOffset(side: 'top' | 'bottom'): {index: number, pos: number} { if(!this.scroll.loadedAll[side]) { const element = (side === 'top' ? this.chatList.firstElementChild : this.chatList.lastElementChild) as HTMLElement; diff --git a/src/lib/appManagers/appStateManager.ts b/src/lib/appManagers/appStateManager.ts index 75e7bf62..343abb28 100644 --- a/src/lib/appManagers/appStateManager.ts +++ b/src/lib/appManagers/appStateManager.ts @@ -183,7 +183,11 @@ export class AppStateManager extends EventListenerBase<{ dialogs: new AppStorage, typeof DATABASE_STATE>(DATABASE_STATE, 'dialogs') }; - public storagesResults: {[key in keyof AppStateManager['storages']]: any[]} = {} as any; + public storagesResults: { + users: User[], + chats: Chat[], + dialogs: Dialog[] + } = {} as any; public storage = stateStorage; diff --git a/src/lib/appManagers/appUsersManager.ts b/src/lib/appManagers/appUsersManager.ts index f5a11637..46e12d4f 100644 --- a/src/lib/appManagers/appUsersManager.ts +++ b/src/lib/appManagers/appUsersManager.ts @@ -46,7 +46,8 @@ export class AppUsersManager { private getTopPeersPromise: Promise; constructor() { - this.clear(); + this.users = this.storage.getCache(); + this.clear(true); setInterval(this.updateUsersStatuses, 60000); @@ -120,7 +121,6 @@ export class AppUsersManager { appStateManager.getState().then((state) => { const users = appStateManager.storagesResults.users; if(users.length) { - this.users = {}; for(let i = 0, length = users.length; i < length; ++i) { const user = users[i]; if(user) { @@ -160,20 +160,23 @@ export class AppUsersManager { }); } - public clear() { - if(this.users) { - for(const userId in this.users) { - if(!appStateManager.isPeerNeeded(+userId)) { + public clear(init = false) { + if(!init) { + const users = appStateManager.storagesResults.users; + for(const _userId in this.users) { + const userId = +_userId; + if(!userId) continue; + if(!appStateManager.isPeerNeeded(userId)) { const user = this.users[userId]; if(user.username) { delete this.usernames[cleanUsername(user.username)]; } - - delete this.users[userId]; + + users.findAndSplice((user) => user.id === userId); + this.storage.delete(userId); } } } else { - this.users = {}; this.usernames = {}; } diff --git a/src/lib/storage.ts b/src/lib/storage.ts index 6d4c70fc..c76c7f4c 100644 --- a/src/lib/storage.ts +++ b/src/lib/storage.ts @@ -265,7 +265,13 @@ export default class AppStorage, T extends D return this.useStorage ? this.deleteDeferred : Promise.resolve(); } - public clear() { + public clear(saveLocal = false) { + if(!saveLocal) { + for(const i in this.cache) { + delete this.cache[i]; + } + } + return this.storage.clear().catch(noop); } @@ -278,7 +284,7 @@ export default class AppStorage, T extends D storage.keysToDelete.clear(); storage.getPromises.forEach((deferred) => deferred.resolve()); storage.getPromises.clear(); - return storage.clear(); + return storage.clear(true); } else { return storage.set(storage.cache); } diff --git a/src/lib/storages/dialogs.ts b/src/lib/storages/dialogs.ts index 0f6a9bdb..6180444d 100644 --- a/src/lib/storages/dialogs.ts +++ b/src/lib/storages/dialogs.ts @@ -57,8 +57,9 @@ export default class DialogsStorage { private apiUpdatesManager: ApiUpdatesManager, private serverTimeManager: ServerTimeManager ) { - this.clear(); this.storage = this.appStateManager.storages.dialogs; + this.dialogs = this.storage.getCache(); + this.clear(true); rootScope.addEventListener('language_change', (e) => { const peerId = appUsersManager.getSelf().id; @@ -117,8 +118,13 @@ export default class DialogsStorage { this.appStateManager.pushToState('allDialogsLoaded', this.allDialogsLoaded); } - public clear() { - this.dialogs = {}; + public clear(init = false) { + if(!init) { + const dialogs = this.appStateManager.storagesResults.dialogs; + dialogs.length = 0; + this.storage.clear(); + } + this.byFolders = {}; this.allDialogsLoaded = {}; this.dialogsOffsetDate = {}; diff --git a/src/lib/storages/filters.ts b/src/lib/storages/filters.ts index 0623ab70..9843a27f 100644 --- a/src/lib/storages/filters.ts +++ b/src/lib/storages/filters.ts @@ -4,7 +4,7 @@ * https://github.com/morethanwords/tweb/blob/master/LICENSE */ -import { copy } from "../../helpers/object"; +import { copy, safeReplaceObject } from "../../helpers/object"; import type { DialogFilter, Update } from "../../layer"; import type { Modify } from "../../types"; import type { AppPeersManager } from "../appManagers/appPeersManager"; @@ -41,9 +41,10 @@ export default class FiltersStorage { /* private apiManager: ApiManagerProxy, */ private rootScope: typeof _rootScope) { this.clear(); + this.filters = {}; this.appStateManager.getState().then((state) => { - this.filters = state.filters; + safeReplaceObject(this.filters, state.filters); for(const filterId in this.filters) { const filter = this.filters[filterId]; @@ -77,8 +78,11 @@ export default class FiltersStorage { }); } - public clear() { - this.filters = {}; + public clear(init = false) { + if(!init) { + safeReplaceObject(this.filters, {}); + } + this.orderIndex = START_ORDER_INDEX; } @@ -243,7 +247,7 @@ export default class FiltersStorage { return keys.map(filterId => this.filters[filterId]).sort((a, b) => a.orderIndex - b.orderIndex); } - const filters: MyDialogFilter[] = await apiManager.invokeApi('messages.getDialogFilters') as any; + const filters: MyDialogFilter[] = await apiManager.invokeApiSingle('messages.getDialogFilters') as any; for(const filter of filters) { this.saveDialogFilter(filter, overwrite); }