当前位置: 首页 > 知识库问答 >
问题:

从JWT令牌获取Spring启动资源服务器中的主体

邵宜年
2023-03-14

我有一个单独的身份验证服务器和一个资源服务器——都是Spring Boot应用程序。我使用OAuth2和JWT令牌进行身份验证和授权。

我可以通过访问身份验证服务器获得令牌:

curl -X POST --user 'client:secret' -d 'grant_type=password&username=john&password=123' http://localhost:9000/auth-server/oauth/token

并通过将令牌附加到请求标头来从资源服务器(在不同的服务器上运行)获取资源时使用它。

但我不清楚的是,确定哪个用户登录了资源服务器。

在auth服务器中,我可以这样做:

@RequestMapping("/user")
public Principal user(Principal user) {
    return user;
}

此终结点将根据所使用的令牌获取当前用户。如果我尝试在资源服务器中做同样的事情,我只得到空的响应。

我需要在资源服务器中以某种方式获取经过身份验证的用户的id,以决定是否应该向他返回一些数据(我有一些资源,这些资源只能由其所有者访问)。

我怎么能这么做?我认为通过使用JWT,我不需要共享同一个令牌存储

如果我的问题不清楚,我可以提供代码示例...我只是想确认我的假设是正确的,这种行为是可以实现的——这是我第一次尝试Spring安全。

资源服务器链接到应用程序中的身份验证服务器。特性:

security.oauth2.resource.userInfoUri: http://localhost:9000/auth-server/user

共有3个答案

松正阳
2023-03-14

您的资源服务器不会自动神奇地从身份验证服务获取主体。他们必须受到约束。将auth令牌插入头中是正确的方法。但是,资源服务器必须“验证”身份验证令牌。验证身份验证服务器验证身份验证令牌后,将返回主体。

因此,您的资源服务器需要调用您的授权服务器上的“/user”。

这里有一个例子。http://technicalrex.com/2015/02/20/stateless-authentication-with-spring-security-and-jwt

秦跃
2023-03-14

我能建议另一种方式吗?

您需要实现自己的令牌生成,并包装到令牌用户数据中。所有你需要它把必要的用户信息放入Claims对象。然后在资源服务器上打开它。

private Map<String, Object> getClaims(UserEntity user) {
    Map<String, Object> claims = new HashMap<>();
    OffsetDateTime now = OffsetDateTime.now(clock);
    OffsetDateTime exp = now.plusMinutes(1);

    //Standard claims
    claims(Claims.ISSUED_AT, Date.from(now.toInstant()).getTime());
    claims(Claims.EXPIRATION, Date.from(exp.toInstant()).getTime());
    claims(Claims.ID, UUID.randomUUID());

    //Private claims
    claims("user.auth", getRoles(user.getRoles()));

    //Clear fields that should not be stored in the token
    claims("user.data", stripUserFields(getApiUser(user)));

    return claims;
}

private String buildJwtToken(Claims claims, String secretKey) throws ApplicationException {
    DefaultJwsHeader header = new DefaultJwsHeader();
    if (secretKey != null) {
        header.setAlgorithm(ALGORITHM);
    }
    String base64EncodedJsonHeader = Base64Util.encode(toJson("header", header), true);
    String base64EncodedJsonBody = Base64Util.encode(toJson("body", claims), true);
    String base64UrlEncodedBaseToken = base64EncodedJsonHeader + "." + base64EncodedJsonBody;
    String hexDigest = createHexDigest(base64UrlEncodedBaseToken, secretKey);
    return base64UrlEncodedBaseToken + "." + Base64Util.encode(hexDigest, true);
}

我们正在使用io.jsonwebtoken库。

夏弘文
2023-03-14

这就是我所做的,对于任何人来说都是如此(这个方法使用JWKs来验证JWTs)。

首先需要设置一个扩展WebSecurity配置适配器的配置bean。班在HttpSecurity对象中,可以使用oauth2ResourceServer。jet()方法,非常好。它将为传入请求寻找JWT,并为传入请求设置主体对象(以及其他对象)。它应该是这样的:

@Configuration
@EnableWebSecurity(debug = true) //optional - helps with debugging your security filters.
public class WebSecurityConfig extends WebSecurityConfigurerAdapter {

@Override
protected void configure(HttpSecurity http) throws Exception {
    http
            .csrf()
            .disable()
            .antMatcher("/cars/**")
            .oauth2ResourceServer().jwt(); // validates the jwt token and also sets the authentication and principal

}

在应用程序中。yml/。属性,则需要指向JWKendpoint:

spring.security.oauth2.resourceserver.jwt.jwk-set-uri: <JWK_ENDPOINT>

在控制器中,可以获取主体和身份验证。

@RequestMapping(method = RequestMethod.GET, value = "/cars/{id}")
@ResponseBody
public Car getCar(@PathVariable("id") String id, Principal principal, Authentication auth) { 

    return new Car(id, "Ford", Color.BLUE, new Owner(principal.getName().toString(), 90120)); //the principal's name is a GUID

}

或者,您可以解析JWT(因为此时,BealerTokenauthenticationFilter已经验证了JWT——在过期和其他方面)以读取声明。这只有在你有一个声称你可以放心使用的时候才有效。

 类似资料:
  • Angular这个代币怎么获得?我试图使用这段代码,但得到一个空值。请帮帮忙。

  • 我在springboot中用jwt令牌开发了一个oauth2服务器,我在注销时遇到了困难http://www.baeldung.com/spring-security-oauth-revoke-tokens 注销后,如果在头中提供令牌并点击/user,则它将提供所有用户信息,而应该抛出并错误地表示用户已注销

  • 您好,我正在JWTTokenStore中使用Spring Security Oauth2。我想在用户将令牌内容与资源请求一起发送回来后从REST服务读取令牌内容。例如:curl-i-H“授权:持有人”http://localhost:8080/api/UserDetails 读取UserDetails服务中的令牌。 非常感谢。

  • 我有一个keydeport服务器在运行。以及作为资源服务器的Spring Boot应用程序。我可以验证并获取令牌,spring boot应用程序将接受令牌。但是当我想从校长那里得到用户名时,我会得到一个UUID,而不是我的电子邮件或用户名。我还为我的KeyClope添加了一个映射器,将preferred_用户名映射到用户名。它正在工作。 JWT信息 我的spring应用程序属性:

  • 我已经实现了SpringBoot2OAuth2OAuthorization服务器。我只想使用Client_凭证来保护资源服务器,我可以从Auth Server获取访问令牌,但当我将其传递给access rest api时,资源服务器不会从授权服务器验证它,并给出无效的访问令牌错误,我正在使用postman来获取访问令牌并访问quest资源服务器。 授权服务器 授权服务器配置 授权服务器Web配置

  • 我有一个配置为设置有关用户权限的其他信息的oAuth2 jwt令牌服务器。 我不知道如何配置我的资源服务器,以提取oauth2服务器设置的用户权限,并将该权限用于Spring Security framework中的@Secured annotated Controller。 我的Auth服务器配置如下: 我的资源服务器配置如下所示: 我的测试用例失败得很惨,它说: {“error”:“inval