Mailspring/internal_packages/notifications/lib/items/offline-notification.jsx

128 lines
3.5 KiB
React
Raw Normal View History

import {NylasSyncStatusStore, React, Actions} from 'nylas-exports';
import {Notification} from 'nylas-component-kit';
const DISCONNECT_DEBOUNCE_INTERVAL = 15000;
const CHECK_STATUS_INTERVAL = 3000
export default class OfflineNotification extends React.Component {
static displayName = 'OfflineNotification';
constructor() {
super();
this._updateInterval = null;
this._setOfflineTimeout = null;
this._setRetryingTimeout = null;
this.state = this.getStateFromStores();
}
componentDidMount() {
this.unlisten = NylasSyncStatusStore.listen(this.onConnectedStatusChanged);
window.addEventListener('browser-window-focus', this.onWindowFocusChanged);
window.addEventListener('browser-window-blur', this.onWindowFocusChanged);
this.ensureCountdownInterval();
}
componentDidUpdate() {
this.ensureCountdownInterval();
}
componentWillUnmount() {
this.unlisten();
window.removeEventListener('browser-window-focus', this.onWindowFocusChanged);
window.removeEventListener('browser-window-blur', this.onWindowFocusChanged);
}
onConnectedStatusChanged = () => {
const nextState = this.getStateFromStores();
if (this.state.connected) {
if (!nextState.connected && !this._setOfflineTimeout) {
this._setOfflineTimeout = setTimeout(this._didBecomeDisconnected, DISCONNECT_DEBOUNCE_INTERVAL);
}
return;
}
if (nextState.connected) {
this._didBecomeConnected();
}
}
onTryAgain = () => {
clearTimeout(this._setRetryingTimeout)
this.setState({retrying: true})
this._setRetryingTimeout = setTimeout(() => this.setState({retrying: false}), 2000)
Actions.retryDeltaConnection();
}
onWindowFocusChanged = () => {
const nextState = this.getStateFromStores();
// If we notice we've reconnected we want to immediately remove the notification.
if (nextState.connected && !this.state.connected) {
this._didBecomeConnected();
return;
}
this.ensureCountdownInterval();
}
getStateFromStores() {
return {connected: NylasSyncStatusStore.connected()};
}
_clearOfflineTimeout = () => {
if (this._setOfflineTimeout) {
clearTimeout(this._setOfflineTimeout);
this._setOfflineTimeout = null;
}
}
_clearUpdateInterval = () => {
if (this._updateInterval) {
clearInterval(this._updateInterval);
this._updateInterval = null;
}
}
_didBecomeConnected = () => {
this._clearOfflineTimeout();
this._clearUpdateInterval();
this.setState({connected: true});
}
_didBecomeDisconnected = () => {
this._clearOfflineTimeout();
// We will call ensureCountdownInterval() in componentDidUpdate when this
// setState is complete.
this.setState({connected: false});
}
ensureCountdownInterval = () => {
this._clearUpdateInterval();
// only attempt to retry if the window is in the foreground to avoid
// the battery hit.
if (!this.state.connected && !document.body.classList.contains('is-blurred')) {
this._updateInterval = setInterval(() => {
Actions.retryDeltaConnection();
}, CHECK_STATUS_INTERVAL);
}
}
render() {
const {connected, retrying} = this.state;
if (connected) {
return <span />;
}
const tryLabel = retrying ? 'Retrying...' : 'Try now';
return (
<Notification
className="offline"
title="Nylas Mail is offline"
priority="5"
icon="volstead-offline.png"
actions={[{label: tryLabel, id: 'try_now', fn: this.onTryAgain}]}
/>
)
}
}