From c60c048c247b1e76b1b3a2c072556629c796efe8 Mon Sep 17 00:00:00 2001 From: Douglas Hall Date: Tue, 14 May 2019 15:57:19 -0400 Subject: [PATCH] Display duplicate TPA provider message. --- src/account-settings/AccountSettingsPage.jsx | 24 ++++++++++++++++++++ src/account-settings/selectors.js | 5 ++++ src/index.jsx | 12 +++++++++- src/reducers.js | 1 + 4 files changed, 41 insertions(+), 1 deletion(-) diff --git a/src/account-settings/AccountSettingsPage.jsx b/src/account-settings/AccountSettingsPage.jsx index 8e96fec..4e7f958 100644 --- a/src/account-settings/AccountSettingsPage.jsx +++ b/src/account-settings/AccountSettingsPage.jsx @@ -73,6 +73,27 @@ class AccountSettingsPage extends React.Component { this.props.saveSettings(formId, values); } + renderDuplicateTpaProviderMessage() { + if (!this.props.duplicateTpaProvider) { + return null; + } + + return ( +
+ + {this.props.duplicateTpaProvider}, + }} + /> + +
+ ); + } + renderManagedProfileMessage() { if (!this.props.profileDataManager) { return null; @@ -303,6 +324,7 @@ class AccountSettingsPage extends React.Component { return (
+ {this.renderDuplicateTpaProviderMessage()}

{this.props.intl.formatMessage(messages['account.settings.page.heading'])}

@@ -369,6 +391,7 @@ AccountSettingsPage.propTypes = { updateDraft: PropTypes.func.isRequired, saveSettings: PropTypes.func.isRequired, fetchSettings: PropTypes.func.isRequired, + duplicateTpaProvider: PropTypes.string, }; AccountSettingsPage.defaultProps = { @@ -384,6 +407,7 @@ AccountSettingsPage.defaultProps = { profileDataManager: null, staticFields: [], hiddenFields: ['secondary_email'], + duplicateTpaProvider: null, }; diff --git a/src/account-settings/selectors.js b/src/account-settings/selectors.js index cdd6289..939da51 100644 --- a/src/account-settings/selectors.js +++ b/src/account-settings/selectors.js @@ -16,6 +16,8 @@ export const userRolesSelector = state => state.authentication.roles || []; export const accountSettingsSelector = state => ({ ...state[storeName] }); +const duplicateTpaProviderSelector = state => state.errors.duplicateTpaProvider; + const editableFieldNameSelector = (state, props) => props.name; const valuesSelector = createSelector( @@ -184,6 +186,7 @@ export const accountSettingsPageSelector = createSelector( hiddenFieldsSelector, timeZonesSelector, countryTimeZonesSelector, + duplicateTpaProviderSelector, ( accountSettings, siteLanguageOptions, @@ -196,6 +199,7 @@ export const accountSettingsPageSelector = createSelector( hiddenFields, timeZoneOptions, countryTimeZoneOptions, + duplicateTpaProvider, ) => ({ siteLanguageOptions, siteLanguage, @@ -210,5 +214,6 @@ export const accountSettingsPageSelector = createSelector( profileDataManager, staticFields, hiddenFields, + duplicateTpaProvider, }), ); diff --git a/src/index.jsx b/src/index.jsx index b46cf61..c5f8f3b 100755 --- a/src/index.jsx +++ b/src/index.jsx @@ -39,7 +39,17 @@ const apiClient = getAuthenticatedAPIClient({ * so that we can hand it all to the redux store's initializer. */ function createInitialState() { - return Object.assign({}, { configuration }, apiClient.getAuthenticationState()); + const errors = {}; + const url = new URL(window.location.href); + + // Extract duplicate third-party auth provider message from query string + errors.duplicateTpaProvider = url.searchParams.get('duplicate_provider'); + if (errors.duplicateTpaProvider) { + // Remove the duplicate_provider query param to avoid bookmarking. + window.history.replaceState(null, '', `${url.protocol}//${url.host}${url.pathname}`); + } + + return Object.assign({}, { configuration }, apiClient.getAuthenticationState(), { errors }); } function configure() { diff --git a/src/reducers.js b/src/reducers.js index e3a6a5d..cc2b161 100755 --- a/src/reducers.js +++ b/src/reducers.js @@ -25,6 +25,7 @@ const createRootReducer = history => // creating the store in data/store.js. authentication: identityReducer, configuration: identityReducer, + errors: identityReducer, i18n: i18nReducer, userAccount, [accountSettingsStoreName]: accountSettingsReducer,