diff --git a/.DS_Store b/.DS_Store index bf9bbbc8..edc6a371 100644 Binary files a/.DS_Store and b/.DS_Store differ diff --git a/.gitignore b/.gitignore index 52409698..6c457299 100644 --- a/.gitignore +++ b/.gitignore @@ -2,3 +2,4 @@ node_modules coverage __pycache__ dist +.DS_Store diff --git a/src/components/misc.ts b/src/components/misc.ts index d48933a4..f5da47f2 100644 --- a/src/components/misc.ts +++ b/src/components/misc.ts @@ -5,6 +5,8 @@ import CryptoWorker from '../lib/crypto/cryptoworker'; import LottieLoader from '../lib/lottieLoader'; import appStickersManager from "../lib/appManagers/appStickersManager"; import appDocsManager from "../lib/appManagers/appDocsManager"; +import {AppImManager} from "../lib/appManagers/appImManager"; +import {AppMediaViewer} from '../lib/appManagers/appMediaViewer'; export type MTDocument = { _: 'document', @@ -39,50 +41,50 @@ export type MTPhotoSize = { let onRippleClick = function(this: HTMLElement, e: MouseEvent) { var $circle = this.firstElementChild as HTMLSpanElement;//this.querySelector('.c-ripple__circle') as HTMLSpanElement; - + var rect = this.parentElement.getBoundingClientRect(); var x = e.clientX - rect.left; //x position within the element. var y = e.clientY - rect.top; - + /* var x = e.pageX - this.parentElement.offsetLeft; var y = e.pageY - this.parentElement.offsetTop - this.parentElement.scrollHeight; */ - + $circle.style.top = y + 'px'; $circle.style.left = x + 'px'; - + this.classList.add('active'); - + //console.log('onrippleclick', e/* e.pageY, this.parentElement.offsetTop */); }; export function ripple(elem: Element) { /* elem.addEventListener('click', function(e) { var $circle = elem.querySelector('.c-ripple__circle') as HTMLSpanElement; - + var x = e.pageX - elem.offsetLeft; var y = e.pageY - elem.offsetTop; - + $circle.style.top = y + 'px'; $circle.style.left = x + 'px'; - + elem.classList.add('active'); }); */ - + let r = document.createElement('div'); r.classList.add('c-ripple'); - + let span = document.createElement('span'); span.classList.add('c-ripple__circle'); - + r.append(span); elem.append(r); - + r.addEventListener('click', onRippleClick); - + let onEnd = () => { r.classList.remove('active'); }; - + for(let type of ['animationend', 'webkitAnimationEnd', 'oanimationend', 'MSAnimationEnd']) { r.addEventListener(type, onEnd); } @@ -213,9 +215,20 @@ export class LazyLoadQueue { } } -export function wrapVideo(doc: MTDocument, container: HTMLDivElement, middleware: () => boolean, messageID: number, justLoader = true, preloader?: ProgressivePreloader) { - if(!container.firstElementChild || container.firstElementChild.tagName != 'IMG') { +export function wrapVideo(this: any, doc: MTDocument, container: HTMLDivElement, message: any, justLoader = true, preloader?: ProgressivePreloader) { + //if(!container.firstElementChild || container.firstElementChild.tagName != 'IMG') { let size = appPhotosManager.setAttachmentSize(doc, container); + //} + + let peerID = this.peerID ? this.peerID : this.currentMessageID; + + //container.classList.add('video'); + + let img = container.firstElementChild as HTMLImageElement || new Image(); + img.setAttribute('message-id', '' + message.id); + + if(!container.contains(img)) { + container.append(img); } //return Promise.resolve(); @@ -227,17 +240,18 @@ export function wrapVideo(doc: MTDocument, container: HTMLDivElement, middleware let loadVideo = () => { let promise = appDocsManager.downloadDoc(doc); - promise.notify = (details: {done: number, total: number}) => { + /* promise.notify = (details: {done: number, total: number}) => { console.log('doc download', promise, details); preloader.setProgress(details.done); - }; + }; */ return promise.then(blob => { - if(!middleware()) { + if((this.peerID ? this.peerID : this.currentMessageID) != peerID) { + this.log.warn('peer changed'); return; } - console.log('loaded doc:', doc, blob, container.firstElementChild); + console.log('loaded doc:', doc, blob, container); let video = document.createElement('video'); video.loop = true; @@ -245,52 +259,50 @@ export function wrapVideo(doc: MTDocument, container: HTMLDivElement, middleware if(!justLoader) { video.controls = true; + } else { + video.volume = 0; } - video.setAttribute('message-id', '' + messageID); + video.setAttribute('message-id', '' + message.id); let source = document.createElement('source'); //source.src = doc.url; source.src = URL.createObjectURL(blob); source.type = doc.mime_type; + + if(img && container.contains(img)) { + container.removeChild(img); + } video.append(source); container.append(video); - if(container.firstElementChild) { - container.firstElementChild.remove(); - } - preloader.detach(); }); }; if(doc.type == 'gif') { - return loadVideo(); + return this.peerID ? this.loadMediaQueuePush(loadVideo) : loadVideo(); } else { // if video - return appPhotosManager.preloadPhoto(doc).then((blob) => { - if(!middleware()) { + let load = () => appPhotosManager.preloadPhoto(doc).then((blob) => { + if((this.peerID ? this.peerID : this.currentMessageID) != peerID) { + this.log.warn('peer changed'); return; } - - if(container.firstElementChild) { - container.firstElementChild.remove(); - } - - let image = new Image(); - image.src = URL.createObjectURL(blob); + + img.src = URL.createObjectURL(blob); /* image.style.height = doc.h + 'px'; image.style.width = doc.w + 'px'; */ - image.setAttribute('message-id', '' + messageID); - - container.append(image); - if(!justLoader) { return loadVideo(); + } else { + preloader.detach(); } }); + + return this.peerID ? this.loadMediaQueuePush(load) : load(); } } @@ -335,10 +347,10 @@ export function scrollable(el: HTMLDivElement, x = false, y = true) { container.classList.add('scrollable'); if(x) container.classList.add('scrollable-x'); if(y) container.classList.add('scrollable-y'); - + container.addEventListener('mouseover', () => { container.classList.add('active'); - + container.addEventListener('mouseout', () => { container.classList.remove('active'); }, {once: true}); @@ -350,6 +362,37 @@ export function scrollable(el: HTMLDivElement, x = false, y = true) { return container; } +export function wrapPhoto(this: AppImManager, photo: any, message: any, container: HTMLDivElement) { + //container.classList.add('photo'); + + let peerID = this.peerID; + + let size = appPhotosManager.setAttachmentSize(photo.id, container); + let image = container.firstElementChild as HTMLImageElement || new Image(); + image.setAttribute('message-id', message.mid); + + if(!container.contains(image)) { + container.append(image); + } + + let preloader = new ProgressivePreloader(container, false); + + let load = () => appPhotosManager.preloadPhoto(photo.id, size).then((blob) => { + if(this.peerID != peerID) { + this.log.warn('peer changed'); + return; + } + + image.src = URL.createObjectURL(blob); + + preloader.detach(); + }); + + console.log('wrapPhoto', load, container, image); + + return this.loadMediaQueue ? this.loadMediaQueuePush(load) : load(); +} + export function wrapSticker(doc: MTDocument, div: HTMLDivElement, middleware?: () => boolean, lazyLoadQueue?: LazyLoadQueue, group?: string, canvas?: boolean) { let stickerType = doc.mime_type == "application/x-tgsticker" ? 2 : (doc.mime_type == "image/webp" ? 1 : 0); @@ -399,24 +442,24 @@ export function wrapSticker(doc: MTDocument, div: HTMLDivElement, middleware?: ( animationData: JSON.parse(json), renderer: canvas ? 'canvas' : 'svg' }, group); - + if(!canvas) { div.addEventListener('mouseover', (e) => { let animation = LottieLoader.getAnimation(div, group); - + if(animation) { //console.log('sticker hover', animation, div); - + // @ts-ignore animation.loop = true; - + // @ts-ignore if(animation.currentFrame == animation.totalFrames - 1) { animation.goToAndPlay(0, true); } else { animation.play(); } - + div.addEventListener('mouseout', () => { // @ts-ignore animation.loop = false; @@ -451,11 +494,11 @@ export function horizontalMenu(tabs: HTMLUListElement, content: HTMLDivElement, tabs.addEventListener('click', function(e) { let target = e.target as HTMLLIElement; - + if(target.tagName != 'LI') { target = findUpTag(target, 'LI'); } - + console.log('tabs click:', target); if(target.classList.contains('active')) return false; diff --git a/src/lib/appManagers/appDialogsManager.ts b/src/lib/appManagers/appDialogsManager.ts index 6da7f549..c3101af4 100644 --- a/src/lib/appManagers/appDialogsManager.ts +++ b/src/lib/appManagers/appDialogsManager.ts @@ -2,13 +2,23 @@ import { MTProto } from "../mtproto/mtproto"; import { $rootScope, findUpTag } from "../utils"; import appImManager from "./appImManager"; import appPeersManager from './appPeersManager'; -import { DialogDom } from "../services"; import appMessagesManager from "./appMessagesManager"; import appUsersManager from "./appUsersManager"; import appSidebarRight from "./appSidebarRight"; import { RichTextProcessor } from "../richtextprocessor"; import { ripple } from "../../components/misc"; +type DialogDom = { + avatarDiv: HTMLDivElement, + captionDiv: HTMLDivElement, + titleSpan: HTMLSpanElement, + statusSpan: HTMLSpanElement, + lastTimeSpan: HTMLSpanElement, + unreadMessagesSpan: HTMLSpanElement, + lastMessageSpan: HTMLSpanElement, + listEl: HTMLLIElement +}; + export class AppDialogsManager { public pinnedChatList = document.getElementById('dialogs-pinned') as HTMLUListElement; public chatList = document.getElementById('dialogs') as HTMLUListElement; @@ -190,13 +200,13 @@ export class AppDialogsManager { } if(document.type == 'video') { - lastMessageText += 'Video'; + lastMessageText = 'Video' + (lastMessage.message ? ', ' : '') + ''; found = true; } else if(document.type == 'voice') { - lastMessageText += 'Voice message'; + lastMessageText = 'Voice message'; found = true; } else if(document.type == 'gif') { - lastMessageText += 'GIF'; + lastMessageText = 'GIF' + (lastMessage.message ? ', ' : '') + ''; found = true; } diff --git a/src/lib/appManagers/appImManager.ts b/src/lib/appManagers/appImManager.ts index 6332eccc..edb416e9 100644 --- a/src/lib/appManagers/appImManager.ts +++ b/src/lib/appManagers/appImManager.ts @@ -4,7 +4,7 @@ import appUsersManager from "./appUsersManager"; import appMessagesManager from "./appMessagesManager"; import appPeersManager from "./appPeersManager"; import appProfileManager from "./appProfileManager"; -import { ProgressivePreloader, wrapDocument, wrapSticker, wrapVideo } from "../../components/misc"; +import { ProgressivePreloader, wrapDocument, wrapSticker, wrapVideo, wrapPhoto } from "../../components/misc"; import appDialogsManager from "./appDialogsManager"; import { RichTextProcessor } from "../richtextprocessor"; import appPhotosManager from "./appPhotosManager"; @@ -121,7 +121,7 @@ export class AppImManager { public scroll: HTMLDivElement = null; public scrollPosition: ScrollPosition = null; - private log: ReturnType; + public log: ReturnType; private preloader: ProgressivePreloader = null; @@ -763,28 +763,9 @@ export class AppImManager { let photo = message.media.photo; this.log('messageMediaPhoto', photo); - bubble.classList.add('photo'); + bubble.classList.add('hide-name', 'photo'); - let size = appPhotosManager.setAttachmentSize(photo.id, attachmentDiv); - let load = () => appPhotosManager.preloadPhoto(photo.id, size).then((blob) => { - if(this.peerID != peerID) { - this.log.warn('peer changed'); - return; - } - - if(attachmentDiv.firstElementChild) { - attachmentDiv.firstElementChild.remove(); - } - - let image = new Image(); - image.src = URL.createObjectURL(blob); - image.setAttribute('message-id', message.mid); - attachmentDiv.append(image); - }); - - bubble.classList.add('hide-name'); - - this.loadMediaQueuePush(load); + wrapPhoto.call(this, photo, message, attachmentDiv); break; } @@ -827,58 +808,18 @@ export class AppImManager { doc = webpage.document; if(doc.type == 'gif' || doc.type == 'video') { - appPhotosManager.setAttachmentSize(doc, preview); - bubble.classList.add('video'); - - let load = () => wrapVideo(doc, preview, () => { - if(this.peerID != peerID) { - this.log.warn('peer changed'); - return false; - } - - loadedVideo = true; - - return true; - }, message.mid); - - this.loadMediaQueuePush(load); + wrapVideo.call(this, doc, preview, message); } else { doc = null; } } if(webpage.photo && !doc) { - appPhotosManager.savePhoto(webpage.photo); // hot-fix because no webpage manager - bubble.classList.add('photo'); - - let size = appPhotosManager.setAttachmentSize(webpage.photo.id, preview); - let load = () => appPhotosManager.preloadPhoto(webpage.photo.id, size).then((blob) => { - if(this.peerID != peerID) { - this.log.warn('peer changed'); - return; - } - - if(loadedVideo) { - return; - } - - let img = preview.firstElementChild as HTMLImageElement || new Image(); - this.log('night running 1', bubble, bubble.scrollHeight, img.src); - - //setTimeout(() => { - img.src = URL.createObjectURL(blob); - ///}, 5e3); - - if(!preview.contains(img)) { - preview.append(img); - } - - this.log('night running 2', bubble, bubble.scrollHeight); - }); + appPhotosManager.savePhoto(webpage.photo); // hot-fix because no webpage manager - this.loadMediaQueuePush(load); + wrapPhoto.call(this, webpage.photo, message, preview); } if(preview) { @@ -943,18 +884,7 @@ export class AppImManager { this.log('never get free 2', doc); bubble.classList.add('video'); - - appPhotosManager.setAttachmentSize(doc, attachmentDiv); - let load = () => wrapVideo(doc, attachmentDiv, () => { - if(this.peerID != peerID) { - this.log.warn('peer changed'); - return false; - } - - return true; - }, message.mid); - - this.loadMediaQueuePush(load); + wrapVideo.call(this, doc, attachmentDiv, message); break; } else { @@ -1055,19 +985,21 @@ export class AppImManager { //} } - let avatarDiv = document.createElement('div'); - avatarDiv.classList.add('user-avatar'); + if(!our && this.peerID < 0) { + let avatarDiv = document.createElement('div'); + avatarDiv.classList.add('user-avatar'); + + this.log('exec loadDialogPhoto', message); + if(message.fromID) { // if no - user hidden + appDialogsManager.loadDialogPhoto(avatarDiv, message.fromID); + } else if(!title && message.fwd_from && message.fwd_from.from_name) { + title = message.fwd_from.from_name; - this.log('exec loadDialogPhoto', message); - if(message.fromID) { // if no - user hidden - appDialogsManager.loadDialogPhoto(avatarDiv, message.fromID); - } else if(!title && message.fwd_from && message.fwd_from.from_name) { - title = message.fwd_from.from_name; - - appDialogsManager.loadDialogPhoto(avatarDiv, title); + appDialogsManager.loadDialogPhoto(avatarDiv, title); + } + + bubble.append(avatarDiv); } - - bubble.append(avatarDiv); } let type = our ? 'out' : 'in'; diff --git a/src/lib/appManagers/appMediaViewer.ts b/src/lib/appManagers/appMediaViewer.ts index 45b764a9..a9ab1643 100644 --- a/src/lib/appManagers/appMediaViewer.ts +++ b/src/lib/appManagers/appMediaViewer.ts @@ -7,8 +7,9 @@ import { $rootScope } from "../utils"; import appMessagesManager from "./appMessagesManager"; import { CancellablePromise } from "../mtproto/apiFileManager"; import { RichTextProcessor } from "../richtextprocessor"; +import { logger } from "../polyfill"; -class AppMediaViewer { +export class AppMediaViewer { private overlaysDiv = document.querySelector('.overlays') as HTMLDivElement; private author = { avatarEl: this.overlaysDiv.querySelector('.user-avatar') as HTMLDivElement, @@ -29,17 +30,21 @@ class AppMediaViewer { }; private reverse = false; - private currentMessageID = 0; + public currentMessageID = 0; private higherMsgID: number | undefined = 0; private lowerMsgID: number | undefined = 0; private preloader: ProgressivePreloader = null; + + public log: ReturnType; constructor() { + this.log = logger('AMV'); this.preloader = new ProgressivePreloader(); this.buttons.close.addEventListener('click', () => { this.overlaysDiv.classList.remove('active'); this.content.container.innerHTML = ''; + this.currentMessageID = 0; }); this.buttons.prev.addEventListener('click', () => { @@ -127,7 +132,7 @@ class AppMediaViewer { } public openMedia(message: any, reverse = false) { - console.log('openMedia doc:', message); + this.log('openMedia doc:', message); let media = message.media.photo || message.media.document || message.media.webpage.document; let isVideo = media.mime_type == 'video/mp4'; @@ -138,7 +143,7 @@ class AppMediaViewer { let container = this.content.container; if(container.firstElementChild) { - container.firstElementChild.remove(); + container.innerHTML = ''; } let date = new Date(media.date * 1000); @@ -163,21 +168,12 @@ class AppMediaViewer { this.overlaysDiv.classList.add('active'); if(isVideo) { - appPhotosManager.setAttachmentSize(media, container); - - this.preloader.attach(container); + //this.preloader.attach(container); //this.preloader.setProgress(75); - console.log('will wrap video'); + this.log('will wrap video'); - wrapVideo(media, container, () => { - if(this.currentMessageID != message.mid) { - console.warn('media viewer changed photo'); - return false; - } - - return true; - }, message.mid, false, this.preloader); + wrapVideo.call(this, media, container, message, false, this.preloader); } else { let size = appPhotosManager.setAttachmentSize(media.id, container, appPhotosManager.windowW, appPhotosManager.windowH); @@ -187,11 +183,11 @@ class AppMediaViewer { let cancellablePromise = appPhotosManager.preloadPhoto(media.id, size); cancellablePromise.then((blob) => { if(this.currentMessageID != message.mid) { - console.warn('media viewer changed photo'); + this.log.warn('media viewer changed photo'); return; } - console.log('indochina', blob); + this.log('indochina', blob); if(container.firstElementChild) { container.firstElementChild.remove(); } diff --git a/src/lib/appManagers/appMessagesManager.ts b/src/lib/appManagers/appMessagesManager.ts index ec274257..c19ad673 100644 --- a/src/lib/appManagers/appMessagesManager.ts +++ b/src/lib/appManagers/appMessagesManager.ts @@ -1639,7 +1639,11 @@ export class AppMessagesManager { public getSearch(peerID = 0, query: string = '', inputFilter: { _?: string - } = {_: 'inputMessagesFilterEmpty'}, maxID: number, limit: number) { + } = {_: 'inputMessagesFilterEmpty'}, maxID: number, limit: number, offsetRate = 0): Promise<{ + count: number, + next_rate: number, + history: number[] + }> { //peerID = peerID ? parseInt(peerID) : 0; var foundMsgs: number[] = []; var useSearchCache = !query; @@ -1713,6 +1717,7 @@ export class AppMessagesManager { default: return Promise.resolve({ count: 0, + next_rate: 0, history: [] as number[] }); } @@ -1756,6 +1761,7 @@ export class AppMessagesManager { return Promise.resolve({ count: 0, + next_rate: 0, history: foundMsgs }); } @@ -1793,7 +1799,7 @@ export class AppMessagesManager { apiPromise = MTProto.apiManager.invokeApi('messages.searchGlobal', { q: query, - offset_date: offsetDate, + offset_rate: offsetRate, offset_peer: AppPeersManager.getInputPeerByID(offsetPeerID), offset_id: appMessagesIDsManager.getMessageLocalID(offsetID), limit: limit || 20 @@ -1808,6 +1814,8 @@ export class AppMessagesManager { appChatsManager.saveApiChats(searchResult.chats); this.saveMessages(searchResult.messages); + console.log('messages.search result:', searchResult); + var foundCount: number = searchResult.count || searchResult.messages.length; foundMsgs = []; @@ -1830,12 +1838,14 @@ export class AppMessagesManager { return { count: foundCount, + next_rate: searchResult.next_rate, history: foundMsgs - } + }; }, (error) => { if(error.code == 400) { error.handled = true; } + return Promise.reject(error); }); } diff --git a/src/lib/appManagers/appPhotosManager.ts b/src/lib/appManagers/appPhotosManager.ts index 99f53aec..651e02e4 100644 --- a/src/lib/appManagers/appPhotosManager.ts +++ b/src/lib/appManagers/appPhotosManager.ts @@ -151,13 +151,13 @@ export class AppPhotosManager { let image = new Image(); image.src = URL.createObjectURL(blob); - image.style.width = '100%'; - image.style.height = '100%'; + // image.style.width = '100%'; + // image.style.height = '100%'; div.append(image); } } - public setAttachmentSize(photoID: any, div: HTMLDivElement, w = 380, h = 0) { + public setAttachmentSize(photoID: any, div: HTMLDivElement, w = 380, h = 0/* 380 */) { let photo: /* MTDocument | MTPhoto */any = null; if(typeof(photoID) === 'string') { @@ -170,11 +170,9 @@ export class AppPhotosManager { let photoSize = this.choosePhotoSize(photo, w, h); //console.log('setAttachmentSize', photo, photo.sizes[0].bytes, div); - let thumb: any; let sizes = photo.sizes || photo.thumbs; - if(sizes && (sizes[0]._ == 'photoStrippedSize' || sizes[0]._ == 'photoCachedSize' && sizes[0].bytes)) { - thumb = sizes[0]; - this.setAttachmentPreview(thumb.bytes, div); + if(sizes && sizes[0].bytes) { + this.setAttachmentPreview(sizes[0].bytes, div); } if(photo._ == 'document' /* && photo.type != 'video' */ && photo.type != 'gif') { diff --git a/src/lib/appManagers/appSidebarLeft.ts b/src/lib/appManagers/appSidebarLeft.ts index fad63e14..e4270087 100644 --- a/src/lib/appManagers/appSidebarLeft.ts +++ b/src/lib/appManagers/appSidebarLeft.ts @@ -2,91 +2,88 @@ import { logger } from "../polyfill"; import { scrollable } from "../../components/misc"; import appMessagesManager from "./appMessagesManager"; import appDialogsManager from "./appDialogsManager"; +import { isElementInViewport } from "../utils"; +import appMessagesIDsManager from "./appMessagesIDsManager"; class AppSidebarLeft { private sidebarEl = document.querySelector('.page-chats .chats-container') as HTMLDivElement; private searchInput = document.getElementById('global-search') as HTMLInputElement; private toolsBtn = this.sidebarEl.querySelector('.sidebar-tools-button') as HTMLButtonElement; private searchContainer = this.sidebarEl.querySelector('#search-container') as HTMLDivElement; - + private listsContainer: HTMLDivElement = null; private searchMessagesList: HTMLUListElement = null; - + private log = logger('SL'); - + private peerID = 0; - + private minMsgID = 0; + private loadedCount = 0; + private foundCount = 0; + private offsetRate = 0; + private searchPromise: Promise = null; + private searchTimeout: number = 0; + private query = ''; + constructor() { this.listsContainer = scrollable(this.searchContainer); this.searchMessagesList = document.createElement('ul'); - + + this.listsContainer.onscroll = this.onSidebarScroll.bind(this); + this.searchContainer.append(this.listsContainer); - + appDialogsManager.setListClickListener(this.searchMessagesList); - + this.searchInput.addEventListener('focus', (e) => { this.toolsBtn.classList.remove('tgico-menu'); this.toolsBtn.classList.add('tgico-back'); this.searchContainer.classList.add('active'); - + if(!this.searchInput.value) { this.searchMessagesList.innerHTML = ''; } - + this.searchInput.addEventListener('blur', (e) => { if(!this.searchInput.value) { this.toolsBtn.classList.add('tgico-menu'); this.toolsBtn.classList.remove('tgico-back'); this.searchContainer.classList.remove('active'); } - - this.peerID = 0; + + /* this.peerID = 0; + this.loadedCount = 0; + this.minMsgID = 0; */ }, {once: true}); }); - + this.searchInput.addEventListener('input', (e) => { //console.log('messageInput input', this.innerText, serializeNodes(Array.from(messageInput.childNodes))); let value = this.searchInput.value; this.log('input', value); - + if(this.listsContainer.contains(this.searchMessagesList)) { this.listsContainer.removeChild(this.searchMessagesList) } - + if(!value.trim()) { return; } - appMessagesManager.getSearch(this.peerID, value, null, 0, 20).then(res => { - if(this.searchInput.value != value) { - return; - } - - this.log('input search result:', res); - - let {count, history} = res; - - this.searchMessagesList.innerHTML = ''; - - history.forEach((msgID: number) => { - let message = appMessagesManager.getMessage(msgID); - let originalDialog = appMessagesManager.getDialogByPeerID(message.peerID)[0]; - - if(!originalDialog) { - this.log.warn('no original dialog by message:', msgID); - return; - } - - let {dialog, dom} = appDialogsManager.addDialog(originalDialog, this.searchMessagesList, false); - appDialogsManager.setLastMessage(dialog, message, dom); - }); - + this.query = value; + this.minMsgID = 0; + this.loadedCount = 0; + this.foundCount = 0; + this.offsetRate = 0; + this.searchMessagesList.innerHTML = ''; + this.searchPromise = null; + this.searchMore().then(() => { this.listsContainer.append(this.searchMessagesList); }); }); - + this.toolsBtn.addEventListener('click', () => { if(this.toolsBtn.classList.contains('tgico-back')) { this.searchInput.value = ''; @@ -95,15 +92,89 @@ class AppSidebarLeft { this.searchContainer.classList.remove('active'); } }); - } + window.addEventListener('resize', () => { + setTimeout(() => this.onSidebarScroll(), 0); + }); + } + + public onSidebarScroll() { + let elements = Array.from(this.searchMessagesList.childNodes).slice(-5); + for(let li of elements) { + if(isElementInViewport(li)) { + this.log('Will load more search'); + + if(!this.searchTimeout) { + this.searchTimeout = setTimeout(() => { + this.searchMore(); + this.searchTimeout = 0; + }, 0); + } + + break; + } + } + } + public beginSearch(peerID?: number) { if(peerID) { this.peerID = peerID; } - + this.searchInput.focus(); } + + private searchMore() { + if(this.searchPromise) return this.searchPromise; + + let query = this.query; + + if(this.loadedCount != 0 && this.loadedCount >= this.foundCount) { + return Promise.resolve(); + } + + let maxID = 0;//appMessagesIDsManager.getMessageIDInfo(this.minMsgID)[0] - 1; + + return this.searchPromise = appMessagesManager.getSearch(this.peerID, query, null, maxID, 20, this.offsetRate).then(res => { + this.searchPromise = null; + + if(this.searchInput.value != query) { + return; + } + + this.log('input search result:', this.peerID, query, null, maxID, 20, res); + + let {count, history, next_rate} = res; + + if(history[0] == this.minMsgID) { + history.shift(); + } + + history.forEach((msgID: number) => { + let message = appMessagesManager.getMessage(msgID); + let originalDialog = appMessagesManager.getDialogByPeerID(message.peerID)[0]; + + if(!originalDialog) { + this.log.warn('no original dialog by message:', msgID); + return; + } + + let {dialog, dom} = appDialogsManager.addDialog(originalDialog, this.searchMessagesList, false); + appDialogsManager.setLastMessage(dialog, message, dom); + }); + + this.minMsgID = history[history.length - 1]; + this.offsetRate = next_rate; + this.loadedCount += history.length; + + if(!this.foundCount) { + this.foundCount = count; + } + }).catch(err => { + this.log.error('search error', err); + this.searchPromise = null; + }); + } } export default new AppSidebarLeft(); diff --git a/src/lib/appManagers/appSidebarRight.ts b/src/lib/appManagers/appSidebarRight.ts index 078a542c..13e0f979 100644 --- a/src/lib/appManagers/appSidebarRight.ts +++ b/src/lib/appManagers/appSidebarRight.ts @@ -9,7 +9,6 @@ import { RichTextProcessor } from "../richtextprocessor"; import { logger } from "../polyfill"; import appImManager from "./appImManager"; import appMediaViewer from "./appMediaViewer"; -import appDocsManager from "./appDocsManager"; class AppSidebarRight { public sidebarEl = document.querySelector('.profile-container') as HTMLDivElement; diff --git a/src/lib/services.ts b/src/lib/services.ts index 8f5d4f8c..b0912874 100644 --- a/src/lib/services.ts +++ b/src/lib/services.ts @@ -30,18 +30,6 @@ export const appStickersManager = AppStickersManager; export const appSidebarRight = AppSidebarRight; export const appSidebarLeft = AppSidebarLeft; - -export type DialogDom = { - avatarDiv: HTMLDivElement, - captionDiv: HTMLDivElement, - titleSpan: HTMLSpanElement, - statusSpan: HTMLSpanElement, - lastTimeSpan: HTMLSpanElement, - unreadMessagesSpan: HTMLSpanElement, - lastMessageSpan: HTMLSpanElement, - listEl: HTMLLIElement -}; - (window as any).Services = { appUsersManager, appChatsManager, diff --git a/src/scss/partials/_chat.scss b/src/scss/partials/_chat.scss index 60e5b73a..0a1c56d1 100644 --- a/src/scss/partials/_chat.scss +++ b/src/scss/partials/_chat.scss @@ -237,7 +237,8 @@ .box.web { width: min-content; - max-width: min-content; + /* max-width: min-content; */ + max-width: 100%; } } @@ -248,7 +249,8 @@ } img, video { - object-fit: contain; + /* object-fit: contain; */ + object-fit: cover; } .emoji { @@ -361,14 +363,17 @@ &:not(.sticker) { .attachment { max-width: 380px; + max-height: 380px; } } &.video { .attachment { + //max-height: fit-content; + img { width: 100%; - height: 100%; + /* height: 100%; */ } } } diff --git a/src/scss/style.scss b/src/scss/style.scss index 8860a77e..b7b83546 100644 --- a/src/scss/style.scss +++ b/src/scss/style.scss @@ -32,6 +32,7 @@ $time-size: 12px; @import "partials/chat"; @import "partials/sidebar"; @import "partials/leftSidebar"; +@import "partials/mediaViewer"; html, body { height: 100%; @@ -1077,136 +1078,7 @@ $width: 100px; } } -.media-viewer { - position: fixed; - top: 0; - left: 0; - right: 0; - bottom: 0; - background: rgba(0, 0, 0, .9); - /* color: $darkgrey; */ - display: flex; - align-items: center; - justify-content: center; - - .media-viewer-author { - position: absolute; - top: 0; - left: 0; - height: 60px; - padding: 8px 8px 8px 80px; - display: flex; - flex-direction: column; - justify-content: center; - color: #8b8b8b; - - .user-avatar { - width: 44px; - height: 44px; - position: absolute; - top: 8px; - left: 20px; - } - - .media-viewer-name { - font-weight: 500; - } - - .media-viewer-date { - font-size: 15px; - } - } - - .media-viewer-buttons { - position: absolute; - top: 0; - right: 0; - display: flex; - flex-flow: row nowrap; - padding: 8px; - - .btn-icon { - margin: 0 .25rem; - } - } - .media-viewer-content { - display: flex; - flex-direction: column; - justify-content: center; - height: 100%; - - .media-viewer-stub { - flex: 1; - } - - .media-viewer-container { - align-self: center; - position: relative; - } - - .media-viewer-media { - display: flex; - align-items: center; - justify-content: center; - - > img, > video { - max-height: calc(100vh - 100px); - max-width: calc(100vw - 16px); - } - } - - .media-viewer-switcher-left, .media-viewer-switcher-right { - position: absolute; - left: 0; - top: 0; - width: 10rem; - height: 100%; - cursor: pointer; - - &:hover { - > span { - opacity: 1; - } - } - } - - .media-viewer-switcher-right { - left: auto; - right: 0; - } - - .media-viewer-prev-button, .media-viewer-next-button { - cursor: pointer; - position: absolute; - color: #fff; - font-size: 3rem; - left: 2rem; - top: 50%; - transform: translateY(-50%) rotate(90deg); - opacity: 0; - transition: .2s opacity; - z-index: 3; - /* box-shadow: 0 1px 2px 0 rgba(16, 35, 47, 0.07); */ - } - - .media-viewer-next-button { - left: auto; - right: 2rem; - transform: translateY(-50%) rotate(-90deg); - } - - .media-viewer-caption { - flex: 1; - text-align: center; - display: flex; - flex-direction: column; - justify-content: center; - align-items: center; - color: $darkgrey; - } - } -} div.scrollable-y::-webkit-scrollbar { /* width: 4px; */ diff --git a/stats.json b/stats.json deleted file mode 100644 index 8635d3b0..00000000 --- a/stats.json +++ /dev/null @@ -1,9665 +0,0 @@ -{ - "errors": [], - "warnings": [ - "asset size limit: The following asset(s) exceed the recommended size limit (244 KiB).\nThis can impact web performance.\nAssets: \n bundle.js (1.09 MiB)", - "entrypoint size limit: The following entrypoint(s) combined asset size exceeds the recommended limit (244 KiB). This can impact web performance.\nEntrypoints:\n main (1.09 MiB)\n bundle.js\n", - "webpack performance recommendations: \nYou can limit the size of your bundles by using import() or require.ensure to lazy load some parts of your application.\nFor more info visit https://webpack.js.org/guides/code-splitting/" - ], - "version": "4.41.2", - "hash": "e5bb06c076e3ed69a540", - "time": 8680, - "builtAt": 1579094416874, - "publicPath": "", - "outputPath": "/Users/kuzmenko/Documents/projects/tweb/public", - "assetsByChunkName": { - "main": "bundle.js" - }, - "assets": [ - { - "name": "assets/fonts/tgico.eot", - "size": 21788, - "chunks": [], - "chunkNames": [], - "info": {}, - "emitted": true - }, - { - "name": "assets/fonts/tgico.svg", - "size": 78299, - "chunks": [], - "chunkNames": [], - "info": {}, - "emitted": true - }, - { - "name": "assets/fonts/tgico.svg.br", - "size": 17893, - "chunks": [], - "chunkNames": [], - "info": {}, - "emitted": true - }, - { - "name": "assets/fonts/tgico.ttf", - "size": 21632, - "chunks": [], - "chunkNames": [], - "info": {}, - "emitted": true - }, - { - "name": "assets/fonts/tgico.woff", - "size": 21708, - "chunks": [], - "chunkNames": [], - "info": {}, - "emitted": true - }, - { - "name": "assets/img/msg-tail-left.svg", - "size": 1026, - "chunks": [], - "chunkNames": [], - "info": {}, - "emitted": true - }, - { - "name": "assets/img/msg-tail-right.svg", - "size": 973, - "chunks": [], - "chunkNames": [], - "info": {}, - "emitted": true - }, - { - "name": "bundle.js", - "size": 1142787, - "chunks": [ - 0 - ], - "chunkNames": [ - "main" - ], - "info": {}, - "emitted": true, - "isOverSizeLimit": true - }, - { - "name": "bundle.js.br", - "size": 225779, - "chunks": [], - "chunkNames": [], - "info": {}, - "emitted": true - }, - { - "name": "c05c8d5242c7b2494d71.worker.js", - "size": 105265, - "chunks": [], - "chunkNames": [], - "info": { - "immutable": true - }, - "emitted": true - }, - { - "name": "c05c8d5242c7b2494d71.worker.js.br", - "size": 30801, - "chunks": [], - "chunkNames": [], - "info": {}, - "emitted": true - } - ], - "filteredAssets": 0, - "entrypoints": { - "main": { - "chunks": [ - 0 - ], - "assets": [ - "bundle.js" - ], - "children": {}, - "childAssets": {}, - "isOverSizeLimit": true - } - }, - "namedChunkGroups": { - "main": { - "chunks": [ - 0 - ], - "assets": [ - "bundle.js" - ], - "children": {}, - "childAssets": {}, - "isOverSizeLimit": true - } - }, - "chunks": [ - { - "id": 0, - "rendered": true, - "initial": true, - "entry": true, - "size": 2285829, - "names": [ - "main" - ], - "files": [ - "bundle.js" - ], - "hash": "744b15056b7f610a19ae", - "siblings": [], - "parents": [], - "children": [], - "childrenByOrder": {}, - "modules": [ - { - "id": 0, - "identifier": "/Users/kuzmenko/Documents/projects/tweb/src/lib/utils.js", - "name": "./src/lib/utils.js", - "index": 29, - "index2": 26, - "size": 19444, - "cacheable": true, - "built": true, - "optional": false, - "prefetched": false, - "chunks": [ - 0 - ], - "issuer": "/Users/kuzmenko/Documents/projects/tweb/node_modules/ts-loader/index.js!/Users/kuzmenko/Documents/projects/tweb/src/lib/mtproto.ts", - "issuerId": 2, - "issuerName": "./src/lib/mtproto.ts", - "issuerPath": [ - { - "id": 18, - "identifier": "/Users/kuzmenko/Documents/projects/tweb/node_modules/ts-loader/index.js!/Users/kuzmenko/Documents/projects/tweb/src/index.ts", - "name": "./src/index.ts", - "profile": { - "factory": 17, - "building": 2295 - } - }, - { - "id": 2, - "identifier": "/Users/kuzmenko/Documents/projects/tweb/node_modules/ts-loader/index.js!/Users/kuzmenko/Documents/projects/tweb/src/lib/mtproto.ts", - "name": "./src/lib/mtproto.ts", - "profile": { - "factory": 1354, - "building": 0, - "dependencies": 287 - } - } - ], - "profile": { - "factory": 1950, - "building": 50, - "dependencies": 703 - }, - "failed": false, - "errors": 0, - "warnings": 0, - "assets": [], - "reasons": [ - { - "moduleId": 2, - "moduleIdentifier": "/Users/kuzmenko/Documents/projects/tweb/node_modules/ts-loader/index.js!/Users/kuzmenko/Documents/projects/tweb/src/lib/mtproto.ts", - "module": "./src/lib/mtproto.ts", - "moduleName": "./src/lib/mtproto.ts", - "type": "cjs require", - "userRequest": "./utils", - "loc": "58:14-32" - }, - { - "moduleId": 12, - "moduleIdentifier": "/Users/kuzmenko/Documents/projects/tweb/node_modules/ts-loader/index.js!/Users/kuzmenko/Documents/projects/tweb/src/lib/services.ts", - "module": "./src/lib/services.ts", - "moduleName": "./src/lib/services.ts", - "type": "cjs require", - "userRequest": "./utils", - "loc": "38:14-32" - }, - { - "moduleId": 15, - "moduleIdentifier": "/Users/kuzmenko/Documents/projects/tweb/node_modules/ts-loader/index.js!/Users/kuzmenko/Documents/projects/tweb/src/lib/tl_utils.ts", - "module": "./src/lib/tl_utils.ts", - "moduleName": "./src/lib/tl_utils.ts", - "type": "cjs require", - "userRequest": "./utils", - "loc": "17:14-32" - }, - { - "moduleId": 16, - "moduleIdentifier": "/Users/kuzmenko/Documents/projects/tweb/node_modules/ts-loader/index.js!/Users/kuzmenko/Documents/projects/tweb/src/lib/cryptoworker.ts", - "module": "./src/lib/cryptoworker.ts", - "moduleName": "./src/lib/cryptoworker.ts", - "type": "cjs require", - "userRequest": "./utils", - "loc": "6:14-32" - }, - { - "moduleId": 17, - "moduleIdentifier": "/Users/kuzmenko/Documents/projects/tweb/src/lib/richtextprocessor.js", - "module": "./src/lib/richtextprocessor.js", - "moduleName": "./src/lib/richtextprocessor.js", - "type": "harmony side effect evaluation", - "userRequest": "./utils", - "loc": "1:0-59" - }, - { - "moduleId": 17, - "moduleIdentifier": "/Users/kuzmenko/Documents/projects/tweb/src/lib/richtextprocessor.js", - "module": "./src/lib/richtextprocessor.js", - "moduleName": "./src/lib/richtextprocessor.js", - "type": "harmony import specifier", - "userRequest": "./utils", - "loc": "108:14-26" - }, - { - "moduleId": 17, - "moduleIdentifier": "/Users/kuzmenko/Documents/projects/tweb/src/lib/richtextprocessor.js", - "module": "./src/lib/richtextprocessor.js", - "moduleName": "./src/lib/richtextprocessor.js", - "type": "harmony import specifier", - "userRequest": "./utils", - "loc": "345:32-36" - }, - { - "moduleId": 17, - "moduleIdentifier": "/Users/kuzmenko/Documents/projects/tweb/src/lib/richtextprocessor.js", - "module": "./src/lib/richtextprocessor.js", - "moduleName": "./src/lib/richtextprocessor.js", - "type": "harmony import specifier", - "userRequest": "./utils", - "loc": "367:11-25" - }, - { - "moduleId": 17, - "moduleIdentifier": "/Users/kuzmenko/Documents/projects/tweb/src/lib/richtextprocessor.js", - "module": "./src/lib/richtextprocessor.js", - "moduleName": "./src/lib/richtextprocessor.js", - "type": "harmony import specifier", - "userRequest": "./utils", - "loc": "398:8-22" - }, - { - "moduleId": 17, - "moduleIdentifier": "/Users/kuzmenko/Documents/projects/tweb/src/lib/richtextprocessor.js", - "module": "./src/lib/richtextprocessor.js", - "moduleName": "./src/lib/richtextprocessor.js", - "type": "harmony import specifier", - "userRequest": "./utils", - "loc": "426:10-24" - }, - { - "moduleId": 17, - "moduleIdentifier": "/Users/kuzmenko/Documents/projects/tweb/src/lib/richtextprocessor.js", - "module": "./src/lib/richtextprocessor.js", - "moduleName": "./src/lib/richtextprocessor.js", - "type": "harmony import specifier", - "userRequest": "./utils", - "loc": "439:10-24" - }, - { - "moduleId": 17, - "moduleIdentifier": "/Users/kuzmenko/Documents/projects/tweb/src/lib/richtextprocessor.js", - "module": "./src/lib/richtextprocessor.js", - "moduleName": "./src/lib/richtextprocessor.js", - "type": "harmony import specifier", - "userRequest": "./utils", - "loc": "457:10-24" - }, - { - "moduleId": 17, - "moduleIdentifier": "/Users/kuzmenko/Documents/projects/tweb/src/lib/richtextprocessor.js", - "module": "./src/lib/richtextprocessor.js", - "moduleName": "./src/lib/richtextprocessor.js", - "type": "harmony import specifier", - "userRequest": "./utils", - "loc": "468:10-24" - }, - { - "moduleId": 17, - "moduleIdentifier": "/Users/kuzmenko/Documents/projects/tweb/src/lib/richtextprocessor.js", - "module": "./src/lib/richtextprocessor.js", - "moduleName": "./src/lib/richtextprocessor.js", - "type": "harmony import specifier", - "userRequest": "./utils", - "loc": "470:10-24" - }, - { - "moduleId": 17, - "moduleIdentifier": "/Users/kuzmenko/Documents/projects/tweb/src/lib/richtextprocessor.js", - "module": "./src/lib/richtextprocessor.js", - "moduleName": "./src/lib/richtextprocessor.js", - "type": "harmony import specifier", - "userRequest": "./utils", - "loc": "483:18-32" - }, - { - "moduleId": 17, - "moduleIdentifier": "/Users/kuzmenko/Documents/projects/tweb/src/lib/richtextprocessor.js", - "module": "./src/lib/richtextprocessor.js", - "moduleName": "./src/lib/richtextprocessor.js", - "type": "harmony import specifier", - "userRequest": "./utils", - "loc": "490:12-26" - }, - { - "moduleId": 17, - "moduleIdentifier": "/Users/kuzmenko/Documents/projects/tweb/src/lib/richtextprocessor.js", - "module": "./src/lib/richtextprocessor.js", - "moduleName": "./src/lib/richtextprocessor.js", - "type": "harmony import specifier", - "userRequest": "./utils", - "loc": "506:76-90" - }, - { - "moduleId": 17, - "moduleIdentifier": "/Users/kuzmenko/Documents/projects/tweb/src/lib/richtextprocessor.js", - "module": "./src/lib/richtextprocessor.js", - "moduleName": "./src/lib/richtextprocessor.js", - "type": "harmony import specifier", - "userRequest": "./utils", - "loc": "536:10-24" - }, - { - "moduleId": 17, - "moduleIdentifier": "/Users/kuzmenko/Documents/projects/tweb/src/lib/richtextprocessor.js", - "module": "./src/lib/richtextprocessor.js", - "moduleName": "./src/lib/richtextprocessor.js", - "type": "harmony import specifier", - "userRequest": "./utils", - "loc": "538:10-24" - }, - { - "moduleId": 17, - "moduleIdentifier": "/Users/kuzmenko/Documents/projects/tweb/src/lib/richtextprocessor.js", - "module": "./src/lib/richtextprocessor.js", - "moduleName": "./src/lib/richtextprocessor.js", - "type": "harmony import specifier", - "userRequest": "./utils", - "loc": "559:10-24" - }, - { - "moduleId": 17, - "moduleIdentifier": "/Users/kuzmenko/Documents/projects/tweb/src/lib/richtextprocessor.js", - "module": "./src/lib/richtextprocessor.js", - "moduleName": "./src/lib/richtextprocessor.js", - "type": "harmony import specifier", - "userRequest": "./utils", - "loc": "565:65-79" - }, - { - "moduleId": 17, - "moduleIdentifier": "/Users/kuzmenko/Documents/projects/tweb/src/lib/richtextprocessor.js", - "module": "./src/lib/richtextprocessor.js", - "moduleName": "./src/lib/richtextprocessor.js", - "type": "harmony import specifier", - "userRequest": "./utils", - "loc": "566:10-24" - }, - { - "moduleId": 17, - "moduleIdentifier": "/Users/kuzmenko/Documents/projects/tweb/src/lib/richtextprocessor.js", - "module": "./src/lib/richtextprocessor.js", - "moduleName": "./src/lib/richtextprocessor.js", - "type": "harmony import specifier", - "userRequest": "./utils", - "loc": "576:12-26" - }, - { - "moduleId": 39, - "moduleIdentifier": "/Users/kuzmenko/Documents/projects/tweb/node_modules/ts-loader/index.js!/Users/kuzmenko/Documents/projects/tweb/src/lib/mtnetworker.ts", - "module": "./src/lib/mtnetworker.ts", - "moduleName": "./src/lib/mtnetworker.ts", - "type": "cjs require", - "userRequest": "./utils", - "loc": "13:14-32" - }, - { - "moduleId": 41, - "moduleIdentifier": "/Users/kuzmenko/Documents/projects/tweb/node_modules/ts-loader/index.js!/Users/kuzmenko/Documents/projects/tweb/src/components/pageSignIn.ts", - "module": "./src/components/pageSignIn.ts", - "moduleName": "./src/components/pageSignIn.ts", - "type": "cjs require", - "userRequest": "../lib/utils", - "loc": "18:14-37" - } - ], - "usedExports": true, - "providedExports": [ - "dT", - "isObject", - "tsNow", - "safeReplaceObject", - "numberWithCommas", - "isElementInViewport", - "copy", - "ripple", - "encodeEntities", - "calcImageInBox", - "emojiUnicode", - "countryCodeEmoji", - "unifiedCountryCodeEmoji", - "SearchIndexManager" - ], - "optimizationBailout": [ - "ModuleConcatenation bailout: Module is referenced from these modules with unsupported syntax: ./src/components/pageSignIn.ts (referenced with cjs require), ./src/lib/cryptoworker.ts (referenced with cjs require), ./src/lib/mtnetworker.ts (referenced with cjs require), ./src/lib/mtproto.ts (referenced with cjs require), ./src/lib/services.ts (referenced with cjs require), ./src/lib/tl_utils.ts (referenced with cjs require)" - ], - "depth": 2, - "source": "/*!\r\n * Webogram v0.7.0 - messaging web application for MTProto\r\n * https://github.com/zhukov/webogram\r\n * Copyright (C) 2014 Igor Zhukov \r\n * https://github.com/zhukov/webogram/blob/master/LICENSE\r\n */\r\nvar _logTimer = (new Date()).getTime()\r\nexport function dT () {\r\n return '[' + (((new Date()).getTime() - _logTimer) / 1000).toFixed(3) + ']'\r\n}\r\n\r\nfunction checkClick (e, noprevent) {\r\n if (e.which == 1 && (e.ctrlKey || e.metaKey) || e.which == 2) {\r\n return true\r\n }\r\n\r\n if (!noprevent) {\r\n e.preventDefault()\r\n }\r\n\r\n return false\r\n}\r\n\r\nfunction isInDOM (element, parentNode) {\r\n if (!element) {\r\n return false\r\n }\r\n parentNode = parentNode || document.body\r\n if (element == parentNode) {\r\n return true\r\n }\r\n return isInDOM(element.parentNode, parentNode)\r\n}\r\n\r\nfunction checkDragEvent (e) {\r\n if (!e || e.target && (e.target.tagName == 'IMG' || e.target.tagName == 'A')) return false\r\n if (e.dataTransfer && e.dataTransfer.types) {\r\n for (var i = 0; i < e.dataTransfer.types.length; i++) {\r\n if (e.dataTransfer.types[i] == 'Files') {\r\n return true\r\n }\r\n }\r\n } else {\r\n return true\r\n }\r\n\r\n return false\r\n}\r\n\r\nfunction cancelEvent (event) {\r\n event = event || window.event\r\n if (event) {\r\n event = event.originalEvent || event\r\n\r\n if (event.stopPropagation) event.stopPropagation()\r\n if (event.preventDefault) event.preventDefault()\r\n event.returnValue = false\r\n event.cancelBubble = true\r\n }\r\n\r\n return false\r\n}\r\n\r\nfunction hasOnclick (element) {\r\n if (element.onclick ||\r\n element.getAttribute('ng-click')) {\r\n return true\r\n }\r\n var events = $._data(element, 'events')\r\n if (events && (events.click || events.mousedown)) {\r\n return true\r\n }\r\n return false\r\n}\r\n\r\nfunction getScrollWidth () {\r\n var outer = $('
').css({\r\n position: 'absolute',\r\n width: 100,\r\n height: 100,\r\n overflow: 'scroll',\r\n top: -9999\r\n }).appendTo($(document.body))\r\n\r\n var scrollbarWidth = outer[0].offsetWidth - outer[0].clientWidth\r\n outer.remove()\r\n\r\n return scrollbarWidth\r\n}\r\n\r\nfunction onCtrlEnter (textarea, cb) {\r\n $(textarea).on('keydown', function (e) {\r\n if (e.keyCode == 13 && (e.ctrlKey || e.metaKey)) {\r\n cb()\r\n return cancelEvent(e)\r\n }\r\n })\r\n}\r\n\r\nfunction setFieldSelection (field, from, to) {\r\n field = $(field)[0]\r\n try {\r\n field.focus()\r\n if (from === undefined || from === false) {\r\n from = field.value.length\r\n }\r\n if (to === undefined || to === false) {\r\n to = from\r\n }\r\n if (field.createTextRange) {\r\n var range = field.createTextRange()\r\n range.collapse(true)\r\n range.moveEnd('character', to)\r\n range.moveStart('character', from)\r\n range.select()\r\n }\r\n else if (field.setSelectionRange) {\r\n field.setSelectionRange(from, to)\r\n }\r\n } catch(e) {}\r\n}\r\n\r\nfunction getFieldSelection (field) {\r\n if (field.selectionStart) {\r\n return field.selectionStart\r\n }\r\n else if (!document.selection) {\r\n return 0\r\n }\r\n\r\n var c = '\\x01'\r\n var sel = document.selection.createRange()\r\n var txt = sel.text\r\n var dup = sel.duplicate()\r\n var len = 0\r\n\r\n try {\r\n dup.moveToElementText(field)\r\n } catch(e) {\r\n return 0\r\n }\r\n\r\n sel.text = txt + c\r\n len = dup.text.indexOf(c)\r\n sel.moveStart('character', -1)\r\n sel.text = ''\r\n\r\n // if (browser.msie && len == -1) {\r\n // return field.value.length\r\n // }\r\n return len\r\n}\r\n\r\nfunction getRichValue (field) {\r\n if (!field) {\r\n return ''\r\n }\r\n var lines = []\r\n var line = []\r\n\r\n getRichElementValue(field, lines, line)\r\n if (line.length) {\r\n lines.push(line.join(''))\r\n }\r\n\r\n var value = lines.join('\\n')\r\n value = value.replace(/\\u00A0/g, ' ')\r\n\r\n return value\r\n}\r\n\r\nfunction getRichValueWithCaret (field) {\r\n if (!field) {\r\n return []\r\n }\r\n var lines = []\r\n var line = []\r\n\r\n var sel = window.getSelection ? window.getSelection() : false\r\n var selNode\r\n var selOffset\r\n if (sel && sel.rangeCount) {\r\n var range = sel.getRangeAt(0)\r\n if (range.startContainer &&\r\n range.startContainer == range.endContainer &&\r\n range.startOffset == range.endOffset) {\r\n selNode = range.startContainer\r\n selOffset = range.startOffset\r\n }\r\n }\r\n\r\n getRichElementValue(field, lines, line, selNode, selOffset)\r\n\r\n if (line.length) {\r\n lines.push(line.join(''))\r\n }\r\n\r\n var value = lines.join('\\n')\r\n var caretPos = value.indexOf('\\x01')\r\n if (caretPos != -1) {\r\n value = value.substr(0, caretPos) + value.substr(caretPos + 1)\r\n }\r\n value = value.replace(/\\u00A0/g, ' ')\r\n\r\n return [value, caretPos]\r\n}\r\n\r\nfunction getRichElementValue (node, lines, line, selNode, selOffset) {\r\n if (node.nodeType == 3) { // TEXT\r\n if (selNode === node) {\r\n var value = node.nodeValue\r\n line.push(value.substr(0, selOffset) + '\\x01' + value.substr(selOffset))\r\n } else {\r\n line.push(node.nodeValue)\r\n }\r\n return\r\n }\r\n if (node.nodeType != 1) { // NON-ELEMENT\r\n return\r\n }\r\n var isSelected = (selNode === node)\r\n var isBlock = node.tagName == 'DIV' || node.tagName == 'P'\r\n var curChild\r\n if (isBlock && line.length || node.tagName == 'BR') {\r\n lines.push(line.join(''))\r\n line.splice(0, line.length)\r\n }\r\n else if (node.tagName == 'IMG') {\r\n if (node.alt) {\r\n line.push(node.alt)\r\n }\r\n }\r\n if (isSelected && !selOffset) {\r\n line.push('\\x01')\r\n }\r\n var curChild = node.firstChild\r\n while (curChild) {\r\n getRichElementValue(curChild, lines, line, selNode, selOffset)\r\n curChild = curChild.nextSibling\r\n }\r\n if (isSelected && selOffset) {\r\n line.push('\\x01')\r\n }\r\n if (isBlock && line.length) {\r\n lines.push(line.join(''))\r\n line.splice(0, line.length)\r\n }\r\n}\r\n\r\nfunction setRichFocus (field, selectNode, noCollapse) {\r\n field.focus()\r\n if (selectNode &&\r\n selectNode.parentNode == field &&\r\n !selectNode.nextSibling &&\r\n !noCollapse) {\r\n field.removeChild(selectNode)\r\n selectNode = null\r\n }\r\n if (window.getSelection && document.createRange) {\r\n var range = document.createRange()\r\n if (selectNode) {\r\n range.selectNode(selectNode)\r\n } else {\r\n range.selectNodeContents(field)\r\n }\r\n if (!noCollapse) {\r\n range.collapse(false)\r\n }\r\n\r\n var sel = window.getSelection()\r\n sel.removeAllRanges()\r\n sel.addRange(range)\r\n }\r\n else if (document.body.createTextRange !== undefined) {\r\n var textRange = document.body.createTextRange()\r\n textRange.moveToElementText(selectNode || field)\r\n if (!noCollapse) {\r\n textRange.collapse(false)\r\n }\r\n textRange.select()\r\n }\r\n}\r\n\r\nfunction getSelectedText () {\r\n var sel = (\r\n window.getSelection && window.getSelection() ||\r\n document.getSelection && document.getSelection() ||\r\n document.selection && document.selection.createRange().text || ''\r\n ).toString().replace(/^\\s+|\\s+$/g, '')\r\n\r\n return sel\r\n}\r\n\r\nfunction scrollToNode (scrollable, node, scroller) {\r\n var elTop = node.offsetTop - 15\r\n var elHeight = node.offsetHeight + 30\r\n var scrollTop = scrollable.scrollTop\r\n var viewportHeight = scrollable.clientHeight\r\n\r\n if (scrollTop > elTop) { // we are below the node to scroll\r\n scrollable.scrollTop = elTop\r\n $(scroller).nanoScroller({flash: true})\r\n }\r\n else if (scrollTop < elTop + elHeight - viewportHeight) { // we are over the node to scroll\r\n scrollable.scrollTop = elTop + elHeight - viewportHeight\r\n $(scroller).nanoScroller({flash: true})\r\n }\r\n}\r\n\r\nif (Config.Modes.animations &&\r\n typeof window.requestAnimationFrame == 'function') {\r\n window.onAnimationFrameCallback = function (cb) {\r\n return (function () {\r\n window.requestAnimationFrame(cb)\r\n })\r\n }\r\n} else {\r\n window.onAnimationFrameCallback = function (cb) {\r\n return cb\r\n }\r\n}\r\n\r\nfunction onContentLoaded (cb) {\r\n cb = onAnimationFrameCallback(cb)\r\n setZeroTimeout(cb)\r\n}\r\n\r\nexport function isObject(object) {\r\n return typeof(object) === 'object' && object !== null;\r\n}\r\n\r\nexport function tsNow (seconds) {\r\n var t = +new Date() + (window.tsOffset || 0)\r\n return seconds ? Math.floor(t / 1000) : t\r\n}\r\n\r\nexport function safeReplaceObject (wasObject, newObject) {\r\n for (var key in wasObject) {\r\n if (!newObject.hasOwnProperty(key) && key.charAt(0) != '$') {\r\n delete wasObject[key]\r\n }\r\n }\r\n for (var key in newObject) {\r\n if (newObject.hasOwnProperty(key)) {\r\n wasObject[key] = newObject[key]\r\n }\r\n }\r\n}\r\n\r\nexport function numberWithCommas(x) {\r\n var parts = x.toString().split(\".\");\r\n parts[0] = parts[0].replace(/\\B(?=(\\d{3})+(?!\\d))/g, \",\");\r\n return parts.join(\".\");\r\n}\r\n\r\nexport function isElementInViewport(el) {\r\n var rect = el.getBoundingClientRect(),\r\n vWidth = window.innerWidth || doc.documentElement.clientWidth,\r\n vHeight = window.innerHeight || doc.documentElement.clientHeight,\r\n efp = function (x, y) { return document.elementFromPoint(x, y) }; \r\n\r\n // Return false if it's not in the viewport\r\n if (rect.right < 0 || rect.bottom < 0 \r\n || rect.left > vWidth || rect.top > vHeight)\r\n return false;\r\n\r\n // Return true if any of its four corners are visible\r\n return (\r\n el.contains(efp(rect.left, rect.top))\r\n || el.contains(efp(rect.right, rect.top))\r\n || el.contains(efp(rect.right, rect.bottom))\r\n || el.contains(efp(rect.left, rect.bottom))\r\n );\r\n}\r\n\r\nexport function copy(obj) {\r\n //in case of premitives\r\n if(obj===null || typeof obj !== \"object\"){\r\n return obj;\r\n }\r\n \r\n //date objects should be \r\n if(obj instanceof Date){\r\n return new Date(obj.getTime());\r\n }\r\n \r\n //handle Array\r\n if(Array.isArray(obj)){\r\n var clonedArr = [];\r\n obj.forEach(function(element){\r\n clonedArr.push(copy(element))\r\n });\r\n return clonedArr;\r\n }\r\n \r\n //lastly, handle objects\r\n let clonedObj = new obj.constructor();\r\n for(var prop in obj){\r\n if(obj.hasOwnProperty(prop)){\r\n clonedObj[prop] = copy(obj[prop]);\r\n }\r\n }\r\n return clonedObj;\r\n}\r\n\r\nexport function ripple(elem/* : HTMLElement */) {\r\n elem.addEventListener('mousedown', function(/* this: typeof elem, */e) {\r\n let rect = this.getBoundingClientRect();\r\n\r\n const startTime = Date.now();\r\n const animationTime = 350;\r\n\r\n let X = e.clientX - rect.left;\r\n let Y = e.clientY - rect.top;\r\n let rippleDiv = document.createElement(\"div\");\r\n rippleDiv.classList.add(\"ripple\");\r\n rippleDiv.setAttribute(\"style\", \"top:\" + Y + \"px; left:\" + X + \"px;\");\r\n this.appendChild(rippleDiv);\r\n\r\n elem.addEventListener('mouseup', () => {\r\n let elapsed = Date.now() - startTime;\r\n\r\n setTimeout(() => {\r\n rippleDiv.parentElement.removeChild(rippleDiv);\r\n }, elapsed < animationTime ? animationTime - elapsed : 0);\r\n }, {once: true});\r\n });\r\n};\r\n\r\nfunction listMergeSorted (list1, list2) {\r\n list1 = list1 || []\r\n list2 = list2 || []\r\n\r\n var result = copy(list1);\r\n\r\n var minID = list1.length ? list1[list1.length - 1] : 0xFFFFFFFF\r\n for (var i = 0; i < list2.length; i++) {\r\n if (list2[i] < minID) {\r\n result.push(list2[i])\r\n }\r\n }\r\n\r\n return result\r\n}\r\n\r\nfunction listUniqSorted (list) {\r\n list = list || []\r\n var resultList = []\r\n var prev = false\r\n for (var i = 0; i < list.length; i++) {\r\n if (list[i] !== prev) {\r\n resultList.push(list[i])\r\n }\r\n prev = list[i]\r\n }\r\n\r\n return resultList\r\n}\r\n\r\nfunction templateUrl (tplName) {\r\n var forceLayout = {\r\n confirm_modal: 'desktop',\r\n error_modal: 'desktop',\r\n media_modal_layout: 'desktop',\r\n slider: 'desktop',\r\n reply_message: 'desktop',\r\n full_round: 'desktop',\r\n message_body: 'desktop',\r\n message_media: 'desktop',\r\n message_attach_game: 'desktop',\r\n forwarded_messages: 'desktop',\r\n chat_invite_link_modal: 'desktop',\r\n reply_markup: 'desktop',\r\n short_message: 'desktop',\r\n pinned_message: 'desktop',\r\n channel_edit_modal: 'desktop',\r\n megagroup_edit_modal: 'desktop',\r\n inline_results: 'desktop',\r\n composer_dropdown: 'desktop',\r\n peer_pinned_message_bar: 'desktop',\r\n report_msgs_modal: 'desktop'\r\n }\r\n var layout = forceLayout[tplName] || (Config.Mobile ? 'mobile' : 'desktop')\r\n return 'partials/' + layout + '/' + tplName + '.html'\r\n}\r\n\r\nexport function encodeEntities (value) {\r\n return value.replace(/&/g, '&').replace(/[\\uD800-\\uDBFF][\\uDC00-\\uDFFF]/g, function (value) {\r\n var hi = value.charCodeAt(0)\r\n var low = value.charCodeAt(1)\r\n return '&#' + (((hi - 0xD800) * 0x400) + (low - 0xDC00) + 0x10000) + ';'\r\n }).replace(/([^\\#-~| |!])/g, function (value) { // non-alphanumeric\r\n return '&#' + value.charCodeAt(0) + ';'\r\n }).replace(//g, '>')\r\n}\r\n\r\nexport function calcImageInBox (imageW, imageH, boxW, boxH, noZooom) {\r\n var boxedImageW = boxW\r\n var boxedImageH = boxH\r\n\r\n if ((imageW / imageH) > (boxW / boxH)) {\r\n boxedImageH = parseInt(imageH * boxW / imageW)\r\n }else {\r\n boxedImageW = parseInt(imageW * boxH / imageH)\r\n if (boxedImageW > boxW) {\r\n boxedImageH = parseInt(boxedImageH * boxW / boxedImageW)\r\n boxedImageW = boxW\r\n }\r\n }\r\n\r\n // if (Config.Navigator.retina) {\r\n // imageW = Math.floor(imageW / 2)\r\n // imageH = Math.floor(imageH / 2)\r\n // }\r\n\r\n if (noZooom && boxedImageW >= imageW && boxedImageH >= imageH) {\r\n boxedImageW = imageW\r\n boxedImageH = imageH\r\n }\r\n\r\n return {w: boxedImageW, h: boxedImageH}\r\n}\r\n\r\n/**\r\n * emojiUnicode\r\n * Get the unicode code of an emoji in base 16.\r\n *\r\n * @name emojiUnicode\r\n * @function\r\n * @param {String} input The emoji character.\r\n * @returns {String} The base 16 unicode code.\r\n */\r\nexport function emojiUnicode (input) {\r\n return emojiUnicode.raw(input).split(' ').map(val => parseInt(val).toString(16)).join('-').toUpperCase();\r\n}\r\n\r\n/**\r\n* emojiunicode.raw\r\n* Get the unicode code points of an emoji in base 16.\r\n*\r\n* @name emojiunicode.raw\r\n* @function\r\n* @param {String} input The emoji character.\r\n* @returns {String} The unicode code points.\r\n*/\r\nemojiUnicode.raw = function (input) {\r\n if(input.length === 1) {\r\n return input.charCodeAt(0).toString();\r\n } else if(input.length > 1) {\r\n const pairs = [];\r\n for (var i = 0; i < input.length; i++) {\r\n if (\r\n // high surrogate\r\n input.charCodeAt(i) >= 0xd800 && input.charCodeAt(i) <= 0xdbff\r\n ) {\r\n if (\r\n input.charCodeAt(i + 1) >= 0xdc00 && input.charCodeAt(i + 1) <= 0xdfff\r\n ) {\r\n // low surrogate\r\n pairs.push(\r\n (input.charCodeAt(i) - 0xd800) * 0x400\r\n + (input.charCodeAt(i + 1) - 0xdc00) + 0x10000\r\n );\r\n }\r\n } else if (input.charCodeAt(i) < 0xd800 || input.charCodeAt(i) > 0xdfff) {\r\n // modifiers and joiners\r\n pairs.push(input.charCodeAt(i))\r\n }\r\n }\r\n return pairs.join(' ');\r\n }\r\n\r\n return '';\r\n};\r\n\r\n// country code regex\r\nconst CC_REGEX = /^[a-z]{2}$/i;\r\n\r\n// offset between uppercase ascii and regional indicator symbols\r\nconst OFFSET = 127397;\r\n\r\n/**\r\n * convert country code to corresponding emoji flag\r\n * @param {string} cc - country code string\r\n * @returns {string} country code emoji\r\n */\r\nexport function countryCodeEmoji(cc/* : string */) {\r\n if(!CC_REGEX.test(cc)) {\r\n const type = typeof cc;\r\n throw new TypeError(\r\n `cc argument must be an ISO 3166-1 alpha-2 string, but got '${\r\n type === 'string' ? cc : type\r\n }' instead.`,\r\n );\r\n }\r\n\r\n const chars = [...cc.toUpperCase()].map(c => c.charCodeAt(0) + OFFSET);\r\n console.log(chars);\r\n return String.fromCodePoint(...chars);\r\n}\r\n\r\nexport function unifiedCountryCodeEmoji(cc/* : string */) {\r\n if(!CC_REGEX.test(cc)) {\r\n const type = typeof cc;\r\n throw new TypeError(\r\n `cc argument must be an ISO 3166-1 alpha-2 string, but got '${\r\n type === 'string' ? cc : type\r\n }' instead.`,\r\n );\r\n }\r\n\r\n const chars = [...cc.toUpperCase()].map(c => c.charCodeAt(0) + OFFSET);\r\n return chars.map(c => c.toString(16).toUpperCase()).join('-');\r\n}\r\n\r\nfunction versionCompare (ver1, ver2) {\r\n if (typeof ver1 !== 'string') {\r\n ver1 = ''\r\n }\r\n if (typeof ver2 !== 'string') {\r\n ver2 = ''\r\n }\r\n ver1 = ver1.replace(/^\\s+|\\s+$/g, '').split('.')\r\n ver2 = ver2.replace(/^\\s+|\\s+$/g, '').split('.')\r\n\r\n var a = Math.max(ver1.length, ver2.length), i\r\n\r\n for (i = 0; i < a; i++) {\r\n if (ver1[i] == ver2[i]) {\r\n continue\r\n }\r\n if (ver1[i] > ver2[i]) {\r\n return 1\r\n } else {\r\n return -1\r\n }\r\n }\r\n\r\n return 0\r\n}\r\n\r\n\r\n var badCharsRe = /[`~!@#$%^&*()\\-_=+\\[\\]\\\\|{}'\";:\\/?.>,<\\s]+/g,\r\n trimRe = /^\\s+|\\s$/g\r\n\r\n function createIndex () {\r\n return {\r\n shortIndexes: {},\r\n fullTexts: {}\r\n }\r\n }\r\n\r\n function cleanSearchText (text) {\r\n var hasTag = text.charAt(0) == '%'\r\n text = text.replace(badCharsRe, ' ').replace(trimRe, '')\r\n text = text.replace(/[^A-Za-z0-9]/g, function (ch) {\r\n var latinizeCh = Config.LatinizeMap[ch]\r\n return latinizeCh !== undefined ? latinizeCh : ch\r\n })\r\n text = text.toLowerCase()\r\n if (hasTag) {\r\n text = '%' + text\r\n }\r\n\r\n return text\r\n }\r\n\r\n function cleanUsername (username) {\r\n return username && username.toLowerCase() || ''\r\n }\r\n\r\n function indexObject (id, searchText, searchIndex) {\r\n if (searchIndex.fullTexts[id] !== undefined) {\r\n return false\r\n }\r\n\r\n searchText = cleanSearchText(searchText)\r\n\r\n if (!searchText.length) {\r\n return false\r\n }\r\n\r\n var shortIndexes = searchIndex.shortIndexes\r\n\r\n searchIndex.fullTexts[id] = searchText\r\n\r\n searchText.split(' ').forEach(function(searchWord) {\r\n var len = Math.min(searchWord.length, 3),\r\n wordPart, i\r\n for (i = 1; i <= len; i++) {\r\n wordPart = searchWord.substr(0, i)\r\n if (shortIndexes[wordPart] === undefined) {\r\n shortIndexes[wordPart] = [id]\r\n } else {\r\n shortIndexes[wordPart].push(id)\r\n }\r\n }\r\n })\r\n }\r\n\r\n function search (query, searchIndex) {\r\n var shortIndexes = searchIndex.shortIndexes\r\n var fullTexts = searchIndex.fullTexts\r\n\r\n query = cleanSearchText(query)\r\n\r\n var queryWords = query.split(' ')\r\n var foundObjs = false,\r\n newFoundObjs, i\r\n var j, searchText\r\n var found\r\n\r\n for (i = 0; i < queryWords.length; i++) {\r\n newFoundObjs = shortIndexes[queryWords[i].substr(0, 3)]\r\n if (!newFoundObjs) {\r\n foundObjs = []\r\n break\r\n }\r\n if (foundObjs === false || foundObjs.length > newFoundObjs.length) {\r\n foundObjs = newFoundObjs\r\n }\r\n }\r\n\r\n newFoundObjs = {}\r\n\r\n for (j = 0; j < foundObjs.length; j++) {\r\n found = true\r\n searchText = fullTexts[foundObjs[j]]\r\n for (i = 0; i < queryWords.length; i++) {\r\n if (searchText.indexOf(queryWords[i]) == -1) {\r\n found = false\r\n break\r\n }\r\n }\r\n if (found) {\r\n newFoundObjs[foundObjs[j]] = true\r\n }\r\n }\r\n\r\n return newFoundObjs\r\n }\r\n\r\n let SearchIndexManager = {\r\n createIndex: createIndex,\r\n indexObject: indexObject,\r\n cleanSearchText: cleanSearchText,\r\n cleanUsername: cleanUsername,\r\n search: search\r\n };\r\n window.SearchIndexManager = SearchIndexManager;\r\n\r\n export {SearchIndexManager};\r\n//})(window)\r\n" - }, - { - "id": 1, - "identifier": "/Users/kuzmenko/Documents/projects/tweb/node_modules/ts-loader/index.js!/Users/kuzmenko/Documents/projects/tweb/src/lib/bin_utils.ts", - "name": "./src/lib/bin_utils.ts", - "index": 22, - "index2": 25, - "size": 28692, - "cacheable": true, - "built": true, - "optional": false, - "prefetched": false, - "chunks": [ - 0 - ], - "issuer": "/Users/kuzmenko/Documents/projects/tweb/node_modules/ts-loader/index.js!/Users/kuzmenko/Documents/projects/tweb/src/lib/mtproto.ts", - "issuerId": 2, - "issuerName": "./src/lib/mtproto.ts", - "issuerPath": [ - { - "id": 18, - "identifier": "/Users/kuzmenko/Documents/projects/tweb/node_modules/ts-loader/index.js!/Users/kuzmenko/Documents/projects/tweb/src/index.ts", - "name": "./src/index.ts", - "profile": { - "factory": 17, - "building": 2295 - } - }, - { - "id": 2, - "identifier": "/Users/kuzmenko/Documents/projects/tweb/node_modules/ts-loader/index.js!/Users/kuzmenko/Documents/projects/tweb/src/lib/mtproto.ts", - "name": "./src/lib/mtproto.ts", - "profile": { - "factory": 1354, - "building": 0, - "dependencies": 287 - } - } - ], - "profile": { - "factory": 1950, - "building": 50, - "dependencies": 703 - }, - "failed": false, - "errors": 0, - "warnings": 0, - "assets": [], - "reasons": [ - { - "moduleId": 2, - "moduleIdentifier": "/Users/kuzmenko/Documents/projects/tweb/node_modules/ts-loader/index.js!/Users/kuzmenko/Documents/projects/tweb/src/lib/mtproto.ts", - "module": "./src/lib/mtproto.ts", - "moduleName": "./src/lib/mtproto.ts", - "type": "cjs require", - "userRequest": "./bin_utils", - "loc": "57:18-40" - }, - { - "moduleId": 9, - "moduleIdentifier": "/Users/kuzmenko/Documents/projects/tweb/node_modules/ts-loader/index.js!/Users/kuzmenko/Documents/projects/tweb/src/lib/filemanager.ts", - "module": "./src/lib/filemanager.ts", - "moduleName": "./src/lib/filemanager.ts", - "type": "cjs require", - "userRequest": "./bin_utils", - "loc": "3:18-40" - }, - { - "moduleId": 12, - "moduleIdentifier": "/Users/kuzmenko/Documents/projects/tweb/node_modules/ts-loader/index.js!/Users/kuzmenko/Documents/projects/tweb/src/lib/services.ts", - "module": "./src/lib/services.ts", - "moduleName": "./src/lib/services.ts", - "type": "cjs require", - "userRequest": "./bin_utils", - "loc": "43:18-40" - }, - { - "moduleId": 15, - "moduleIdentifier": "/Users/kuzmenko/Documents/projects/tweb/node_modules/ts-loader/index.js!/Users/kuzmenko/Documents/projects/tweb/src/lib/tl_utils.ts", - "module": "./src/lib/tl_utils.ts", - "moduleName": "./src/lib/tl_utils.ts", - "type": "cjs require", - "userRequest": "./bin_utils", - "loc": "16:18-40" - }, - { - "moduleId": 16, - "moduleIdentifier": "/Users/kuzmenko/Documents/projects/tweb/node_modules/ts-loader/index.js!/Users/kuzmenko/Documents/projects/tweb/src/lib/cryptoworker.ts", - "module": "./src/lib/cryptoworker.ts", - "moduleName": "./src/lib/cryptoworker.ts", - "type": "cjs require", - "userRequest": "./bin_utils", - "loc": "7:18-40" - }, - { - "moduleId": 38, - "moduleIdentifier": "/Users/kuzmenko/Documents/projects/tweb/node_modules/ts-loader/index.js!/Users/kuzmenko/Documents/projects/tweb/src/lib/idb.ts", - "module": "./src/lib/idb.ts", - "moduleName": "./src/lib/idb.ts", - "type": "cjs require", - "userRequest": "./bin_utils", - "loc": "6:18-40" - }, - { - "moduleId": 39, - "moduleIdentifier": "/Users/kuzmenko/Documents/projects/tweb/node_modules/ts-loader/index.js!/Users/kuzmenko/Documents/projects/tweb/src/lib/mtnetworker.ts", - "module": "./src/lib/mtnetworker.ts", - "moduleName": "./src/lib/mtnetworker.ts", - "type": "cjs require", - "userRequest": "./bin_utils", - "loc": "14:18-40" - }, - { - "moduleId": 42, - "moduleIdentifier": "/Users/kuzmenko/Documents/projects/tweb/node_modules/ts-loader/index.js!/Users/kuzmenko/Documents/projects/tweb/src/components/pageAuthCode.ts", - "module": "./src/components/pageAuthCode.ts", - "moduleName": "./src/components/pageAuthCode.ts", - "type": "cjs require", - "userRequest": "../lib/bin_utils", - "loc": "13:18-45" - }, - { - "moduleId": 45, - "moduleIdentifier": "/Users/kuzmenko/Documents/projects/tweb/node_modules/ts-loader/index.js!/Users/kuzmenko/Documents/projects/tweb/src/components/pagePassword.ts", - "module": "./src/components/pagePassword.ts", - "moduleName": "./src/components/pagePassword.ts", - "type": "cjs require", - "userRequest": "../lib/bin_utils", - "loc": "13:18-45" - } - ], - "usedExports": true, - "providedExports": null, - "optimizationBailout": [ - "ModuleConcatenation bailout: Module is not an ECMAScript module" - ], - "depth": 2, - "source": "\"use strict\";\n/*!\n * Webogram v0.7.0 - messaging web application for MTProto\n * https://github.com/zhukov/webogram\n * Copyright (C) 2014 Igor Zhukov \n * https://github.com/zhukov/webogram/blob/master/LICENSE\n */\nvar __awaiter = (this && this.__awaiter) || function (thisArg, _arguments, P, generator) {\n function adopt(value) { return value instanceof P ? value : new P(function (resolve) { resolve(value); }); }\n return new (P || (P = Promise))(function (resolve, reject) {\n function fulfilled(value) { try { step(generator.next(value)); } catch (e) { reject(e); } }\n function rejected(value) { try { step(generator[\"throw\"](value)); } catch (e) { reject(e); } }\n function step(result) { result.done ? resolve(result.value) : adopt(result.value).then(fulfilled, rejected); }\n step((generator = generator.apply(thisArg, _arguments || [])).next());\n });\n};\nvar __generator = (this && this.__generator) || function (thisArg, body) {\n var _ = { label: 0, sent: function() { if (t[0] & 1) throw t[1]; return t[1]; }, trys: [], ops: [] }, f, y, t, g;\n return g = { next: verb(0), \"throw\": verb(1), \"return\": verb(2) }, typeof Symbol === \"function\" && (g[Symbol.iterator] = function() { return this; }), g;\n function verb(n) { return function (v) { return step([n, v]); }; }\n function step(op) {\n if (f) throw new TypeError(\"Generator is already executing.\");\n while (_) try {\n if (f = 1, y && (t = op[0] & 2 ? y[\"return\"] : op[0] ? y[\"throw\"] || ((t = y[\"return\"]) && t.call(y), 0) : y.next) && !(t = t.call(y, op[1])).done) return t;\n if (y = 0, t) op = [op[0] & 2, t.value];\n switch (op[0]) {\n case 0: case 1: t = op; break;\n case 4: _.label++; return { value: op[1], done: false };\n case 5: _.label++; y = op[1]; op = [0]; continue;\n case 7: op = _.ops.pop(); _.trys.pop(); continue;\n default:\n if (!(t = _.trys, t = t.length > 0 && t[t.length - 1]) && (op[0] === 6 || op[0] === 2)) { _ = 0; continue; }\n if (op[0] === 3 && (!t || (op[1] > t[0] && op[1] < t[3]))) { _.label = op[1]; break; }\n if (op[0] === 6 && _.label < t[1]) { _.label = t[1]; t = op; break; }\n if (t && _.label < t[2]) { _.label = t[2]; _.ops.push(op); break; }\n if (t[2]) _.ops.pop();\n _.trys.pop(); continue;\n }\n op = body.call(thisArg, _);\n } catch (e) { op = [6, e]; y = 0; } finally { f = t = 0; }\n if (op[0] & 5) throw op[1]; return { value: op[0] ? op[1] : void 0, done: true };\n }\n};\nvar __importStar = (this && this.__importStar) || function (mod) {\n if (mod && mod.__esModule) return mod;\n var result = {};\n if (mod != null) for (var k in mod) if (Object.hasOwnProperty.call(mod, k)) result[k] = mod[k];\n result[\"default\"] = mod;\n return result;\n};\nvar __importDefault = (this && this.__importDefault) || function (mod) {\n return (mod && mod.__esModule) ? mod : { \"default\": mod };\n};\nObject.defineProperty(exports, \"__esModule\", { value: true });\n// @ts-ignore\nvar jsbn_1 = require(\"jsbn\");\n// @ts-ignore\nvar Rusha = __importStar(require(\"rusha/dist/rusha.min.js\"));\nvar leemon_1 = require(\"leemon\");\n//import CryptoJS from 'crypto-js';\n// @ts-ignore\nvar pako_inflate_min_js_1 = __importDefault(require(\"pako/dist/pako_inflate.min.js\"));\nvar CryptoJS = require(\"./crypto.js\");\nrequire(\"./closure_long.js\");\nvar goog = this.goog;\nfunction bigint(num) {\n return new jsbn_1.BigInteger(num.toString(16), 16);\n}\nexports.bigint = bigint;\nfunction bigStringInt(strNum) {\n return new jsbn_1.BigInteger(strNum, 10);\n}\nexports.bigStringInt = bigStringInt;\n/* export function dHexDump (bytes) {\n var arr = []\n for (var i = 0; i < bytes.length; i++) {\n if (i && !(i % 2)) {\n if (!(i % 16)) {\n arr.push('\\n')\n } else if (!(i % 4)) {\n arr.push(' ')\n } else {\n arr.push(' ')\n }\n }\n arr.push((bytes[i] < 16 ? '0' : '') + bytes[i].toString(16))\n }\n\n console.log(arr.join(''))\n} */\nfunction bytesToHex(bytes) {\n bytes = bytes || [];\n var arr = [];\n for (var i = 0; i < bytes.length; i++) {\n arr.push((bytes[i] < 16 ? '0' : '') + (bytes[i] || 0).toString(16));\n }\n return arr.join('');\n}\nexports.bytesToHex = bytesToHex;\nfunction bytesFromHex(hexString) {\n var len = hexString.length, i;\n var start = 0;\n var bytes = [];\n if (hexString.length % 2) {\n bytes.push(parseInt(hexString.charAt(0), 16));\n start++;\n }\n for (i = start; i < len; i += 2) {\n bytes.push(parseInt(hexString.substr(i, 2), 16));\n }\n return bytes;\n}\nexports.bytesFromHex = bytesFromHex;\nfunction bytesToBase64(bytes) {\n var mod3;\n var result = '';\n for (var nLen = bytes.length, nUint24 = 0, nIdx = 0; nIdx < nLen; nIdx++) {\n mod3 = nIdx % 3;\n nUint24 |= bytes[nIdx] << (16 >>> mod3 & 24);\n if (mod3 === 2 || nLen - nIdx === 1) {\n result += String.fromCharCode(uint6ToBase64(nUint24 >>> 18 & 63), uint6ToBase64(nUint24 >>> 12 & 63), uint6ToBase64(nUint24 >>> 6 & 63), uint6ToBase64(nUint24 & 63));\n nUint24 = 0;\n }\n }\n return result.replace(/A(?=A$|$)/g, '=');\n}\nexports.bytesToBase64 = bytesToBase64;\nfunction uint6ToBase64(nUint6) {\n return nUint6 < 26\n ? nUint6 + 65\n : nUint6 < 52\n ? nUint6 + 71\n : nUint6 < 62\n ? nUint6 - 4\n : nUint6 === 62\n ? 43\n : nUint6 === 63\n ? 47\n : 65;\n}\nexports.uint6ToBase64 = uint6ToBase64;\nfunction base64ToBlob(base64str, mimeType) {\n var sliceSize = 1024;\n var byteCharacters = atob(base64str);\n var bytesLength = byteCharacters.length;\n var slicesCount = Math.ceil(bytesLength / sliceSize);\n var byteArrays = new Array(slicesCount);\n for (var sliceIndex = 0; sliceIndex < slicesCount; ++sliceIndex) {\n var begin = sliceIndex * sliceSize;\n var end = Math.min(begin + sliceSize, bytesLength);\n var bytes = new Array(end - begin);\n for (var offset = begin, i = 0; offset < end; ++i, ++offset) {\n bytes[i] = byteCharacters[offset].charCodeAt(0);\n }\n byteArrays[sliceIndex] = new Uint8Array(bytes);\n }\n return blobConstruct(byteArrays, mimeType);\n}\nexports.base64ToBlob = base64ToBlob;\nfunction dataUrlToBlob(url) {\n // var name = 'b64blob ' + url.length\n // console.time(name)\n var urlParts = url.split(',');\n var base64str = urlParts[1];\n var mimeType = urlParts[0].split(':')[1].split(';')[0];\n var blob = base64ToBlob(base64str, mimeType);\n // console.timeEnd(name)\n return blob;\n}\nexports.dataUrlToBlob = dataUrlToBlob;\nfunction blobConstruct(blobParts, mimeType) {\n if (mimeType === void 0) { mimeType = ''; }\n var blob;\n var safeMimeType = blobSafeMimeType(mimeType);\n try {\n blob = new Blob(blobParts, { type: safeMimeType });\n }\n catch (e) {\n // @ts-ignore\n var bb = new BlobBuilder;\n blobParts.forEach(function (blobPart) {\n bb.append(blobPart);\n });\n blob = bb.getBlob(safeMimeType);\n }\n return blob;\n}\nexports.blobConstruct = blobConstruct;\nfunction blobSafeMimeType(mimeType) {\n if ([\n 'image/jpeg',\n 'image/png',\n 'image/gif',\n 'image/webp',\n 'image/bmp',\n 'video/mp4',\n 'video/webm',\n 'video/quicktime',\n 'audio/ogg',\n 'audio/mpeg',\n 'audio/mp4',\n ].indexOf(mimeType) == -1) {\n return 'application/octet-stream';\n }\n return mimeType;\n}\nexports.blobSafeMimeType = blobSafeMimeType;\nfunction bytesCmp(bytes1, bytes2) {\n var len = bytes1.length;\n if (len != bytes2.length) {\n return false;\n }\n for (var i = 0; i < len; i++) {\n if (bytes1[i] != bytes2[i]) {\n return false;\n }\n }\n return true;\n}\nexports.bytesCmp = bytesCmp;\nfunction bytesXor(bytes1, bytes2) {\n var len = bytes1.length;\n var bytes = [];\n for (var i = 0; i < len; ++i) {\n bytes[i] = bytes1[i] ^ bytes2[i];\n }\n return bytes;\n}\nexports.bytesXor = bytesXor;\nfunction bytesToWords(bytes) {\n if (bytes instanceof ArrayBuffer) {\n bytes = new Uint8Array(bytes);\n }\n var len = bytes.length;\n var words = [];\n var i;\n for (i = 0; i < len; i++) {\n words[i >>> 2] |= bytes[i] << (24 - (i % 4) * 8);\n }\n return new CryptoJS.lib.WordArray.init(words, len);\n}\nfunction bytesFromWords(wordArray) {\n var words = wordArray.words;\n var sigBytes = wordArray.sigBytes;\n var bytes = [];\n for (var i = 0; i < sigBytes; i++) {\n bytes.push((words[i >>> 2] >>> (24 - (i % 4) * 8)) & 0xff);\n }\n return bytes;\n}\nfunction bytesFromBigInt(bigInt, len) {\n var bytes = bigInt.toByteArray();\n if (len && bytes.length < len) {\n var padding = [];\n for (var i = 0, needPadding = len - bytes.length; i < needPadding; i++) {\n padding[i] = 0;\n }\n if (bytes instanceof ArrayBuffer) {\n bytes = bufferConcat(padding, bytes);\n }\n else {\n bytes = padding.concat(bytes);\n }\n }\n else {\n while (!bytes[0] && (!len || bytes.length > len)) {\n bytes = bytes.slice(1);\n }\n }\n return bytes;\n}\nexports.bytesFromBigInt = bytesFromBigInt;\nfunction bytesFromLeemonBigInt(bigInt) {\n var str = leemon_1.bigInt2str(bigInt, 16);\n return bytesFromHex(str);\n}\nexports.bytesFromLeemonBigInt = bytesFromLeemonBigInt;\nfunction bytesToArrayBuffer(b) {\n return (new Uint8Array(b)).buffer;\n}\nexports.bytesToArrayBuffer = bytesToArrayBuffer;\nfunction convertToArrayBuffer(bytes) {\n // Be careful with converting subarrays!!\n if (bytes instanceof ArrayBuffer) {\n return bytes;\n }\n if (bytes.buffer !== undefined &&\n bytes.buffer.byteLength == bytes.length * bytes.BYTES_PER_ELEMENT) {\n return bytes.buffer;\n }\n return bytesToArrayBuffer(bytes);\n}\nexports.convertToArrayBuffer = convertToArrayBuffer;\nfunction convertToUint8Array(bytes) {\n if (bytes.buffer !== undefined) {\n return bytes;\n }\n return new Uint8Array(bytes);\n}\nexports.convertToUint8Array = convertToUint8Array;\nfunction convertToByteArray(bytes) {\n if (Array.isArray(bytes)) {\n return bytes;\n }\n bytes = convertToUint8Array(bytes);\n var newBytes = [];\n for (var i = 0, len = bytes.length; i < len; i++) {\n newBytes.push(bytes[i]);\n }\n return newBytes;\n}\nexports.convertToByteArray = convertToByteArray;\nfunction bytesFromArrayBuffer(buffer) {\n var len = buffer.byteLength;\n var byteView = new Uint8Array(buffer);\n var bytes = [];\n for (var i = 0; i < len; ++i) {\n bytes[i] = byteView[i];\n }\n return bytes;\n}\nexports.bytesFromArrayBuffer = bytesFromArrayBuffer;\nfunction bufferConcat(buffer1, buffer2) {\n var l1 = buffer1.byteLength || buffer1.length;\n var l2 = buffer2.byteLength || buffer2.length;\n var tmp = new Uint8Array(l1 + l2);\n tmp.set(buffer1 instanceof ArrayBuffer ? new Uint8Array(buffer1) : buffer1, 0);\n tmp.set(buffer2 instanceof ArrayBuffer ? new Uint8Array(buffer2) : buffer2, l1);\n return tmp.buffer;\n}\nexports.bufferConcat = bufferConcat;\nfunction bufferConcats() {\n var args = [];\n for (var _i = 0; _i < arguments.length; _i++) {\n args[_i] = arguments[_i];\n }\n var length = 0;\n args.forEach(function (b) { return length += b.byteLength || b.length; });\n var tmp = new Uint8Array(length);\n var lastLength = 0;\n args.forEach(function (b) {\n tmp.set(b instanceof ArrayBuffer ? new Uint8Array(b) : b, lastLength);\n lastLength += b.byteLength || b.length;\n });\n return tmp /* .buffer */;\n}\nexports.bufferConcats = bufferConcats;\nfunction longToInts(sLong) {\n var divRem = bigStringInt(sLong).divideAndRemainder(bigint(0x100000000));\n return [divRem[0].intValue(), divRem[1].intValue()];\n}\nexports.longToInts = longToInts;\nfunction longToBytes(sLong) {\n return bytesFromWords({ words: longToInts(sLong), sigBytes: 8 }).reverse();\n}\nexports.longToBytes = longToBytes;\nfunction longFromInts(high, low) {\n return bigint(high).shiftLeft(32).add(bigint(low)).toString(10);\n}\nexports.longFromInts = longFromInts;\nfunction intToUint(val) {\n if (typeof (val) === 'string')\n val = parseInt(val);\n if (val < 0) {\n val = val + 4294967296;\n }\n return val;\n}\nexports.intToUint = intToUint;\nfunction uintToInt(val) {\n if (val > 2147483647) {\n val = val - 4294967296;\n }\n return val;\n}\nexports.uintToInt = uintToInt;\nfunction sha1HashSync(bytes) {\n var hash = Rusha.createHash();\n hash.update(bytes);\n var hashBytes = hash.digest();\n //console.log('sha1HashSync', bytes, hashBytes);\n //rushaInstance = rushaInstance || new Rusha(1024 * 1024);\n // console.log(dT(), 'SHA-1 hash start', bytes.byteLength || bytes.length)\n /* var hashBytes = rushaInstance.rawDigest(bytes).buffer; */\n // console.log(dT(), 'SHA-1 hash finish')\n return hashBytes;\n}\nexports.sha1HashSync = sha1HashSync;\nfunction sha1BytesSync(bytes) {\n return bytesFromArrayBuffer(sha1HashSync(bytes));\n}\nexports.sha1BytesSync = sha1BytesSync;\nfunction sha256HashSync(bytes) {\n // console.log(dT(), 'SHA-2 hash start', bytes.byteLength || bytes.length)\n var hashWords = CryptoJS.SHA256(bytesToWords(bytes));\n // console.log(dT(), 'SHA-2 hash finish')\n var hashBytes = bytesFromWords(hashWords);\n return hashBytes;\n}\nexports.sha256HashSync = sha256HashSync;\nfunction rsaEncrypt(publicKey, bytes) {\n bytes = addPadding(bytes, 255);\n // console.log('RSA encrypt start')\n var N = new jsbn_1.BigInteger(publicKey.modulus, 16);\n var E = new jsbn_1.BigInteger(publicKey.exponent, 16);\n var X = new jsbn_1.BigInteger(bytes);\n var encryptedBigInt = X.modPowInt(E, N), encryptedBytes = bytesFromBigInt(encryptedBigInt, 256);\n // console.log('RSA encrypt finish')\n return encryptedBytes;\n}\nexports.rsaEncrypt = rsaEncrypt;\nfunction addPadding(bytes, blockSize, zeroes, full) {\n if (full === void 0) { full = false; }\n blockSize = blockSize || 16;\n var len = bytes.byteLength || bytes.length;\n var needPadding = blockSize - (len % blockSize);\n if (needPadding > 0 && (needPadding < blockSize || full)) {\n var padding = new Array(needPadding);\n if (zeroes) {\n for (var i = 0; i < needPadding; i++) {\n padding[i] = 0;\n }\n }\n else {\n (new jsbn_1.SecureRandom()).nextBytes(padding);\n }\n if (bytes instanceof ArrayBuffer) {\n bytes = bufferConcat(bytes, padding);\n }\n else {\n bytes = bytes.concat(padding);\n }\n }\n return bytes;\n}\nexports.addPadding = addPadding;\nfunction aesEncryptSync(bytes, keyBytes, ivBytes) {\n var len = bytes.byteLength || bytes.length;\n // console.log(dT(), 'AES encrypt start', len/*, bytesToHex(keyBytes), bytesToHex(ivBytes)*/)\n bytes = addPadding(bytes);\n var encryptedWords = CryptoJS.AES.encrypt(bytesToWords(bytes), bytesToWords(keyBytes), {\n iv: bytesToWords(ivBytes),\n padding: CryptoJS.pad.NoPadding,\n mode: CryptoJS.mode.IGE\n }).ciphertext;\n var encryptedBytes = bytesFromWords(encryptedWords);\n // console.log(dT(), 'AES encrypt finish')\n return encryptedBytes;\n}\nexports.aesEncryptSync = aesEncryptSync;\nfunction aesDecryptSync(encryptedBytes, keyBytes, ivBytes) {\n // console.log(dT(), 'AES decrypt start', encryptedBytes.length)\n var decryptedWords = CryptoJS.AES.decrypt({ ciphertext: bytesToWords(encryptedBytes) }, bytesToWords(keyBytes), {\n iv: bytesToWords(ivBytes),\n padding: CryptoJS.pad.NoPadding,\n mode: CryptoJS.mode.IGE\n });\n var bytes = bytesFromWords(decryptedWords);\n // console.log(dT(), 'AES decrypt finish')\n return bytes;\n}\nexports.aesDecryptSync = aesDecryptSync;\nfunction getDerivation(hash, salt, password, iterations, keyLength) {\n if (hash === void 0) { hash = 'SHA-512'; }\n return __awaiter(this, void 0, void 0, function () {\n var passwordBuffer, importedKey, saltBuffer, params, derivation;\n return __generator(this, function (_a) {\n switch (_a.label) {\n case 0:\n passwordBuffer = password;\n return [4 /*yield*/, crypto.subtle.importKey(\"raw\", passwordBuffer, \"PBKDF2\", false, [\"deriveBits\", 'deriveKey'])];\n case 1:\n importedKey = _a.sent();\n saltBuffer = salt /* textEncoder.encode(salt); */;\n params = { name: \"PBKDF2\", hash: hash, salt: saltBuffer, iterations: iterations };\n return [4 /*yield*/, crypto.subtle.deriveBits(params, importedKey, keyLength * 8)];\n case 2:\n derivation = _a.sent();\n return [2 /*return*/, derivation];\n }\n });\n });\n}\nfunction getKey(derivation) {\n return __awaiter(this, void 0, void 0, function () {\n var ivlen, keylen, derivedKey, iv, importedEncryptionKey;\n return __generator(this, function (_a) {\n switch (_a.label) {\n case 0:\n ivlen = 16;\n keylen = 32;\n derivedKey = derivation.slice(0, keylen);\n iv = derivation.slice(-ivlen);\n return [4 /*yield*/, crypto.subtle.importKey('raw', derivedKey, { name: 'AES-CBC', length: 256 }, false, ['encrypt'])];\n case 1:\n importedEncryptionKey = _a.sent();\n return [2 /*return*/, {\n key: importedEncryptionKey,\n iv: iv\n }];\n }\n });\n });\n}\nfunction encrypt(text, keyObject) {\n return __awaiter(this, void 0, void 0, function () {\n var textBuffer, encryptedText;\n return __generator(this, function (_a) {\n switch (_a.label) {\n case 0:\n textBuffer = text;\n return [4 /*yield*/, crypto.subtle.encrypt({ name: 'AES-CBC', iv: keyObject.iv }, keyObject.key, textBuffer)];\n case 1:\n encryptedText = _a.sent();\n return [2 /*return*/, encryptedText];\n }\n });\n });\n}\n/* import * as crypto from 'crypto'; */\nfunction hash_pbkdf2(/* hasher: 'string', */ buffer, salt, iterations) {\n return __awaiter(this, void 0, void 0, function () {\n var importKey, deriveKey, bits;\n return __generator(this, function (_a) {\n switch (_a.label) {\n case 0: return [4 /*yield*/, window.crypto.subtle.importKey(\"raw\", //only \"raw\" is allowed\n buffer, //your password\n {\n name: \"PBKDF2\",\n }, false, //whether the key is extractable (i.e. can be used in exportKey)\n [\"deriveKey\", \"deriveBits\"] //can be any combination of \"deriveKey\" and \"deriveBits\"\n )];\n case 1:\n importKey = _a.sent();\n return [4 /*yield*/, window.crypto.subtle.deriveKey({\n \"name\": \"PBKDF2\",\n salt: salt,\n iterations: iterations,\n hash: { name: \"SHA-512\" },\n }, importKey, //your key from generateKey or importKey\n {\n name: \"AES-CTR\",\n //the generateKey parameters for that type of algorithm\n length: 256,\n }, false, //whether the derived key is extractable (i.e. can be used in exportKey)\n [\"encrypt\", \"decrypt\"] //limited to the options in that algorithm's importKey\n )];\n case 2:\n deriveKey = _a.sent();\n bits = window.crypto.subtle.deriveBits({\n \"name\": \"PBKDF2\",\n salt: salt,\n iterations: iterations,\n hash: { name: \"SHA-512\" },\n }, importKey, //your key from generateKey or importKey\n 512 //the number of bits you want to derive\n );\n return [2 /*return*/, bits];\n }\n });\n });\n}\nexports.hash_pbkdf2 = hash_pbkdf2;\nfunction gzipUncompress(bytes, toString) {\n // console.log('Gzip uncompress start')\n // @ts-ignore\n //var result = (new Zlib.Gunzip(bytes)).decompress();\n var result = pako_inflate_min_js_1.default.inflate(bytes, toString ? { to: 'string' } : undefined);\n // console.log('Gzip uncompress finish')\n return result;\n}\nexports.gzipUncompress = gzipUncompress;\nfunction nextRandomInt(maxValue) {\n return Math.floor(Math.random() * maxValue);\n}\nexports.nextRandomInt = nextRandomInt;\nfunction pqPrimeFactorization(pqBytes) {\n var what = new jsbn_1.BigInteger(pqBytes);\n var result = false;\n // console.log(dT(), 'PQ start', pqBytes, what.toString(16), what.bitLength())\n try {\n result = pqPrimeLeemon(leemon_1.str2bigInt(what.toString(16), 16, Math.ceil(64 / leemon_1.bpe) + 1));\n }\n catch (e) {\n console.error('Pq leemon Exception', e);\n }\n if (result === false && what.bitLength() <= 64) {\n // console.time('PQ long')\n try {\n result = pqPrimeLong(goog.math.Long.fromString(what.toString(16), 16));\n }\n catch (e) {\n console.error('Pq long Exception', e);\n }\n // console.timeEnd('PQ long')\n }\n // console.log(result)\n if (result === false) {\n // console.time('pq BigInt')\n result = pqPrimeBigInteger(what);\n // console.timeEnd('pq BigInt')\n }\n // console.log(dT(), 'PQ finish')\n return result;\n}\nexports.pqPrimeFactorization = pqPrimeFactorization;\nfunction pqPrimeBigInteger(what) {\n var it = 0, g;\n for (var i = 0; i < 3; i++) {\n var q = (nextRandomInt(128) & 15) + 17;\n var x = bigint(nextRandomInt(1000000000) + 1);\n var y = x.clone();\n var lim = 1 << (i + 18);\n for (var j = 1; j < lim; j++) {\n ++it;\n var a = x.clone();\n var b = x.clone();\n var c = bigint(q);\n while (!b.equals(jsbn_1.BigInteger.ZERO)) {\n if (!b.and(jsbn_1.BigInteger.ONE).equals(jsbn_1.BigInteger.ZERO)) {\n c = c.add(a);\n if (c.compareTo(what) > 0) {\n c = c.subtract(what);\n }\n }\n a = a.add(a);\n if (a.compareTo(what) > 0) {\n a = a.subtract(what);\n }\n b = b.shiftRight(1);\n }\n x = c.clone();\n var z = x.compareTo(y) < 0 ? y.subtract(x) : x.subtract(y);\n g = z.gcd(what);\n if (!g.equals(jsbn_1.BigInteger.ONE)) {\n break;\n }\n if ((j & (j - 1)) == 0) {\n y = x.clone();\n }\n }\n if (g.compareTo(jsbn_1.BigInteger.ONE) > 0) {\n break;\n }\n }\n var f = what.divide(g), P, Q;\n if (g.compareTo(f) > 0) {\n P = f;\n Q = g;\n }\n else {\n P = g;\n Q = f;\n }\n return [bytesFromBigInt(P), bytesFromBigInt(Q), it];\n}\nexports.pqPrimeBigInteger = pqPrimeBigInteger;\nfunction gcdLong(a, b) {\n while (a.notEquals(goog.math.Long.ZERO) && b.notEquals(goog.math.Long.ZERO)) {\n while (b.and(goog.math.Long.ONE).equals(goog.math.Long.ZERO)) {\n b = b.shiftRight(1);\n }\n while (a.and(goog.math.Long.ONE).equals(goog.math.Long.ZERO)) {\n a = a.shiftRight(1);\n }\n if (a.compare(b) > 0) {\n a = a.subtract(b);\n }\n else {\n b = b.subtract(a);\n }\n }\n return b.equals(goog.math.Long.ZERO) ? a : b;\n}\nexports.gcdLong = gcdLong;\nfunction pqPrimeLong(what) {\n var it = 0, g;\n for (var i = 0; i < 3; i++) {\n var q = goog.math.Long.fromInt((nextRandomInt(128) & 15) + 17);\n var x = goog.math.Long.fromInt(nextRandomInt(1000000000) + 1);\n var y = x;\n var lim = 1 << (i + 18);\n for (var j = 1; j < lim; j++) {\n ++it;\n var a = x;\n var b = x;\n var c = q;\n while (b.notEquals(goog.math.Long.ZERO)) {\n if (b.and(goog.math.Long.ONE).notEquals(goog.math.Long.ZERO)) {\n c = c.add(a);\n if (c.compare(what) > 0) {\n c = c.subtract(what);\n }\n }\n a = a.add(a);\n if (a.compare(what) > 0) {\n a = a.subtract(what);\n }\n b = b.shiftRight(1);\n }\n x = c;\n var z = x.compare(y) < 0 ? y.subtract(x) : x.subtract(y);\n g = gcdLong(z, what);\n if (g.notEquals(goog.math.Long.ONE)) {\n break;\n }\n if ((j & (j - 1)) == 0) {\n y = x;\n }\n }\n if (g.compare(goog.math.Long.ONE) > 0) {\n break;\n }\n }\n var f = what.div(g), P, Q;\n if (g.compare(f) > 0) {\n P = f;\n Q = g;\n }\n else {\n P = g;\n Q = f;\n }\n return [bytesFromHex(P.toString(16)), bytesFromHex(Q.toString(16)), it];\n}\nexports.pqPrimeLong = pqPrimeLong;\nfunction pqPrimeLeemon(what) {\n var minBits = 64;\n var minLen = Math.ceil(minBits / leemon_1.bpe) + 1;\n var it = 0;\n var i, q;\n var j, lim;\n var P;\n var Q;\n var a = new Array(minLen);\n var b = new Array(minLen);\n var c = new Array(minLen);\n var g = new Array(minLen);\n var z = new Array(minLen);\n var x = new Array(minLen);\n var y = new Array(minLen);\n for (i = 0; i < 3; i++) {\n q = (nextRandomInt(128) & 15) + 17;\n leemon_1.copyInt_(x, nextRandomInt(1000000000) + 1);\n leemon_1.copy_(y, x);\n lim = 1 << (i + 18);\n for (j = 1; j < lim; j++) {\n ++it;\n leemon_1.copy_(a, x);\n leemon_1.copy_(b, x);\n leemon_1.copyInt_(c, q);\n while (!leemon_1.isZero(b)) {\n if (b[0] & 1) {\n leemon_1.add_(c, a);\n if (leemon_1.greater(c, what)) {\n leemon_1.sub_(c, what);\n }\n }\n leemon_1.add_(a, a);\n if (leemon_1.greater(a, what)) {\n leemon_1.sub_(a, what);\n }\n leemon_1.rightShift_(b, 1);\n }\n leemon_1.copy_(x, c);\n if (leemon_1.greater(x, y)) {\n leemon_1.copy_(z, x);\n leemon_1.sub_(z, y);\n }\n else {\n leemon_1.copy_(z, y);\n leemon_1.sub_(z, x);\n }\n leemon_1.eGCD_(z, what, g, a, b);\n if (!leemon_1.equalsInt(g, 1)) {\n break;\n }\n if ((j & (j - 1)) == 0) {\n leemon_1.copy_(y, x);\n }\n }\n if (leemon_1.greater(g, leemon_1.one)) {\n break;\n }\n }\n leemon_1.divide_(what, g, x, y);\n if (leemon_1.greater(g, x)) {\n P = x;\n Q = g;\n }\n else {\n P = g;\n Q = x;\n }\n // console.log(dT(), 'done', bigInt2str(what, 10), bigInt2str(P, 10), bigInt2str(Q, 10))\n return [bytesFromLeemonBigInt(P), bytesFromLeemonBigInt(Q), it];\n}\nexports.pqPrimeLeemon = pqPrimeLeemon;\nfunction bytesModPow(x, y, m) {\n try {\n var xBigInt = leemon_1.str2bigInt(bytesToHex(x), 16);\n var yBigInt = leemon_1.str2bigInt(bytesToHex(y), 16);\n var mBigInt = leemon_1.str2bigInt(bytesToHex(m), 16);\n var resBigInt = leemon_1.powMod(xBigInt, yBigInt, mBigInt);\n return bytesFromHex(leemon_1.bigInt2str(resBigInt, 16));\n }\n catch (e) {\n console.error('mod pow error', e);\n }\n return bytesFromBigInt(new jsbn_1.BigInteger(x).modPow(new jsbn_1.BigInteger(y), new jsbn_1.BigInteger(m)), 256);\n}\nexports.bytesModPow = bytesModPow;\n" - }, - { - "id": 2, - "identifier": "/Users/kuzmenko/Documents/projects/tweb/node_modules/ts-loader/index.js!/Users/kuzmenko/Documents/projects/tweb/src/lib/mtproto.ts", - "name": "./src/lib/mtproto.ts", - "index": 19, - "index2": 33, - "size": 92532, - "cacheable": true, - "built": true, - "optional": false, - "prefetched": false, - "chunks": [ - 0 - ], - "issuer": "/Users/kuzmenko/Documents/projects/tweb/node_modules/ts-loader/index.js!/Users/kuzmenko/Documents/projects/tweb/src/index.ts", - "issuerId": 18, - "issuerName": "./src/index.ts", - "issuerPath": [ - { - "id": 18, - "identifier": "/Users/kuzmenko/Documents/projects/tweb/node_modules/ts-loader/index.js!/Users/kuzmenko/Documents/projects/tweb/src/index.ts", - "name": "./src/index.ts", - "profile": { - "factory": 17, - "building": 2295 - } - } - ], - "profile": { - "factory": 1354, - "building": 0, - "dependencies": 287 - }, - "failed": false, - "errors": 0, - "warnings": 0, - "assets": [], - "reasons": [ - { - "moduleId": 12, - "moduleIdentifier": "/Users/kuzmenko/Documents/projects/tweb/node_modules/ts-loader/index.js!/Users/kuzmenko/Documents/projects/tweb/src/lib/services.ts", - "module": "./src/lib/services.ts", - "moduleName": "./src/lib/services.ts", - "type": "cjs require", - "userRequest": "./mtproto", - "loc": "37:16-36" - }, - { - "moduleId": 18, - "moduleIdentifier": "/Users/kuzmenko/Documents/projects/tweb/node_modules/ts-loader/index.js!/Users/kuzmenko/Documents/projects/tweb/src/index.ts", - "module": "./src/index.ts", - "moduleName": "./src/index.ts", - "type": "cjs require", - "userRequest": "./lib/mtproto", - "loc": "21:16-40" - }, - { - "moduleId": 39, - "moduleIdentifier": "/Users/kuzmenko/Documents/projects/tweb/node_modules/ts-loader/index.js!/Users/kuzmenko/Documents/projects/tweb/src/lib/mtnetworker.ts", - "module": "./src/lib/mtnetworker.ts", - "moduleName": "./src/lib/mtnetworker.ts", - "type": "cjs require", - "userRequest": "./mtproto", - "loc": "15:16-36" - }, - { - "moduleId": 41, - "moduleIdentifier": "/Users/kuzmenko/Documents/projects/tweb/node_modules/ts-loader/index.js!/Users/kuzmenko/Documents/projects/tweb/src/components/pageSignIn.ts", - "module": "./src/components/pageSignIn.ts", - "moduleName": "./src/components/pageSignIn.ts", - "type": "cjs require", - "userRequest": "../lib/mtproto", - "loc": "13:16-41" - }, - { - "moduleId": 42, - "moduleIdentifier": "/Users/kuzmenko/Documents/projects/tweb/node_modules/ts-loader/index.js!/Users/kuzmenko/Documents/projects/tweb/src/components/pageAuthCode.ts", - "module": "./src/components/pageAuthCode.ts", - "moduleName": "./src/components/pageAuthCode.ts", - "type": "cjs require", - "userRequest": "../lib/mtproto", - "loc": "15:16-41" - }, - { - "moduleId": 43, - "moduleIdentifier": "/Users/kuzmenko/Documents/projects/tweb/node_modules/ts-loader/index.js!/Users/kuzmenko/Documents/projects/tweb/src/components/pageSignUp.ts", - "module": "./src/components/pageSignUp.ts", - "moduleName": "./src/components/pageSignUp.ts", - "type": "cjs require", - "userRequest": "../lib/mtproto", - "loc": "6:16-41" - }, - { - "moduleId": 45, - "moduleIdentifier": "/Users/kuzmenko/Documents/projects/tweb/node_modules/ts-loader/index.js!/Users/kuzmenko/Documents/projects/tweb/src/components/pagePassword.ts", - "module": "./src/components/pagePassword.ts", - "moduleName": "./src/components/pagePassword.ts", - "type": "cjs require", - "userRequest": "../lib/mtproto", - "loc": "15:16-41" - } - ], - "usedExports": true, - "providedExports": null, - "optimizationBailout": [ - "ModuleConcatenation bailout: Module is not an ECMAScript module" - ], - "depth": 1, - "source": "\"use strict\";\n/*!\n * Webogram v0.7.0 - messaging web application for MTProto\n * https://github.com/zhukov/webogram\n * Copyright (C) 2014 Igor Zhukov \n * https://github.com/zhukov/webogram/blob/master/LICENSE\n */\nvar __awaiter = (this && this.__awaiter) || function (thisArg, _arguments, P, generator) {\n function adopt(value) { return value instanceof P ? value : new P(function (resolve) { resolve(value); }); }\n return new (P || (P = Promise))(function (resolve, reject) {\n function fulfilled(value) { try { step(generator.next(value)); } catch (e) { reject(e); } }\n function rejected(value) { try { step(generator[\"throw\"](value)); } catch (e) { reject(e); } }\n function step(result) { result.done ? resolve(result.value) : adopt(result.value).then(fulfilled, rejected); }\n step((generator = generator.apply(thisArg, _arguments || [])).next());\n });\n};\nvar __generator = (this && this.__generator) || function (thisArg, body) {\n var _ = { label: 0, sent: function() { if (t[0] & 1) throw t[1]; return t[1]; }, trys: [], ops: [] }, f, y, t, g;\n return g = { next: verb(0), \"throw\": verb(1), \"return\": verb(2) }, typeof Symbol === \"function\" && (g[Symbol.iterator] = function() { return this; }), g;\n function verb(n) { return function (v) { return step([n, v]); }; }\n function step(op) {\n if (f) throw new TypeError(\"Generator is already executing.\");\n while (_) try {\n if (f = 1, y && (t = op[0] & 2 ? y[\"return\"] : op[0] ? y[\"throw\"] || ((t = y[\"return\"]) && t.call(y), 0) : y.next) && !(t = t.call(y, op[1])).done) return t;\n if (y = 0, t) op = [op[0] & 2, t.value];\n switch (op[0]) {\n case 0: case 1: t = op; break;\n case 4: _.label++; return { value: op[1], done: false };\n case 5: _.label++; y = op[1]; op = [0]; continue;\n case 7: op = _.ops.pop(); _.trys.pop(); continue;\n default:\n if (!(t = _.trys, t = t.length > 0 && t[t.length - 1]) && (op[0] === 6 || op[0] === 2)) { _ = 0; continue; }\n if (op[0] === 3 && (!t || (op[1] > t[0] && op[1] < t[3]))) { _.label = op[1]; break; }\n if (op[0] === 6 && _.label < t[1]) { _.label = t[1]; t = op; break; }\n if (t && _.label < t[2]) { _.label = t[2]; _.ops.push(op); break; }\n if (t[2]) _.ops.pop();\n _.trys.pop(); continue;\n }\n op = body.call(thisArg, _);\n } catch (e) { op = [6, e]; y = 0; } finally { f = t = 0; }\n if (op[0] & 5) throw op[1]; return { value: op[0] ? op[1] : void 0, done: true };\n }\n};\nvar __importStar = (this && this.__importStar) || function (mod) {\n if (mod && mod.__esModule) return mod;\n var result = {};\n if (mod != null) for (var k in mod) if (Object.hasOwnProperty.call(mod, k)) result[k] = mod[k];\n result[\"default\"] = mod;\n return result;\n};\nvar __importDefault = (this && this.__importDefault) || function (mod) {\n return (mod && mod.__esModule) ? mod : { \"default\": mod };\n};\nObject.defineProperty(exports, \"__esModule\", { value: true });\nvar Config = __importStar(require(\"./config\"));\nvar storage_1 = __importDefault(require(\"./storage\"));\nvar bin_utils_1 = require(\"./bin_utils\");\nvar utils_1 = require(\"./utils\");\nvar tl_utils_1 = require(\"./tl_utils\");\nvar cryptoworker_1 = __importDefault(require(\"./cryptoworker\"));\nvar filemanager_1 = __importDefault(require(\"./filemanager\"));\nvar idb_1 = __importDefault(require(\"./idb\"));\nvar mtnetworker_1 = require(\"./mtnetworker\");\nvar leemon_1 = require(\"leemon\");\nvar $rootScope = {\n $broadcast: function (name, detail) {\n console.log(utils_1.dT(), 'Broadcasting ' + name + ' event, with args:', detail);\n //console.trace();\n var myCustomEvent = new CustomEvent(name, { detail: detail });\n document.dispatchEvent(myCustomEvent);\n },\n};\n/* let qSync = {\n when: function(result: any) {\n return Promise.resolve(result);\n },\n reject: function (result: any) {\n return {\n then: function(cb: any, badcb: any) {\n if(badcb) {\n return badcb(result);\n }\n }\n };\n }\n}; */\nvar TelegramMeWebService = /** @class */ (function () {\n function TelegramMeWebService() {\n this.disabled = Config.Modes.test ||\n Config.App.domains.indexOf(location.hostname) == -1 ||\n location.protocol != 'http:' && location.protocol != 'https:' ||\n location.protocol == 'https:' && location.hostname != 'web.telegram.org';\n }\n TelegramMeWebService.prototype.setAuthorized = function (canRedirect) {\n if (this.disabled) {\n return false;\n }\n storage_1.default.get('tgme_sync').then(function (curValue) {\n var ts = utils_1.tsNow(true);\n if (canRedirect &&\n curValue &&\n curValue.canRedirect == canRedirect &&\n curValue.ts + 86400 > ts) {\n return false;\n }\n storage_1.default.set({ tgme_sync: { canRedirect: canRedirect, ts: ts } });\n var urls = [\n '//telegram.me/_websync_?authed=' + (canRedirect ? '1' : '0'),\n '//t.me/_websync_?authed=' + (canRedirect ? '1' : '0')\n ];\n urls.forEach(function (url) {\n var script = document.createElement('script');\n script.onload = script.onerror = function () {\n //document.body.removeChild(script);\n script.remove();\n };\n script.src = url;\n document.body.appendChild(script);\n });\n });\n };\n return TelegramMeWebService;\n}());\nexports.TelegramMeWebService = TelegramMeWebService;\nexports.telegramMeWebService = new TelegramMeWebService();\n// @ts-ignore\n// костыль\n//import * as jsbn from 'jsbn';\nvar jsbn_1 = require(\"jsbn\");\n//import { SecureRandom } from '../types';\n// @ts-ignore\nglobalThis.BigInteger = jsbn_1.BigInteger;\n//let SecureRandom = jsbn.SecureRandom;\nvar chromeMatches = navigator.userAgent.match(/Chrome\\/(\\d+(\\.\\d+)?)/);\nvar chromeVersion = chromeMatches && parseFloat(chromeMatches[1]) || false;\nvar xhrSendBuffer = !('ArrayBufferView' in window) && (chromeVersion > 0 && chromeVersion < 30);\nvar MTProto;\n(function (MTProto) {\n var MTProto_ = /** @class */ (function () {\n function MTProto_() {\n /* public chromeMatches = navigator.userAgent.match(/Chrome\\/(\\d+(\\.\\d+)?)/);\n public chromeVersion = this.chromeMatches && parseFloat(this.chromeMatches[1]) || false;\n public xhrSendBuffer = !('ArrayBufferView' in window) && (this.chromeVersion > 0 && this.chromeVersion < 30); */\n this.secureRandom = null;\n this.secureRandom = new jsbn_1.SecureRandom();\n //$($window).on('click keydown', rng_seed_time);\n }\n return MTProto_;\n }());\n MTProto.MTProto_ = MTProto_;\n var DcConfigurator = /** @class */ (function () {\n function DcConfigurator() {\n // it was DcConfigurator\n this.sslSubdomains = ['pluto', 'venus', 'aurora', 'vesta', 'flora'];\n this.dcOptions = Config.Modes.test\n ? [\n { id: 1, host: '149.154.175.10', port: 80 },\n { id: 2, host: '149.154.167.40', port: 80 },\n { id: 3, host: '149.154.175.117', port: 80 }\n ]\n : [\n { id: 1, host: '149.154.175.50', port: 80 },\n { id: 2, host: '149.154.167.50', port: 80 },\n { id: 3, host: '149.154.175.100', port: 80 },\n { id: 4, host: '149.154.167.91', port: 80 },\n { id: 5, host: '149.154.171.5', port: 80 }\n ];\n /* public dcOptions = Config.Modes.test ? [{\n id: 2,\n host: '149.154.167.40',\n port: 443\n }] : [{\n id: 2,\n host: '149.154.167.50',\n port: 443\n }]; */\n this.chosenServers = {};\n }\n DcConfigurator.prototype.chooseServer = function (dcID, upload) {\n if (!(dcID in this.chosenServers)) {\n var chosenServer = false, i, dcOption;\n if (Config.Modes.ssl || !Config.Modes.http) {\n var subdomain = this.sslSubdomains[dcID - 1] + (upload ? '-1' : '');\n var path = Config.Modes.test ? 'apiw_test1' : 'apiw1';\n chosenServer = 'https://' + subdomain + '.web.telegram.org/' + path;\n return chosenServer;\n }\n for (i = 0; i < this.dcOptions.length; i++) {\n dcOption = this.dcOptions[i];\n if (dcOption.id == dcID) {\n chosenServer = 'http://' + dcOption.host + (dcOption.port != 80 ? ':' + dcOption.port : '') + '/apiw1';\n break;\n }\n }\n // @ts-ignore\n chosenServers[dcID] = chosenServer;\n }\n // @ts-ignore\n return chosenServers[dcID];\n };\n return DcConfigurator;\n }());\n MTProto.DcConfigurator = DcConfigurator;\n var RSAKeysManager = /** @class */ (function () {\n function RSAKeysManager() {\n /**\n * Server public key, obtained from here: https://core.telegram.org/api/obtaining_api_id\n *\n *\n * -----BEGIN RSA PUBLIC KEY-----\n * MIIBCgKCAQEAwVACPi9w23mF3tBkdZz+zwrzKOaaQdr01vAbU4E1pvkfj4sqDsm6\n * lyDONS789sVoD/xCS9Y0hkkC3gtL1tSfTlgCMOOul9lcixlEKzwKENj1Yz/s7daS\n * an9tqw3bfUV/nqgbhGX81v/+7RFAEd+RwFnK7a+XYl9sluzHRyVVaTTveB2GazTw\n * Efzk2DWgkBluml8OREmvfraX3bkHZJTKX4EQSjBbbdJ2ZXIsRrYOXfaA+xayEGB+\n * 8hdlLmAjbCVfaigxX0CDqWeR1yFL9kwd9P0NsZRPsmoqVwMbMu7mStFai6aIhc3n\n * Slv8kg9qv1m6XHVQY3PnEw+QQtqSIXklHwIDAQAB\n * -----END RSA PUBLIC KEY-----\n *\n * -----BEGIN PUBLIC KEY-----\n * MIIBIjANBgkqhkiG9w0BAQEFAAOCAQ8AMIIBCgKCAQEAruw2yP/BCcsJliRoW5eB\n * VBVle9dtjJw+OYED160Wybum9SXtBBLXriwt4rROd9csv0t0OHCaTmRqBcQ0J8fx\n * hN6/cpR1GWgOZRUAiQxoMnlt0R93LCX/j1dnVa/gVbCjdSxpbrfY2g2L4frzjJvd\n * l84Kd9ORYjDEAyFnEA7dD556OptgLQQ2e2iVNq8NZLYTzLp5YpOdO1doK+ttrltg\n * gTCy5SrKeLoCPPbOgGsdxJxyz5KKcZnSLj16yE5HvJQn0CNpRdENvRUXe6tBP78O\n * 39oJ8BTHp9oIjd6XWXAsp2CvK45Ol8wFXGF710w9lwCGNbmNxNYhtIkdqfsEcwR5\n * JwIDAQAB\n * -----END PUBLIC KEY-----\n *\n * -----BEGIN PUBLIC KEY-----\n * MIIBIjANBgkqhkiG9w0BAQEFAAOCAQ8AMIIBCgKCAQEAvfLHfYH2r9R70w8prHbl\n * Wt/nDkh+XkgpflqQVcnAfSuTtO05lNPspQmL8Y2XjVT4t8cT6xAkdgfmmvnvRPOO\n * KPi0OfJXoRVylFzAQG/j83u5K3kRLbae7fLccVhKZhY46lvsueI1hQdLgNV9n1cQ\n * 3TDS2pQOCtovG4eDl9wacrXOJTG2990VjgnIKNA0UMoP+KF03qzryqIt3oTvZq03\n * DyWdGK+AZjgBLaDKSnC6qD2cFY81UryRWOab8zKkWAnhw2kFpcqhI0jdV5QaSCEx\n * vnsjVaX0Y1N0870931/5Jb9ICe4nweZ9kSDF/gip3kWLG0o8XQpChDfyvsqB9OLV\n * /wIDAQAB\n * -----END PUBLIC KEY-----\n *\n * -----BEGIN PUBLIC KEY-----\n * MIIBIjANBgkqhkiG9w0BAQEFAAOCAQ8AMIIBCgKCAQEAs/ditzm+mPND6xkhzwFI\n * z6J/968CtkcSE/7Z2qAJiXbmZ3UDJPGrzqTDHkO30R8VeRM/Kz2f4nR05GIFiITl\n * 4bEjvpy7xqRDspJcCFIOcyXm8abVDhF+th6knSU0yLtNKuQVP6voMrnt9MV1X92L\n * GZQLgdHZbPQz0Z5qIpaKhdyA8DEvWWvSUwwc+yi1/gGaybwlzZwqXYoPOhwMebzK\n * Uk0xW14htcJrRrq+PXXQbRzTMynseCoPIoke0dtCodbA3qQxQovE16q9zz4Otv2k\n * 4j63cz53J+mhkVWAeWxVGI0lltJmWtEYK6er8VqqWot3nqmWMXogrgRLggv/Nbbo\n * oQIDAQAB\n * -----END PUBLIC KEY-----\n *\n * -----BEGIN PUBLIC KEY-----\n * MIIBIjANBgkqhkiG9w0BAQEFAAOCAQ8AMIIBCgKCAQEAvmpxVY7ld/8DAjz6F6q0\n * 5shjg8/4p6047bn6/m8yPy1RBsvIyvuDuGnP/RzPEhzXQ9UJ5Ynmh2XJZgHoE9xb\n * nfxL5BXHplJhMtADXKM9bWB11PU1Eioc3+AXBB8QiNFBn2XI5UkO5hPhbb9mJpjA\n * 9Uhw8EdfqJP8QetVsI/xrCEbwEXe0xvifRLJbY08/Gp66KpQvy7g8w7VB8wlgePe\n * xW3pT13Ap6vuC+mQuJPyiHvSxjEKHgqePji9NP3tJUFQjcECqcm0yV7/2d0t/pbC\n * m+ZH1sadZspQCEPPrtbkQBlvHb4OLiIWPGHKSMeRFvp3IWcmdJqXahxLCUS1Eh6M\n * AQIDAQAB\n * -----END PUBLIC KEY-----\n *\n * Bytes can be got via\n * $ openssl rsa -pubin -in key.pub -text -noout\n */\n this.publisKeysHex = [{\n modulus: 'c150023e2f70db7985ded064759cfecf0af328e69a41daf4d6f01b538135a6f91f8f8b2a0ec9ba9720ce352efcf6c5680ffc424bd634864902de0b4bd6d49f4e580230e3ae97d95c8b19442b3c0a10d8f5633fecedd6926a7f6dab0ddb7d457f9ea81b8465fcd6fffeed114011df91c059caedaf97625f6c96ecc74725556934ef781d866b34f011fce4d835a090196e9a5f0e4449af7eb697ddb9076494ca5f81104a305b6dd27665722c46b60e5df680fb16b210607ef217652e60236c255f6a28315f4083a96791d7214bf64c1df4fd0db1944fb26a2a57031b32eee64ad15a8ba68885cde74a5bfc920f6abf59ba5c75506373e7130f9042da922179251f',\n exponent: '010001'\n }, {\n modulus: 'aeec36c8ffc109cb099624685b97815415657bd76d8c9c3e398103d7ad16c9bba6f525ed0412d7ae2c2de2b44e77d72cbf4b7438709a4e646a05c43427c7f184debf72947519680e651500890c6832796dd11f772c25ff8f576755afe055b0a3752c696eb7d8da0d8be1faf38c9bdd97ce0a77d3916230c4032167100edd0f9e7a3a9b602d04367b689536af0d64b613ccba7962939d3b57682beb6dae5b608130b2e52aca78ba023cf6ce806b1dc49c72cf928a7199d22e3d7ac84e47bc9427d0236945d10dbd15177bab413fbf0edfda09f014c7a7da088dde9759702ca760af2b8e4e97cc055c617bd74c3d97008635b98dc4d621b4891da9fb0473047927',\n exponent: '010001'\n }, {\n modulus: 'bdf2c77d81f6afd47bd30f29ac76e55adfe70e487e5e48297e5a9055c9c07d2b93b4ed3994d3eca5098bf18d978d54f8b7c713eb10247607e69af9ef44f38e28f8b439f257a11572945cc0406fe3f37bb92b79112db69eedf2dc71584a661638ea5becb9e23585074b80d57d9f5710dd30d2da940e0ada2f1b878397dc1a72b5ce2531b6f7dd158e09c828d03450ca0ff8a174deacebcaa22dde84ef66ad370f259d18af806638012da0ca4a70baa83d9c158f3552bc9158e69bf332a45809e1c36905a5caa12348dd57941a482131be7b2355a5f4635374f3bd3ddf5ff925bf4809ee27c1e67d9120c5fe08a9de458b1b4a3c5d0a428437f2beca81f4e2d5ff',\n exponent: '010001'\n }, {\n modulus: 'b3f762b739be98f343eb1921cf0148cfa27ff7af02b6471213fed9daa0098976e667750324f1abcea4c31e43b7d11f1579133f2b3d9fe27474e462058884e5e1b123be9cbbc6a443b2925c08520e7325e6f1a6d50e117eb61ea49d2534c8bb4d2ae4153fabe832b9edf4c5755fdd8b19940b81d1d96cf433d19e6a22968a85dc80f0312f596bd2530c1cfb28b5fe019ac9bc25cd9c2a5d8a0f3a1c0c79bcca524d315b5e21b5c26b46babe3d75d06d1cd33329ec782a0f22891ed1db42a1d6c0dea431428bc4d7aabdcf3e0eb6fda4e23eb7733e7727e9a1915580796c55188d2596d2665ad1182ba7abf15aaa5a8b779ea996317a20ae044b820bff35b6e8a1',\n exponent: '010001'\n }, {\n modulus: 'be6a71558ee577ff03023cfa17aab4e6c86383cff8a7ad38edb9fafe6f323f2d5106cbc8cafb83b869cffd1ccf121cd743d509e589e68765c96601e813dc5b9dfc4be415c7a6526132d0035ca33d6d6075d4f535122a1cdfe017041f1088d1419f65c8e5490ee613e16dbf662698c0f54870f0475fa893fc41eb55b08ff1ac211bc045ded31be27d12c96d8d3cfc6a7ae8aa50bf2ee0f30ed507cc2581e3dec56de94f5dc0a7abee0be990b893f2887bd2c6310a1e0a9e3e38bd34fded2541508dc102a9c9b4c95effd9dd2dfe96c29be647d6c69d66ca500843cfaed6e440196f1dbe0e2e22163c61ca48c79116fa77216726749a976a1c4b0944b5121e8c01',\n exponent: '010001'\n }];\n this.publicKeysParsed = {};\n this.prepared = false;\n }\n // prepareRsaKeys\n RSAKeysManager.prototype.prepare = function () {\n if (this.prepared) {\n return;\n }\n for (var i = 0; i < this.publisKeysHex.length; i++) {\n var keyParsed = this.publisKeysHex[i];\n var RSAPublicKey = new tl_utils_1.TLSerialization();\n RSAPublicKey.storeBytes(bin_utils_1.bytesFromHex(keyParsed.modulus), 'n');\n RSAPublicKey.storeBytes(bin_utils_1.bytesFromHex(keyParsed.exponent), 'e');\n var buffer = RSAPublicKey.getBuffer();\n var fingerprintBytes = bin_utils_1.sha1BytesSync(buffer).slice(-8);\n fingerprintBytes.reverse();\n // @ts-ignore\n this.publicKeysParsed[bin_utils_1.bytesToHex(fingerprintBytes)] = {\n modulus: keyParsed.modulus,\n exponent: keyParsed.exponent\n };\n }\n this.prepared = true;\n };\n // selectRsaKeyByFingerPrint\n RSAKeysManager.prototype.select = function (fingerprints) {\n this.prepare();\n var fingerprintHex, foundKey, i;\n for (i = 0; i < fingerprints.length; i++) {\n fingerprintHex = bin_utils_1.bigStringInt(fingerprints[i]).toString(16);\n // @ts-ignore\n if (foundKey = this.publicKeysParsed[fingerprintHex]) {\n return Object.assign({\n fingerprint: fingerprints[i]\n }, foundKey);\n }\n }\n return false;\n };\n return RSAKeysManager;\n }());\n MTProto.RSAKeysManager = RSAKeysManager;\n var TimeManager = /** @class */ (function () {\n function TimeManager() {\n var _this = this;\n this.lastMessageID = [0, 0];\n this.timeOffset = 0;\n storage_1.default.get('server_time_offset').then(function (to) {\n if (to) {\n _this.timeOffset = to;\n }\n });\n }\n TimeManager.prototype.generateID = function () {\n var timeTicks = utils_1.tsNow(), timeSec = Math.floor(timeTicks / 1000) + this.timeOffset, timeMSec = timeTicks % 1000, random = bin_utils_1.nextRandomInt(0xFFFF);\n var messageID = [timeSec, (timeMSec << 21) | (random << 3) | 4];\n if (this.lastMessageID[0] > messageID[0] ||\n this.lastMessageID[0] == messageID[0] && this.lastMessageID[1] >= messageID[1]) {\n messageID = [this.lastMessageID[0], this.lastMessageID[1] + 4];\n }\n this.lastMessageID = messageID;\n // console.log('generated msg id', messageID, timeOffset)\n return bin_utils_1.longFromInts(messageID[0], messageID[1]);\n };\n TimeManager.prototype.applyServerTime = function (serverTime, localTime) {\n var newTimeOffset = serverTime - Math.floor((localTime || utils_1.tsNow()) / 1000);\n var changed = Math.abs(this.timeOffset - newTimeOffset) > 10;\n storage_1.default.set({\n server_time_offset: newTimeOffset\n });\n this.lastMessageID = [0, 0];\n this.timeOffset = newTimeOffset;\n console.log(utils_1.dT(), 'Apply server time', serverTime, localTime, newTimeOffset, changed);\n return changed;\n };\n return TimeManager;\n }());\n MTProto.TimeManager = TimeManager;\n var Authorizer = /** @class */ (function () {\n function Authorizer( /* $http: any */) {\n this.cached = {};\n /* delete $http.defaults.headers.post['Content-Type'];\n delete $http.defaults.headers.common['Accept']; */\n }\n Authorizer.prototype.mtpSendPlainRequest = function (dcID, requestBuffer) {\n var requestLength = requestBuffer.byteLength, requestArray = new Int32Array(requestBuffer);\n var header = new tl_utils_1.TLSerialization();\n header.storeLongP(0, 0, 'auth_key_id'); // Auth key\n header.storeLong(MTProto.timeManager.generateID(), 'msg_id'); // Msg_id\n header.storeInt(requestLength, 'request_length');\n var headerBuffer = header.getBuffer(), headerArray = new Int32Array(headerBuffer);\n var headerLength = headerBuffer.byteLength;\n var resultBuffer = new ArrayBuffer(headerLength + requestLength), resultArray = new Int32Array(resultBuffer);\n resultArray.set(headerArray);\n resultArray.set(requestArray, headerArray.length);\n var requestData = xhrSendBuffer ? resultBuffer : resultArray, requestPromise;\n var url = MTProto.dcConfigurator.chooseServer(dcID);\n var baseError = {\n code: 406,\n type: 'NETWORK_BAD_RESPONSE',\n url: url\n };\n console.log('mtpSendPlainRequest: creating requestPromise');\n return /* requestPromise = */ fetch(url, { method: 'POST', body: requestData })\n .then(function (response) {\n console.log('response', response);\n if (response.status != 200)\n throw response;\n return response.arrayBuffer();\n })\n /* .catch(err => {console.log('asdasdasd', err); }); */\n /* try {\n requestPromise = fetch(url, {method: 'POST', body: requestData});\n } catch(e) {\n requestPromise = $q.reject(Object.assign(baseError, {\n originalError: e\n }));\n } */\n /* return requestPromise */ .then(function (result) {\n console.log('mtpSendPlainRequest: in good sector', result);\n if (!result || !result.byteLength) {\n return Promise.reject(baseError);\n //return this.$q.reject(baseError);\n }\n try {\n var deserializer = new tl_utils_1.TLDeserialization(result, { mtproto: true });\n var auth_key_id = deserializer.fetchLong('auth_key_id');\n var msg_id = deserializer.fetchLong('msg_id');\n var msg_len = deserializer.fetchInt('msg_len');\n }\n catch (e) {\n console.error('mtpSendPlainRequest: deserialization went bad', e);\n var error = Object.assign(baseError, { originalError: e });\n throw error;\n //return Promise.reject(error);\n //return $q.reject(error);\n }\n return deserializer;\n }, function (error) {\n if (!error.message && !error.type) {\n error = Object.assign(baseError, {\n originalError: error\n });\n }\n return Promise.reject(error);\n //return $q.reject(error);\n });\n };\n Authorizer.prototype.mtpSendReqPQ = function (auth) {\n var _this = this;\n var deferred = auth.deferred;\n var request = new tl_utils_1.TLSerialization({\n mtproto: true\n });\n request.storeMethod('req_pq', {\n nonce: auth.nonce\n });\n console.log(utils_1.dT(), 'Send req_pq', bin_utils_1.bytesToHex(auth.nonce));\n this.mtpSendPlainRequest(auth.dcID, request.getBuffer()).then(function (deserializer) {\n var response = deserializer.fetchObject('ResPQ');\n if (response._ != 'resPQ') {\n throw new Error('[MT] resPQ response invalid: ' + response._);\n }\n if (!bin_utils_1.bytesCmp(auth.nonce, response.nonce)) {\n throw new Error('[MT] resPQ nonce mismatch');\n }\n auth.serverNonce = response.server_nonce;\n auth.pq = response.pq;\n auth.fingerprints = response.server_public_key_fingerprints;\n console.log(utils_1.dT(), 'Got ResPQ', bin_utils_1.bytesToHex(auth.serverNonce), bin_utils_1.bytesToHex(auth.pq), auth.fingerprints);\n auth.publicKey = MTProto.rsaKeysManager.select(auth.fingerprints);\n if (!auth.publicKey) {\n throw new Error('[MT] No public key found');\n }\n console.log(utils_1.dT(), 'PQ factorization start', auth.pq);\n cryptoworker_1.default.factorize(auth.pq).then(function (pAndQ) {\n auth.p = pAndQ[0];\n auth.q = pAndQ[1];\n console.log(utils_1.dT(), 'PQ factorization done', pAndQ[2]);\n _this.mtpSendReqDhParams(auth);\n }, function (error) {\n console.log('Worker error', error, error.stack);\n deferred.reject(error);\n });\n }, function (error) {\n console.error(utils_1.dT(), 'req_pq error', error.message);\n deferred.reject(error);\n });\n setTimeout(function () {\n MTProto.rsaKeysManager.prepare();\n });\n };\n Authorizer.prototype.mtpSendReqDhParams = function (auth) {\n var _this = this;\n var deferred = auth.deferred;\n auth.newNonce = new Array(32);\n MTProto.secureRandom.nextBytes(auth.newNonce);\n var data = new tl_utils_1.TLSerialization({ mtproto: true });\n data.storeObject({\n _: 'p_q_inner_data',\n pq: auth.pq,\n p: auth.p,\n q: auth.q,\n nonce: auth.nonce,\n server_nonce: auth.serverNonce,\n new_nonce: auth.newNonce\n }, 'P_Q_inner_data', 'DECRYPTED_DATA');\n // @ts-ignore\n var dataWithHash = bin_utils_1.sha1BytesSync(data.getBuffer()).concat(data.getBytes());\n var request = new tl_utils_1.TLSerialization({ mtproto: true });\n request.storeMethod('req_DH_params', {\n nonce: auth.nonce,\n server_nonce: auth.serverNonce,\n p: auth.p,\n q: auth.q,\n public_key_fingerprint: auth.publicKey.fingerprint,\n encrypted_data: bin_utils_1.rsaEncrypt(auth.publicKey, dataWithHash)\n });\n console.log(utils_1.dT(), 'Send req_DH_params');\n this.mtpSendPlainRequest(auth.dcID, request.getBuffer()).then(function (deserializer) {\n var response = deserializer.fetchObject('Server_DH_Params', 'RESPONSE');\n console.log(utils_1.dT(), 'Sent req_DH_params, response:', response);\n if (response._ != 'server_DH_params_fail' && response._ != 'server_DH_params_ok') {\n deferred.reject(new Error('[MT] Server_DH_Params response invalid: ' + response._));\n return false;\n }\n if (!bin_utils_1.bytesCmp(auth.nonce, response.nonce)) {\n deferred.reject(new Error('[MT] Server_DH_Params nonce mismatch'));\n return false;\n }\n if (!bin_utils_1.bytesCmp(auth.serverNonce, response.server_nonce)) {\n deferred.reject(new Error('[MT] Server_DH_Params server_nonce mismatch'));\n return false;\n }\n if (response._ == 'server_DH_params_fail') {\n var newNonceHash = bin_utils_1.sha1BytesSync(auth.newNonce).slice(-16);\n if (!bin_utils_1.bytesCmp(newNonceHash, response.new_nonce_hash)) {\n deferred.reject(new Error('[MT] server_DH_params_fail new_nonce_hash mismatch'));\n return false;\n }\n deferred.reject(new Error('[MT] server_DH_params_fail'));\n return false;\n }\n // fill auth object\n try {\n _this.mtpDecryptServerDhDataAnswer(auth, response.encrypted_answer);\n }\n catch (e) {\n console.error(utils_1.dT(), 'mtpDecryptServerDhDataAnswer FAILED!', e);\n deferred.reject(e);\n return false;\n }\n console.log(utils_1.dT(), 'mtpSendReqDhParams: executing mtpSendSetClientDhParams...');\n _this.mtpSendSetClientDhParams(auth);\n }, function (error) {\n console.log(utils_1.dT(), 'Send req_DH_params FAIL!', error);\n deferred.reject(error);\n });\n };\n Authorizer.prototype.mtpDecryptServerDhDataAnswer = function (auth, encryptedAnswer) {\n auth.localTime = utils_1.tsNow();\n auth.tmpAesKey = bin_utils_1.sha1BytesSync(auth.newNonce.concat(auth.serverNonce)).concat(bin_utils_1.sha1BytesSync(auth.serverNonce.concat(auth.newNonce)).slice(0, 12));\n auth.tmpAesIv = bin_utils_1.sha1BytesSync(auth.serverNonce.concat(auth.newNonce)).slice(12).concat(bin_utils_1.sha1BytesSync([].concat(auth.newNonce, auth.newNonce)), auth.newNonce.slice(0, 4));\n var answerWithHash = bin_utils_1.aesDecryptSync(encryptedAnswer, auth.tmpAesKey, auth.tmpAesIv);\n var hash = answerWithHash.slice(0, 20);\n var answerWithPadding = answerWithHash.slice(20);\n var buffer = bin_utils_1.bytesToArrayBuffer(answerWithPadding);\n var deserializer = new tl_utils_1.TLDeserialization(buffer, { mtproto: true });\n var response = deserializer.fetchObject('Server_DH_inner_data');\n if (response._ != 'server_DH_inner_data') {\n throw new Error('[MT] server_DH_inner_data response invalid: ' + response /* constructor */);\n }\n if (!bin_utils_1.bytesCmp(auth.nonce, response.nonce)) {\n throw new Error('[MT] server_DH_inner_data nonce mismatch');\n }\n if (!bin_utils_1.bytesCmp(auth.serverNonce, response.server_nonce)) {\n throw new Error('[MT] server_DH_inner_data serverNonce mismatch');\n }\n console.log(utils_1.dT(), 'Done decrypting answer');\n auth.g = response.g;\n auth.dhPrime = response.dh_prime;\n auth.gA = response.g_a;\n auth.serverTime = response.server_time;\n auth.retry = 0;\n this.mtpVerifyDhParams(auth.g, auth.dhPrime, auth.gA);\n var offset = deserializer.getOffset();\n if (!bin_utils_1.bytesCmp(hash, bin_utils_1.sha1BytesSync(answerWithPadding.slice(0, offset)))) {\n throw new Error('[MT] server_DH_inner_data SHA1-hash mismatch');\n }\n MTProto.timeManager.applyServerTime(auth.serverTime, auth.localTime);\n };\n Authorizer.prototype.mtpVerifyDhParams = function (g, dhPrime, gA) {\n console.log(utils_1.dT(), 'Verifying DH params');\n var dhPrimeHex = bin_utils_1.bytesToHex(dhPrime);\n if (g != 3 ||\n dhPrimeHex !== 'c71caeb9c6b1c9048e6c522f70f13f73980d40238e3e21c14934d037563d930f48198a0aa7c14058229493d22530f4dbfa336f6e0ac925139543aed44cce7c3720fd51f69458705ac68cd4fe6b6b13abdc9746512969328454f18faf8c595f642477fe96bb2a941d5bcd1d4ac8cc49880708fa9b378e3c4f3a9060bee67cf9a4a4a695811051907e162753b56b0f6b410dba74d8a84b2a14b3144e0ef1284754fd17ed950d5965b4b9dd46582db1178d169c6bc465b0d6ff9ca3928fef5b9ae4e418fc15e83ebea0f87fa9ff5eed70050ded2849f47bf959d956850ce929851f0d8115f635b105ee2e4e15d04b2454bf6f4fadf034b10403119cd8e3b92fcc5b') {\n // The verified value is from https://core.telegram.org/mtproto/security_guidelines\n throw new Error('[MT] DH params are not verified: unknown dhPrime');\n }\n console.log(utils_1.dT(), 'dhPrime cmp OK');\n var gABigInt = new jsbn_1.BigInteger(bin_utils_1.bytesToHex(gA), 16);\n var dhPrimeBigInt = new jsbn_1.BigInteger(dhPrimeHex, 16);\n if (gABigInt.compareTo(jsbn_1.BigInteger.ONE) <= 0) {\n throw new Error('[MT] DH params are not verified: gA <= 1');\n }\n if (gABigInt.compareTo(dhPrimeBigInt.subtract(jsbn_1.BigInteger.ONE)) >= 0) {\n throw new Error('[MT] DH params are not verified: gA >= dhPrime - 1');\n }\n console.log(utils_1.dT(), '1 < gA < dhPrime-1 OK');\n var two = new jsbn_1.BigInteger(/* null */ '');\n two.fromInt(2);\n var twoPow = two.pow(2048 - 64);\n if (gABigInt.compareTo(twoPow) < 0) {\n throw new Error('[MT] DH params are not verified: gA < 2^{2048-64}');\n }\n if (gABigInt.compareTo(dhPrimeBigInt.subtract(twoPow)) >= 0) {\n throw new Error('[MT] DH params are not verified: gA > dhPrime - 2^{2048-64}');\n }\n console.log(utils_1.dT(), '2^{2048-64} < gA < dhPrime-2^{2048-64} OK');\n return true;\n };\n Authorizer.prototype.mtpSendSetClientDhParams = function (auth) {\n var _this = this;\n var deferred = auth.deferred;\n var gBytes = bin_utils_1.bytesFromHex(auth.g.toString(16));\n auth.b = new Array(256);\n MTProto.secureRandom.nextBytes(auth.b);\n cryptoworker_1.default.modPow(gBytes, auth.b, auth.dhPrime).then(function (gB) {\n var data = new tl_utils_1.TLSerialization({ mtproto: true });\n data.storeObject({\n _: 'client_DH_inner_data',\n nonce: auth.nonce,\n server_nonce: auth.serverNonce,\n retry_id: [0, auth.retry++],\n g_b: gB\n }, 'Client_DH_Inner_Data');\n // @ts-ignore\n var dataWithHash = bin_utils_1.sha1BytesSync(data.getBuffer()).concat(data.getBytes());\n var encryptedData = bin_utils_1.aesEncryptSync(dataWithHash, auth.tmpAesKey, auth.tmpAesIv);\n var request = new tl_utils_1.TLSerialization({ mtproto: true });\n request.storeMethod('set_client_DH_params', {\n nonce: auth.nonce,\n server_nonce: auth.serverNonce,\n encrypted_data: encryptedData\n });\n console.log(utils_1.dT(), 'Send set_client_DH_params');\n _this.mtpSendPlainRequest(auth.dcID, request.getBuffer()).then(function (deserializer) {\n var response = deserializer.fetchObject('Set_client_DH_params_answer');\n if (response._ != 'dh_gen_ok' && response._ != 'dh_gen_retry' && response._ != 'dh_gen_fail') {\n deferred.reject(new Error('[MT] Set_client_DH_params_answer response invalid: ' + response._));\n return false;\n }\n if (!bin_utils_1.bytesCmp(auth.nonce, response.nonce)) {\n deferred.reject(new Error('[MT] Set_client_DH_params_answer nonce mismatch'));\n return false;\n }\n if (!bin_utils_1.bytesCmp(auth.serverNonce, response.server_nonce)) {\n deferred.reject(new Error('[MT] Set_client_DH_params_answer server_nonce mismatch'));\n return false;\n }\n cryptoworker_1.default.modPow(auth.gA, auth.b, auth.dhPrime).then(function (authKey) {\n var authKeyHash = bin_utils_1.sha1BytesSync(authKey), authKeyAux = authKeyHash.slice(0, 8), authKeyID = authKeyHash.slice(-8);\n console.log(utils_1.dT(), 'Got Set_client_DH_params_answer', response._);\n switch (response._) {\n case 'dh_gen_ok':\n var newNonceHash1 = bin_utils_1.sha1BytesSync(auth.newNonce.concat([1], authKeyAux)).slice(-16);\n if (!bin_utils_1.bytesCmp(newNonceHash1, response.new_nonce_hash1)) {\n deferred.reject(new Error('[MT] Set_client_DH_params_answer new_nonce_hash1 mismatch'));\n return false;\n }\n var serverSalt = bin_utils_1.bytesXor(auth.newNonce.slice(0, 8), auth.serverNonce.slice(0, 8));\n // console.log('Auth successfull!', authKeyID, authKey, serverSalt);\n auth.authKeyID = authKeyID;\n auth.authKey = authKey;\n auth.serverSalt = serverSalt;\n deferred.resolve(auth);\n break;\n case 'dh_gen_retry':\n var newNonceHash2 = bin_utils_1.sha1BytesSync(auth.newNonce.concat([2], authKeyAux)).slice(-16);\n if (!bin_utils_1.bytesCmp(newNonceHash2, response.new_nonce_hash2)) {\n deferred.reject(new Error('[MT] Set_client_DH_params_answer new_nonce_hash2 mismatch'));\n return false;\n }\n return _this.mtpSendSetClientDhParams(auth);\n case 'dh_gen_fail':\n var newNonceHash3 = bin_utils_1.sha1BytesSync(auth.newNonce.concat([3], authKeyAux)).slice(-16);\n if (!bin_utils_1.bytesCmp(newNonceHash3, response.new_nonce_hash3)) {\n deferred.reject(new Error('[MT] Set_client_DH_params_answer new_nonce_hash3 mismatch'));\n return false;\n }\n deferred.reject(new Error('[MT] Set_client_DH_params_answer fail'));\n return false;\n }\n }, deferred.reject);\n }, deferred.reject);\n }, deferred.reject);\n };\n // mtpAuth\n Authorizer.prototype.auth = function (dcID) {\n var _this = this;\n if (dcID in this.cached) {\n return this.cached[dcID];\n }\n var nonce = [];\n for (var i = 0; i < 16; i++) {\n nonce.push(bin_utils_1.nextRandomInt(0xFF));\n }\n if (!MTProto.dcConfigurator.chooseServer(dcID)) {\n return Promise.reject(new Error('[MT] No server found for dc ' + dcID));\n }\n var promise = new Promise(function (resolve, reject) {\n var auth = {\n dcID: dcID,\n nonce: nonce,\n deferred: { resolve: resolve, reject: reject }\n };\n //this.cached[dcID] = auth.deferred.promise;\n _this.cached[dcID] = promise;\n setTimeout(function () {\n _this.mtpSendReqPQ(auth);\n });\n }).catch(function () {\n delete _this.cached[dcID];\n });\n return promise;\n //return this.cached[dcID];\n };\n return Authorizer;\n }());\n MTProto.Authorizer = Authorizer;\n var NetworkerFactory = /** @class */ (function () {\n function NetworkerFactory( /*public AppRuntimeManager: any , $rootScope: any */) {\n /* delete $http.defaults.headers.post['Content-Type']\n delete $http.defaults.headers.common['Accept'] */\n this.updatesProcessor = null;\n this.iii = 0;\n this.offline = false;\n this.offlineInited = false;\n this.akStopped = false;\n /* $rootScope.retryOnline = function() {\n $(document.body).trigger('online');\n } */\n }\n NetworkerFactory.prototype.startAll = function () {\n if (this.akStopped) {\n this.akStopped = false;\n // @ts-ignore\n this.updatesProcessor({\n _: 'new_session_created'\n }, true);\n }\n };\n NetworkerFactory.prototype.stopAll = function () {\n this.akStopped = true;\n };\n NetworkerFactory.prototype.setUpdatesProcessor = function (callback) {\n this.updatesProcessor = callback;\n };\n NetworkerFactory.prototype.getNetworker = function (dcID, authKey, serverSalt, options) {\n console.log(utils_1.dT(), 'NetworkerFactory: creating new instance of MTPNetworker...');\n return new mtnetworker_1.MTPNetworker(this, dcID, authKey, serverSalt, options);\n };\n return NetworkerFactory;\n }());\n MTProto.NetworkerFactory = NetworkerFactory;\n var ApiManager = /** @class */ (function () {\n function ApiManager() {\n //MtpSingleInstanceService.start();\n var _this = this;\n this.cachedNetworkers = {};\n this.cachedUploadNetworkers = {};\n this.cachedExportPromise = {};\n this.baseDcID = false;\n this.telegramMeNotified = false;\n storage_1.default.get('dc').then(function (dcID) {\n if (dcID) {\n _this.baseDcID = dcID;\n }\n });\n }\n ApiManager.prototype.telegramMeNotify = function (newValue) {\n if (this.telegramMeNotified !== newValue) {\n this.telegramMeNotified = newValue;\n exports.telegramMeWebService.setAuthorized(this.telegramMeNotified);\n }\n };\n // mtpSetUserAuth\n ApiManager.prototype.setUserAuth = function (dcID, userAuth) {\n var fullUserAuth = Object.assign({ dcID: dcID }, userAuth);\n storage_1.default.set({\n dc: dcID,\n user_auth: fullUserAuth\n });\n this.telegramMeNotify(true);\n $rootScope.$broadcast('user_auth', fullUserAuth);\n this.baseDcID = dcID;\n };\n // mtpLogOut\n ApiManager.prototype.logOut = function () {\n var _this = this;\n var storageKeys = [];\n for (var dcID = 1; dcID <= 5; dcID++) {\n storageKeys.push('dc' + dcID + '_auth_key');\n }\n // WebPushApiManager.forceUnsubscribe(); // WARNING\n return storage_1.default.get(storageKeys).then(function (storageResult) {\n var logoutPromises = [];\n for (var i = 0; i < storageResult.length; i++) {\n if (storageResult[i]) {\n logoutPromises.push(_this.invokeApi('auth.logOut', {}, { dcID: i + 1, ignoreErrors: true }));\n }\n }\n return Promise.all(logoutPromises).then(function () {\n storage_1.default.remove('dc', 'user_auth');\n _this.baseDcID = false;\n _this.telegramMeNotify(false);\n return _this.mtpClearStorage();\n }, function (error) {\n storageKeys.push('dc', 'user_auth');\n storage_1.default.remove(storageKeys);\n _this.baseDcID = false;\n error.handled = true;\n _this.telegramMeNotify(false);\n return _this.mtpClearStorage();\n });\n });\n };\n ApiManager.prototype.mtpClearStorage = function () {\n var saveKeys = ['user_auth', 't_user_auth', 'dc', 't_dc'];\n for (var dcID = 1; dcID <= 5; dcID++) {\n saveKeys.push('dc' + dcID + '_auth_key');\n saveKeys.push('t_dc' + dcID + '_auth_key');\n }\n storage_1.default.noPrefix();\n storage_1.default.get(saveKeys).then(function (values) {\n storage_1.default.clear().then(function () {\n var restoreObj = {};\n saveKeys.forEach(function (key, i) {\n var value = values[i];\n if (value !== false && value !== undefined) {\n restoreObj[key] = value;\n }\n });\n storage_1.default.noPrefix();\n return storage_1.default.set(restoreObj);\n });\n });\n };\n // mtpGetNetworker\n ApiManager.prototype.getNetworker = function (dcID, options) {\n if (options === void 0) { options = {}; }\n var cache = (options.fileUpload || options.fileDownload)\n ? this.cachedUploadNetworkers\n : this.cachedNetworkers;\n if (!dcID) {\n throw new Error('get Networker without dcID');\n }\n if (cache[dcID] !== undefined) {\n return Promise.resolve(cache[dcID]);\n //return qSync.when(cache[dcID]);\n }\n var akk = 'dc' + dcID + '_auth_key';\n var ssk = 'dc' + dcID + '_server_salt';\n // WARNING added []\n return storage_1.default.get([akk, ssk]).then(function (result) {\n if (cache[dcID] !== undefined) {\n return cache[dcID];\n }\n var authKeyHex = result[0];\n var serverSaltHex = result[1];\n // console.log('ass', dcID, authKeyHex, serverSaltHex)\n if (authKeyHex && authKeyHex.length == 512) {\n if (!serverSaltHex || serverSaltHex.length != 16) {\n serverSaltHex = 'AAAAAAAAAAAAAAAA';\n }\n var authKey = bin_utils_1.bytesFromHex(authKeyHex);\n var serverSalt = bin_utils_1.bytesFromHex(serverSaltHex);\n return cache[dcID] = MTProto.networkerFactory.getNetworker(dcID, authKey, serverSalt, options);\n }\n if (!options.createNetworker) {\n return Promise.reject({ type: 'AUTH_KEY_EMPTY', code: 401 });\n //return $q.reject({type: 'AUTH_KEY_EMPTY', code: 401})\n }\n return MTProto.authorizer.auth(dcID).then(function (auth) {\n var _a;\n var storeObj = (_a = {},\n _a[akk] = bin_utils_1.bytesToHex(auth.authKey),\n _a[ssk] = bin_utils_1.bytesToHex(auth.serverSalt),\n _a);\n storage_1.default.set(storeObj);\n return cache[dcID] = MTProto.networkerFactory.getNetworker(dcID, auth.authKey, auth.serverSalt, options);\n }, function (error) {\n console.log('Get networker error', error, error.stack);\n return Promise.reject(error);\n //return $q.reject(error);\n });\n });\n };\n // mtpInvokeApi\n ApiManager.prototype.invokeApi = function (method, params, options) {\n var _this = this;\n if (params === void 0) { params = {}; }\n if (options === void 0) { options = {}; }\n console.log(utils_1.dT(), 'Invoke api', method, params, options);\n return new Promise(function (resolve, reject) {\n var rejectPromise = function (error) {\n if (!error) {\n error = { type: 'ERROR_EMPTY' };\n }\n else if (!utils_1.isObject(error)) {\n error = { message: error };\n }\n reject(error);\n if (options.ignoreErrors) {\n return;\n }\n if (error.code == 406) {\n error.handled = true;\n }\n if (!options.noErrorBox) {\n error.input = method;\n error.stack = stack || (error.originalError && error.originalError.stack) || error.stack || (new Error()).stack;\n setTimeout(function () {\n if (!error.handled) {\n if (error.code == 401) {\n // @ts-ignore WARNING!\n _this.logOut().finally(function () {\n if (location.protocol == 'http:' &&\n !Config.Modes.http &&\n Config.App.domains.indexOf(location.hostname) != -1) {\n location.href = location.href.replace(/^http:/, 'https:');\n }\n else {\n location.hash = '/login';\n // AppRuntimeManager.reload(); // WARNING\n }\n });\n }\n else {\n // ErrorService.show({error: error}); // WARNING\n }\n error.handled = true;\n }\n }, 100);\n }\n };\n var dcID;\n var cachedNetworker;\n var stack = (new Error()).stack || 'empty stack';\n var performRequest = function (networker) {\n return (cachedNetworker = networker)\n .wrapApiCall(method, params, options)\n .then(resolve, function (error) {\n console.error(utils_1.dT(), 'Error', error.code, error.type, _this.baseDcID, dcID);\n if (error.code == 401 && _this.baseDcID == dcID) {\n storage_1.default.remove('dc', 'user_auth');\n _this.telegramMeNotify(false);\n rejectPromise(error);\n }\n else if (error.code == 401 && _this.baseDcID && dcID != _this.baseDcID) {\n if (_this.cachedExportPromise[dcID] === undefined) {\n var promise = new Promise(function (exportResolve, exportReject) {\n _this.invokeApi('auth.exportAuthorization', { dc_id: dcID }, { noErrorBox: true }).then(function (exportedAuth) {\n _this.invokeApi('auth.importAuthorization', {\n id: exportedAuth.id,\n bytes: exportedAuth.bytes\n }, { dcID: dcID, noErrorBox: true }).then(exportResolve, exportReject);\n }, exportReject);\n });\n _this.cachedExportPromise[dcID] = promise;\n }\n _this.cachedExportPromise[dcID].then(function () {\n (cachedNetworker = networker).wrapApiCall(method, params, options).then(resolve, rejectPromise);\n }, rejectPromise);\n }\n else if (error.code == 303) {\n var newDcID = error.type.match(/^(PHONE_MIGRATE_|NETWORK_MIGRATE_|USER_MIGRATE_)(\\d+)/)[2];\n if (newDcID != dcID) {\n if (options.dcID) {\n options.dcID = newDcID;\n }\n else {\n storage_1.default.set({ dc: _this.baseDcID = newDcID });\n }\n _this.getNetworker(newDcID, options).then(function (networker) {\n networker.wrapApiCall(method, params, options).then(resolve, rejectPromise);\n }, rejectPromise);\n }\n }\n else if (!options.rawError && error.code == 420) {\n var waitTime = error.type.match(/^FLOOD_WAIT_(\\d+)/)[1] || 10;\n if (waitTime > (options.timeout || 60)) {\n return rejectPromise(error);\n }\n setTimeout(function () {\n performRequest(cachedNetworker);\n }, waitTime * 1000);\n }\n else if (!options.rawError && (error.code == 500 || error.type == 'MSG_WAIT_FAILED')) {\n var now = utils_1.tsNow();\n if (options.stopTime) {\n if (now >= options.stopTime) {\n return rejectPromise(error);\n }\n }\n else {\n options.stopTime = now + (options.timeout !== undefined ? options.timeout : 10) * 1000;\n }\n options.waitTime = options.waitTime ? Math.min(60, options.waitTime * 1.5) : 1;\n setTimeout(function () {\n performRequest(cachedNetworker);\n }, options.waitTime * 1000);\n }\n else {\n rejectPromise(error);\n }\n });\n };\n if (dcID = (options.dcID || _this.baseDcID)) {\n _this.getNetworker(dcID, options).then(performRequest, rejectPromise);\n }\n else {\n storage_1.default.get('dc').then(function (baseDcID) {\n _this.getNetworker(dcID = baseDcID || 2, options).then(performRequest, rejectPromise);\n });\n }\n });\n };\n // mtpGetUserID\n ApiManager.prototype.getUserID = function () {\n var _this = this;\n return storage_1.default.get('user_auth').then(function (auth) {\n _this.telegramMeNotify(auth && auth.id > 0 || false);\n return auth.id || 0;\n });\n };\n ApiManager.prototype.getBaseDcID = function () {\n return this.baseDcID || false;\n };\n return ApiManager;\n }());\n MTProto.ApiManager = ApiManager;\n var ApiFileManager = /** @class */ (function () {\n function ApiFileManager() {\n this.cachedFs = false;\n this.cachedFsPromise = false;\n this.cachedSavePromises = {};\n this.cachedDownloadPromises = {};\n this.cachedDownloads = {};\n this.downloadPulls = {};\n this.downloadActives = {};\n this.index = 0;\n }\n ApiFileManager.prototype.downloadRequest = function (dcID, cb, activeDelta) {\n var _this = this;\n if (this.downloadPulls[dcID] === undefined) {\n this.downloadPulls[dcID] = [];\n this.downloadActives[dcID] = 0;\n }\n var downloadPull = this.downloadPulls[dcID];\n var promise = new Promise(function (resolve, reject) {\n // WARNING deferred!\n downloadPull.push({ cb: cb, deferred: { resolve: resolve, reject: reject }, activeDelta: activeDelta });\n });\n setTimeout(function () {\n _this.downloadCheck(dcID);\n }, 0);\n return promise;\n };\n ApiFileManager.prototype.downloadCheck = function (dcID) {\n var _this = this;\n var downloadPull = this.downloadPulls[dcID];\n var downloadLimit = dcID == 'upload' ? 11 : 5;\n if (this.downloadActives[dcID] >= downloadLimit || !downloadPull || !downloadPull.length) {\n return false;\n }\n var data = downloadPull.shift();\n var activeDelta = data.activeDelta || 1;\n this.downloadActives[dcID] += activeDelta;\n this.index++;\n data.cb()\n .then(function (result) {\n _this.downloadActives[dcID] -= activeDelta;\n _this.downloadCheck(dcID);\n data.deferred.resolve(result);\n }, function (error) {\n _this.downloadActives[dcID] -= activeDelta;\n _this.downloadCheck(dcID);\n data.deferred.reject(error);\n });\n };\n ApiFileManager.prototype.getFileName = function (location) {\n switch (location._) {\n case 'inputDocumentFileLocation':\n var fileName = (location.file_name || '').split('.', 2);\n var ext = fileName[1] || '';\n if (location.stickerType == 1 /* && !WebpManager.isWebpSupported() */) { // warning\n ext += 'webp'; /* 'png'; */\n }\n else if (location.stickerType == 2) {\n ext += 'tgs';\n }\n var versionPart = location.version ? ('v' + location.version) : '';\n return fileName[0] + '_' + location.id + versionPart + (ext ? '.' + ext : ext);\n default:\n if (!location.volume_id && !location.file_reference) {\n console.trace('Empty location', location);\n }\n var ext = 'jpg';\n if (location.stickerType == 1) {\n ext = 'webp' /* WebpManager.isWebpSupported() ? 'webp' : 'png'*/;\n }\n else if (location.stickerType == 2) {\n ext += 'tgs';\n }\n if (location.volume_id) {\n return location.volume_id + '_' + location.local_id + '_' + location.secret + '.' + ext;\n }\n else {\n return location.id + '_' + location.access_hash + '.' + ext;\n }\n }\n };\n ApiFileManager.prototype.getTempFileName = function (file) {\n var size = file.size || -1;\n var random = bin_utils_1.nextRandomInt(0xFFFFFFFF);\n return '_temp' + random + '_' + size;\n };\n ApiFileManager.prototype.getCachedFile = function (location) {\n if (!location) {\n return false;\n }\n var fileName = this.getFileName(location);\n return this.cachedDownloads[fileName] || false;\n };\n ApiFileManager.prototype.getFileStorage = function () {\n if (!Config.Modes.memory_only) {\n /* if(TmpfsFileStorage.isAvailable()) {\n return TmpfsFileStorage;\n } */\n if (idb_1.default.isAvailable()) {\n return idb_1.default;\n }\n }\n return idb_1.default /* MemoryFileStorage */;\n };\n ApiFileManager.prototype.saveSmallFile = function (location, bytes) {\n var _this = this;\n var fileName = this.getFileName(location);\n if (!this.cachedSavePromises[fileName]) {\n this.cachedSavePromises[fileName] = this.getFileStorage().saveFile(fileName, bytes).then(function (blob) {\n return _this.cachedDownloads[fileName] = blob;\n }, function (error) {\n delete _this.cachedSavePromises[fileName];\n });\n }\n return this.cachedSavePromises[fileName];\n };\n ApiFileManager.prototype.downloadSmallFile = function (location, options) {\n var _this = this;\n if (options === void 0) { options = {}; }\n if (!filemanager_1.default.isAvailable()) {\n return Promise.reject({ type: 'BROWSER_BLOB_NOT_SUPPORTED' });\n }\n var dcID = options.dcID || location.dc_id;\n var mimeType = options.mimeType || 'image/jpeg';\n var fileName = this.getFileName(location);\n var cachedPromise = this.cachedSavePromises[fileName] || this.cachedDownloadPromises[fileName];\n if (cachedPromise) {\n return cachedPromise;\n }\n var fileStorage = this.getFileStorage();\n return this.cachedDownloadPromises[fileName] = fileStorage.getFile(fileName).then(function (blob) {\n return _this.cachedDownloads[fileName] = blob;\n }, function () {\n var downloadPromise = _this.downloadRequest(dcID, function () {\n var inputLocation = location;\n if (!inputLocation._ || inputLocation._ == 'fileLocation') {\n inputLocation = Object.assign({}, location, { _: 'inputFileLocation' });\n }\n var params = {\n flags: 0,\n location: inputLocation,\n offset: 0,\n limit: 1024 * 1024\n };\n console.log('next small promise', params);\n return MTProto.apiManager.invokeApi('upload.getFile', params, {\n dcID: dcID,\n fileDownload: true,\n createNetworker: true,\n noErrorBox: true\n });\n }, dcID);\n var processDownloaded = function (bytes) {\n return Promise.resolve(bytes);\n /* if(!location.sticker || WebpManager.isWebpSupported()) {\n return qSync.when(bytes);\n }\n \n return WebpManager.getPngBlobFromWebp(bytes); */\n };\n return fileStorage.getFileWriter(fileName, mimeType).then(function (fileWriter) {\n return downloadPromise.then(function (result) {\n return processDownloaded(result.bytes).then(function (proccessedResult) {\n return filemanager_1.default.write(fileWriter, proccessedResult).then(function () {\n return _this.cachedDownloads[fileName] = fileWriter.finalize();\n });\n });\n });\n });\n });\n };\n ApiFileManager.prototype.getDownloadedFile = function (location, size) {\n var fileStorage = this.getFileStorage();\n var fileName = this.getFileName(location);\n return fileStorage.getFile(fileName, size);\n };\n ApiFileManager.prototype.downloadFile = function (dcID, location, size, options) {\n var _this = this;\n if (options === void 0) { options = {}; }\n if (!filemanager_1.default.isAvailable()) {\n return Promise.reject({ type: 'BROWSER_BLOB_NOT_SUPPORTED' });\n }\n /* var processSticker = false;\n if(location.sticker && !WebpManager.isWebpSupported()) {\n if(options.toFileEntry || size > 524288) {\n delete location.sticker;\n } else {\n processSticker = true;\n options.mime = 'image/png';\n }\n } */\n // console.log(dT(), 'Dload file', dcID, location, size)\n var fileName = this.getFileName(location);\n var toFileEntry = options.toFileEntry || null;\n var cachedPromise = this.cachedSavePromises[fileName] || this.cachedDownloadPromises[fileName];\n var fileStorage = this.getFileStorage();\n // console.log(dT(), 'fs', fileStorage.name, fileName, cachedPromise)\n if (cachedPromise) {\n if (toFileEntry) {\n return cachedPromise.then(function (blob) {\n return filemanager_1.default.copy(blob, toFileEntry);\n });\n }\n return cachedPromise;\n }\n //var deferred = $q.defer()\n var deferredHelper = { notify: function () { } };\n var deferred = new Promise(function (resolve, reject) {\n deferredHelper.resolve = resolve;\n deferredHelper.reject = reject;\n });\n Object.assign(deferred, deferredHelper);\n var canceled = false;\n var resolved = false;\n var mimeType = options.mime_type || 'image/jpeg', cacheFileWriter;\n var errorHandler = function (error) {\n deferred.reject(error);\n errorHandler = function () { };\n if (cacheFileWriter &&\n (!error || error.type != 'DOWNLOAD_CANCELED')) {\n cacheFileWriter.truncate(0);\n }\n };\n fileStorage.getFile(fileName, size).then(function (blob) {\n if (toFileEntry) {\n filemanager_1.default.copy(blob, toFileEntry).then(function () {\n deferred.resolve();\n }, errorHandler);\n }\n else {\n deferred.resolve(_this.cachedDownloads[fileName] = blob);\n }\n }, function () {\n var fileWriterPromise = toFileEntry ? filemanager_1.default.getFileWriter(toFileEntry) : fileStorage.getFileWriter(fileName, mimeType);\n var processDownloaded = function (bytes) {\n return Promise.resolve(bytes);\n /* if(!processSticker) {\n return Promise.resolve(bytes);\n }\n \n return WebpManager.getPngBlobFromWebp(bytes); */\n };\n fileWriterPromise.then(function (fileWriter) {\n cacheFileWriter = fileWriter;\n var limit = 524288, offset;\n var startOffset = 0;\n var writeFilePromise = Promise.resolve(), writeFileDeferred;\n if (fileWriter.length) {\n startOffset = fileWriter.length;\n if (startOffset >= size) {\n if (toFileEntry) {\n deferred.resolve();\n }\n else {\n deferred.resolve(_this.cachedDownloads[fileName] = fileWriter.finalize());\n }\n return;\n }\n fileWriter.seek(startOffset);\n deferred.notify({ done: startOffset, total: size });\n }\n var _loop_1 = function () {\n //writeFileDeferred = $q.defer();\n var writeFileDeferredHelper = {};\n writeFileDeferred = new Promise(function (resolve, reject) {\n writeFileDeferredHelper.resolve = resolve;\n writeFileDeferredHelper.reject = reject;\n });\n Object.assign(writeFileDeferred, writeFileDeferredHelper);\n ;\n (function (isFinal, offset, writeFileDeferred, writeFilePromise) {\n return _this.downloadRequest(dcID, function () {\n if (canceled) {\n return Promise.resolve();\n }\n return MTProto.apiManager.invokeApi('upload.getFile', {\n flags: 0,\n location: location,\n offset: offset,\n limit: limit\n }, {\n dcID: dcID,\n fileDownload: true,\n singleInRequest: 'safari' in window,\n createNetworker: true\n });\n }, dcID).then(function (result) {\n writeFilePromise.then(function () {\n if (canceled) {\n return Promise.resolve();\n }\n return processDownloaded(result.bytes).then(function (processedResult) {\n return filemanager_1.default.write(fileWriter, processedResult).then(function () {\n writeFileDeferred.resolve();\n }, errorHandler).then(function () {\n if (isFinal) {\n resolved = true;\n if (toFileEntry) {\n deferred.resolve();\n }\n else {\n deferred.resolve(_this.cachedDownloads[fileName] = fileWriter.finalize());\n }\n }\n else {\n deferred.notify({ done: offset + limit, total: size });\n }\n });\n });\n });\n });\n })(offset + limit >= size, offset, writeFileDeferred, writeFilePromise);\n writeFilePromise = writeFileDeferred;\n };\n for (offset = startOffset; offset < size; offset += limit) {\n _loop_1();\n }\n });\n });\n deferred.cancel = function () {\n if (!canceled && !resolved) {\n canceled = true;\n delete _this.cachedDownloadPromises[fileName];\n errorHandler({ type: 'DOWNLOAD_CANCELED' });\n }\n };\n if (!toFileEntry) {\n this.cachedDownloadPromises[fileName] = deferred;\n }\n return deferred;\n };\n ApiFileManager.prototype.uploadFile = function (file) {\n var fileSize = file.size, isBigFile = fileSize >= 10485760, canceled = false, resolved = false, doneParts = 0, partSize = 262144, // 256 Kb\n activeDelta = 2;\n if (fileSize > 67108864) {\n partSize = 524288;\n activeDelta = 4;\n }\n else if (fileSize < 102400) {\n partSize = 32768;\n activeDelta = 1;\n }\n var totalParts = Math.ceil(fileSize / partSize);\n if (totalParts > 3000) {\n return Promise.reject({ type: 'FILE_TOO_BIG' });\n }\n var fileID = [bin_utils_1.nextRandomInt(0xFFFFFFFF), bin_utils_1.nextRandomInt(0xFFFFFFFF)];\n //var deferred = $q.defer();\n var deferredHelper = { notify: function () { } };\n var deferred = new Promise(function (resolve, reject) {\n deferredHelper.resolve = resolve;\n deferredHelper.reject = reject;\n return Promise.resolve();\n });\n Object.assign(deferred, deferredHelper);\n var errorHandler = function (error) {\n console.error(utils_1.dT(), 'Up Error', error);\n deferred.reject(error);\n canceled = true;\n errorHandler = function () { };\n };\n var _part = 0, resultInputFile = {\n _: isBigFile ? 'inputFileBig' : 'inputFile',\n id: fileID,\n parts: totalParts,\n name: file.name,\n md5_checksum: ''\n };\n var _loop_2 = function (offset) {\n var part = _part++; // 0, 1\n this_1.downloadRequest('upload', function () {\n return new Promise(function (uploadResolve, uploadReject) {\n var reader = new FileReader();\n var blob = file.slice(offset, offset + partSize);\n reader.onloadend = function (e) {\n if (canceled) {\n uploadReject();\n return;\n }\n if (e.target.readyState != FileReader.DONE) {\n console.error(utils_1.dT(), 'wrong readyState!');\n return;\n }\n console.log(utils_1.dT(), 'Starting to upload file, isBig:', isBigFile, fileID, part);\n MTProto.apiManager.invokeApi(isBigFile ? 'upload.saveBigFilePart' : 'upload.saveFilePart', {\n file_id: fileID,\n file_part: part,\n file_total_parts: totalParts,\n bytes: e.target.result\n }, {\n startMaxLength: partSize + 256,\n fileUpload: true,\n singleInRequest: true\n }).then(function (result) {\n doneParts++;\n uploadResolve();\n console.log(utils_1.dT(), 'Progress', doneParts * partSize / fileSize);\n if (doneParts >= totalParts) {\n deferred.resolve(resultInputFile);\n resolved = true;\n }\n else {\n deferred.notify({ done: doneParts * partSize, total: fileSize });\n }\n }, errorHandler);\n };\n reader.readAsArrayBuffer(blob);\n });\n }, activeDelta);\n };\n var this_1 = this;\n for (var offset = 0; offset < fileSize; offset += partSize) {\n _loop_2(offset);\n }\n deferred.cancel = function () {\n console.log('cancel upload', canceled, resolved);\n if (!canceled && !resolved) {\n canceled = true;\n errorHandler({ type: 'UPLOAD_CANCELED' });\n }\n };\n return deferred;\n };\n return ApiFileManager;\n }());\n MTProto.ApiFileManager = ApiFileManager;\n var ServerTimeManager = /** @class */ (function () {\n function ServerTimeManager() {\n var _this = this;\n this.timestampNow = utils_1.tsNow(true);\n this.midnightNoOffset = this.timestampNow - (this.timestampNow % 86400);\n this.midnightOffseted = new Date();\n this.midnightOffset = this.midnightNoOffset - (Math.floor(+this.midnightOffseted / 1000));\n this.serverTimeOffset = 0;\n this.timeParams = {\n midnightOffset: this.midnightOffset,\n serverTimeOffset: this.serverTimeOffset\n };\n this.midnightOffseted.setHours(0);\n this.midnightOffseted.setMinutes(0);\n this.midnightOffseted.setSeconds(0);\n storage_1.default.get('server_time_offset').then(function (to) {\n if (to) {\n _this.serverTimeOffset = to;\n _this.timeParams.serverTimeOffset = to;\n }\n });\n }\n return ServerTimeManager;\n }());\n MTProto.ServerTimeManager = ServerTimeManager;\n var PasswordManager = /** @class */ (function () {\n function PasswordManager() {\n }\n PasswordManager.prototype.getState = function (options) {\n if (options === void 0) { options = {}; }\n return MTProto.apiManager.invokeApi('account.getPassword', {}, options).then(function (result) {\n return result;\n });\n };\n /* public updateSettings(state: any, settings: any) {\n var currentHashPromise;\n var newHashPromise;\n var params: any = {\n new_settings: {\n _: 'account.passwordInputSettings',\n flags: 0,\n hint: settings.hint || ''\n }\n };\n \n if(typeof settings.cur_password === 'string' &&\n settings.cur_password.length > 0) {\n currentHashPromise = this.makePasswordHash(state.current_salt, settings.cur_password);\n } else {\n currentHashPromise = Promise.resolve([]);\n }\n \n if (typeof settings.new_password === 'string' &&\n settings.new_password.length > 0) {\n var saltRandom = new Array(8);\n var newSalt = bufferConcat(state.new_salt, saltRandom);\n secureRandom.nextBytes(saltRandom);\n newHashPromise = this.makePasswordHash(newSalt, settings.new_password);\n params.new_settings.new_salt = newSalt;\n params.new_settings.flags |= 1;\n } else {\n if(typeof settings.new_password === 'string') {\n params.new_settings.flags |= 1;\n params.new_settings.new_salt = [];\n }\n newHashPromise = Promise.resolve([]);\n }\n \n if(typeof settings.email === 'string') {\n params.new_settings.flags |= 2;\n params.new_settings.email = settings.email || '';\n }\n \n return Promise.all([currentHashPromise, newHashPromise]).then((hashes) => {\n params.current_password_hash = hashes[0];\n params.new_settings.new_password_hash = hashes[1];\n \n return apiManager.invokeApi('account.updatePasswordSettings', params);\n });\n } */\n PasswordManager.prototype.check = function (state, password, options) {\n if (options === void 0) { options = {}; }\n return this.computeCheck(password, state).then(function (inputCheckPassword) {\n return MTProto.apiManager.invokeApi('auth.checkPassword', {\n password: inputCheckPassword\n }, options);\n });\n };\n PasswordManager.prototype.requestRecovery = function (options) {\n if (options === void 0) { options = {}; }\n return MTProto.apiManager.invokeApi('auth.requestPasswordRecovery', {}, options);\n };\n PasswordManager.prototype.recover = function (code, options) {\n if (options === void 0) { options = {}; }\n return MTProto.apiManager.invokeApi('auth.recoverPassword', {\n code: code\n }, options);\n };\n /* public makePasswordHash(salt: any, password: any) {\n var passwordUTF8 = unescape(encodeURIComponent(password));\n \n var buffer = new ArrayBuffer(passwordUTF8.length);\n var byteView = new Uint8Array(buffer);\n for(var i = 0, len = passwordUTF8.length; i < len; i++) {\n byteView[i] = passwordUTF8.charCodeAt(i);\n }\n \n buffer = bufferConcat(bufferConcat(salt, byteView), salt);\n \n return CryptoWorker.sha256Hash(buffer);\n } */\n PasswordManager.prototype.makePasswordHash = function (password, client_salt, server_salt) {\n var passwordUTF8 = unescape(encodeURIComponent(password));\n // @ts-ignore\n var textEncoder = new TextEncoder(\"utf-8\");\n var passwordBuffer = textEncoder.encode(passwordUTF8);\n // right\n var buffer = bin_utils_1.bufferConcats(client_salt, passwordBuffer, client_salt);\n return cryptoworker_1.default.sha256Hash(buffer).then(function (buffer) {\n console.log('encoded 1', bin_utils_1.bytesToHex(new Uint8Array(buffer)));\n buffer = bin_utils_1.bufferConcats(server_salt, buffer, server_salt);\n return cryptoworker_1.default.sha256Hash(buffer).then(function (buffer) {\n console.log('encoded 2', buffer, bin_utils_1.bytesToHex(new Uint8Array(buffer)));\n return cryptoworker_1.default.pbkdf2(new Uint8Array(buffer), client_salt, 100000).then(function (hash) {\n console.log('encoded 3', hash, bin_utils_1.bytesToHex(new Uint8Array(hash)));\n hash = bin_utils_1.bufferConcats(server_salt, hash, server_salt);\n return cryptoworker_1.default.sha256Hash(hash).then(function (buffer) {\n console.log('got password hash:', buffer, bin_utils_1.bytesToHex(new Uint8Array(buffer)));\n return buffer;\n });\n });\n });\n });\n };\n PasswordManager.prototype.computeCheck = function (password, state) {\n return __awaiter(this, void 0, void 0, function () {\n var algo, p, B, g, check_prime_and_good, pw_hash, x, padArray, pForHash, gForHash, b_for_hash, g_x, k, kg_x, is_good_mod_exp_first, generate_and_check_random, _a, a, a_for_hash, u, g_b, ux, a_ux, S, K, h1, h2, buff, _b, _c, M1, out;\n var _this = this;\n return __generator(this, function (_d) {\n switch (_d.label) {\n case 0:\n algo = state.current_algo;\n p = leemon_1.str2bigInt(bin_utils_1.bytesToHex(algo.p), 16);\n B = leemon_1.str2bigInt(bin_utils_1.bytesToHex(state.srp_B), 16);\n g = leemon_1.int2bigInt(algo.g, 32, 256);\n console.log('p', leemon_1.bigInt2str(p, 16));\n console.log('B', leemon_1.bigInt2str(B, 16));\n check_prime_and_good = function (bytes, g) {\n var good_prime = 'c71caeb9c6b1c9048e6c522f70f13f73980d40238e3e21c14934d037563d930f48198a0aa7c14058229493d22530f4dbfa336f6e0ac925139543aed44cce7c3720fd51f69458705ac68cd4fe6b6b13abdc9746512969328454f18faf8c595f642477fe96bb2a941d5bcd1d4ac8cc49880708fa9b378e3c4f3a9060bee67cf9a4a4a695811051907e162753b56b0f6b410dba74d8a84b2a14b3144e0ef1284754fd17ed950d5965b4b9dd46582db1178d169c6bc465b0d6ff9ca3928fef5b9ae4e418fc15e83ebea0f87fa9ff5eed70050ded2849f47bf959d956850ce929851f0d8115f635b105ee2e4e15d04b2454bf6f4fadf034b10403119cd8e3b92fcc5b';\n if (bin_utils_1.bytesToHex(bytes) == good_prime && [3, 4, 5, 7].indexOf(g) !== -1) {\n return true;\n }\n // TO-DO check_prime_and_good_check\n };\n return [4 /*yield*/, this.makePasswordHash(password, new Uint8Array(algo.salt1), new Uint8Array(algo.salt2))];\n case 1:\n pw_hash = _d.sent();\n x = leemon_1.str2bigInt(bin_utils_1.bytesToHex(new Uint8Array(pw_hash)), 16);\n console.warn('computed pw_hash:', pw_hash, x, bin_utils_1.bytesToHex(new Uint8Array(pw_hash)));\n padArray = function (arr, len, fill) {\n if (fill === void 0) { fill = 0; }\n return Array(len).fill(fill).concat(arr).slice(-len);\n };\n pForHash = padArray(bin_utils_1.bytesFromHex(leemon_1.bigInt2str(p, 16)), 256);\n gForHash = padArray(bin_utils_1.bytesFromHex(leemon_1.bigInt2str(g, 16)), 256);\n b_for_hash = padArray(bin_utils_1.bytesFromHex(leemon_1.bigInt2str(B, 16)), 256);\n console.log(bin_utils_1.bytesToHex(pForHash));\n console.log(bin_utils_1.bytesToHex(gForHash));\n console.log(bin_utils_1.bytesToHex(b_for_hash));\n g_x = leemon_1.powMod(g, x, p);\n console.log('g_x', leemon_1.bigInt2str(g_x, 16));\n return [4 /*yield*/, cryptoworker_1.default.sha256Hash(bin_utils_1.bufferConcat(pForHash, gForHash))];\n case 2:\n k = _d.sent();\n k = leemon_1.str2bigInt(bin_utils_1.bytesToHex(new Uint8Array(k)), 16);\n console.log('k', leemon_1.bigInt2str(k, 16));\n kg_x = leemon_1.mod(leemon_1.mult(k, g_x), p);\n // good\n console.log('kg_x', leemon_1.bigInt2str(kg_x, 16));\n is_good_mod_exp_first = function (modexp, prime) {\n var diff = leemon_1.sub(prime, modexp);\n var min_diff_bits_count = 2048 - 64;\n var max_mod_exp_size = 256;\n if (leemon_1.negative(diff) ||\n leemon_1.bitSize(diff) < min_diff_bits_count ||\n leemon_1.bitSize(modexp) < min_diff_bits_count ||\n Math.floor((leemon_1.bitSize(modexp) + 7) / 8) > max_mod_exp_size)\n return false;\n return true;\n };\n generate_and_check_random = function () { return __awaiter(_this, void 0, void 0, function () {\n var random_size, a_1, A, a_for_hash_1, s, u_1;\n return __generator(this, function (_a) {\n switch (_a.label) {\n case 0:\n random_size = 256;\n _a.label = 1;\n case 1:\n if (!true) return [3 /*break*/, 4];\n a_1 = leemon_1.str2bigInt(bin_utils_1.bytesToHex(state.secure_random), 16);\n A = leemon_1.powMod(g, a_1, p);\n if (!is_good_mod_exp_first(A, p)) return [3 /*break*/, 3];\n a_for_hash_1 = bin_utils_1.bytesFromHex(leemon_1.bigInt2str(A, 16));\n return [4 /*yield*/, cryptoworker_1.default.sha256Hash(bin_utils_1.bufferConcat(new Uint8Array(a_for_hash_1), new Uint8Array(b_for_hash)))];\n case 2:\n s = _a.sent();\n u_1 = leemon_1.str2bigInt(bin_utils_1.bytesToHex(new Uint8Array(s)), 16);\n //if(u > 0)\n if (!leemon_1.isZero(u_1) && !leemon_1.negative(u_1))\n return [2 /*return*/, { a: a_1, a_for_hash: a_for_hash_1, u: u_1 }];\n _a.label = 3;\n case 3: return [3 /*break*/, 1];\n case 4: return [2 /*return*/];\n }\n });\n }); };\n return [4 /*yield*/, generate_and_check_random()];\n case 3:\n _a = _d.sent(), a = _a.a, a_for_hash = _a.a_for_hash, u = _a.u;\n console.log('a', leemon_1.bigInt2str(a, 16));\n console.log('a_for_hash', bin_utils_1.bytesToHex(a_for_hash));\n console.log('u', leemon_1.bigInt2str(u, 16));\n // g_b = (B - kg_x) % p\n console.log('B - kg_x', leemon_1.bigInt2str(leemon_1.sub(B, kg_x), 16));\n if (!leemon_1.greater(B, kg_x)) {\n console.log('negative');\n g_b = leemon_1.add(B, p);\n }\n else\n g_b = B;\n g_b = leemon_1.mod(leemon_1.sub(g_b, kg_x), p);\n ux = leemon_1.mult(u, x);\n a_ux = leemon_1.add(a, ux);\n S = leemon_1.powMod(g_b, a_ux, p);\n return [4 /*yield*/, cryptoworker_1.default.sha256Hash(padArray(bin_utils_1.bytesFromHex(leemon_1.bigInt2str(S, 16)), 256))];\n case 4:\n K = _d.sent();\n return [4 /*yield*/, cryptoworker_1.default.sha256Hash(pForHash)];\n case 5:\n h1 = _d.sent();\n return [4 /*yield*/, cryptoworker_1.default.sha256Hash(gForHash)];\n case 6:\n h2 = _d.sent();\n h1 = bin_utils_1.bytesXor(new Uint8Array(h1), new Uint8Array(h2));\n _b = bin_utils_1.bufferConcats;\n _c = [h1];\n return [4 /*yield*/, cryptoworker_1.default.sha256Hash(algo.salt1)];\n case 7:\n _c = _c.concat([_d.sent()]);\n return [4 /*yield*/, cryptoworker_1.default.sha256Hash(algo.salt2)];\n case 8:\n buff = _b.apply(void 0, _c.concat([_d.sent(),\n a_for_hash,\n b_for_hash,\n K]));\n return [4 /*yield*/, cryptoworker_1.default.sha256Hash(buff)];\n case 9:\n M1 = _d.sent();\n out = {\n _: 'inputCheckPasswordSRP',\n srp_id: state.srp_id,\n A: new Uint8Array(a_for_hash),\n M1: new Uint8Array(M1)\n };\n console.log('out', bin_utils_1.bytesToHex(out.A), bin_utils_1.bytesToHex(out.M1));\n return [2 /*return*/, out];\n }\n });\n });\n };\n return PasswordManager;\n }());\n MTProto.PasswordManager = PasswordManager;\n MTProto.passwordManager = new PasswordManager();\n MTProto.secureRandom = new jsbn_1.SecureRandom();\n //export const mtproto = new MTProto();\n MTProto.dcConfigurator = new DcConfigurator();\n MTProto.rsaKeysManager = new RSAKeysManager();\n MTProto.timeManager = new TimeManager();\n MTProto.authorizer = new Authorizer();\n MTProto.networkerFactory = new NetworkerFactory();\n MTProto.apiManager = new ApiManager();\n MTProto.apiFileManager = new ApiFileManager();\n MTProto.serverTimeManager = new ServerTimeManager();\n})(MTProto = exports.MTProto || (exports.MTProto = {}));\nwindow.MTProto = MTProto;\n" - }, - { - "id": 3, - "identifier": "/Users/kuzmenko/Documents/projects/tweb/node_modules/css-loader/dist/runtime/api.js", - "name": "./node_modules/css-loader/dist/runtime/api.js", - "index": 3, - "index2": 0, - "size": 2677, - "cacheable": true, - "built": true, - "optional": false, - "prefetched": false, - "chunks": [ - 0 - ], - "issuer": "/Users/kuzmenko/Documents/projects/tweb/node_modules/css-loader/dist/cjs.js!/Users/kuzmenko/Documents/projects/tweb/node_modules/overlayscrollbars/css/OverlayScrollbars.min.css", - "issuerId": 22, - "issuerName": "./node_modules/css-loader/dist/cjs.js!./node_modules/overlayscrollbars/css/OverlayScrollbars.min.css", - "issuerPath": [ - { - "id": 18, - "identifier": "/Users/kuzmenko/Documents/projects/tweb/node_modules/ts-loader/index.js!/Users/kuzmenko/Documents/projects/tweb/src/index.ts", - "name": "./src/index.ts", - "profile": { - "factory": 17, - "building": 2295 - } - }, - { - "id": 21, - "identifier": "/Users/kuzmenko/Documents/projects/tweb/node_modules/style-loader/dist/index.js!/Users/kuzmenko/Documents/projects/tweb/node_modules/css-loader/dist/cjs.js!/Users/kuzmenko/Documents/projects/tweb/node_modules/overlayscrollbars/css/OverlayScrollbars.min.css", - "name": "./node_modules/overlayscrollbars/css/OverlayScrollbars.min.css", - "profile": { - "factory": 1354, - "building": 0, - "dependencies": 287 - } - }, - { - "id": 22, - "identifier": "/Users/kuzmenko/Documents/projects/tweb/node_modules/css-loader/dist/cjs.js!/Users/kuzmenko/Documents/projects/tweb/node_modules/overlayscrollbars/css/OverlayScrollbars.min.css", - "name": "./node_modules/css-loader/dist/cjs.js!./node_modules/overlayscrollbars/css/OverlayScrollbars.min.css", - "profile": { - "factory": 185, - "building": 23 - } - } - ], - "profile": { - "factory": 726, - "building": 109 - }, - "failed": false, - "errors": 0, - "warnings": 0, - "assets": [], - "reasons": [ - { - "moduleId": 20, - "moduleIdentifier": "/Users/kuzmenko/Documents/projects/tweb/node_modules/css-loader/dist/cjs.js!/Users/kuzmenko/Documents/projects/tweb/node_modules/resolve-url-loader/index.js!/Users/kuzmenko/Documents/projects/tweb/node_modules/sass-loader/dist/cjs.js??ref--4-3!/Users/kuzmenko/Documents/projects/tweb/src/materialize.scss", - "module": "./node_modules/css-loader/dist/cjs.js!./node_modules/resolve-url-loader!./node_modules/sass-loader/dist/cjs.js??ref--4-3!./src/materialize.scss", - "moduleName": "./node_modules/css-loader/dist/cjs.js!./node_modules/resolve-url-loader!./node_modules/sass-loader/dist/cjs.js??ref--4-3!./src/materialize.scss", - "type": "cjs require", - "userRequest": "../node_modules/css-loader/dist/runtime/api.js", - "loc": "1:27-84" - }, - { - "moduleId": 22, - "moduleIdentifier": "/Users/kuzmenko/Documents/projects/tweb/node_modules/css-loader/dist/cjs.js!/Users/kuzmenko/Documents/projects/tweb/node_modules/overlayscrollbars/css/OverlayScrollbars.min.css", - "module": "./node_modules/css-loader/dist/cjs.js!./node_modules/overlayscrollbars/css/OverlayScrollbars.min.css", - "moduleName": "./node_modules/css-loader/dist/cjs.js!./node_modules/overlayscrollbars/css/OverlayScrollbars.min.css", - "type": "cjs require", - "userRequest": "../../css-loader/dist/runtime/api.js", - "loc": "1:27-74" - }, - { - "moduleId": 24, - "moduleIdentifier": "/Users/kuzmenko/Documents/projects/tweb/node_modules/css-loader/dist/cjs.js!/Users/kuzmenko/Documents/projects/tweb/node_modules/resolve-url-loader/index.js!/Users/kuzmenko/Documents/projects/tweb/node_modules/sass-loader/dist/cjs.js??ref--4-3!/Users/kuzmenko/Documents/projects/tweb/src/scss/style.scss", - "module": "./node_modules/css-loader/dist/cjs.js!./node_modules/resolve-url-loader!./node_modules/sass-loader/dist/cjs.js??ref--4-3!./src/scss/style.scss", - "moduleName": "./node_modules/css-loader/dist/cjs.js!./node_modules/resolve-url-loader!./node_modules/sass-loader/dist/cjs.js??ref--4-3!./src/scss/style.scss", - "type": "cjs require", - "userRequest": "../../node_modules/css-loader/dist/runtime/api.js", - "loc": "1:27-87" - }, - { - "moduleId": 28, - "moduleIdentifier": "/Users/kuzmenko/Documents/projects/tweb/node_modules/css-loader/dist/cjs.js!/Users/kuzmenko/Documents/projects/tweb/node_modules/resolve-url-loader/index.js!/Users/kuzmenko/Documents/projects/tweb/node_modules/sass-loader/dist/cjs.js??ref--4-3!/Users/kuzmenko/Documents/projects/tweb/src/scss/tgico.scss", - "module": "./node_modules/css-loader/dist/cjs.js!./node_modules/resolve-url-loader!./node_modules/sass-loader/dist/cjs.js??ref--4-3!./src/scss/tgico.scss", - "moduleName": "./node_modules/css-loader/dist/cjs.js!./node_modules/resolve-url-loader!./node_modules/sass-loader/dist/cjs.js??ref--4-3!./src/scss/tgico.scss", - "type": "cjs require", - "userRequest": "../../node_modules/css-loader/dist/runtime/api.js", - "loc": "1:27-87" - } - ], - "usedExports": true, - "providedExports": null, - "optimizationBailout": [ - "ModuleConcatenation bailout: Module is not an ECMAScript module" - ], - "depth": 3, - "source": "\"use strict\";\n\n/*\n MIT License http://www.opensource.org/licenses/mit-license.php\n Author Tobias Koppers @sokra\n*/\n// css base code, injected by the css-loader\n// eslint-disable-next-line func-names\nmodule.exports = function (useSourceMap) {\n var list = []; // return the list of modules as css string\n\n list.toString = function toString() {\n return this.map(function (item) {\n var content = cssWithMappingToString(item, useSourceMap);\n\n if (item[2]) {\n return \"@media \".concat(item[2], \"{\").concat(content, \"}\");\n }\n\n return content;\n }).join('');\n }; // import a list of modules into the list\n // eslint-disable-next-line func-names\n\n\n list.i = function (modules, mediaQuery) {\n if (typeof modules === 'string') {\n // eslint-disable-next-line no-param-reassign\n modules = [[null, modules, '']];\n }\n\n var alreadyImportedModules = {};\n\n for (var i = 0; i < this.length; i++) {\n // eslint-disable-next-line prefer-destructuring\n var id = this[i][0];\n\n if (id != null) {\n alreadyImportedModules[id] = true;\n }\n }\n\n for (var _i = 0; _i < modules.length; _i++) {\n var item = modules[_i]; // skip already imported module\n // this implementation is not 100% perfect for weird media query combinations\n // when a module is imported multiple times with different media queries.\n // I hope this will never occur (Hey this way we have smaller bundles)\n\n if (item[0] == null || !alreadyImportedModules[item[0]]) {\n if (mediaQuery && !item[2]) {\n item[2] = mediaQuery;\n } else if (mediaQuery) {\n item[2] = \"(\".concat(item[2], \") and (\").concat(mediaQuery, \")\");\n }\n\n list.push(item);\n }\n }\n };\n\n return list;\n};\n\nfunction cssWithMappingToString(item, useSourceMap) {\n var content = item[1] || ''; // eslint-disable-next-line prefer-destructuring\n\n var cssMapping = item[3];\n\n if (!cssMapping) {\n return content;\n }\n\n if (useSourceMap && typeof btoa === 'function') {\n var sourceMapping = toComment(cssMapping);\n var sourceURLs = cssMapping.sources.map(function (source) {\n return \"/*# sourceURL=\".concat(cssMapping.sourceRoot).concat(source, \" */\");\n });\n return [content].concat(sourceURLs).concat([sourceMapping]).join('\\n');\n }\n\n return [content].join('\\n');\n} // Adapted from convert-source-map (MIT)\n\n\nfunction toComment(sourceMap) {\n // eslint-disable-next-line no-undef\n var base64 = btoa(unescape(encodeURIComponent(JSON.stringify(sourceMap))));\n var data = \"sourceMappingURL=data:application/json;charset=utf-8;base64,\".concat(base64);\n return \"/*# \".concat(data, \" */\");\n}" - }, - { - "id": 4, - "identifier": "/Users/kuzmenko/Documents/projects/tweb/node_modules/style-loader/dist/runtime/injectStylesIntoStyleTag.js", - "name": "./node_modules/style-loader/dist/runtime/injectStylesIntoStyleTag.js", - "index": 4, - "index2": 2, - "size": 6909, - "cacheable": true, - "built": true, - "optional": false, - "prefetched": false, - "chunks": [ - 0 - ], - "issuer": "/Users/kuzmenko/Documents/projects/tweb/node_modules/style-loader/dist/index.js!/Users/kuzmenko/Documents/projects/tweb/node_modules/css-loader/dist/cjs.js!/Users/kuzmenko/Documents/projects/tweb/node_modules/resolve-url-loader/index.js!/Users/kuzmenko/Documents/projects/tweb/node_modules/sass-loader/dist/cjs.js??ref--4-3!/Users/kuzmenko/Documents/projects/tweb/src/materialize.scss", - "issuerId": 19, - "issuerName": "./src/materialize.scss", - "issuerPath": [ - { - "id": 18, - "identifier": "/Users/kuzmenko/Documents/projects/tweb/node_modules/ts-loader/index.js!/Users/kuzmenko/Documents/projects/tweb/src/index.ts", - "name": "./src/index.ts", - "profile": { - "factory": 17, - "building": 2295 - } - }, - { - "id": 19, - "identifier": "/Users/kuzmenko/Documents/projects/tweb/node_modules/style-loader/dist/index.js!/Users/kuzmenko/Documents/projects/tweb/node_modules/css-loader/dist/cjs.js!/Users/kuzmenko/Documents/projects/tweb/node_modules/resolve-url-loader/index.js!/Users/kuzmenko/Documents/projects/tweb/node_modules/sass-loader/dist/cjs.js??ref--4-3!/Users/kuzmenko/Documents/projects/tweb/src/materialize.scss", - "name": "./src/materialize.scss", - "profile": { - "factory": 1354, - "building": 0, - "dependencies": 287 - } - } - ], - "profile": { - "factory": 187, - "building": 2741, - "dependencies": 0 - }, - "failed": false, - "errors": 0, - "warnings": 0, - "assets": [], - "reasons": [ - { - "moduleId": 19, - "moduleIdentifier": "/Users/kuzmenko/Documents/projects/tweb/node_modules/style-loader/dist/index.js!/Users/kuzmenko/Documents/projects/tweb/node_modules/css-loader/dist/cjs.js!/Users/kuzmenko/Documents/projects/tweb/node_modules/resolve-url-loader/index.js!/Users/kuzmenko/Documents/projects/tweb/node_modules/sass-loader/dist/cjs.js??ref--4-3!/Users/kuzmenko/Documents/projects/tweb/src/materialize.scss", - "module": "./src/materialize.scss", - "moduleName": "./src/materialize.scss", - "type": "cjs require", - "userRequest": "!../node_modules/style-loader/dist/runtime/injectStylesIntoStyleTag.js", - "loc": "12:13-94" - }, - { - "moduleId": 21, - "moduleIdentifier": "/Users/kuzmenko/Documents/projects/tweb/node_modules/style-loader/dist/index.js!/Users/kuzmenko/Documents/projects/tweb/node_modules/css-loader/dist/cjs.js!/Users/kuzmenko/Documents/projects/tweb/node_modules/overlayscrollbars/css/OverlayScrollbars.min.css", - "module": "./node_modules/overlayscrollbars/css/OverlayScrollbars.min.css", - "moduleName": "./node_modules/overlayscrollbars/css/OverlayScrollbars.min.css", - "type": "cjs require", - "userRequest": "!../../style-loader/dist/runtime/injectStylesIntoStyleTag.js", - "loc": "12:13-84" - }, - { - "moduleId": 23, - "moduleIdentifier": "/Users/kuzmenko/Documents/projects/tweb/node_modules/style-loader/dist/index.js!/Users/kuzmenko/Documents/projects/tweb/node_modules/css-loader/dist/cjs.js!/Users/kuzmenko/Documents/projects/tweb/node_modules/resolve-url-loader/index.js!/Users/kuzmenko/Documents/projects/tweb/node_modules/sass-loader/dist/cjs.js??ref--4-3!/Users/kuzmenko/Documents/projects/tweb/src/scss/style.scss", - "module": "./src/scss/style.scss", - "moduleName": "./src/scss/style.scss", - "type": "cjs require", - "userRequest": "!../../node_modules/style-loader/dist/runtime/injectStylesIntoStyleTag.js", - "loc": "12:13-97" - }, - { - "moduleId": 27, - "moduleIdentifier": "/Users/kuzmenko/Documents/projects/tweb/node_modules/style-loader/dist/index.js!/Users/kuzmenko/Documents/projects/tweb/node_modules/css-loader/dist/cjs.js!/Users/kuzmenko/Documents/projects/tweb/node_modules/resolve-url-loader/index.js!/Users/kuzmenko/Documents/projects/tweb/node_modules/sass-loader/dist/cjs.js??ref--4-3!/Users/kuzmenko/Documents/projects/tweb/src/scss/tgico.scss", - "module": "./src/scss/tgico.scss", - "moduleName": "./src/scss/tgico.scss", - "type": "cjs require", - "userRequest": "!../../node_modules/style-loader/dist/runtime/injectStylesIntoStyleTag.js", - "loc": "12:13-97" - } - ], - "usedExports": true, - "providedExports": null, - "optimizationBailout": [ - "ModuleConcatenation bailout: Module is not an ECMAScript module" - ], - "depth": 2, - "source": "\"use strict\";\n\nvar stylesInDom = {};\n\nvar isOldIE = function isOldIE() {\n var memo;\n return function memorize() {\n if (typeof memo === 'undefined') {\n // Test for IE <= 9 as proposed by Browserhacks\n // @see http://browserhacks.com/#hack-e71d8692f65334173fee715c222cb805\n // Tests for existence of standard globals is to allow style-loader\n // to operate correctly into non-standard environments\n // @see https://github.com/webpack-contrib/style-loader/issues/177\n memo = Boolean(window && document && document.all && !window.atob);\n }\n\n return memo;\n };\n}();\n\nvar getTarget = function getTarget() {\n var memo = {};\n return function memorize(target) {\n if (typeof memo[target] === 'undefined') {\n var styleTarget = document.querySelector(target); // Special case to return head of iframe instead of iframe itself\n\n if (window.HTMLIFrameElement && styleTarget instanceof window.HTMLIFrameElement) {\n try {\n // This will throw an exception if access to iframe is blocked\n // due to cross-origin restrictions\n styleTarget = styleTarget.contentDocument.head;\n } catch (e) {\n // istanbul ignore next\n styleTarget = null;\n }\n }\n\n memo[target] = styleTarget;\n }\n\n return memo[target];\n };\n}();\n\nfunction listToStyles(list, options) {\n var styles = [];\n var newStyles = {};\n\n for (var i = 0; i < list.length; i++) {\n var item = list[i];\n var id = options.base ? item[0] + options.base : item[0];\n var css = item[1];\n var media = item[2];\n var sourceMap = item[3];\n var part = {\n css: css,\n media: media,\n sourceMap: sourceMap\n };\n\n if (!newStyles[id]) {\n styles.push(newStyles[id] = {\n id: id,\n parts: [part]\n });\n } else {\n newStyles[id].parts.push(part);\n }\n }\n\n return styles;\n}\n\nfunction addStylesToDom(styles, options) {\n for (var i = 0; i < styles.length; i++) {\n var item = styles[i];\n var domStyle = stylesInDom[item.id];\n var j = 0;\n\n if (domStyle) {\n domStyle.refs++;\n\n for (; j < domStyle.parts.length; j++) {\n domStyle.parts[j](item.parts[j]);\n }\n\n for (; j < item.parts.length; j++) {\n domStyle.parts.push(addStyle(item.parts[j], options));\n }\n } else {\n var parts = [];\n\n for (; j < item.parts.length; j++) {\n parts.push(addStyle(item.parts[j], options));\n }\n\n stylesInDom[item.id] = {\n id: item.id,\n refs: 1,\n parts: parts\n };\n }\n }\n}\n\nfunction insertStyleElement(options) {\n var style = document.createElement('style');\n\n if (typeof options.attributes.nonce === 'undefined') {\n var nonce = typeof __webpack_nonce__ !== 'undefined' ? __webpack_nonce__ : null;\n\n if (nonce) {\n options.attributes.nonce = nonce;\n }\n }\n\n Object.keys(options.attributes).forEach(function (key) {\n style.setAttribute(key, options.attributes[key]);\n });\n\n if (typeof options.insert === 'function') {\n options.insert(style);\n } else {\n var target = getTarget(options.insert || 'head');\n\n if (!target) {\n throw new Error(\"Couldn't find a style target. This probably means that the value for the 'insert' parameter is invalid.\");\n }\n\n target.appendChild(style);\n }\n\n return style;\n}\n\nfunction removeStyleElement(style) {\n // istanbul ignore if\n if (style.parentNode === null) {\n return false;\n }\n\n style.parentNode.removeChild(style);\n}\n/* istanbul ignore next */\n\n\nvar replaceText = function replaceText() {\n var textStore = [];\n return function replace(index, replacement) {\n textStore[index] = replacement;\n return textStore.filter(Boolean).join('\\n');\n };\n}();\n\nfunction applyToSingletonTag(style, index, remove, obj) {\n var css = remove ? '' : obj.css; // For old IE\n\n /* istanbul ignore if */\n\n if (style.styleSheet) {\n style.styleSheet.cssText = replaceText(index, css);\n } else {\n var cssNode = document.createTextNode(css);\n var childNodes = style.childNodes;\n\n if (childNodes[index]) {\n style.removeChild(childNodes[index]);\n }\n\n if (childNodes.length) {\n style.insertBefore(cssNode, childNodes[index]);\n } else {\n style.appendChild(cssNode);\n }\n }\n}\n\nfunction applyToTag(style, options, obj) {\n var css = obj.css;\n var media = obj.media;\n var sourceMap = obj.sourceMap;\n\n if (media) {\n style.setAttribute('media', media);\n }\n\n if (sourceMap && btoa) {\n css += \"\\n/*# sourceMappingURL=data:application/json;base64,\".concat(btoa(unescape(encodeURIComponent(JSON.stringify(sourceMap)))), \" */\");\n } // For old IE\n\n /* istanbul ignore if */\n\n\n if (style.styleSheet) {\n style.styleSheet.cssText = css;\n } else {\n while (style.firstChild) {\n style.removeChild(style.firstChild);\n }\n\n style.appendChild(document.createTextNode(css));\n }\n}\n\nvar singleton = null;\nvar singletonCounter = 0;\n\nfunction addStyle(obj, options) {\n var style;\n var update;\n var remove;\n\n if (options.singleton) {\n var styleIndex = singletonCounter++;\n style = singleton || (singleton = insertStyleElement(options));\n update = applyToSingletonTag.bind(null, style, styleIndex, false);\n remove = applyToSingletonTag.bind(null, style, styleIndex, true);\n } else {\n style = insertStyleElement(options);\n update = applyToTag.bind(null, style, options);\n\n remove = function remove() {\n removeStyleElement(style);\n };\n }\n\n update(obj);\n return function updateStyle(newObj) {\n if (newObj) {\n if (newObj.css === obj.css && newObj.media === obj.media && newObj.sourceMap === obj.sourceMap) {\n return;\n }\n\n update(obj = newObj);\n } else {\n remove();\n }\n };\n}\n\nmodule.exports = function (list, options) {\n options = options || {};\n options.attributes = typeof options.attributes === 'object' ? options.attributes : {}; // Force single-tag solution on IE6-9, which has a hard limit on the # of