feat: cleaned up poll once for display name

pull/3056/head
William Grant 1 year ago
parent 8e41d51632
commit 038589114f

@ -1,7 +1,17 @@
/* eslint-disable no-await-in-loop */ /* eslint-disable no-await-in-loop */
/* eslint-disable more/no-then */ /* eslint-disable more/no-then */
/* eslint-disable @typescript-eslint/no-misused-promises */ /* eslint-disable @typescript-eslint/no-misused-promises */
import { compact, concat, difference, flatten, last, sample, toNumber, uniqBy } from 'lodash'; import {
compact,
concat,
difference,
flatten,
isEmpty,
last,
sample,
toNumber,
uniqBy,
} from 'lodash';
import { Data, Snode } from '../../../data/data'; import { Data, Snode } from '../../../data/data';
import { SignalService } from '../../../protobuf'; import { SignalService } from '../../../protobuf';
import * as Receiver from '../../../receiver/receiver'; import * as Receiver from '../../../receiver/receiver';
@ -26,6 +36,7 @@ import { IncomingMessage } from '../../messages/incoming/IncomingMessage';
import { ed25519Str } from '../../onions/onionPath'; import { ed25519Str } from '../../onions/onionPath';
import { StringUtils, UserUtils } from '../../utils'; import { StringUtils, UserUtils } from '../../utils';
import { perfEnd, perfStart } from '../../utils/Performance'; import { perfEnd, perfStart } from '../../utils/Performance';
import { NotFoundError } from '../../utils/errors';
import { LibSessionUtil } from '../../utils/libsession/libsession_utils'; import { LibSessionUtil } from '../../utils/libsession/libsession_utils';
import { SnodeNamespace, SnodeNamespaces } from './namespaces'; import { SnodeNamespace, SnodeNamespaces } from './namespaces';
import { SnodeAPIRetrieve } from './retrieveRequest'; import { SnodeAPIRetrieve } from './retrieveRequest';
@ -349,7 +360,7 @@ export class SwarmPolling {
private async handleSharedConfigMessages( private async handleSharedConfigMessages(
userConfigMessagesMerged: Array<RetrieveMessageItem>, userConfigMessagesMerged: Array<RetrieveMessageItem>,
returnAndKeepInMemory?: boolean returnDisplayNameOnly?: boolean
): Promise<string> { ): Promise<string> {
const extractedUserConfigMessage = compact( const extractedUserConfigMessage = compact(
userConfigMessagesMerged.map((m: RetrieveMessageItem) => { userConfigMessagesMerged.map((m: RetrieveMessageItem) => {
@ -396,7 +407,7 @@ export class SwarmPolling {
`handleConfigMessagesViaLibSession of "${allDecryptedConfigMessages.length}" messages with libsession` `handleConfigMessagesViaLibSession of "${allDecryptedConfigMessages.length}" messages with libsession`
); );
if (returnAndKeepInMemory) { if (returnDisplayNameOnly) {
let displayName = ''; let displayName = '';
try { try {
@ -421,14 +432,13 @@ export class SwarmPolling {
]); ]);
const userInfo = await UserConfigWrapperActions.getUserInfo(); const userInfo = await UserConfigWrapperActions.getUserInfo();
window.log.debug(`WIP: [SwarmPolling] userInfo: ${JSON.stringify(userInfo)}`);
if (!userInfo) { if (!userInfo) {
throw new Error('UserInfo not found'); throw new Error('UserInfo not found');
} }
displayName = userInfo.name; displayName = userInfo.name;
} catch (e) { } catch (e) {
window.log.warn( window.log.warn(
'[SwarmPolling] LibSessionUtil.initializeLibSessionUtilWrappers failed with', 'LibSessionUtil.initializeLibSessionUtilWrappers failed with',
e.message e.message
); );
} finally { } finally {
@ -653,77 +663,58 @@ export class SwarmPolling {
// return the cached value // return the cached value
return this.lastHashes[nodeEdKey][pubkey][namespace]; return this.lastHashes[nodeEdKey][pubkey][namespace];
} }
public async pollOnceForOurDisplayName(): Promise<string> {
/**
* Only exposed as public for testing
*/
public async pollOnceForDisplayName(pubkey: PubKey): Promise<string> {
const polledPubkey = pubkey.key;
const swarmSnodes = await snodePool.getSwarmFor(polledPubkey);
// Select nodes for which we already have lastHashes
const alreadyPolled = swarmSnodes.filter((n: Snode) => this.lastHashes[n.pubkey_ed25519]);
let toPollFrom = alreadyPolled.length ? alreadyPolled[0] : null;
// If we need more nodes, select randomly from the remaining nodes:
if (!toPollFrom) {
const notPolled = difference(swarmSnodes, alreadyPolled);
toPollFrom = sample(notPolled) as Snode;
}
let resultsFromUserProfile: RetrieveMessagesResultsBatched | null;
try { try {
resultsFromUserProfile = await SnodeAPIRetrieve.retrieveDisplayName( const pubkey = UserUtils.getOurPubKeyFromCache();
toPollFrom, const polledPubkey = pubkey.key;
UserUtils.getOurPubKeyStrFromCache() const swarmSnodes = await snodePool.getSwarmFor(polledPubkey);
);
} catch (e) { // Select nodes for which we already have lastHashes
if (e.message === ERROR_CODE_NO_CONNECT) { const alreadyPolled = swarmSnodes.filter((n: Snode) => this.lastHashes[n.pubkey_ed25519]);
if (window.inboxStore?.getState().onionPaths.isOnline) { let toPollFrom = alreadyPolled.length ? alreadyPolled[0] : null;
window.inboxStore?.dispatch(updateIsOnline(false));
} // If we need more nodes, select randomly from the remaining nodes:
} else if (!window.inboxStore?.getState().onionPaths.isOnline) { if (!toPollFrom) {
window.inboxStore?.dispatch(updateIsOnline(true)); const notPolled = difference(swarmSnodes, alreadyPolled);
toPollFrom = sample(notPolled) as Snode;
} }
window.log.warn( const resultsFromUserProfile = await SnodeAPIRetrieve.retrieveDisplayName(
`pollOnceForDisplayName of ${pubkey} namespace: SnodeNamespaces.UserProfile failed with: ${e.message}` toPollFrom,
pubkey.key
); );
resultsFromUserProfile = null;
}
// check if we just fetched the details from the config namespaces. // check if we just fetched the details from the config namespaces.
// If yes, merge them together and exclude them from the rest of the messages. // If yes, merge them together and exclude them from the rest of the messages.
if (resultsFromUserProfile?.length) { if (!resultsFromUserProfile?.length) {
throw new Error('resultsFromUserProfile is empty');
}
const userConfigMessages = resultsFromUserProfile const userConfigMessages = resultsFromUserProfile
.filter(m => SnodeNamespace.isUserConfigNamespace(m.namespace)) .filter(m => SnodeNamespace.isUserConfigNamespace(m.namespace))
.map(r => r.messages.messages); .map(r => r.messages.messages);
const userConfigMessagesMerged = flatten(compact(userConfigMessages)); const userConfigMessagesMerged = flatten(compact(userConfigMessages));
if (!userConfigMessagesMerged.length) {
if (userConfigMessagesMerged.length) { throw new Error('after merging there are no user config messages');
const displayName = await this.handleSharedConfigMessages(userConfigMessagesMerged, true);
return displayName;
} }
} const displayName = await this.handleSharedConfigMessages(userConfigMessagesMerged, true);
return '';
}
public async pollForOurDisplayName(): Promise<string> { if (isEmpty(displayName)) {
if (!window.getGlobalOnlineStatus()) { throw new NotFoundError('Got a config message from network but without a displayName...');
window?.log?.error('pollForOurDisplayName: offline'); }
// Very important to set up a new polling call so we do retry at some point
setTimeout(this.pollForOurDisplayName.bind(this), SWARM_POLLING_TIMEOUT.ACTIVE);
return '';
}
try { window.log.debug(`WIP: [pollOnceForOurDisplayName] displayName ${displayName}`);
const displayName = await this.pollOnceForDisplayName(UserUtils.getOurPubKeyFromCache());
window.log.debug(`WIP: [pollForOurDisplayName] displayName ${displayName}`);
return displayName; return displayName;
} catch (e) { } catch (e) {
window?.log?.warn('pollForOurDisplayName exception: ', e); if (e.message === ERROR_CODE_NO_CONNECT) {
if (window.inboxStore?.getState().onionPaths.isOnline) {
window.inboxStore?.dispatch(updateIsOnline(false));
}
} else if (!window.inboxStore?.getState().onionPaths.isOnline) {
window.inboxStore?.dispatch(updateIsOnline(true));
}
window.log.debug(`WIP: [pollOnceForOurDisplayName] no displayName found`, e);
throw e; throw e;
} }
} }

@ -84,7 +84,7 @@ export async function signInByLinkingDevice(
await saveRecoveryPhrase(mnemonic); await saveRecoveryPhrase(mnemonic);
const pubKeyString = toHex(identityKeyPair.pubKey); const pubKeyString = toHex(identityKeyPair.pubKey);
const displayName = await getSwarmPollingInstance().pollForOurDisplayName(); const displayName = await getSwarmPollingInstance().pollOnceForOurDisplayName();
if (isEmpty(pubKeyString)) { if (isEmpty(pubKeyString)) {
throw new Error("We don't have a pubkey from the recovery password..."); throw new Error("We don't have a pubkey from the recovery password...");

Loading…
Cancel
Save