Notifications v2 (part 1) #93
1366
dist/bundle.js
vendored
|
@ -28,7 +28,8 @@
|
|||
},
|
||||
"dependencies": {
|
||||
"proxy-polyfill": "0.1.6",
|
||||
"reselect": "^3.0.0"
|
||||
"reselect": "^3.0.0",
|
||||
"uuid": "^3.3.2"
|
||||
},
|
||||
"devDependencies": {
|
||||
"babel-core": "^6.26.0",
|
||||
|
|
|
@ -211,4 +211,9 @@ export const DO_PREPARE_EDIT = 'DO_PREPARE_EDIT';
|
|||
|
||||
// Notifications
|
||||
export const CREATE_NOTIFICATION = 'CREATE_NOTIFICATION';
|
||||
export const DISMISS_NOTIFICATION = 'DISMISS_NOTIFICATION';
|
||||
export const EDIT_NOTIFICATION = 'EDIT_NOTIFICATION';
|
||||
export const DELETE_NOTIFICATION = 'DELETE_NOTIFICATION';
|
||||
export const CREATE_TOAST = 'CREATE_TOAST';
|
||||
export const DISMISS_TOAST = 'DISMISS_TOAST';
|
||||
export const CREATE_ERROR = 'CREATE_ERROR';
|
||||
export const DISMISS_ERROR = 'DISMISS_ERROR';
|
||||
|
|
|
@ -1,30 +0,0 @@
|
|||
export const CONFIRM_FILE_REMOVE = 'confirm_file_remove';
|
||||
export const CONFIRM_EXTERNAL_LINK = 'confirm_external_link';
|
||||
export const INCOMPATIBLE_DAEMON = 'incompatible_daemon';
|
||||
export const FILE_TIMEOUT = 'file_timeout';
|
||||
export const DOWNLOADING = 'downloading';
|
||||
export const AUTO_UPDATE_DOWNLOADED = 'auto_update_downloaded';
|
||||
export const AUTO_UPDATE_CONFIRM = 'auto_update_confirm';
|
||||
export const ERROR = 'error';
|
||||
export const INSUFFICIENT_CREDITS = 'insufficient_credits';
|
||||
export const UPGRADE = 'upgrade';
|
||||
export const WELCOME = 'welcome';
|
||||
export const EMAIL_COLLECTION = 'email_collection';
|
||||
export const PHONE_COLLECTION = 'phone_collection';
|
||||
export const FIRST_REWARD = 'first_reward';
|
||||
export const AUTHENTICATION_FAILURE = 'auth_failure';
|
||||
export const TRANSACTION_FAILED = 'transaction_failed';
|
||||
export const REWARD_APPROVAL_REQUIRED = 'reward_approval_required';
|
||||
export const REWARD_GENERATED_CODE = 'reward_generated_code';
|
||||
export const AFFIRM_PURCHASE = 'affirm_purchase';
|
||||
export const CONFIRM_CLAIM_REVOKE = 'confirm_claim_revoke';
|
||||
export const FIRST_SUBSCRIPTION = 'firstSubscription';
|
||||
export const SEND_TIP = 'send_tip';
|
||||
export const SOCIAL_SHARE = 'social_share';
|
||||
export const PUBLISH = 'publish';
|
||||
export const SEARCH = 'search';
|
||||
export const CONFIRM_TRANSACTION = 'confirm_transaction';
|
||||
export const CONFIRM_THUMBNAIL_UPLOAD = 'confirm_thumbnail_upload';
|
||||
export const WALLET_ENCRYPT = 'wallet_encrypt';
|
||||
export const WALLET_DECRYPT = 'wallet_decrypt';
|
||||
export const WALLET_UNLOCK = 'wallet_unlock';
|
22
src/index.js
|
@ -1,5 +1,4 @@
|
|||
import * as ACTIONS from 'constants/action_types';
|
||||
import * as MODALS from 'constants/modal_types';
|
||||
import * as THUMBNAIL_STATUSES from 'constants/thumbnail_upload_statuses';
|
||||
import * as SEARCH_TYPES from 'constants/search';
|
||||
import * as SETTINGS from 'constants/settings';
|
||||
|
@ -12,19 +11,10 @@ import Lbryapi from 'lbryapi';
|
|||
import { selectState as selectSearchState } from 'redux/selectors/search';
|
||||
|
||||
// types
|
||||
export { Notification } from 'types/Notification';
|
||||
export { Toast } from 'types/Notification';
|
||||
|
||||
// constants
|
||||
export {
|
||||
ACTIONS,
|
||||
MODALS,
|
||||
THUMBNAIL_STATUSES,
|
||||
SEARCH_TYPES,
|
||||
SETTINGS,
|
||||
TRANSACTIONS,
|
||||
SORT_OPTIONS,
|
||||
PAGES,
|
||||
};
|
||||
export { ACTIONS, THUMBNAIL_STATUSES, SEARCH_TYPES, SETTINGS, TRANSACTIONS, SORT_OPTIONS, PAGES };
|
||||
|
||||
// common
|
||||
export { Lbry, Lbryapi };
|
||||
|
@ -41,7 +31,7 @@ export {
|
|||
} from 'lbryURI';
|
||||
|
||||
// actions
|
||||
export { doNotify, doHideNotification } from 'redux/actions/notifications';
|
||||
export { doToast, doDismissToast, doError, doDismissError } from 'redux/actions/notifications';
|
||||
|
||||
export {
|
||||
doFetchClaimsByChannel,
|
||||
|
@ -108,11 +98,7 @@ export { blacklistReducer } from 'redux/reducers/blacklist';
|
|||
// selectors
|
||||
export { selectBlackListedOutpoints } from 'redux/selectors/blacklist';
|
||||
|
||||
export {
|
||||
selectNotification,
|
||||
selectNotificationProps,
|
||||
selectSnack,
|
||||
} from 'redux/selectors/notifications';
|
||||
export { selectToast, selectError } from 'redux/selectors/notifications';
|
||||
|
||||
export {
|
||||
makeSelectClaimForUri,
|
||||
|
|
|
@ -2,7 +2,7 @@ import * as ACTIONS from 'constants/action_types';
|
|||
import Lbry from 'lbry';
|
||||
import Lbryapi from 'lbryapi';
|
||||
import { normalizeURI } from 'lbryURI';
|
||||
import { doNotify } from 'redux/actions/notifications';
|
||||
import { doToast } from 'redux/actions/notifications';
|
||||
import { selectMyClaimsRaw, selectResolvingUris } from 'redux/selectors/claims';
|
||||
import { batchActions } from 'util/batchActions';
|
||||
import { doFetchTransactions } from 'redux/actions/wallet';
|
||||
|
@ -86,11 +86,9 @@ export function doAbandonClaim(txid, nout) {
|
|||
|
||||
const errorCallback = () => {
|
||||
dispatch(
|
||||
doNotify({
|
||||
title: 'Transaction failed',
|
||||
message: 'Error abandoning claim',
|
||||
type: 'error',
|
||||
displayType: ['snackbar', 'toast'],
|
||||
doToast({
|
||||
message: 'Transaction failed',
|
||||
isError: true,
|
||||
})
|
||||
);
|
||||
};
|
||||
|
@ -104,10 +102,8 @@ export function doAbandonClaim(txid, nout) {
|
|||
},
|
||||
});
|
||||
dispatch(
|
||||
doNotify({
|
||||
title: 'Transaction successful',
|
||||
doToast({
|
||||
message: 'Successfully abandoned your claim',
|
||||
displayType: ['snackbar', 'toast'],
|
||||
})
|
||||
);
|
||||
|
||||
|
@ -117,11 +113,9 @@ export function doAbandonClaim(txid, nout) {
|
|||
dispatch(doFetchTransactions());
|
||||
} else {
|
||||
dispatch(
|
||||
doNotify({
|
||||
title: 'Transaction failed',
|
||||
doToast({
|
||||
message: 'Error abandoning claim',
|
||||
type: 'error',
|
||||
displayType: ['snackbar', 'toast'],
|
||||
isError: true,
|
||||
})
|
||||
);
|
||||
}
|
||||
|
|
|
@ -1,20 +1,39 @@
|
|||
// @flow
|
||||
import type { ToastParams } from 'types/Notification';
|
||||
import * as ACTIONS from 'constants/action_types';
|
||||
import type { Notification, NotificationProps } from 'types/Notification';
|
||||
import uuid from 'uuid/v4';
|
||||
|
||||
export function doToast(params: ToastParams) {
|
||||
if (!params) {
|
||||
throw Error("'params' object is required to create a toast notification");
|
||||
}
|
||||
|
||||
export function doNotify(notification: Notification, notificationProps: NotificationProps) {
|
||||
return {
|
||||
type: ACTIONS.CREATE_NOTIFICATION,
|
||||
type: ACTIONS.CREATE_TOAST,
|
||||
data: {
|
||||
notification,
|
||||
// using this syntax to create an object if notificationProps is undefined
|
||||
notificationProps: { ...notificationProps },
|
||||
id: uuid(),
|
||||
params,
|
||||
},
|
||||
};
|
||||
}
|
||||
|
||||
export function doHideNotification() {
|
||||
export function doDismissToast() {
|
||||
return {
|
||||
type: ACTIONS.DISMISS_NOTIFICATION,
|
||||
type: ACTIONS.DISMISS_TOAST,
|
||||
};
|
||||
}
|
||||
|
||||
export function doError(error: string | {}) {
|
||||
return {
|
||||
type: ACTIONS.CREATE_ERROR,
|
||||
data: {
|
||||
error,
|
||||
},
|
||||
};
|
||||
}
|
||||
|
||||
export function doDismissError() {
|
||||
return {
|
||||
type: ACTIONS.DISMISS_ERROR,
|
||||
};
|
||||
}
|
||||
|
|
|
@ -1,6 +1,6 @@
|
|||
import * as ACTIONS from 'constants/action_types';
|
||||
import Lbry from 'lbry';
|
||||
import { doNotify } from 'redux/actions/notifications';
|
||||
import { doToast } from 'redux/actions/notifications';
|
||||
import { selectBalance } from 'redux/selectors/wallet';
|
||||
import { creditsToString } from 'util/formatCredits';
|
||||
|
||||
|
@ -96,11 +96,9 @@ export function doSendDraftTransaction(address, amount) {
|
|||
|
||||
if (balance - amount <= 0) {
|
||||
dispatch(
|
||||
doNotify({
|
||||
doToast({
|
||||
title: 'Insufficient credits',
|
||||
message: 'Insufficient credits',
|
||||
type: 'error',
|
||||
displayType: ['modal', 'toast'],
|
||||
})
|
||||
);
|
||||
return;
|
||||
|
@ -116,11 +114,8 @@ export function doSendDraftTransaction(address, amount) {
|
|||
type: ACTIONS.SEND_TRANSACTION_COMPLETED,
|
||||
});
|
||||
dispatch(
|
||||
doNotify({
|
||||
title: 'Credits sent',
|
||||
doToast({
|
||||
message: `You sent ${amount} LBC`,
|
||||
type: 'error',
|
||||
displayType: ['snackbar', 'toast'],
|
||||
linkText: 'History',
|
||||
linkTarget: '/wallet',
|
||||
})
|
||||
|
@ -131,11 +126,9 @@ export function doSendDraftTransaction(address, amount) {
|
|||
data: { error: response },
|
||||
});
|
||||
dispatch(
|
||||
doNotify({
|
||||
title: 'Transaction failed',
|
||||
doToast({
|
||||
message: 'Transaction failed',
|
||||
type: 'error',
|
||||
displayType: ['snackbar', 'toast'],
|
||||
isError: true,
|
||||
})
|
||||
);
|
||||
}
|
||||
|
@ -147,11 +140,9 @@ export function doSendDraftTransaction(address, amount) {
|
|||
data: { error: error.message },
|
||||
});
|
||||
dispatch(
|
||||
doNotify({
|
||||
title: 'Transaction failed',
|
||||
doToast({
|
||||
message: 'Transaction failed',
|
||||
type: 'error',
|
||||
displayType: ['snackbar', 'toast'],
|
||||
isError: true,
|
||||
})
|
||||
);
|
||||
};
|
||||
|
@ -184,11 +175,9 @@ export function doSendTip(amount, claimId, uri, successCallback, errorCallback)
|
|||
|
||||
if (balance - amount <= 0) {
|
||||
dispatch(
|
||||
doNotify({
|
||||
title: 'Insufficient credits',
|
||||
doToast({
|
||||
message: 'Insufficient credits',
|
||||
type: 'error',
|
||||
displayType: ['modal', 'toast'],
|
||||
isError: true,
|
||||
})
|
||||
);
|
||||
return;
|
||||
|
@ -196,11 +185,10 @@ export function doSendTip(amount, claimId, uri, successCallback, errorCallback)
|
|||
|
||||
const success = () => {
|
||||
dispatch(
|
||||
doNotify({
|
||||
doToast({
|
||||
message: __(`You sent ${amount} LBC as a tip, Mahalo!`),
|
||||
linkText: __('History'),
|
||||
linkTarget: __('/wallet'),
|
||||
displayType: ['snackbar'],
|
||||
})
|
||||
);
|
||||
|
||||
|
@ -215,9 +203,9 @@ export function doSendTip(amount, claimId, uri, successCallback, errorCallback)
|
|||
|
||||
const error = (err) => {
|
||||
dispatch(
|
||||
doNotify({
|
||||
doToast({
|
||||
message: __(`There was an error sending support funds.`),
|
||||
displayType: ['snackbar'],
|
||||
isError: true,
|
||||
})
|
||||
);
|
||||
|
||||
|
|
|
@ -1,55 +1,102 @@
|
|||
That was just a typo. Fixed That was just a typo. Fixed
Why the circular reference? Why the circular reference?
I don't entirely understand this routine.
That was just a typo. Fixed That was just a typo. Fixed
|
||||
// @flow
|
||||
Why the circular reference? Why the circular reference?
I don't entirely understand this routine.
That was just a typo. Fixed That was just a typo. Fixed
|
||||
import type {
|
||||
Why the circular reference? Why the circular reference?
I don't entirely understand this routine.
That was just a typo. Fixed That was just a typo. Fixed
|
||||
NotificationState,
|
||||
Why the circular reference? Why the circular reference?
I don't entirely understand this routine.
That was just a typo. Fixed That was just a typo. Fixed
|
||||
DoToast,
|
||||
Why the circular reference? Why the circular reference?
I don't entirely understand this routine.
That was just a typo. Fixed That was just a typo. Fixed
|
||||
DoNotification,
|
||||
Why the circular reference? Why the circular reference?
I don't entirely understand this routine.
That was just a typo. Fixed That was just a typo. Fixed
|
||||
DoEditNotification,
|
||||
Why the circular reference? Why the circular reference?
I don't entirely understand this routine.
That was just a typo. Fixed That was just a typo. Fixed
|
||||
DoDeleteNotification,
|
||||
Why the circular reference? Why the circular reference?
I don't entirely understand this routine.
That was just a typo. Fixed That was just a typo. Fixed
|
||||
} from 'types/Notification';
|
||||
Why the circular reference? Why the circular reference?
I don't entirely understand this routine.
That was just a typo. Fixed That was just a typo. Fixed
|
||||
import * as ACTIONS from 'constants/action_types';
|
||||
import * as MODALS from 'constants/modal_types';
|
||||
Why the circular reference? Why the circular reference?
I don't entirely understand this routine.
That was just a typo. Fixed That was just a typo. Fixed
|
||||
import { handleActions } from 'util/redux-utils';
|
||||
Why the circular reference? Why the circular reference?
I don't entirely understand this routine.
That was just a typo. Fixed That was just a typo. Fixed
|
||||
|
||||
const reducers = {};
|
||||
Why the circular reference? Why the circular reference?
I don't entirely understand this routine.
That was just a typo. Fixed That was just a typo. Fixed
|
||||
|
||||
Why the circular reference? Why the circular reference?
I don't entirely understand this routine.
That was just a typo. Fixed That was just a typo. Fixed
|
||||
const defaultState = {
|
||||
Why the circular reference? Why the circular reference?
I don't entirely understand this routine.
That was just a typo. Fixed That was just a typo. Fixed
|
||||
// First-in, first-out
|
||||
Why the circular reference? Why the circular reference?
I don't entirely understand this routine.
That was just a typo. Fixed That was just a typo. Fixed
|
||||
queue: [],
|
||||
Why the circular reference? Why the circular reference?
I don't entirely understand this routine.
That was just a typo. Fixed That was just a typo. Fixed
|
||||
const defaultState: NotificationState = {
|
||||
Why the circular reference? Why the circular reference?
I don't entirely understand this routine.
That was just a typo. Fixed That was just a typo. Fixed
|
||||
notifications: [],
|
||||
Why the circular reference? Why the circular reference?
I don't entirely understand this routine.
That was just a typo. Fixed That was just a typo. Fixed
|
||||
toasts: [],
|
||||
Why the circular reference? Why the circular reference?
I don't entirely understand this routine.
That was just a typo. Fixed That was just a typo. Fixed
|
||||
errors: [],
|
||||
Why the circular reference? Why the circular reference?
I don't entirely understand this routine.
That was just a typo. Fixed That was just a typo. Fixed
|
||||
};
|
||||
|
||||
reducers[ACTIONS.CREATE_NOTIFICATION] = (state, action) => {
|
||||
Why the circular reference? Why the circular reference?
I don't entirely understand this routine.
That was just a typo. Fixed That was just a typo. Fixed
|
||||
const { notification, notificationProps } = action.data;
|
||||
Why the circular reference? Why the circular reference?
I don't entirely understand this routine.
That was just a typo. Fixed That was just a typo. Fixed
|
||||
const { title, message, type, error, displayType, id } = notification;
|
||||
Why the circular reference? Why the circular reference?
I don't entirely understand this routine.
That was just a typo. Fixed That was just a typo. Fixed
|
||||
const notificationsReducer = handleActions(
|
||||
Why the circular reference? Why the circular reference?
I don't entirely understand this routine.
That was just a typo. Fixed That was just a typo. Fixed
|
||||
{
|
||||
Why the circular reference? Why the circular reference?
I don't entirely understand this routine.
That was just a typo. Fixed That was just a typo. Fixed
|
||||
// Toasts
|
||||
Why the circular reference? Why the circular reference?
I don't entirely understand this routine.
That was just a typo. Fixed That was just a typo. Fixed
|
||||
[ACTIONS.CREATE_TOAST]: (state: NotificationState, action: DoToast) => {
|
||||
Why the circular reference? Why the circular reference?
I don't entirely understand this routine.
That was just a typo. Fixed That was just a typo. Fixed
|
||||
const toast = action.data;
|
||||
Why the circular reference? Why the circular reference?
I don't entirely understand this routine.
That was just a typo. Fixed That was just a typo. Fixed
|
||||
const newToasts = state.toasts.slice();
|
||||
Why the circular reference? Why the circular reference?
I don't entirely understand this routine.
That was just a typo. Fixed That was just a typo. Fixed
|
||||
newToasts.push(toast);
|
||||
Why the circular reference? Why the circular reference?
I don't entirely understand this routine.
That was just a typo. Fixed That was just a typo. Fixed
|
||||
|
||||
const queue = Object.assign([], state.queue);
|
||||
Why the circular reference? Why the circular reference?
I don't entirely understand this routine.
That was just a typo. Fixed That was just a typo. Fixed
|
||||
queue.push({
|
||||
Why the circular reference? Why the circular reference?
I don't entirely understand this routine.
That was just a typo. Fixed That was just a typo. Fixed
|
||||
notification: {
|
||||
Why the circular reference? Why the circular reference?
I don't entirely understand this routine.
That was just a typo. Fixed That was just a typo. Fixed
|
||||
id,
|
||||
Why the circular reference? Why the circular reference?
I don't entirely understand this routine.
That was just a typo. Fixed That was just a typo. Fixed
|
||||
title,
|
||||
Why the circular reference? Why the circular reference?
I don't entirely understand this routine.
That was just a typo. Fixed That was just a typo. Fixed
|
||||
message,
|
||||
Why the circular reference? Why the circular reference?
I don't entirely understand this routine.
That was just a typo. Fixed That was just a typo. Fixed
|
||||
type,
|
||||
Why the circular reference? Why the circular reference?
I don't entirely understand this routine.
That was just a typo. Fixed That was just a typo. Fixed
|
||||
error,
|
||||
Why the circular reference? Why the circular reference?
I don't entirely understand this routine.
That was just a typo. Fixed That was just a typo. Fixed
|
||||
displayType,
|
||||
Why the circular reference? Why the circular reference?
I don't entirely understand this routine.
That was just a typo. Fixed That was just a typo. Fixed
|
||||
return {
|
||||
Why the circular reference? Why the circular reference?
I don't entirely understand this routine.
That was just a typo. Fixed That was just a typo. Fixed
|
||||
...state,
|
||||
Why the circular reference? Why the circular reference?
I don't entirely understand this routine.
That was just a typo. Fixed That was just a typo. Fixed
|
||||
toasts: newToasts,
|
||||
Why the circular reference? Why the circular reference?
I don't entirely understand this routine.
That was just a typo. Fixed That was just a typo. Fixed
|
||||
};
|
||||
Why the circular reference? Why the circular reference?
I don't entirely understand this routine.
That was just a typo. Fixed That was just a typo. Fixed
|
||||
},
|
||||
notificationProps,
|
||||
Why the circular reference? Why the circular reference?
I don't entirely understand this routine.
That was just a typo. Fixed That was just a typo. Fixed
|
||||
});
|
||||
Why the circular reference? Why the circular reference?
I don't entirely understand this routine.
That was just a typo. Fixed That was just a typo. Fixed
|
||||
[ACTIONS.DISMISS_TOAST]: (state: NotificationState) => {
|
||||
Why the circular reference? Why the circular reference?
I don't entirely understand this routine.
That was just a typo. Fixed That was just a typo. Fixed
|
||||
const newToasts = state.toasts.slice();
|
||||
Why the circular reference? Why the circular reference?
I don't entirely understand this routine.
That was just a typo. Fixed That was just a typo. Fixed
|
||||
newToasts.shift();
|
||||
Why the circular reference? Why the circular reference?
I don't entirely understand this routine.
That was just a typo. Fixed That was just a typo. Fixed
|
||||
|
||||
return Object.assign({}, state, {
|
||||
Why the circular reference? Why the circular reference?
I don't entirely understand this routine.
That was just a typo. Fixed That was just a typo. Fixed
|
||||
queue,
|
||||
Why the circular reference? Why the circular reference?
I don't entirely understand this routine.
That was just a typo. Fixed That was just a typo. Fixed
|
||||
});
|
||||
Why the circular reference? Why the circular reference?
I don't entirely understand this routine.
That was just a typo. Fixed That was just a typo. Fixed
|
||||
};
|
||||
Why the circular reference? Why the circular reference?
I don't entirely understand this routine.
That was just a typo. Fixed That was just a typo. Fixed
|
||||
return {
|
||||
Why the circular reference? Why the circular reference?
I don't entirely understand this routine.
That was just a typo. Fixed That was just a typo. Fixed
|
||||
...state,
|
||||
Why the circular reference? Why the circular reference?
I don't entirely understand this routine.
That was just a typo. Fixed That was just a typo. Fixed
|
||||
toasts: newToasts,
|
||||
Why the circular reference? Why the circular reference?
I don't entirely understand this routine.
That was just a typo. Fixed That was just a typo. Fixed
|
||||
};
|
||||
Why the circular reference? Why the circular reference?
I don't entirely understand this routine.
That was just a typo. Fixed That was just a typo. Fixed
|
||||
},
|
||||
Why the circular reference? Why the circular reference?
I don't entirely understand this routine.
That was just a typo. Fixed That was just a typo. Fixed
|
||||
|
||||
reducers[ACTIONS.DISMISS_NOTIFICATION] = state => {
|
||||
Why the circular reference? Why the circular reference?
I don't entirely understand this routine.
That was just a typo. Fixed That was just a typo. Fixed
|
||||
const queue = Object.assign([], state.queue);
|
||||
Why the circular reference? Why the circular reference?
I don't entirely understand this routine.
That was just a typo. Fixed That was just a typo. Fixed
|
||||
queue.shift();
|
||||
Why the circular reference? Why the circular reference?
I don't entirely understand this routine.
That was just a typo. Fixed That was just a typo. Fixed
|
||||
// Notifications
|
||||
Why the circular reference? Why the circular reference?
I don't entirely understand this routine.
That was just a typo. Fixed That was just a typo. Fixed
|
||||
[ACTIONS.CREATE_NOTIFICATION]: (state: NotificationState, action: DoNotification) => {
|
||||
Why the circular reference? Why the circular reference?
I don't entirely understand this routine.
That was just a typo. Fixed That was just a typo. Fixed
|
||||
const notification = action.data;
|
||||
Why the circular reference? Why the circular reference?
I don't entirely understand this routine.
That was just a typo. Fixed That was just a typo. Fixed
|
||||
const newNotifications = state.notifications.slice();
|
||||
Why the circular reference? Why the circular reference?
I don't entirely understand this routine.
That was just a typo. Fixed That was just a typo. Fixed
|
||||
newNotifications.push(notification);
|
||||
Why the circular reference? Why the circular reference?
I don't entirely understand this routine.
That was just a typo. Fixed That was just a typo. Fixed
|
||||
|
||||
return Object.assign({}, state, {
|
||||
Why the circular reference? Why the circular reference?
I don't entirely understand this routine.
That was just a typo. Fixed That was just a typo. Fixed
|
||||
queue,
|
||||
Why the circular reference? Why the circular reference?
I don't entirely understand this routine.
That was just a typo. Fixed That was just a typo. Fixed
|
||||
});
|
||||
Why the circular reference? Why the circular reference?
I don't entirely understand this routine.
That was just a typo. Fixed That was just a typo. Fixed
|
||||
};
|
||||
Why the circular reference? Why the circular reference?
I don't entirely understand this routine.
That was just a typo. Fixed That was just a typo. Fixed
|
||||
return {
|
||||
Why the circular reference? Why the circular reference?
I don't entirely understand this routine.
That was just a typo. Fixed That was just a typo. Fixed
|
||||
...state,
|
||||
Why the circular reference? Why the circular reference?
I don't entirely understand this routine.
That was just a typo. Fixed That was just a typo. Fixed
|
||||
notifications: newNotifications,
|
||||
Why the circular reference? Why the circular reference?
I don't entirely understand this routine.
That was just a typo. Fixed That was just a typo. Fixed
|
||||
};
|
||||
Why the circular reference? Why the circular reference?
I don't entirely understand this routine.
That was just a typo. Fixed That was just a typo. Fixed
|
||||
},
|
||||
Why the circular reference? Why the circular reference?
I don't entirely understand this routine.
That was just a typo. Fixed That was just a typo. Fixed
|
||||
// Used to mark notifications as read/dismissed
|
||||
Why the circular reference? Why the circular reference?
I don't entirely understand this routine.
That was just a typo. Fixed That was just a typo. Fixed
|
||||
[ACTIONS.EDIT_NOTIFICATION]: (state: NotificationState, action: DoEditNotification) => {
|
||||
Why the circular reference? Why the circular reference?
I don't entirely understand this routine.
That was just a typo. Fixed That was just a typo. Fixed
|
||||
const { notification } = action.data;
|
||||
Why the circular reference? Why the circular reference?
I don't entirely understand this routine.
That was just a typo. Fixed That was just a typo. Fixed
|
||||
let notifications = state.notifications.slice();
|
||||
Why the circular reference? Why the circular reference?
I don't entirely understand this routine.
That was just a typo. Fixed That was just a typo. Fixed
|
||||
|
||||
reducers[ACTIONS.HISTORY_NAVIGATE] = state => {
|
||||
Why the circular reference? Why the circular reference?
I don't entirely understand this routine.
That was just a typo. Fixed That was just a typo. Fixed
|
||||
const queue = Object.assign([], state.queue);
|
||||
Why the circular reference? Why the circular reference?
I don't entirely understand this routine.
That was just a typo. Fixed That was just a typo. Fixed
|
||||
if (queue[0] && queue[0].notification.id === MODALS.SEARCH) {
|
||||
Why the circular reference? Why the circular reference?
I don't entirely understand this routine.
That was just a typo. Fixed That was just a typo. Fixed
|
||||
queue.shift();
|
||||
Why the circular reference? Why the circular reference?
I don't entirely understand this routine.
That was just a typo. Fixed That was just a typo. Fixed
|
||||
return Object.assign({}, state, { queue });
|
||||
Why the circular reference? Why the circular reference?
I don't entirely understand this routine.
That was just a typo. Fixed That was just a typo. Fixed
|
||||
}
|
||||
Why the circular reference? Why the circular reference?
I don't entirely understand this routine.
That was just a typo. Fixed That was just a typo. Fixed
|
||||
return state;
|
||||
Why the circular reference? Why the circular reference?
I don't entirely understand this routine.
That was just a typo. Fixed That was just a typo. Fixed
|
||||
};
|
||||
Why the circular reference? Why the circular reference?
I don't entirely understand this routine.
That was just a typo. Fixed That was just a typo. Fixed
|
||||
notifications = notifications.map(
|
||||
Why the circular reference? Why the circular reference?
I don't entirely understand this routine.
That was just a typo. Fixed That was just a typo. Fixed
|
||||
(pastNotification) =>
|
||||
Why the circular reference? Why the circular reference?
I don't entirely understand this routine.
That was just a typo. Fixed That was just a typo. Fixed
|
||||
pastNotification.id === notification.id ? notification : pastNotification
|
||||
Why the circular reference? Why the circular reference?
I don't entirely understand this routine.
That was just a typo. Fixed That was just a typo. Fixed
|
||||
);
|
||||
Why the circular reference? Why the circular reference?
I don't entirely understand this routine.
That was just a typo. Fixed That was just a typo. Fixed
|
||||
|
||||
export function notificationsReducer(state = defaultState, action) {
|
||||
Why the circular reference? Why the circular reference?
I don't entirely understand this routine.
That was just a typo. Fixed That was just a typo. Fixed
|
||||
const handler = reducers[action.type];
|
||||
Why the circular reference? Why the circular reference?
I don't entirely understand this routine.
That was just a typo. Fixed That was just a typo. Fixed
|
||||
if (handler) return handler(state, action);
|
||||
Why the circular reference? Why the circular reference?
I don't entirely understand this routine.
That was just a typo. Fixed That was just a typo. Fixed
|
||||
return state;
|
||||
Why the circular reference? Why the circular reference?
I don't entirely understand this routine.
That was just a typo. Fixed That was just a typo. Fixed
|
||||
}
|
||||
Why the circular reference? Why the circular reference?
I don't entirely understand this routine.
That was just a typo. Fixed That was just a typo. Fixed
|
||||
return {
|
||||
Why the circular reference? Why the circular reference?
I don't entirely understand this routine.
That was just a typo. Fixed That was just a typo. Fixed
|
||||
...state,
|
||||
Why the circular reference? Why the circular reference?
I don't entirely understand this routine.
That was just a typo. Fixed That was just a typo. Fixed
|
||||
notifications,
|
||||
Why the circular reference? Why the circular reference?
I don't entirely understand this routine.
That was just a typo. Fixed That was just a typo. Fixed
|
||||
};
|
||||
Why the circular reference? Why the circular reference?
I don't entirely understand this routine.
That was just a typo. Fixed That was just a typo. Fixed
|
||||
},
|
||||
Why the circular reference? Why the circular reference?
I don't entirely understand this routine.
That was just a typo. Fixed That was just a typo. Fixed
|
||||
[ACTIONS.DELETE_NOTIFICATION]: (state: NotificationState, action: DoDeleteNotification) => {
|
||||
Why the circular reference? Why the circular reference?
I don't entirely understand this routine.
That was just a typo. Fixed That was just a typo. Fixed
|
||||
const { id } = action.data;
|
||||
Why the circular reference? Why the circular reference?
I don't entirely understand this routine.
That was just a typo. Fixed That was just a typo. Fixed
|
||||
let newNotifications = state.notifications.slice();
|
||||
Why the circular reference? Why the circular reference?
I don't entirely understand this routine.
That was just a typo. Fixed That was just a typo. Fixed
|
||||
newNotifications = newNotifications.filter((notification) => notification.id !== id);
|
||||
Why the circular reference? Why the circular reference?
I don't entirely understand this routine.
That was just a typo. Fixed That was just a typo. Fixed
|
||||
|
||||
Why the circular reference? Why the circular reference?
I don't entirely understand this routine.
That was just a typo. Fixed That was just a typo. Fixed
|
||||
return {
|
||||
Why the circular reference? Why the circular reference?
I don't entirely understand this routine.
That was just a typo. Fixed That was just a typo. Fixed
|
||||
...state,
|
||||
Why the circular reference? Why the circular reference?
I don't entirely understand this routine.
That was just a typo. Fixed That was just a typo. Fixed
|
||||
notifications: newNotifications,
|
||||
Why the circular reference? Why the circular reference?
I don't entirely understand this routine.
That was just a typo. Fixed That was just a typo. Fixed
|
||||
};
|
||||
Why the circular reference? Why the circular reference?
I don't entirely understand this routine.
That was just a typo. Fixed That was just a typo. Fixed
|
||||
},
|
||||
Why the circular reference? Why the circular reference?
I don't entirely understand this routine.
That was just a typo. Fixed That was just a typo. Fixed
|
||||
|
||||
Why the circular reference? Why the circular reference?
I don't entirely understand this routine.
That was just a typo. Fixed That was just a typo. Fixed
|
||||
// Errors
|
||||
Why the circular reference? Why the circular reference?
I don't entirely understand this routine.
That was just a typo. Fixed That was just a typo. Fixed
|
||||
[ACTIONS.CREATE_ERROR]: (state: NotificationState, action: DoToast) => {
|
||||
Why the circular reference? Why the circular reference?
I don't entirely understand this routine.
That was just a typo. Fixed That was just a typo. Fixed
|
||||
const error = action.data;
|
||||
Why the circular reference? Why the circular reference?
I don't entirely understand this routine.
That was just a typo. Fixed That was just a typo. Fixed
|
||||
const newErrors = state.errors.slice();
|
||||
Why the circular reference? Why the circular reference?
I don't entirely understand this routine.
That was just a typo. Fixed That was just a typo. Fixed
|
||||
newErrors.push(error);
|
||||
Why the circular reference? Why the circular reference?
I don't entirely understand this routine.
That was just a typo. Fixed That was just a typo. Fixed
|
||||
|
||||
Why the circular reference? Why the circular reference?
I don't entirely understand this routine.
That was just a typo. Fixed That was just a typo. Fixed
|
||||
return {
|
||||
Why the circular reference? Why the circular reference?
I don't entirely understand this routine.
That was just a typo. Fixed That was just a typo. Fixed
|
||||
...state,
|
||||
Why the circular reference? Why the circular reference?
I don't entirely understand this routine.
That was just a typo. Fixed That was just a typo. Fixed
|
||||
errors: newErrors,
|
||||
Why the circular reference? Why the circular reference?
I don't entirely understand this routine.
That was just a typo. Fixed That was just a typo. Fixed
|
||||
};
|
||||
Why the circular reference? Why the circular reference?
I don't entirely understand this routine.
That was just a typo. Fixed That was just a typo. Fixed
|
||||
},
|
||||
Why the circular reference? Why the circular reference?
I don't entirely understand this routine.
That was just a typo. Fixed That was just a typo. Fixed
|
||||
[ACTIONS.DISMISS_ERROR]: (state: NotificationState) => {
|
||||
Why the circular reference? Why the circular reference?
I don't entirely understand this routine.
That was just a typo. Fixed That was just a typo. Fixed
|
||||
const newErrors = state.errors.slice();
|
||||
Why the circular reference? Why the circular reference?
I don't entirely understand this routine.
That was just a typo. Fixed That was just a typo. Fixed
|
||||
newErrors.shift();
|
||||
Why the circular reference? Why the circular reference?
I don't entirely understand this routine.
That was just a typo. Fixed That was just a typo. Fixed
|
||||
|
||||
Why the circular reference? Why the circular reference?
I don't entirely understand this routine.
That was just a typo. Fixed That was just a typo. Fixed
|
||||
return {
|
||||
Why the circular reference? Why the circular reference?
I don't entirely understand this routine.
That was just a typo. Fixed That was just a typo. Fixed
|
||||
...state,
|
||||
Why the circular reference? Why the circular reference?
I don't entirely understand this routine.
That was just a typo. Fixed That was just a typo. Fixed
|
||||
errors: newErrors,
|
||||
Why the circular reference? Why the circular reference?
I don't entirely understand this routine.
That was just a typo. Fixed That was just a typo. Fixed
|
||||
};
|
||||
Why the circular reference? Why the circular reference?
I don't entirely understand this routine.
That was just a typo. Fixed That was just a typo. Fixed
|
||||
},
|
||||
Why the circular reference? Why the circular reference?
I don't entirely understand this routine.
That was just a typo. Fixed That was just a typo. Fixed
|
||||
},
|
||||
Why the circular reference? Why the circular reference?
I don't entirely understand this routine.
That was just a typo. Fixed That was just a typo. Fixed
|
||||
defaultState
|
||||
Why the circular reference? Why the circular reference?
I don't entirely understand this routine.
That was just a typo. Fixed That was just a typo. Fixed
|
||||
);
|
||||
Why the circular reference? Why the circular reference?
I don't entirely understand this routine.
That was just a typo. Fixed That was just a typo. Fixed
|
||||
|
||||
Why the circular reference? Why the circular reference?
I don't entirely understand this routine.
That was just a typo. Fixed That was just a typo. Fixed
|
||||
export { notificationsReducer };
|
||||
Why the circular reference? Why the circular reference?
I don't entirely understand this routine.
That was just a typo. Fixed That was just a typo. Fixed
|
||||
|
|
|||
Why the circular reference? Why the circular reference?
I don't entirely understand this routine.
That was just a typo. Fixed That was just a typo. Fixed
Why the circular reference? Why the circular reference?
I don't entirely understand this routine.
That was just a typo. Fixed That was just a typo. Fixed
|
|
@ -1,30 +1,26 @@
|
|||
import { createSelector } from 'reselect';
|
||||
|
||||
export const selectState = state => state.notifications || {};
|
||||
export const selectState = (state) => state.notifications || {};
|
||||
|
||||
export const selectNotificationData = createSelector(
|
||||
selectState,
|
||||
state => (state.queue.length > 0 ? state.queue[0] : {})
|
||||
);
|
||||
|
||||
export const selectNotification = createSelector(
|
||||
selectNotificationData,
|
||||
notificationData => notificationData.notification
|
||||
);
|
||||
|
||||
export const selectNotificationProps = createSelector(
|
||||
selectNotificationData,
|
||||
notificationData => notificationData.notificationProps
|
||||
);
|
||||
|
||||
export const selectSnack = createSelector(
|
||||
// No props for snackbar
|
||||
selectNotification,
|
||||
notification => {
|
||||
if (notification && notification.displayType) {
|
||||
return notification.displayType.indexOf('snackbar') > -1 ? notification : undefined;
|
||||
}
|
||||
|
||||
return undefined;
|
||||
export const selectToast = createSelector(selectState, (state) => {
|
||||
if (state.toasts.length) {
|
||||
const { id, params } = state.toasts[0];
|
||||
return {
|
||||
id,
|
||||
...params,
|
||||
};
|
||||
}
|
||||
);
|
||||
|
||||
return null;
|
||||
});
|
||||
|
||||
export const selectError = createSelector(selectState, (state) => {
|
||||
if (state.errors.length) {
|
||||
const { error } = state.errors[0];
|
||||
return {
|
||||
error,
|
||||
Could be Could be `state.toasts.length !== 0`, I'm mostly indifferent - style vs speed
|
||||
};
|
||||
}
|
||||
|
||||
return null;
|
||||
});
|
||||
|
|
|
@ -1,19 +1,97 @@
|
|||
// @flow
|
||||
export type Notification = {
|
||||
id: ?string,
|
||||
title: ?string,
|
||||
import * as ACTIONS from 'constants/action_types';
|
||||
|
||||
/*
|
||||
Toasts:
|
||||
- First-in, first-out queue
|
||||
- Simple messages that are shown in response to user interactions
|
||||
- Never saved
|
||||
- If they are the result of errors, use the isError flag when creating
|
||||
- For errors that should interrupt user behavior, use Error
|
||||
*/
|
||||
export type ToastParams = {
|
||||
message: string,
|
||||
type: string,
|
||||
error: ?string,
|
||||
displayType: mixed,
|
||||
|
||||
// additional properties for SnackBar
|
||||
linkText: ?string,
|
||||
linkTarget: ?string,
|
||||
title?: string,
|
||||
linkText?: string,
|
||||
linkTarget?: string,
|
||||
isError?: boolean,
|
||||
};
|
||||
|
||||
// Used for retreiving data from redux store
|
||||
export type NotificationProps = {
|
||||
uri: ?string,
|
||||
path: ?string,
|
||||
export type Toast = {
|
||||
id: string,
|
||||
params: ToastParams,
|
||||
};
|
||||
|
||||
export type DoToast = {
|
||||
type: ACTIONS.CREATE_TOAST,
|
||||
Any particular reason for renaming to toasts? All toasts are notifications, but not all notifications are toasts. EDIT: Just saw that there are three types of notifications, toasts, events and errors. I don't feel too strongly about this, but I think we could use a better name instead of events. Just to add to this, I'm wary of using Any particular reason for renaming to toasts? All toasts are notifications, but not all notifications are toasts.
EDIT: Just saw that there are three types of notifications, toasts, events and errors. I don't feel too strongly about this, but I think we could use a better name instead of events.
Just to add to this, I'm wary of using `Event` because we already have events in Javascript, so it may lead to some confusion for new code contributors not familiar with the codebase.
|
||||
data: Toast,
|
||||
};
|
||||
|
||||
/*
|
||||
Notifications:
|
||||
- List of notifications based on user interactions/app notifications
|
||||
- Always saved, but can be manually deleted
|
||||
- Can happen in the background, or because of user interaction (ex: publish confirmed)
|
||||
*/
|
||||
export type Notification = {
|
||||
id: string, // Unique id
|
||||
dateCreated: number,
|
||||
isRead: boolean, // Used to display "new" notifications that a user hasn't seen yet
|
||||
source?: string, // The type/area an notification is from. Used for sorting (ex: publishes, transactions)
|
||||
// We may want to use priority/isDismissed in the future to specify how urgent a notification is
|
||||
// and if the user should see it immediately
|
||||
// isDissmied: boolean,
|
||||
// priority?: number
|
||||
};
|
||||
|
||||
export type DoNotification = {
|
||||
type: ACTIONS.CREATE_NOTIFICATION,
|
||||
data: Notification,
|
||||
};
|
||||
|
||||
export type DoEditNotification = {
|
||||
type: ACTIONS.EDIT_NOTIFICATION,
|
||||
data: {
|
||||
id: string,
|
||||
isRead: boolean,
|
||||
// In the future we can add `isDismissed` if we decide to show notifications as they come in
|
||||
// Similar to Facebook's notifications in the corner of the screen
|
||||
// isDismissed: boolean,
|
||||
},
|
||||
};
|
||||
|
||||
export type DoDeleteNotification = {
|
||||
type: ACTIONS.DELETE_NOTIFICATION,
|
||||
data: {
|
||||
id: string, // The id to delete
|
||||
},
|
||||
};
|
||||
|
||||
/*
|
||||
Errors:
|
||||
- First-in, first-out queue
|
||||
- Errors that should interupt user behavior
|
||||
- For errors that can be shown without interrupting a user, use Toast with the isError flag
|
||||
*/
|
||||
export type Error = {
|
||||
title: string,
|
||||
text: string,
|
||||
};
|
||||
|
||||
export type DoError = {
|
||||
type: ACTIONS.CREATE_ERROR,
|
||||
data: Error,
|
||||
};
|
||||
|
||||
export type DoDismissError = {
|
||||
type: ACTIONS.DISMISS_ERROR,
|
||||
};
|
||||
|
||||
/*
|
||||
NotificationState
|
||||
*/
|
||||
export type NotificationState = {
|
||||
notifications: Array<Notification>,
|
||||
errors: Array<Error>,
|
||||
toasts: Array<Toast>,
|
||||
};
|
||||
|
|
|
@ -5977,6 +5977,10 @@ uuid@^3.1.0:
|
|||
version "3.2.1"
|
||||
resolved "https://registry.yarnpkg.com/uuid/-/uuid-3.2.1.tgz#12c528bb9d58d0b9265d9a2f6f0fe8be17ff1f14"
|
||||
|
||||
uuid@^3.3.2:
|
||||
version "3.3.2"
|
||||
resolved "https://registry.yarnpkg.com/uuid/-/uuid-3.3.2.tgz#1b4af4955eb3077c501c23872fc6513811587131"
|
||||
|
||||
v8-compile-cache@^1.1.2:
|
||||
version "1.1.2"
|
||||
resolved "https://registry.yarnpkg.com/v8-compile-cache/-/v8-compile-cache-1.1.2.tgz#8d32e4f16974654657e676e0e467a348e89b0dc4"
|
||||
|
|
Why the circular reference?
I don't entirely understand this routine.