added option to send skip sending nonce if desired, closes #704, closes #683,

pull/743/merge
Justin Richer 2014-12-18 23:22:59 -05:00
parent 9aa45f8efb
commit bbeaeb06e3
5 changed files with 77 additions and 20 deletions

View File

@ -242,7 +242,10 @@ public class OIDCAuthenticationFilter extends AbstractAuthenticationProcessingFi
session.setAttribute(REDIRECT_URI_SESION_VARIABLE, redirectUri); session.setAttribute(REDIRECT_URI_SESION_VARIABLE, redirectUri);
// this value comes back in the id token and is checked there // this value comes back in the id token and is checked there
String nonce = createNonce(session); String nonce = null;
if (serverConfig.isNonceEnabled()) {
nonce = createNonce(session);
}
// this value comes back in the auth code response // this value comes back in the auth code response
String state = createState(session); String state = createState(session);
@ -543,21 +546,30 @@ public class OIDCAuthenticationFilter extends AbstractAuthenticationProcessingFi
// compare the nonce to our stored claim // compare the nonce to our stored claim
String nonce = idClaims.getStringClaim("nonce"); String nonce = idClaims.getStringClaim("nonce");
if (Strings.isNullOrEmpty(nonce)) {
if (serverConfig.isNonceEnabled()) {
logger.error("ID token did not contain a nonce claim."); if (Strings.isNullOrEmpty(nonce)) {
throw new AuthenticationServiceException("ID token did not contain a nonce claim."); logger.error("ID token did not contain a nonce claim.");
}
throw new AuthenticationServiceException("ID token did not contain a nonce claim.");
String storedNonce = getStoredNonce(session); }
if (!nonce.equals(storedNonce)) {
logger.error("Possible replay attack detected! The comparison of the nonce in the returned " String storedNonce = getStoredNonce(session);
+ "ID Token to the session " + NONCE_SESSION_VARIABLE + " failed. Expected " + storedNonce + " got " + nonce + "."); if (!nonce.equals(storedNonce)) {
logger.error("Possible replay attack detected! The comparison of the nonce in the returned "
throw new AuthenticationServiceException( + "ID Token to the session " + NONCE_SESSION_VARIABLE + " failed. Expected " + storedNonce + " got " + nonce + ".");
"Possible replay attack detected! The comparison of the nonce in the returned "
+ "ID Token to the session " + NONCE_SESSION_VARIABLE + " failed. Expected " + storedNonce + " got " + nonce + "."); throw new AuthenticationServiceException(
"Possible replay attack detected! The comparison of the nonce in the returned "
+ "ID Token to the session " + NONCE_SESSION_VARIABLE + " failed. Expected " + storedNonce + " got " + nonce + ".");
}
} else {
if (!Strings.isNullOrEmpty(nonce)) {
logger.error("Possible injection attack! The server returned a nonce value where none was sent or expected: " + nonce);
throw new AuthenticationServiceException(
"Possible injection attack! The server returned a nonce value where none was sent or expected: " + nonce);
}
} }
// pull the subject (user id) out as a claim on the id_token // pull the subject (user id) out as a claim on the id_token

View File

@ -68,7 +68,9 @@ public class EncryptedAuthRequestUrlBuilder implements AuthRequestUrlBuilder {
claims.setClaim("redirect_uri", redirectUri); claims.setClaim("redirect_uri", redirectUri);
// this comes back in the id token // this comes back in the id token
claims.setClaim("nonce", nonce); if (nonce != null) {
claims.setClaim("nonce", nonce);
}
// this comes back in the auth request return // this comes back in the auth request return
claims.setClaim("state", state); claims.setClaim("state", state);

View File

@ -54,7 +54,9 @@ public class PlainAuthRequestUrlBuilder implements AuthRequestUrlBuilder {
uriBuilder.addParameter("redirect_uri", redirectUri); uriBuilder.addParameter("redirect_uri", redirectUri);
uriBuilder.addParameter("nonce", nonce); if (nonce != null) {
uriBuilder.addParameter("nonce", nonce);
}
uriBuilder.addParameter("state", state); uriBuilder.addParameter("state", state);

View File

@ -61,7 +61,9 @@ public class SignedAuthRequestUrlBuilder implements AuthRequestUrlBuilder {
claims.setClaim("redirect_uri", redirectUri); claims.setClaim("redirect_uri", redirectUri);
// this comes back in the id token // this comes back in the id token
claims.setClaim("nonce", nonce); if (nonce != null) {
claims.setClaim("nonce", nonce);
}
// this comes back in the auth request return // this comes back in the auth request return
claims.setClaim("state", state); claims.setClaim("state", state);

View File

@ -205,6 +205,12 @@ public class ServerConfiguration {
private Boolean requireRequestUriRegistration; private Boolean requireRequestUriRegistration;
private String opPolicyUri; private String opPolicyUri;
private String opTosUri; private String opTosUri;
//
// extensions to the discoverable methods
//
// how do we send the access token to the userinfo endpoint?
private UserInfoTokenMethod userInfoTokenMethod; private UserInfoTokenMethod userInfoTokenMethod;
public enum UserInfoTokenMethod { public enum UserInfoTokenMethod {
@ -213,6 +219,9 @@ public class ServerConfiguration {
QUERY; QUERY;
} }
// do we create and send a nonce value?
private boolean nonceEnabled = true;
/** /**
* @return the authorizationEndpointUri * @return the authorizationEndpointUri
*/ */
@ -671,6 +680,23 @@ public class ServerConfiguration {
public void setUserInfoTokenMethod(UserInfoTokenMethod userInfoTokenMethod) { public void setUserInfoTokenMethod(UserInfoTokenMethod userInfoTokenMethod) {
this.userInfoTokenMethod = userInfoTokenMethod; this.userInfoTokenMethod = userInfoTokenMethod;
} }
/**
* @return the nonceEnabled
*/
public boolean isNonceEnabled() {
return nonceEnabled;
}
/**
* @param nonceEnabled the nonceEnabled to set
*/
public void setNonceEnabled(boolean nonceEnabled) {
this.nonceEnabled = nonceEnabled;
}
/* (non-Javadoc)
* @see java.lang.Object#hashCode()
*/
@Override @Override
public int hashCode() { public int hashCode() {
final int prime = 31; final int prime = 31;
@ -731,6 +757,7 @@ public class ServerConfiguration {
: introspectionEndpointUri.hashCode()); : introspectionEndpointUri.hashCode());
result = prime * result + ((issuer == null) ? 0 : issuer.hashCode()); result = prime * result + ((issuer == null) ? 0 : issuer.hashCode());
result = prime * result + ((jwksUri == null) ? 0 : jwksUri.hashCode()); result = prime * result + ((jwksUri == null) ? 0 : jwksUri.hashCode());
result = prime * result + (nonceEnabled ? 1231 : 1237);
result = prime * result result = prime * result
+ ((opPolicyUri == null) ? 0 : opPolicyUri.hashCode()); + ((opPolicyUri == null) ? 0 : opPolicyUri.hashCode());
result = prime * result result = prime * result
@ -796,6 +823,10 @@ public class ServerConfiguration {
* result * result
+ ((uiLocalesSupported == null) ? 0 : uiLocalesSupported + ((uiLocalesSupported == null) ? 0 : uiLocalesSupported
.hashCode()); .hashCode());
result = prime
* result
+ ((userInfoTokenMethod == null) ? 0 : userInfoTokenMethod
.hashCode());
result = prime * result result = prime * result
+ ((userInfoUri == null) ? 0 : userInfoUri.hashCode()); + ((userInfoUri == null) ? 0 : userInfoUri.hashCode());
result = prime result = prime
@ -812,6 +843,9 @@ public class ServerConfiguration {
: userinfoSigningAlgValuesSupported.hashCode()); : userinfoSigningAlgValuesSupported.hashCode());
return result; return result;
} }
/* (non-Javadoc)
* @see java.lang.Object#equals(java.lang.Object)
*/
@Override @Override
public boolean equals(Object obj) { public boolean equals(Object obj) {
if (this == obj) { if (this == obj) {
@ -942,6 +976,9 @@ public class ServerConfiguration {
} else if (!jwksUri.equals(other.jwksUri)) { } else if (!jwksUri.equals(other.jwksUri)) {
return false; return false;
} }
if (nonceEnabled != other.nonceEnabled) {
return false;
}
if (opPolicyUri == null) { if (opPolicyUri == null) {
if (other.opPolicyUri != null) { if (other.opPolicyUri != null) {
return false; return false;
@ -1077,6 +1114,9 @@ public class ServerConfiguration {
} else if (!uiLocalesSupported.equals(other.uiLocalesSupported)) { } else if (!uiLocalesSupported.equals(other.uiLocalesSupported)) {
return false; return false;
} }
if (userInfoTokenMethod != other.userInfoTokenMethod) {
return false;
}
if (userInfoUri == null) { if (userInfoUri == null) {
if (other.userInfoUri != null) { if (other.userInfoUri != null) {
return false; return false;
@ -1111,5 +1151,4 @@ public class ServerConfiguration {
return true; return true;
} }
} }