when file download completes, notify through snackbar if on subscriptions page; formatting
This commit is contained in:
parent
cedafdbe14
commit
386e9271ff
8 changed files with 84 additions and 48 deletions
|
@ -15,3 +15,4 @@ export const AUTOMATIC_DARK_MODE_ENABLED = 'automaticDarkModeEnabled';
|
|||
export const AUTOPLAY = 'autoplay';
|
||||
export const RESULT_COUNT = 'resultCount';
|
||||
export const OS_NOTIFICATIONS_ENABLED = 'osNotificationsEnabled';
|
||||
export const AUTO_DOWNLOAD = 'autoDownload';
|
||||
|
|
|
@ -30,6 +30,7 @@ const select = state => ({
|
|||
autoplay: makeSelectClientSetting(settings.AUTOPLAY)(state),
|
||||
walletEncrypted: selectWalletIsEncrypted(state),
|
||||
osNotificationsEnabled: selectosNotificationsEnabled(state),
|
||||
autoDownload: makeSelectClientSetting(settings.AUTO_DOWNLOAD)(state),
|
||||
});
|
||||
|
||||
const perform = dispatch => ({
|
||||
|
|
|
@ -31,6 +31,7 @@ type Props = {
|
|||
themes: Array<string>,
|
||||
automaticDarkModeEnabled: boolean,
|
||||
autoplay: boolean,
|
||||
autoDownload: boolean,
|
||||
encryptWallet: () => void,
|
||||
decryptWallet: () => void,
|
||||
walletEncrypted: boolean,
|
||||
|
@ -59,6 +60,7 @@ class SettingsPage extends React.PureComponent<Props, State> {
|
|||
(this: any).onAutoplayChange = this.onAutoplayChange.bind(this);
|
||||
(this: any).clearCache = this.clearCache.bind(this);
|
||||
(this: any).onDesktopNotificationsChange = this.onDesktopNotificationsChange.bind(this);
|
||||
(this: any).onAutoDownloadChange = this.onAutoDownloadChange.bind(this);
|
||||
// (this: any).onLanguageChange = this.onLanguageChange.bind(this)
|
||||
}
|
||||
|
||||
|
@ -119,6 +121,10 @@ class SettingsPage extends React.PureComponent<Props, State> {
|
|||
this.props.setClientSetting(settings.SHOW_NSFW, event.target.checked);
|
||||
}
|
||||
|
||||
onAutoDownloadChange(event: SyntheticInputEvent<*>) {
|
||||
this.props.setClientSetting(settings.AUTO_DOWNLOAD, event.target.checked);
|
||||
}
|
||||
|
||||
onChangeEncryptWallet() {
|
||||
const { props } = this;
|
||||
props.walletEncrypted ? props.decryptWallet() : props.encryptWallet();
|
||||
|
@ -157,6 +163,7 @@ class SettingsPage extends React.PureComponent<Props, State> {
|
|||
autoplay,
|
||||
walletEncrypted,
|
||||
osNotificationsEnabled,
|
||||
autoDownload,
|
||||
} = this.props;
|
||||
|
||||
const noDaemonSettings = !daemonSettings || Object.keys(daemonSettings).length === 0;
|
||||
|
@ -265,6 +272,13 @@ class SettingsPage extends React.PureComponent<Props, State> {
|
|||
checked={autoplay}
|
||||
postfix={__('Autoplay media files')}
|
||||
/>
|
||||
<FormField
|
||||
type="checkbox"
|
||||
name="auto_download"
|
||||
onChange={this.onAutoDownloadChange}
|
||||
checked={autoDownload}
|
||||
postfix={__('Automatically download new content')}
|
||||
/>
|
||||
<FormField
|
||||
type="checkbox"
|
||||
name="show_nsfw"
|
||||
|
|
|
@ -18,7 +18,7 @@ import { doFetchDaemonSettings } from 'redux/actions/settings';
|
|||
import { doAuthNavigate } from 'redux/actions/navigation';
|
||||
import { doAuthenticate } from 'redux/actions/user';
|
||||
import { doPause } from 'redux/actions/media';
|
||||
import { doCheckSubscriptions } from 'redux/actions/subscriptions';
|
||||
import { doCheckSubscriptionsInit } from 'redux/actions/subscriptions';
|
||||
import {
|
||||
selectIsUpgradeSkipped,
|
||||
selectUpdateUrl,
|
||||
|
@ -347,7 +347,7 @@ export function doDaemonReady() {
|
|||
dispatch(doCheckUpgradeAvailable());
|
||||
}
|
||||
dispatch(doCheckUpgradeSubscribe());
|
||||
dispatch(doCheckSubscriptions());
|
||||
dispatch(doCheckSubscriptionsInit());
|
||||
};
|
||||
}
|
||||
|
||||
|
|
|
@ -110,6 +110,7 @@ export function doUpdateLoadStatus(uri, outpoint) {
|
|||
dispatch(doUpdateLoadStatus(uri, outpoint));
|
||||
}, DOWNLOAD_POLL_INTERVAL);
|
||||
} else if (fileInfo.completed) {
|
||||
const state = getState();
|
||||
// TODO this isn't going to get called if they reload the client before
|
||||
// the download finished
|
||||
dispatch({
|
||||
|
@ -121,13 +122,13 @@ export function doUpdateLoadStatus(uri, outpoint) {
|
|||
},
|
||||
});
|
||||
|
||||
const badgeNumber = selectBadgeNumber(getState());
|
||||
const badgeNumber = selectBadgeNumber(state);
|
||||
setBadge(badgeNumber === 0 ? '' : `${badgeNumber}`);
|
||||
|
||||
const totalProgress = selectTotalDownloadProgress(getState());
|
||||
const totalProgress = selectTotalDownloadProgress(state);
|
||||
setProgressBar(totalProgress);
|
||||
|
||||
const notifications = selectNotifications(getState());
|
||||
const notifications = selectNotifications(state);
|
||||
if (notifications[uri] && notifications[uri].type === NOTIFICATION_TYPES.DOWNLOADING) {
|
||||
const count = Object.keys(notifications).reduce(
|
||||
(acc, cur) =>
|
||||
|
@ -138,7 +139,14 @@ export function doUpdateLoadStatus(uri, outpoint) {
|
|||
0
|
||||
);
|
||||
|
||||
if (selectosNotificationsEnabled(getState())) {
|
||||
if (state.navigation.currentPath === '/subscriptions') {
|
||||
dispatch(
|
||||
doNotify({
|
||||
message: `'${fileInfo.metadata.title}' has been downloaded`,
|
||||
displayType: ['snackbar'],
|
||||
})
|
||||
);
|
||||
} else if (selectosNotificationsEnabled(state)) {
|
||||
const notif = new window.Notification(notifications[uri].subscription.channelName, {
|
||||
body: `Posted ${fileInfo.metadata.title}${
|
||||
count > 1 && count < 10 ? ` and ${count - 1} other new items` : ''
|
||||
|
|
|
@ -1,14 +1,12 @@
|
|||
// @flow
|
||||
import * as ACTIONS from 'constants/action_types';
|
||||
import * as NOTIFICATION_TYPES from 'constants/notification_types';
|
||||
import * as SETTINGS from 'constants/settings';
|
||||
import rewards from 'rewards';
|
||||
import type {
|
||||
Dispatch,
|
||||
SubscriptionState,
|
||||
SubscriptionNotifications,
|
||||
} from 'redux/reducers/subscriptions';
|
||||
import type { Dispatch, SubscriptionNotifications } from 'redux/reducers/subscriptions';
|
||||
import type { Subscription } from 'types/subscription';
|
||||
import { selectSubscriptions } from 'redux/selectors/subscriptions';
|
||||
import { selectSubscriptions, selectDownloadingCount } from 'redux/selectors/subscriptions';
|
||||
import { makeSelectClientSetting } from 'redux/selectors/settings';
|
||||
import { Lbry, buildURI, parseURI } from 'lbry-redux';
|
||||
import { doPurchaseUri } from 'redux/actions/content';
|
||||
import { doClaimRewardType } from 'redux/actions/rewards';
|
||||
|
@ -16,7 +14,7 @@ import Promise from 'bluebird';
|
|||
import Lbryio from 'lbryio';
|
||||
|
||||
const CHECK_SUBSCRIPTIONS_INTERVAL = 15 * 60 * 1000;
|
||||
const SUBSCRIPTION_DOWNLOAD_LIMIT = 1;
|
||||
const SUBSCRIPTION_DOWNLOAD_LIMIT = 3;
|
||||
|
||||
export const doFetchMySubscriptions = () => (dispatch: Dispatch, getState: () => any) => {
|
||||
const {
|
||||
|
@ -127,29 +125,28 @@ export const setSubscriptionNotification = (
|
|||
});
|
||||
|
||||
export const doCheckSubscription = (subscription: Subscription, notify?: boolean) => (
|
||||
dispatch: Dispatch
|
||||
dispatch: Dispatch,
|
||||
getState: () => {}
|
||||
) => {
|
||||
// this action is not implemented
|
||||
dispatch({
|
||||
type: ACTIONS.CHECK_SUBSCRIPTION_STARTED,
|
||||
data: subscription,
|
||||
});
|
||||
// no dispatching FETCH_CHANNEL_CLAIMS_STARTED; causes loading issues on <SubscriptionsPage>
|
||||
|
||||
Lbry.claim_list_by_channel({ uri: subscription.uri, page: 1 }).then(result => {
|
||||
const claimResult = result[subscription.uri] || {};
|
||||
const { claims_in_channel: claimsInChannel } = claimResult;
|
||||
|
||||
const autodownload = true; // temp
|
||||
|
||||
const latestIndex = claimsInChannel.findIndex(
|
||||
claim => `${claim.name}#${claim.claim_id}` === subscription.latest
|
||||
);
|
||||
|
||||
if (claimsInChannel.length && latestIndex !== 0) {
|
||||
claimsInChannel.slice(0, latestIndex === -1 ? 10 : latestIndex).forEach((claim, index) => {
|
||||
claimsInChannel.slice(0, latestIndex === -1 ? 10 : latestIndex).forEach(claim => {
|
||||
const uri = buildURI({ contentName: claim.name, claimId: claim.claim_id }, false);
|
||||
const state = getState();
|
||||
const downloadCount = selectDownloadingCount(state);
|
||||
const shouldDownload = Boolean(
|
||||
index < SUBSCRIPTION_DOWNLOAD_LIMIT && !claim.value.stream.metadata.fee
|
||||
downloadCount < SUBSCRIPTION_DOWNLOAD_LIMIT &&
|
||||
!claim.value.stream.metadata.fee &&
|
||||
makeSelectClientSetting(SETTINGS.AUTO_DOWNLOAD)(state)
|
||||
);
|
||||
if (notify) {
|
||||
dispatch(
|
||||
|
@ -160,10 +157,11 @@ export const doCheckSubscription = (subscription: Subscription, notify?: boolean
|
|||
)
|
||||
);
|
||||
}
|
||||
if (autodownload && shouldDownload) {
|
||||
if (shouldDownload) {
|
||||
dispatch(doPurchaseUri(uri, { cost: 0 }));
|
||||
}
|
||||
});
|
||||
|
||||
dispatch(
|
||||
setSubscriptionLatest(
|
||||
{
|
||||
|
@ -182,13 +180,18 @@ export const doCheckSubscription = (subscription: Subscription, notify?: boolean
|
|||
)
|
||||
)
|
||||
);
|
||||
}
|
||||
});
|
||||
|
||||
// this action is not implemented
|
||||
dispatch({
|
||||
type: ACTIONS.CHECK_SUBSCRIPTION_COMPLETED,
|
||||
data: subscription,
|
||||
// calling FETCH_CHANNEL_CLAIMS_COMPLETED after not calling STARTED
|
||||
// means it will delete a non-existant fetchingChannelClaims[uri]
|
||||
dispatch({
|
||||
type: ACTIONS.FETCH_CHANNEL_CLAIMS_COMPLETED,
|
||||
data: {
|
||||
uri: subscription.uri,
|
||||
claims: claimsInChannel || [],
|
||||
page: 1,
|
||||
},
|
||||
});
|
||||
}
|
||||
});
|
||||
};
|
||||
|
||||
|
@ -253,18 +256,20 @@ export const doChannelUnsubscribe = (subscription: Subscription) => (
|
|||
}
|
||||
};
|
||||
|
||||
export const doCheckSubscriptions = () => (
|
||||
dispatch: Dispatch,
|
||||
getState: () => SubscriptionState
|
||||
) => {
|
||||
function doCheck() {
|
||||
const subscriptions = selectSubscriptions(getState());
|
||||
subscriptions.forEach((sub: Subscription) => {
|
||||
dispatch(doCheckSubscription(sub, true));
|
||||
});
|
||||
}
|
||||
setTimeout(doCheck, 2000); // bad fix for not getting subs on load
|
||||
const checkSubscriptionsTimer = setInterval(doCheck, 1000 * 20); // temporary; 20 seconds for testing
|
||||
export const doCheckSubscriptions = () => (dispatch: Dispatch, getState: () => any) => {
|
||||
const state = getState();
|
||||
const subscriptions = selectSubscriptions(state);
|
||||
subscriptions.forEach((sub: Subscription) => {
|
||||
dispatch(doCheckSubscription(sub, true));
|
||||
});
|
||||
};
|
||||
|
||||
export const doCheckSubscriptionsInit = () => (dispatch: Dispatch) => {
|
||||
setTimeout(() => dispatch(doCheckSubscriptions()), 5000); // bad fix for not getting subs on load
|
||||
const checkSubscriptionsTimer = setInterval(
|
||||
() => dispatch(doCheckSubscriptions()),
|
||||
CHECK_SUBSCRIPTIONS_INTERVAL
|
||||
);
|
||||
dispatch({
|
||||
type: ACTIONS.CHECK_SUBSCRIPTIONS_SUBSCRIBE,
|
||||
data: { checkSubscriptionsTimer },
|
||||
|
|
|
@ -26,6 +26,7 @@ const defaultState = {
|
|||
automaticDarkModeEnabled: getLocalStorageSetting(SETTINGS.AUTOMATIC_DARK_MODE_ENABLED, false),
|
||||
autoplay: getLocalStorageSetting(SETTINGS.AUTOPLAY, false),
|
||||
resultCount: Number(getLocalStorageSetting(SETTINGS.RESULT_COUNT, 50)),
|
||||
autoDownload: getLocalStorageSetting(SETTINGS.AUTO_DOWNLOAD, false),
|
||||
osNotificationsEnabled: Boolean(
|
||||
getLocalStorageSetting(SETTINGS.OS_NOTIFICATIONS_ENABLED, true)
|
||||
),
|
||||
|
|
|
@ -1,3 +1,4 @@
|
|||
import * as NOTIFICATION_TYPES from 'constants/notification_types';
|
||||
import { createSelector } from 'reselect';
|
||||
import {
|
||||
selectAllClaimsByChannel,
|
||||
|
@ -25,7 +26,7 @@ export const selectSubscriptionClaims = createSelector(
|
|||
return [];
|
||||
}
|
||||
|
||||
const fetchedSubscriptions = [];
|
||||
let fetchedSubscriptions = [];
|
||||
|
||||
savedSubscriptions.forEach(subscription => {
|
||||
let channelClaims = [];
|
||||
|
@ -39,18 +40,18 @@ export const selectSubscriptionClaims = createSelector(
|
|||
// loop over the list of ids and grab the claim
|
||||
pageOneChannelIds.forEach(id => {
|
||||
const grabbedClaim = allClaims[id];
|
||||
channelClaims.push(grabbedClaim);
|
||||
channelClaims = channelClaims.concat([grabbedClaim]);
|
||||
});
|
||||
}
|
||||
|
||||
fetchedSubscriptions.push({
|
||||
claims: channelClaims,
|
||||
fetchedSubscriptions = fetchedSubscriptions.concat([{
|
||||
claims: [...channelClaims],
|
||||
channelName: subscription.channelName,
|
||||
uri: subscription.uri,
|
||||
});
|
||||
}]);
|
||||
});
|
||||
|
||||
return fetchedSubscriptions;
|
||||
return [...fetchedSubscriptions];
|
||||
}
|
||||
);
|
||||
|
||||
|
@ -69,3 +70,8 @@ export const selectSubscriptionsBeingFetched = createSelector(
|
|||
return fetchingSubscriptionMap;
|
||||
}
|
||||
);
|
||||
|
||||
export const selectDownloadingCount = createSelector(
|
||||
selectNotifications,
|
||||
notifs => Object.values(notifs).reduce((acc, notif) => notif.type === NOTIFICATION_TYPES.DOWNLOADING ? acc + 1 : acc, 0)
|
||||
);
|
||||
|
|
Loading…
Add table
Reference in a new issue