Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
18 changes: 7 additions & 11 deletions console2/src/components/pages/UnauthorizedPage/index.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -23,17 +23,11 @@ import * as React from 'react';
import { RedirectButton } from '../../organisms';

import './styles.css';
import { Card, CardContent, CardHeader, Divider, Image } from 'semantic-ui-react';
import { useContext, useEffect } from 'react';
import { UserSessionContext } from '../../../session';

export default () => {
const session = useContext(UserSessionContext);

useEffect(() => {
session.setUserInfo(undefined);
}, [session]);
import {Card, CardContent, CardDescription, CardHeader, Divider, Image} from 'semantic-ui-react';
import {withRouter} from "react-router";

export default withRouter((props) => {
const error = new URLSearchParams(props.location.search).get('error');
return (
<div className="flexbox-container">
<Card centered={true}>
Expand All @@ -42,6 +36,8 @@ export default () => {

<CardHeader>You are not authorized.</CardHeader>

{error && <CardDescription>Error: {error}</CardDescription>}

<Divider />

<RedirectButton primary={true} fluid={true} location={'/'}>
Expand All @@ -51,4 +47,4 @@ export default () => {
</Card>
</div>
);
};
});
1 change: 1 addition & 0 deletions server/dist/src/main/resources/concord-server.conf
Original file line number Diff line number Diff line change
Expand Up @@ -589,6 +589,7 @@ concord-server {
urlBase = "http://concord.example.com"
afterLoginUrl = "http://concord.example.com"
afterLogoutUrl = "http://concord.example.com/#/logout/done"
onErrorUrl = "http://concord.example.com/#/unauthorized"

scopes = [ "openid", "profile", "email", "groups"]

Expand Down
17 changes: 17 additions & 0 deletions server/plugins/oidc/README.md
Original file line number Diff line number Diff line change
Expand Up @@ -23,6 +23,23 @@ concord-server {
}
```

For running in development mode (i.e. on `localhost`), callback URLs must be
in the form of

```
http://localhost:8001/api/service/oidc/callback?client_name=oidc
```

Note the `client_name=oidc` query parameter, it is required by the plugin and
must be present in the provider's configuration.

The plugin uses the following scopes: `openid`, `profile`, `email`, `groups`.
Which may or may not be enabled by default in the provider's configuration.

Okta, for example, does not provide the `groups` scope by default. You can
add it in the "Security" -> "API" -> "Authorization Servers" -> your_server ->
"Scope" section.

### Interactive Login

Configure the Concord Console to use custom logout/login URLs:
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -37,30 +37,42 @@ public class OidcAuthFilter implements Filter {

public static final String URL = "/api/service/oidc/auth";

private final Config config;
private final PluginConfiguration pluginConfig;
private final Config oidcConfig;
private final OidcClient<?> client;

@Inject
public OidcAuthFilter(@Named("oidc") Config config, OidcClient<?> client) {
this.config = config;
public OidcAuthFilter(PluginConfiguration pluginConfig, @Named("oidc") Config oidcConfig, OidcClient<?> client) {
this.pluginConfig = pluginConfig;
this.oidcConfig = oidcConfig;
this.client = client;

if (pluginConfig.isEnabled() && !client.isInitialized()) {
client.init();
}
}

@Override
@SuppressWarnings("unchecked")
public void doFilter(ServletRequest request, ServletResponse response, FilterChain chain) throws IOException, ServletException {
public void doFilter(ServletRequest request, ServletResponse response, FilterChain chain) throws IOException {
HttpServletRequest req = (HttpServletRequest) request;
HttpServletResponse resp = (HttpServletResponse) response;

if (!pluginConfig.isEnabled()) {
resp.sendError(HttpServletResponse.SC_BAD_REQUEST, "OIDC disabled");
return;
}

JEEContext context = new JEEContext(req, resp);

String redirectUrl = req.getParameter("from");
context.getSessionStore().set(context, Pac4jConstants.REQUESTED_URL, redirectUrl);

RedirectionAction action = client.getRedirectionAction(context)
RedirectionAction action = client.getRedirectionActionBuilder()
.getRedirectionAction(context)
.orElseThrow(() -> new IllegalStateException("Can't get a redirection action for the request"));

config.getHttpActionAdapter().adapt(action, context);
oidcConfig.getHttpActionAdapter().adapt(action, context);
}

@Override
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -72,6 +72,16 @@ public void doFilter(ServletRequest request, ServletResponse response, FilterCha
postLoginUrl = cfg.getAfterLoginUrl();
}

String error = req.getParameter("error");
if (error != null) {
String derivedError = "unknown";
if ("access_denied".equals(error)) {
derivedError = "oidc_access_denied";
}
resp.sendRedirect(resp.encodeRedirectURL(cfg.getOnErrorUrl() + "?from=" + postLoginUrl + "&error=" + derivedError));
return;
}

try {
CallbackLogic<?, JEEContext> callback = pac4jConfig.getCallbackLogic();
callback.perform(context, pac4jConfig, pac4jConfig.getHttpActionAdapter(), postLoginUrl, true, false, true, OidcPluginModule.CLIENT_NAME);
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -58,6 +58,10 @@ public class PluginConfiguration {
@Config("oidc.afterLogoutUrl")
private String afterLogoutUrl;

@Inject
@Config("oidc.onErrorUrl")
private String onErrorUrl;

@Inject
@Nullable
@Config("oidc.scopes")
Expand Down Expand Up @@ -102,6 +106,10 @@ public String getAfterLogoutUrl() {
return afterLogoutUrl;
}

public String getOnErrorUrl() {
return onErrorUrl;
}

public List<String> getScopes() {
return scopes;
}
Expand Down
Loading