From d2ab0cda62799face3caa1973a57849d2f337f00 Mon Sep 17 00:00:00 2001 From: Mike Gouline Date: Tue, 18 Dec 2012 11:20:53 +1100 Subject: [PATCH] Implements OpenID domain filtering Adds ability to only allow email addresses under specific domains to be used for OpenID login. The allowed domains can be configured in etc/gerrit.config under section [auth] as "openIdDomain". The values are then stored across GerritConfig and AuthConfig. If at least one openIdDomain is configured, OpenIdServiceImpl checks for a match on the email address used for login and returns error otherwise. The need for this was described in Google Groups to limit OpenID to Google Apps domain(s) of a company when using Gerrit for internal development. Change-Id: I549059e7ecea827009b632ef2e38d2ccdddf7cfb --- Documentation/config-gerrit.txt | 10 +++++++ .../httpd/auth/openid/OpenIdServiceImpl.java | 28 +++++++++++++++++++ .../gerrit/server/config/AuthConfig.java | 7 +++++ 3 files changed, 45 insertions(+) diff --git a/Documentation/config-gerrit.txt b/Documentation/config-gerrit.txt index 0a5628acbc..1cad4108fc 100644 --- a/Documentation/config-gerrit.txt +++ b/Documentation/config-gerrit.txt @@ -193,6 +193,16 @@ end with `$`) or be a simple prefix (any other string). By default, the list contains two values, `http://` and `https://`, allowing Gerrit to trust any OpenID it receives. +[[auth.openIdDomain]]auth.openIdDomain:: ++ +List of allowed OpenID email address domains. Only used if +`auth.type` is set to "OPENID" or "OPENID_SSO". ++ +Domain is case insensitive and must be in the same form as it +appears in the email address, for example, "example.com". ++ +By default, any domain is accepted. + [[auth.maxOpenIdSessionAge]]auth.maxOpenIdSessionAge:: + Time in seconds before an OpenID provider must force the user diff --git a/gerrit-openid/src/main/java/com/google/gerrit/httpd/auth/openid/OpenIdServiceImpl.java b/gerrit-openid/src/main/java/com/google/gerrit/httpd/auth/openid/OpenIdServiceImpl.java index 0593bce94f..2946436fcc 100644 --- a/gerrit-openid/src/main/java/com/google/gerrit/httpd/auth/openid/OpenIdServiceImpl.java +++ b/gerrit-openid/src/main/java/com/google/gerrit/httpd/auth/openid/OpenIdServiceImpl.java @@ -101,6 +101,7 @@ class OpenIdServiceImpl implements OpenIdService { private final AccountManager accountManager; private final ConsumerManager manager; private final List allowedOpenIDs; + private final List openIdDomains; /** Maximum age, in seconds, before forcing re-authentication of account. */ private final int papeMaxAuthAge; @@ -142,6 +143,7 @@ class OpenIdServiceImpl implements OpenIdService { accountManager = am; manager = new ConsumerManager(); allowedOpenIDs = ac.getAllowedOpenIDs(); + openIdDomains = ac.getOpenIdDomains(); papeMaxAuthAge = (int) ConfigUtil.getTimeUnit(config, // "auth", null, "maxOpenIdSessionAge", -1, TimeUnit.SECONDS); } @@ -355,6 +357,32 @@ class OpenIdServiceImpl implements OpenIdService { areq.setEmailAddress(fetchRsp.getAttributeValue("Email")); } + if (openIdDomains != null && openIdDomains.size() > 0) { + // Administrator limited email domains, which can be used for OpenID. + // Login process will only work if the passed email matches one + // of these domains. + // + final String email = areq.getEmailAddress(); + int emailAtIndex = email.lastIndexOf("@"); + if (emailAtIndex >= 0 && emailAtIndex < email.length() - 1) { + final String emailDomain = email.substring(emailAtIndex); + + boolean match = false; + for (String domain : openIdDomains) { + if (emailDomain.equalsIgnoreCase(domain)) { + match = true; + break; + } + } + + if (!match) { + log.error("Domain disallowed: " + emailDomain); + cancelWithError(req, rsp, "Domain disallowed"); + return; + } + } + } + if (claimedIdentifier != null) { // The user used a claimed identity which has delegated to the verified // identity we have in our AuthRequest above. We still should have a diff --git a/gerrit-server/src/main/java/com/google/gerrit/server/config/AuthConfig.java b/gerrit-server/src/main/java/com/google/gerrit/server/config/AuthConfig.java index 9916257ad7..a56d64e725 100644 --- a/gerrit-server/src/main/java/com/google/gerrit/server/config/AuthConfig.java +++ b/gerrit-server/src/main/java/com/google/gerrit/server/config/AuthConfig.java @@ -25,6 +25,7 @@ import com.google.inject.Singleton; import org.eclipse.jgit.lib.Config; import java.util.ArrayList; +import java.util.Arrays; import java.util.Collection; import java.util.Collections; import java.util.List; @@ -40,6 +41,7 @@ public class AuthConfig { private final boolean gitBasicAuth; private final String logoutUrl; private final String openIdSsoUrl; + private final List openIdDomains; private final List trustedOpenIDs; private final List allowedOpenIDs; private final String cookiePath; @@ -56,6 +58,7 @@ public class AuthConfig { httpHeader = cfg.getString("auth", null, "httpheader"); logoutUrl = cfg.getString("auth", null, "logouturl"); openIdSsoUrl = cfg.getString("auth", null, "openidssourl"); + openIdDomains = Arrays.asList(cfg.getStringList("auth", null, "openIdDomain")); trustedOpenIDs = toPatterns(cfg, "trustedOpenID"); allowedOpenIDs = toPatterns(cfg, "allowedOpenID"); cookiePath = cfg.getString("auth", null, "cookiepath"); @@ -127,6 +130,10 @@ public class AuthConfig { return openIdSsoUrl; } + public List getOpenIdDomains() { + return openIdDomains; + } + public String getCookiePath() { return cookiePath; }