Add flag to global config to enable/disable api keys as additional authentication method (#1606)

Add flag to global config to enable/disable API keys as additional authentication method.

Fixes #1599
This commit is contained in:
Eduard Heimbuch
2021-03-25 12:06:22 +01:00
committed by GitHub
parent 96d2e2cc1b
commit 73c1609d92
15 changed files with 126 additions and 18 deletions

View File

@@ -57,6 +57,7 @@ public class ConfigDto extends HalRepresentation implements UpdateConfigDto {
private long loginAttemptLimitTimeout;
private boolean enabledXsrfProtection;
private boolean enabledUserConverter;
private boolean enabledApiKeys;
private String namespaceStrategy;
private String loginInfoUrl;
private String releaseFeedUrl;

View File

@@ -28,10 +28,10 @@ import com.google.common.base.Strings;
import de.otto.edison.hal.Embedded;
import de.otto.edison.hal.Links;
import org.apache.shiro.SecurityUtils;
import sonia.scm.config.ScmConfiguration;
import sonia.scm.group.GroupCollector;
import sonia.scm.user.EMail;
import sonia.scm.user.User;
import sonia.scm.user.UserManager;
import sonia.scm.user.UserPermissions;
import sonia.scm.web.EdisonHalAppender;
@@ -44,15 +44,15 @@ import static de.otto.edison.hal.Links.linkingTo;
public class MeDtoFactory extends HalAppenderMapper {
private final ResourceLinks resourceLinks;
private final UserManager userManager;
private final GroupCollector groupCollector;
private final ScmConfiguration scmConfiguration;
private final EMail eMail;
@Inject
public MeDtoFactory(ResourceLinks resourceLinks, UserManager userManager, GroupCollector groupCollector, EMail eMail) {
public MeDtoFactory(ResourceLinks resourceLinks, GroupCollector groupCollector, ScmConfiguration scmConfiguration, EMail eMail) {
this.resourceLinks = resourceLinks;
this.userManager = userManager;
this.groupCollector = groupCollector;
this.scmConfiguration = scmConfiguration;
this.eMail = eMail;
}
@@ -96,7 +96,7 @@ public class MeDtoFactory extends HalAppenderMapper {
if (!user.isExternal() && UserPermissions.changePassword(user).isPermitted()) {
linksBuilder.single(link("password", resourceLinks.me().passwordChange()));
}
if (UserPermissions.changeApiKeys(user).isPermitted()) {
if (scmConfiguration.isEnabledApiKeys() && UserPermissions.changeApiKeys(user).isPermitted()) {
linksBuilder.single(link("apiKeys", resourceLinks.apiKeyCollection().self(user.getName())));
}

View File

@@ -33,6 +33,7 @@ import org.apache.shiro.authz.AuthorizationException;
import org.apache.shiro.realm.AuthenticatingRealm;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
import sonia.scm.config.ScmConfiguration;
import sonia.scm.plugin.Extension;
import sonia.scm.repository.RepositoryRole;
import sonia.scm.repository.RepositoryRoleManager;
@@ -53,12 +54,14 @@ public class ApiKeyRealm extends AuthenticatingRealm {
private final ApiKeyService apiKeyService;
private final DAORealmHelper helper;
private final RepositoryRoleManager repositoryRoleManager;
private final ScmConfiguration scmConfiguration;
@Inject
public ApiKeyRealm(ApiKeyService apiKeyService, DAORealmHelperFactory helperFactory, RepositoryRoleManager repositoryRoleManager) {
public ApiKeyRealm(ApiKeyService apiKeyService, DAORealmHelperFactory helperFactory, RepositoryRoleManager repositoryRoleManager, ScmConfiguration scmConfiguration) {
this.apiKeyService = apiKeyService;
this.helper = helperFactory.create(NAME);
this.repositoryRoleManager = repositoryRoleManager;
this.scmConfiguration = scmConfiguration;
setAuthenticationTokenClass(BearerToken.class);
setCredentialsMatcher(new AllowAllCredentialsMatcher());
}
@@ -66,7 +69,7 @@ public class ApiKeyRealm extends AuthenticatingRealm {
@Override
@SuppressWarnings("java:S4738") // java.util.Base64 has no canDecode method
public boolean supports(AuthenticationToken token) {
if (token instanceof UsernamePasswordToken || token instanceof BearerToken) {
if (scmConfiguration.isEnabledApiKeys() && (token instanceof UsernamePasswordToken || token instanceof BearerToken)) {
boolean isBase64 = BaseEncoding.base64().canDecode(getPassword(token));
if (!isBase64) {
LOG.debug("Ignoring non base 64 token; this is probably a JWT token or a normal password");