Springboot通过Controller从Authentication获取用户名 [英] Springboot get username from Authentication via Controller

查看:167
本文介绍了Springboot通过Controller从Authentication获取用户名的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

问题:我想仅从 authenticate.getName()... 获取/提取用户名/电子邮件,如果可能,而不是使用解析字符串.

Problem: I would like to get/extract the username/email only from authenticate.getName()... if possible, not by using parsing the string.

authentication.getName() 或 principal.getName() 值:

[username]: org.springframework.security.core.userdetails.User@21463e7a: Username: butitoy@iyotbihagay.com; Password: [PROTECTED]; Enabled: true; AccountNonExpired: true; credentialsNonExpired: true; AccountNonLocked: true; Not granted any authorities

在本例中,我只想获取用户名的值,即 butitoy@iyotbihagay.com

解决方案:

由于我只想获取用户名/电子邮件 (butitoy@iyotbihagay.com),并且它返回整个主要内容/文本(上图),因此我将我在主题中设置的值替换为主要值... 到电子邮件值.. 它现在可以工作了.

Since I only want to get the username/email (butitoy@iyotbihagay.com), and it is returning the whole principal content/text (above), I replaced the value I set in the subject from the pricipal value... to the email value.. and it works now.

@Override
protected void successfulAuthentication(HttpServletRequest req,
                                        HttpServletResponse res,
                                        FilterChain chain,
                                        Authentication auth) throws IOException, ServletException {
    String email = auth.getName();
    String principal = auth.getPrincipal().toString();
    Date expiration = new Date(System.currentTimeMillis() + SecurityConstants.EXPIRATION_TIME);
    String token = Jwts.builder()
            .setSubject(email) //from principal to email
            .setExpiration(expiration)
            .signWith(SignatureAlgorithm.HS512, SecurityConstants.SECRET.getBytes())
            .compact();
    AuthenticatedUser loginUser = new AuthenticatedUser(email);
    loginUser.setToken(token);
    String jsonUser = Util.objectToJsonResponseAsString(loginUser, "user");
    res.addHeader(SecurityConstants.HEADER_STRING, SecurityConstants.TOKEN_PREFIX + token);
    res.setContentType("application/json");
    res.setCharacterEncoding(ConstantUtil.DEFAULT_ENCODING);
    res.getWriter().write(jsonUser);
}

我现在可以使用不同的方式获取用户名/电子邮件值,例如你们建议的方式……甚至是我目前使用的方式.我现在不需要任何特殊的解析来从 Authentication 对象中获取电子邮件值.

I can now get the username/email value using different ways like the one you guys are suggesting... even the one I am currently using. I do not need any special parsing now just to get the email value from the Authentication object.

在我之前使用 Spring 的非 RESTful 应用程序中...我可以使用控制器方法参数中注入的 Authentication 类轻松获取用户名.

On my previous non RESTful application using Spring... I can easily get the username using Authentication class injected in the controller method parameter.

控制器:

...  
public Ticket getBySwertresNo(Authentication authentication, @PathVariable String swertresNo) {  
    logger.debug("Inside getBySwertresNo: " + swertresNo);  
    System.out.println("
[username]: " + authentication.getName() + "
");  
    return m_sugalService.getSwertresInfoBySwertresNo(swertresNo);  
}  
...  

控制台:

[username]: butitoy@iyotbihagay.com

现在,在我当前的项目中……我使用了 RESTful 方法,在成功验证后,我返回了一个令牌,该令牌将在请求标头中使用/注入.我可以使用令牌登录...但是当我获得 authentication.getName() 的值时...返回的不仅仅是电子邮件地址,它还包含一些其他信息.

Now, on my current project... I used a RESTful approach and after successful authentication, I am returning a token which will be used/injected in the request header. I can login using the token... but when I get the value of authentication.getName()... the return is not just the email address but it contains some other information.

控制台(REST + JWT):

[username]: org.springframework.security.core.userdetails.User@21463e7a: Username: butitoy@iyotbihagay.com; Password: [PROTECTED]; Enabled: true; AccountNonExpired: true; credentialsNonExpired: true; AccountNonLocked: true; Not granted any authorities

我只想获取用户名值butitoy@iyotbihagay.com".

I would like to get only the username value which is "butitoy@iyotbihagay.com".

JWT 身份验证过滤器:

public class JWTAuthenticationFilter extends UsernamePasswordAuthenticationFilter {

    private AuthenticationManager authenticationManager;

    public JWTAuthenticationFilter(AuthenticationManager authenticationManager) {
        this.authenticationManager = authenticationManager;
    }

    @Override
    public Authentication attemptAuthentication(HttpServletRequest req,
                                                HttpServletResponse res) throws AuthenticationException {
        String username = req.getParameter("username");
        String password = req.getParameter("password");
        UsernamePasswordAuthenticationToken authenticationToken = new UsernamePasswordAuthenticationToken(username, password);
        Authentication authentication = authenticationManager.authenticate(authenticationToken);
        return authentication;
    }

    @Override
    protected void successfulAuthentication(HttpServletRequest req,
                                            HttpServletResponse res,
                                            FilterChain chain,
                                            Authentication auth) throws IOException, ServletException {
        String email = auth.getName();
        String principal = auth.getPrincipal().toString();
        Date expiration = new Date(System.currentTimeMillis() + SecurityConstants.EXPIRATION_TIME);
        String token = Jwts.builder()
                .setSubject(principal)
                .setExpiration(expiration)
                .signWith(SignatureAlgorithm.HS512, SecurityConstants.SECRET.getBytes())
                .compact();
        AuthenticatedUser loginUser = new AuthenticatedUser(email);
        loginUser.setToken(token);
        String jsonUser = Util.objectToJsonResponseAsString(loginUser, "user");
        res.addHeader(SecurityConstants.HEADER_STRING, SecurityConstants.TOKEN_PREFIX + token);
        res.setContentType("application/json");
        res.setCharacterEncoding(ConstantUtil.DEFAULT_ENCODING);
        res.getWriter().write(jsonUser);
    }

}

JWT 授权过滤器:

public class JWTAuthorizationFilter extends BasicAuthenticationFilter {

    public JWTAuthorizationFilter(AuthenticationManager authManager) {
        super(authManager);
    }

    @Override
    protected void doFilterInternal(HttpServletRequest req,
                                    HttpServletResponse res,
                                    FilterChain chain) throws IOException, ServletException {
        String header = req.getHeader(SecurityConstants.HEADER_STRING);

        if (header == null || !header.startsWith(SecurityConstants.TOKEN_PREFIX)) {
            chain.doFilter(req, res);
            return;
        }

        UsernamePasswordAuthenticationToken authentication = getAuthentication(req);

SecurityContextHolder.getContext().setAuthentication(authentication);
        chain.doFilter(req, res);
    }

    private UsernamePasswordAuthenticationToken getAuthentication(HttpServletRequest request) {
        String token = request.getHeader(SecurityConstants.HEADER_STRING);
        if (token != null) {
            // parse the token.
            String user = Jwts.parser()
                    .setSigningKey(SecurityConstants.SECRET.getBytes())
                    .parseClaimsJws(token.replace(SecurityConstants.TOKEN_PREFIX, ""))
                    .getBody()
                    .getSubject();

            if (user != null) {
                return new UsernamePasswordAuthenticationToken(user, null, new ArrayList<>());
            }
            return null;
        }
        return null;
    }

}

推荐答案

我认为你可以在类型的注入控制器参数中使用 authentication.getNameprincipal.getName身份验证Principal:

I think you can use authentication.getName and principal.getName in the injected controller argument of type Authentication and Principal:

@Controller
@RequestMapping("/info")
public class GetNameController {

    @RequestMapping(value = "/name", method = RequestMethod.GET)
    public String getName(Authentication authentication, Principal principal) {
        System.out.println(authentication.getName());
        System.out.println("-----------------");
        System.out.println(principal.getName());
        return "";
    }
}

可以生产

admin
-----------------
admin

这篇关于Springboot通过Controller从Authentication获取用户名的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆