mirror of
https://github.com/scm-manager/scm-manager.git
synced 2025-11-17 18:51:10 +01:00
Disable xsrf for mercurial hook tokens
This commit is contained in:
@@ -32,6 +32,7 @@ import sonia.scm.repository.hooks.HookServer;
|
|||||||
import sonia.scm.security.AccessToken;
|
import sonia.scm.security.AccessToken;
|
||||||
import sonia.scm.security.AccessTokenBuilderFactory;
|
import sonia.scm.security.AccessTokenBuilderFactory;
|
||||||
import sonia.scm.security.CipherUtil;
|
import sonia.scm.security.CipherUtil;
|
||||||
|
import sonia.scm.security.Xsrf;
|
||||||
import sonia.scm.web.HgUtil;
|
import sonia.scm.web.HgUtil;
|
||||||
|
|
||||||
import javax.inject.Inject;
|
import javax.inject.Inject;
|
||||||
@@ -109,11 +110,18 @@ public class DefaultHgEnvironmentBuilder implements HgEnvironmentBuilder {
|
|||||||
|
|
||||||
private void write(ImmutableMap.Builder<String, String> env) {
|
private void write(ImmutableMap.Builder<String, String> env) {
|
||||||
env.put(ENV_HOOK_PORT, String.valueOf(getHookPort()));
|
env.put(ENV_HOOK_PORT, String.valueOf(getHookPort()));
|
||||||
AccessToken accessToken = accessTokenBuilderFactory.create().build();
|
env.put(ENV_BEARER_TOKEN, accessToken());
|
||||||
env.put(ENV_BEARER_TOKEN, CipherUtil.getInstance().encode(accessToken.compact()));
|
|
||||||
env.put(ENV_CHALLENGE, hookEnvironment.getChallenge());
|
env.put(ENV_CHALLENGE, hookEnvironment.getChallenge());
|
||||||
}
|
}
|
||||||
|
|
||||||
|
private String accessToken() {
|
||||||
|
AccessToken accessToken = accessTokenBuilderFactory.create()
|
||||||
|
// disable xsrf protection, because we can not access the http servlet request for verification
|
||||||
|
.custom(Xsrf.TOKEN_KEY, null)
|
||||||
|
.build();
|
||||||
|
return CipherUtil.getInstance().encode(accessToken.compact());
|
||||||
|
}
|
||||||
|
|
||||||
private synchronized int getHookPort() {
|
private synchronized int getHookPort() {
|
||||||
if (hookPort > 0) {
|
if (hookPort > 0) {
|
||||||
return hookPort;
|
return hookPort;
|
||||||
|
|||||||
@@ -38,6 +38,7 @@ import sonia.scm.repository.hooks.HookServer;
|
|||||||
import sonia.scm.security.AccessToken;
|
import sonia.scm.security.AccessToken;
|
||||||
import sonia.scm.security.AccessTokenBuilderFactory;
|
import sonia.scm.security.AccessTokenBuilderFactory;
|
||||||
import sonia.scm.security.CipherUtil;
|
import sonia.scm.security.CipherUtil;
|
||||||
|
import sonia.scm.security.Xsrf;
|
||||||
|
|
||||||
import javax.annotation.Nonnull;
|
import javax.annotation.Nonnull;
|
||||||
import java.io.File;
|
import java.io.File;
|
||||||
@@ -118,7 +119,7 @@ class DefaultHgEnvironmentBuilderTest {
|
|||||||
|
|
||||||
private void applyAccessToken(String compact) {
|
private void applyAccessToken(String compact) {
|
||||||
AccessToken accessToken = mock(AccessToken.class);
|
AccessToken accessToken = mock(AccessToken.class);
|
||||||
when(accessTokenBuilderFactory.create().build()).thenReturn(accessToken);
|
when(accessTokenBuilderFactory.create().custom(Xsrf.TOKEN_KEY, null).build()).thenReturn(accessToken);
|
||||||
when(accessToken.compact()).thenReturn(compact);
|
when(accessToken.compact()).thenReturn(compact);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|||||||
@@ -30,6 +30,7 @@ import com.google.common.collect.Maps;
|
|||||||
import io.jsonwebtoken.Claims;
|
import io.jsonwebtoken.Claims;
|
||||||
import io.jsonwebtoken.Jwts;
|
import io.jsonwebtoken.Jwts;
|
||||||
import io.jsonwebtoken.SignatureAlgorithm;
|
import io.jsonwebtoken.SignatureAlgorithm;
|
||||||
|
import io.jsonwebtoken.security.Keys;
|
||||||
import org.apache.shiro.SecurityUtils;
|
import org.apache.shiro.SecurityUtils;
|
||||||
import org.apache.shiro.authz.AuthorizationException;
|
import org.apache.shiro.authz.AuthorizationException;
|
||||||
import org.apache.shiro.subject.Subject;
|
import org.apache.shiro.subject.Subject;
|
||||||
@@ -87,8 +88,6 @@ public final class JwtAccessTokenBuilder implements AccessTokenBuilder {
|
|||||||
|
|
||||||
@Override
|
@Override
|
||||||
public JwtAccessTokenBuilder custom(String key, Object value) {
|
public JwtAccessTokenBuilder custom(String key, Object value) {
|
||||||
Preconditions.checkArgument(!Strings.isNullOrEmpty(key), "null or empty value not allowed");
|
|
||||||
Preconditions.checkArgument(value != null, "null or empty value not allowed");
|
|
||||||
this.custom.put(key, value);
|
this.custom.put(key, value);
|
||||||
return this;
|
return this;
|
||||||
}
|
}
|
||||||
@@ -183,8 +182,8 @@ public final class JwtAccessTokenBuilder implements AccessTokenBuilder {
|
|||||||
|
|
||||||
|
|
||||||
if (refreshableFor > 0) {
|
if (refreshableFor > 0) {
|
||||||
long refreshExpiration = refreshableForUnit.toMillis(refreshableFor);
|
long re = refreshableForUnit.toMillis(refreshableFor);
|
||||||
claims.put(JwtAccessToken.REFRESHABLE_UNTIL_CLAIM_KEY, new Date(now.toEpochMilli() + refreshExpiration).getTime());
|
claims.put(JwtAccessToken.REFRESHABLE_UNTIL_CLAIM_KEY, new Date(now.toEpochMilli() + re).getTime());
|
||||||
} else if (refreshExpiration != null) {
|
} else if (refreshExpiration != null) {
|
||||||
claims.put(JwtAccessToken.REFRESHABLE_UNTIL_CLAIM_KEY, Date.from(refreshExpiration));
|
claims.put(JwtAccessToken.REFRESHABLE_UNTIL_CLAIM_KEY, Date.from(refreshExpiration));
|
||||||
}
|
}
|
||||||
@@ -198,10 +197,11 @@ public final class JwtAccessTokenBuilder implements AccessTokenBuilder {
|
|||||||
claims.setIssuer(issuer);
|
claims.setIssuer(issuer);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
// sign token and create compact version
|
// sign token and create compact version
|
||||||
String compact = Jwts.builder()
|
String compact = Jwts.builder()
|
||||||
.setClaims(claims)
|
.setClaims(claims)
|
||||||
.signWith(SignatureAlgorithm.HS256, key.getBytes())
|
.signWith(Keys.hmacShaKeyFor(key.getBytes()), SignatureAlgorithm.HS256)
|
||||||
.compact();
|
.compact();
|
||||||
|
|
||||||
return new JwtAccessToken(claims, compact);
|
return new JwtAccessToken(claims, compact);
|
||||||
|
|||||||
Reference in New Issue
Block a user