summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
-rw-r--r--web/src/App.jsx12
-rw-r--r--web/src/ZuulAuthProvider.jsx3
-rw-r--r--web/src/actions/user.js3
-rw-r--r--web/src/pages/AuthCallback.jsx46
-rw-r--r--web/src/reducers/user.js3
-rw-r--r--web/src/routes.js7
6 files changed, 55 insertions, 19 deletions
diff --git a/web/src/App.jsx b/web/src/App.jsx
index 5dd3b09d9..da7b2aa03 100644
--- a/web/src/App.jsx
+++ b/web/src/App.jsx
@@ -69,6 +69,8 @@ import { fetchConfigErrorsAction } from './actions/configErrors'
import { routes } from './routes'
import { setTenantAction } from './actions/tenant'
import { configureAuthFromTenant, configureAuthFromInfo } from './actions/auth'
+import { getHomepageUrl } from './api'
+import AuthCallbackPage from './pages/AuthCallback'
class App extends React.Component {
static propTypes = {
@@ -82,6 +84,7 @@ class App extends React.Component {
dispatch: PropTypes.func,
isKebabDropdownOpen: PropTypes.bool,
user: PropTypes.object,
+ auth: PropTypes.object,
}
state = {
@@ -117,6 +120,12 @@ class App extends React.Component {
const { info, tenant } = this.props
const allRoutes = []
+ if ((window.location.origin + window.location.pathname) ===
+ (getHomepageUrl() + 'auth_callback')) {
+ // Sit on the auth callback page until login and token
+ // validation is complete (it will internally redirect when complete)
+ return <AuthCallbackPage/>
+ }
if (info.isFetching) {
return <Fetching />
}
@@ -482,6 +491,7 @@ export default withRouter(connect(
info: state.info,
tenant: state.tenant,
timezone: state.timezone,
- user: state.user
+ user: state.user,
+ auth: state.auth,
})
)(App))
diff --git a/web/src/ZuulAuthProvider.jsx b/web/src/ZuulAuthProvider.jsx
index 7f844e843..b5d538c90 100644
--- a/web/src/ZuulAuthProvider.jsx
+++ b/web/src/ZuulAuthProvider.jsx
@@ -67,7 +67,8 @@ class ZuulAuthProvider extends React.Component {
onSignIn: async (user) => {
// Update redux with the logged in state and send the
// credentials to any other tabs.
- this.props.dispatch(userLoggedIn(user))
+ const redirect = localStorage.getItem('zuul_auth_redirect')
+ this.props.dispatch(userLoggedIn(user, redirect))
this.props.channel.postMessage({
type: 'signIn',
auth_params: auth_params,
diff --git a/web/src/actions/user.js b/web/src/actions/user.js
index 9b3261c9f..d01d4c24c 100644
--- a/web/src/actions/user.js
+++ b/web/src/actions/user.js
@@ -36,11 +36,12 @@ export const fetchUserACLRequest = (tenant) => ({
tenant: tenant,
})
-export const userLoggedIn = (user) => (dispatch) => {
+export const userLoggedIn = (user, redirect) => (dispatch) => {
dispatch({
type: USER_LOGGED_IN,
user: user,
token: getToken(user),
+ redirect: redirect,
})
}
diff --git a/web/src/pages/AuthCallback.jsx b/web/src/pages/AuthCallback.jsx
index c31f1d222..c8f765be2 100644
--- a/web/src/pages/AuthCallback.jsx
+++ b/web/src/pages/AuthCallback.jsx
@@ -13,29 +13,55 @@
// under the License.
import React, { useEffect } from 'react'
+import PropTypes from 'prop-types'
+import { connect } from 'react-redux'
import { useHistory } from 'react-router-dom'
-
-import { Fetching } from '../containers/Fetching'
+import {
+ EmptyState,
+ EmptyStateBody,
+ EmptyStateIcon,
+ Spinner,
+ Title,
+} from '@patternfly/react-core'
+import {
+ FingerprintIcon,
+} from '@patternfly/react-icons'
// Several pages use the location hash in a way that would be
// difficult to disentangle from the OIDC callback parameters. This
// dedicated callback page accepts the OIDC params and then internally
// redirects to the page we saved before redirecting to the IDP.
-function AuthCallbackPage() {
- let history = useHistory()
+function AuthCallbackPage(props) {
+ const history = useHistory()
+ const { user } = props
useEffect(() => {
- const redirect = localStorage.getItem('zuul_auth_redirect')
- history.push(redirect)
- }, [history])
+ if (user.redirect) {
+ history.push(user.redirect)
+ }
+ }, [history, user])
return (
<>
- <div>Login successful. You will be redirected shortly...</div>
- <Fetching />
+ <EmptyState>
+ <EmptyStateIcon icon={FingerprintIcon} />
+ <Title headingLevel="h1">Login in progress</Title>
+ <EmptyStateBody>
+ <p>
+ You will be redirected shortly...
+ </p>
+ <Spinner size="xl" />
+ </EmptyStateBody>
+ </EmptyState>
</>
)
}
-export default AuthCallbackPage
+AuthCallbackPage.propTypes = {
+ user: PropTypes.object,
+}
+
+export default connect((state) => ({
+ user: state.user,
+}))(AuthCallbackPage)
diff --git a/web/src/reducers/user.js b/web/src/reducers/user.js
index 1a36fdae1..215cbfb1a 100644
--- a/web/src/reducers/user.js
+++ b/web/src/reducers/user.js
@@ -29,6 +29,7 @@ export default (state = {
scope: [],
isAdmin: false,
tenant: null,
+ redirect: null,
}, action) => {
switch (action.type) {
case USER_LOGGED_IN: {
@@ -36,6 +37,7 @@ export default (state = {
isFetching: false,
data: action.user,
token: action.token,
+ redirect: action.redirect,
scope: [],
isAdmin: false
}
@@ -45,6 +47,7 @@ export default (state = {
isFetching: false,
data: null,
token: null,
+ redirect: null,
scope: [],
isAdmin: false
}
diff --git a/web/src/routes.js b/web/src/routes.js
index a60216a97..886b1a645 100644
--- a/web/src/routes.js
+++ b/web/src/routes.js
@@ -34,7 +34,6 @@ import ConfigErrorsPage from './pages/ConfigErrors'
import TenantsPage from './pages/Tenants'
import StreamPage from './pages/Stream'
import OpenApiPage from './pages/OpenApi'
-import AuthCallbackPage from './pages/AuthCallback'
// The Route object are created in the App component.
// Object with a title are created in the menu.
@@ -162,11 +161,7 @@ const routes = () => [
component: ComponentsPage,
noTenantPrefix: true,
},
- {
- to: '/auth_callback',
- component: AuthCallbackPage,
- noTenantPrefix: true,
- },
+ // auth_callback is handled in App.jsx
]
export { routes }