美文网首页
Spring Boot 实现Jsonp

Spring Boot 实现Jsonp

作者: yellow_han | 来源:发表于2019-06-19 09:42 被阅读0次

1、SpringBoot 1.x实现方式

JsonpAdvice.java
import org.springframework.web.bind.annotation.ControllerAdvice;
import org.springframework.web.servlet.mvc.method.annotation.AbstractJsonpResponseBodyAdvice;
@ControllerAdvice(basePackages = "com.hsshy.beam.web.controller")
public class JsonpAdvice extends AbstractJsonpResponseBodyAdvice{
    public JsonpAdvice() {
 
        super("callback","jsonp");
    }
}

2、SpringBoot 2.x实现方式(2.x把AbstractJsonpResponseBodyAdvice移除了),实现方式:利用fastjson。

Jsonp.java
import com.alibaba.fastjson.JSON;
import com.alibaba.fastjson.serializer.SerializeConfig;
import com.alibaba.fastjson.serializer.SerializerFeature;
import com.alibaba.fastjson.serializer.ToStringSerializer;
import com.alibaba.fastjson.serializer.ValueFilter;
import com.alibaba.fastjson.support.config.FastJsonConfig;
import com.alibaba.fastjson.support.spring.FastJsonHttpMessageConverter;
import com.gizhi.beam.core.config.JSONPObject;
import org.apache.commons.logging.Log;
import org.apache.commons.logging.LogFactory;
import org.springframework.context.annotation.Bean;
import org.springframework.core.MethodParameter;
import org.springframework.http.MediaType;
import org.springframework.http.server.ServerHttpRequest;
import org.springframework.http.server.ServerHttpResponse;
import org.springframework.http.server.ServletServerHttpRequest;
import org.springframework.http.server.ServletServerHttpResponse;
import org.springframework.web.bind.annotation.ControllerAdvice;
import org.springframework.web.servlet.mvc.method.annotation.ResponseBodyAdvice;
import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;
import java.io.IOException;
import java.io.OutputStream;
import java.math.BigInteger;
import java.nio.charset.Charset;
import java.util.ArrayList;
import java.util.List;
import java.util.regex.Pattern;

@ControllerAdvice
public class Jsonp extends FastJsonHttpMessageConverter implements ResponseBodyAdvice {

    private static final Pattern CALLBACK_PARAM_PATTERN = Pattern.compile("[0-9A-Za-z_\\.]*");
    private final Log logger = LogFactory.getLog(this.getClass());
    public static final Charset UTF8 = Charset.forName("UTF-8");
    public static final Charset GBK = Charset.forName("GBK");
    private Charset charset;
    private SerializerFeature[] features;
    @Override
    public Object beforeBodyWrite(Object o, MethodParameter methodParameter, MediaType mediaType, Class aClass, ServerHttpRequest serverHttpRequest, ServerHttpResponse serverHttpResponse) {

        HttpServletRequest servletRequest = ((ServletServerHttpRequest) serverHttpRequest).getServletRequest();
        HttpServletResponse response = ((ServletServerHttpResponse) serverHttpResponse).getServletResponse();
        String value = servletRequest.getParameter("callback");

        if(value !=null){
            if (this.isValidJsonpQueryParam(value)) {
                JSONPObject jsonp = new JSONPObject(value, o);
                String text = JSON.toJSONString(jsonp.getJson(), this.features);
                String jsonpText = new StringBuilder(jsonp.getFunction()).append("(").append(text).append(")").toString();
                byte[] bytes ;
                //根据前端需要返回对应的编码,默认均是utf-8
                if(text.contains("gbk")){
                    bytes = jsonpText.getBytes(this.GBK);
                }
                else {
                    bytes = jsonpText.getBytes(this.charset);

                }

                OutputStream out = null;
                try {
                    out = response.getOutputStream();
                    out.write(bytes);
                    out.flush();
                    out.close();
                } catch (IOException e) {

                }
            }
            if (this.logger.isDebugEnabled()) {
                this.logger.debug("Ignoring invalid jsonp parameter value: " + value);
            }
        }
      return o;
    }



    @Override
    public boolean supports(MethodParameter methodParameter, Class aClass) {
        return true;
    }
    protected boolean isValidJsonpQueryParam(String value) {
        return CALLBACK_PARAM_PATTERN.matcher(value).matches();
    }
    public Jsonp() {
        super();
        this.charset = UTF8;
        this.features = new SerializerFeature[0];
    }

    @Bean
    public FastJsonHttpMessageConverter fastJsonHttpMessageConverter() {
        FastJsonHttpMessageConverter converter = new FastJsonHttpMessageConverter();
        converter.setFastJsonConfig(fastjsonConfig());
        converter.setSupportedMediaTypes(getSupportedMediaType());
        return converter;
    }

    /**
     * fastjson的配置
     */
    public FastJsonConfig fastjsonConfig() {
        FastJsonConfig fastJsonConfig = new FastJsonConfig();
        fastJsonConfig.setSerializerFeatures(
                SerializerFeature.PrettyFormat,
                SerializerFeature.WriteMapNullValue,
                SerializerFeature.WriteEnumUsingToString
        );
        fastJsonConfig.setDateFormat("yyyy-MM-dd HH:mm:ss");
        ValueFilter valueFilter = new ValueFilter() {
            public Object process(Object o, String s, Object o1) {
                if (null == o1) {

                    o1 = "";
                }
                return o1;
            }
        };

        fastJsonConfig.setSerializeFilters(valueFilter);

        //解决Long转json精度丢失的问题
        SerializeConfig serializeConfig = SerializeConfig.globalInstance;
        serializeConfig.put(BigInteger.class, ToStringSerializer.instance);
        serializeConfig.put(Long.class, ToStringSerializer.instance);
        serializeConfig.put(Long.TYPE, ToStringSerializer.instance);
        fastJsonConfig.setSerializeConfig(serializeConfig);
        return fastJsonConfig;
    }

    /**
     * 支持的mediaType类型
     */
    public List<MediaType> getSupportedMediaType() {
        ArrayList<MediaType> mediaTypes = new ArrayList<>();
        mediaTypes.add(MediaType.APPLICATION_JSON_UTF8);
        return mediaTypes;
    }


}

相关文章

网友评论

      本文标题:Spring Boot 实现Jsonp

      本文链接:https://www.haomeiwen.com/subject/stfhqctx.html