繁体   English   中英

根据Jersey的请求查询参数自定义Jackson的反序列化?

[英]Customizing Jackson's deserialization depending on Jersey's request query param?

我在我的REST API上使用Jackson 24.1 + Jersey 2.10。

为了以自定义格式解析日期,我有一个像这样的Jackson解串器:

public class JsonDateSerializer extends JsonSerializer<Date>{

    private static final SimpleDateFormat dateFormat = new SimpleDateFormat("MM-dd-yyyy");

    @Override
    public void serialize(Date date, JsonGenerator gen, SerializerProvider provider)
            throws IOException, JsonProcessingException {

        String formattedDate = dateFormat.format(date);

        gen.writeString(formattedDate);
    }

}

但是我想根据用户是否包含给定的请求标头来更改日期反序列化的方式。 为此,我需要在Jackson的反序列化器中访问Jersey的HttpRequestContext对象...

像这样一起使用时,是否可以在JAckson的序列化器/反序列化器中访问Jersey的上下文?

谢谢!!

据我所知,您不能直接从反序列化器访问HttpRequest,但是,我在对象中使用了一个标志来做类似的事情。

    @XmlElement(name = "date")
    public String getDate() {
        return (formatFlag) ? dateFormatter1.format(date): dateFormatter2.format(date);
    }

那么当然formatFlag可以是@XmlTransient

编辑

是的ContextResolverFactory确实为上下文解析器缓存...我以不同的方式工作,希望这可以帮助-

为Date创建XMLAdapter作为Spring bean

import java.util.Date;
import javax.inject.Inject;
import javax.inject.Named;
import javax.xml.bind.annotation.adapters.XmlAdapter;
import org.apache.commons.lang3.time.DateFormatUtils;

@Named
public class RequestBasedXMLAdapter extends XmlAdapter<String, Date> {
    @Inject
    private RequestData requestData;

    @Override
    public String marshal(Date value) throws Exception {

        return DateFormatUtils.format(value, requestData.getMyDateFormat());
    }

    @Override
    public Date unmarshal(String value) throws Exception {
        // i am not interested in incoming date
        return new Date();
    }
}

创建请求范围的bean

import javax.inject.Named;
import org.springframework.context.annotation.Scope;
import org.springframework.context.annotation.ScopedProxyMode;

@Named
@Scope(value = "request", proxyMode = ScopedProxyMode.TARGET_CLASS)
public class RequestData {
    private String myDateFormat;

    public String getMyDateFormat() {
        return myDateFormat;
    }

    public void setMyDateFormat(String myQueryParam) {
        this.myDateFormat = myQueryParam;
    }
}

为JAXBContext创建上下文解析器

  1. 注入spring应用程序上下文
  2. 从上下文获取定义为Spring bean的XMLAdapter
  3. 通过修改以下方法返回自定义jaxbcontext(实现为装饰器)

     public JAXBMarshaller createMarshaller() throws JAXBException { JAXBMarshaller marshaller = delegate.createMarshaller(); marshaller.setAdapter(adapter); return marshaller; } public JAXBUnmarshaller createUnmarshaller() throws JAXBException { JAXBUnmarshaller unmarshaller = delegate.createUnmarshaller(); unmarshaller.setAdapter(adapter); return unmarshaller; } 

现在在您的Resource类中(已定义GET / POST方法的位置)

  1. 注入请求范围的bean RequestData
  2. 从RequestData中的查询/标头参数设置dateformat

在Response类中将您的Date字段注释为

 @XmlJavaTypeAdapter(RequestBasedXMLAdapter.class)
 private Date myCustomDate = new Date();

现在您应该能够根据您的要求更改日期格式

另请注意,我正在使用Moxy


老答案

我认为您可以通过返回不同的ObjectMapper ...

尝试

  1. 为ObjectMapper编写一个ContextResolver
  2. 使用@Context注入HTTPHeader
  3. 根据您的标头参数返回差异。 使用适当的日期格式的映射器

上述方法的缺点是,相同的日期格式将应用于该响应中的所有日期。

暂无
暂无

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM