You cannot select more than 25 topics
Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.
279 lines
6.9 KiB
TypeScript
279 lines
6.9 KiB
TypeScript
import React from 'react';
|
|
import { QRCode } from 'react-qr-svg';
|
|
|
|
import { SessionModal } from './session/SessionModal';
|
|
import { SessionButton } from './session/SessionButton';
|
|
|
|
interface Props {
|
|
i18n: any;
|
|
onClose: any;
|
|
pubKeyToUnpair: string | null;
|
|
pubKey: string | null;
|
|
}
|
|
|
|
interface State {
|
|
currentPubKey: string | null;
|
|
accepted: boolean;
|
|
isListening: boolean;
|
|
success: boolean;
|
|
loading: boolean;
|
|
view:
|
|
| 'default'
|
|
| 'waitingForRequest'
|
|
| 'requestReceived'
|
|
| 'requestAccepted'
|
|
| 'confirmUnpair';
|
|
pubKeyRequests: Array<any>;
|
|
data: Array<any>;
|
|
}
|
|
|
|
export class DevicePairingDialog extends React.Component<Props, State> {
|
|
constructor(props: any) {
|
|
super(props);
|
|
|
|
this.closeDialog = this.closeDialog.bind(this);
|
|
this.onKeyUp = this.onKeyUp.bind(this);
|
|
this.startReceivingRequests = this.startReceivingRequests.bind(this);
|
|
this.stopReceivingRequests = this.stopReceivingRequests.bind(this);
|
|
this.getPubkeyName = this.getPubkeyName.bind(this);
|
|
|
|
this.state = {
|
|
currentPubKey: this.props.pubKey,
|
|
accepted: false,
|
|
isListening: false,
|
|
success: false,
|
|
loading: true,
|
|
view: 'default',
|
|
pubKeyRequests: [],
|
|
data: [],
|
|
};
|
|
}
|
|
|
|
public componentDidMount() {
|
|
this.getSecondaryDevices();
|
|
}
|
|
|
|
public render() {
|
|
const { i18n } = this.props;
|
|
|
|
const waitingForRequest = this.state.view === 'waitingForRequest';
|
|
const nothingPaired = this.state.data.length === 0;
|
|
|
|
// const renderPairedDevices = this.state.data.map((pubKey: any) => {
|
|
// const pubKeyInfo = this.getPubkeyName(pubKey);
|
|
// const isFinalItem =
|
|
// this.state.data[this.state.data.length - 1] === pubKey;
|
|
|
|
// return (
|
|
// <div key={pubKey}>
|
|
// <p>
|
|
// {pubKeyInfo.deviceAlias}
|
|
// <br />
|
|
// <span className="text-subtle">Pairing Secret:</span>{' '}
|
|
// {pubKeyInfo.secretWords}
|
|
// </p>
|
|
// {!isFinalItem ? <hr className="text-soft fullwidth" /> : null}
|
|
// </div>
|
|
// );
|
|
// });
|
|
|
|
return (
|
|
<>
|
|
{!this.state.loading && (
|
|
<SessionModal
|
|
title={i18n('pairedDevices')}
|
|
onOk={() => null}
|
|
onClose={this.closeDialog}
|
|
>
|
|
{waitingForRequest ? (
|
|
<div className="session-modal__centered">
|
|
<h3>{i18n('waitingForDeviceToRegister')}</h3>
|
|
<small className="text-subtle">
|
|
{i18n('pairNewDevicePrompt')}
|
|
</small>
|
|
<div className="spacer-lg" />
|
|
|
|
<div id="qr">
|
|
<QRCode
|
|
value={window.textsecure.storage.user.getNumber()}
|
|
bgColor="#FFFFFF"
|
|
fgColor="#000000"
|
|
level="L"
|
|
/>
|
|
</div>
|
|
|
|
<div className="spacer-lg" />
|
|
<div className="session-modal__button-group__center">
|
|
<SessionButton
|
|
text={i18n('cancel')}
|
|
onClick={this.stopReceivingRequests}
|
|
/>
|
|
</div>
|
|
</div>
|
|
) : (
|
|
<>
|
|
{nothingPaired ? (
|
|
<div className="session-modal__centered">
|
|
<div>{i18n('noPairedDevices')}</div>
|
|
</div>
|
|
) : (
|
|
<div className="session-modal__centered">
|
|
{'renderPairedDevices'}
|
|
</div>
|
|
)}
|
|
|
|
<div className="spacer-lg" />
|
|
<div className="session-modal__button-group__center">
|
|
<SessionButton
|
|
text={i18n('pairNewDevice')}
|
|
onClick={this.startReceivingRequests}
|
|
/>
|
|
</div>
|
|
</>
|
|
)}
|
|
</SessionModal>
|
|
)}
|
|
</>
|
|
);
|
|
}
|
|
|
|
private showView(
|
|
view?:
|
|
| 'default'
|
|
| 'waitingForRequest'
|
|
| 'requestReceived'
|
|
| 'requestAccepted'
|
|
| 'confirmUnpair'
|
|
) {
|
|
if (!view) {
|
|
this.setState({
|
|
view: 'default',
|
|
});
|
|
|
|
return;
|
|
}
|
|
|
|
if (view === 'waitingForRequest') {
|
|
this.setState({
|
|
view,
|
|
isListening: true,
|
|
});
|
|
|
|
return;
|
|
}
|
|
this.setState({ view });
|
|
}
|
|
|
|
private getSecondaryDevices() {
|
|
const secondaryDevices = window.libloki.storage
|
|
.getSecondaryDevicesFor(this.state.currentPubKey)
|
|
.then(() => {
|
|
this.setState({
|
|
data: secondaryDevices,
|
|
loading: false,
|
|
});
|
|
});
|
|
}
|
|
|
|
private startReceivingRequests() {
|
|
this.showView('waitingForRequest');
|
|
}
|
|
|
|
private getPubkeyName(pubKey: string | null) {
|
|
if (!pubKey) {
|
|
return {};
|
|
}
|
|
|
|
const secretWords = window.mnemonic.pubkey_to_secret_words(pubKey);
|
|
const conv = window.ConversationController.get(this.state.currentPubKey);
|
|
const deviceAlias = conv ? conv.getNickname() : 'Unnamed Device';
|
|
|
|
return { deviceAlias, secretWords };
|
|
}
|
|
|
|
private stopReceivingRequests() {
|
|
if (this.state.success) {
|
|
const aliasKey = 'deviceAlias';
|
|
const deviceAlias = this.getPubkeyName(this.state.currentPubKey)[
|
|
aliasKey
|
|
];
|
|
|
|
const conv = window.ConversationController.get(this.state.currentPubKey);
|
|
if (conv) {
|
|
conv.setNickname(deviceAlias);
|
|
}
|
|
}
|
|
|
|
this.showView();
|
|
}
|
|
|
|
// private requestReceived(secondaryDevicePubKey: string | EventHandlerNonNull) {
|
|
// // FIFO: push at the front of the array with unshift()
|
|
// this.state.pubKeyRequests.unshift(secondaryDevicePubKey);
|
|
// if (!this.state.currentPubKey) {
|
|
// this.nextPubKey();
|
|
|
|
// this.showView('requestReceived');
|
|
// }
|
|
// }
|
|
|
|
// private allowDevice() {
|
|
// this.setState({
|
|
// accepted: true,
|
|
// });
|
|
// window.Whisper.trigger(
|
|
// 'devicePairingRequestAccepted',
|
|
// this.state.currentPubKey,
|
|
// (errors: any) => {
|
|
// this.transmisssionCB(errors);
|
|
|
|
// return true;
|
|
// }
|
|
// );
|
|
// this.showView();
|
|
// }
|
|
|
|
// private transmisssionCB(errors: any) {
|
|
// if (!errors) {
|
|
// this.setState({
|
|
// success: true,
|
|
// });
|
|
// } else {
|
|
// return;
|
|
// }
|
|
// }
|
|
|
|
// private skipDevice() {
|
|
// window.Whisper.trigger(
|
|
// 'devicePairingRequestRejected',
|
|
// this.state.currentPubKey
|
|
// );
|
|
// this.nextPubKey();
|
|
// this.showView();
|
|
// }
|
|
|
|
// private nextPubKey() {
|
|
// // FIFO: pop at the back of the array using pop()
|
|
// const pubKeyRequests = this.state.pubKeyRequests;
|
|
// this.setState({
|
|
// currentPubKey: pubKeyRequests.pop(),
|
|
// });
|
|
// }
|
|
|
|
private onKeyUp(event: any) {
|
|
switch (event.key) {
|
|
case 'Esc':
|
|
case 'Escape':
|
|
this.closeDialog();
|
|
break;
|
|
default:
|
|
}
|
|
}
|
|
|
|
private closeDialog() {
|
|
window.removeEventListener('keyup', this.onKeyUp);
|
|
this.stopReceivingRequests();
|
|
this.props.onClose();
|
|
}
|
|
}
|