zoukankan      html  css  js  c++  java
  • 使用fastjson时spring security oauth2获取token格式变化

    1.问题

    使用下面请求获取token时

    http://localhost:8080/oauth/token?grant_type=client_credentials&scope=select&client_id=client_1&client_secret=123456

    预期返回值

    {
        "access_token": "b0f73d20-1c74-43f6-991d-3b4ca74fc4d4",
        "token_type": "bearer",
        "expires_in": 41374,
        "scope": "select"
    }

    但是返回值为

    {
    "expiration": 1513752144897,
    "expired": false,
    "expiresIn": 604799,
    "refreshToken": {
    "expiration": 1515739344897,
    "value": "dae50004-939c-40f2-98d8-4882374e08c7"
    },
    "scope": [
    "api"
    ],
    "tokenType": "bearer",
    "value": "1e2c4181-01be-4aa1-8042-c2d2f74008d0"
    }

    2.原因

    使用fastjson而不是默认的Jackson

    3.解决方法

    新写OAuth2AccessTokenMessageConverter类

    public class OAuth2AccessTokenMessageConverter extends AbstractHttpMessageConverter<OAuth2AccessToken> {
    
        private final FastJsonHttpMessageConverter delegateMessageConverter;
    
        public OAuth2AccessTokenMessageConverter() {
            super(MediaType.APPLICATION_JSON);
            this.delegateMessageConverter = new FastJsonHttpMessageConverter();
        }
    
        @Override
        protected boolean supports(Class<?> clazz) {
            return OAuth2AccessToken.class.isAssignableFrom(clazz);
        }
    
        @Override
        protected OAuth2AccessToken readInternal(Class<? extends OAuth2AccessToken> clazz, HttpInputMessage inputMessage)
                throws IOException, HttpMessageNotReadableException {
            throw new UnsupportedOperationException(
                    "This converter is only used for converting from externally aqcuired form data");
        }
    
        @Override
        protected void writeInternal(OAuth2AccessToken accessToken, HttpOutputMessage outputMessage) throws IOException,
                HttpMessageNotWritableException {
            Map<String, Object> data = new HashMap<>(8);
            data.put(OAuth2AccessToken.ACCESS_TOKEN, accessToken.getValue());
            data.put(OAuth2AccessToken.TOKEN_TYPE, accessToken.getTokenType());
            data.put(OAuth2AccessToken.EXPIRES_IN, accessToken.getExpiresIn());
            data.put(OAuth2AccessToken.SCOPE, String.join(" ", accessToken.getScope()));
            OAuth2RefreshToken refreshToken = accessToken.getRefreshToken();
            if (Objects.nonNull(refreshToken)) {
                data.put(OAuth2AccessToken.REFRESH_TOKEN, refreshToken.getValue());
            }
            delegateMessageConverter.write(data, MediaType.APPLICATION_JSON, outputMessage);
        }
    
    }

    加入MessageConverters

    @Configuration
    public class Oauth2WebMvcConfigurer implements WebMvcConfigurer {
    
        @Override
        public void configureMessageConverters(List<HttpMessageConverter<?>> converters) {
           converters.add(0, new FastJsonHttpMessageConverter());
           converters.add(0, new OAuth2AccessTokenMessageConverter());
        }
    }

    4.参考文档

    参考FelixFly回答 https://github.com/alibaba/fastjson/issues/1640

    https://blog.csdn.net/yuelangyc/article/details/88235639

  • 相关阅读:
    you-get 下载网络上的富媒体信息
    响应式布局
    网页头部的声明应该是用 lang="";
    htm、html、shtml网页区别
    请求头出现Provisional headers are shown
    配置nginx直接使用webpack生成的gz压缩文件,而不用nginx自己压缩
    babel-plugin-equire
    VUE中$refs的基本用法
    element-ui--按需引入
    vue ts ,vue使用typescript,三种组件传值方式
  • 原文地址:https://www.cnblogs.com/SmilingEye/p/13391651.html
Copyright © 2011-2022 走看看