【问题标题】:Return OAuth Token information on user creation endpoint返回有关用户创建端点的 OAuth 令牌信息
【发布时间】:2020-04-07 21:51:52
【问题描述】:

我目前正在使用 Spring Boot 实现 REST Api,并通过 OAuth2 进行保护。这是我目前的情况:

  1. 用户注册端点、成功响应示例和控制器方法实现

POST http://<host>/users/register

{
  "id": "6061b5c0-a817-4fff-ba1f-c7f4e94080ed",
  "name": "Name",
  "email": "user@email.com",
  "password": "$2a$12$R7yw/HbLmFzMpkzsWOqLp.I.itHRo7B/9MXKNrpArvK/Lfta0Z.I.",
  "createdAt": "2019-12-14T22:00:46.682+0000"
  ...
}
@PostMapping(value = "/register")
public ResponseEntity<User> register(@RequestBody final User user) {
    final User createdUser = mUsersService.create(user);
    return new ResponseEntity<>(createdUser, HttpStatus.CREATED);
}
  1. 令牌端点和示例响应

POST http://&lt;host&gt;/oauth/token

{
  "access_token": "03bd76f0-20bd-45ef-9adb-b0903345e590",
  "token_type": "bearer",
  "refresh_token": "a1022bbd-407a-4899-b1b0-20a889ed0419",
  "expires_in": 82373,
  "scope": "read write"
}

如何在 /users/register 端点上返回令牌 JSON(由 /oauth/token 端点返回)。

【问题讨论】:

    标签: spring-boot spring-security spring-security-oauth2


    【解决方案1】:

    使用下面的方法,

    private OAuth2AccessToken getToken(LoginResource loginResource) {
        String access_token_url = "http://localhost:8080/api/oauth/token";
        ResourceOwnerPasswordResourceDetails resourceDetails = new ResourceOwnerPasswordResourceDetails();
        resourceDetails.setGrantType("password");
        resourceDetails.setAccessTokenUri(access_token_url);
    
        //-- set the clients info
        resourceDetails.setClientId("clientId");
        resourceDetails.setClientSecret("clientSecret");
    
        // set scopes
        List<String> scopes = new ArrayList<>();
        scopes.add("read"); 
        scopes.add("write");
        scopes.add("trust");
        resourceDetails.setScope(scopes);
    
        //-- set Resource Owner info
        resourceDetails.setUsername(loginResource.getUserName());
        resourceDetails.setPassword(loginResource.getPassword());
        OAuth2RestTemplate oAuth2RestTemplate = new OAuth2RestTemplate(resourceDetails);
        return oAuth2RestTemplate.getAccessToken(); 
    }
    

    【讨论】:

      【解决方案2】:

      最后,在检查了进入/oauth/token端点的数据后,我得出了以下解决方案:

          private static final String PARAM_GRANT_TYPE = "grant_type";
          private static final String PARAM_USERNAME = "username";
          private static final String PARAM_PASSWORD = "password";
          private static final String PARAM_GRANT_TYPE_VALUE_PASSWORD = "password";
      
          @Autowired
          private UsersService mUsersService;
      
          @Autowired
          private TokenEndpoint mTokenEndpoint;
      
          @PostMapping(value = "/register")
          public ResponseEntity<OAuth2AccessToken> register(final Principal principal,
                                                            @RequestParam final String name,
                                                            @RequestParam final String email,
                                                            @RequestParam final String password) throws HttpRequestMethodNotSupportedException {
              final User user = mUsersService.create(name, email, password);
      
              final Map<String, String> tokenParameters = new HashMap<>(3);
              tokenParameters.put(PARAM_GRANT_TYPE, PARAM_GRANT_TYPE_VALUE_PASSWORD);
              tokenParameters.put(PARAM_USERNAME, email);
              tokenParameters.put(PARAM_PASSWORD, password);
      
              return mTokenEndpoint.postAccessToken(principal, tokenParameters);
          }
      

      我所做的是使用转发的 Principal(在我的例子中是客户端身份验证)和普通的 password grant_type 参数调用 POST 令牌端点。

      【讨论】:

        猜你喜欢
        • 1970-01-01
        • 2015-06-23
        • 2021-03-12
        • 1970-01-01
        • 2015-04-28
        • 2021-09-09
        • 1970-01-01
        • 2019-06-15
        • 2016-08-28
        相关资源
        最近更新 更多