【问题标题】:Spring Integration ObjectToJsonTransformer and headers propagation in responseSpring Integration ObjectToJsonTransformer 和响应中的标头传播
【发布时间】:2021-06-17 09:52:48
【问题描述】:

我正在设置一个应该执行以下操作的集成流程:

接受一个对象????将其序列化为 JSON ????通过 TCP 套接字发送它???收到 JSON 响应 ????将其反序列化为一个对象(与输入的类型不同)

为了进行序列化和反序列化,我使用了两个@Transformer,分别是ObjectToJsonTransformerJsonToObjectTransformer

我的问题是ObjectToJsonTransformer 创建了一个Message,它在其标头中包含序列化对象的类型,并且这些标头被传播到我从远程端点收到的响应中。我希望收到的Message 是全新的,但事实并非如此,我也不完全明白为什么。

保留这些标头会导致响应被反序列化为输入对象类型,而不是所需的输出类型。

我的解决方法是将此行添加到我的MessageHandler

tcpOutboundGateway.setNotPropagatedHeaders(JsonHeaders.HEADERS.toArray(new String[0]));

但我觉得我做错了什么。

这是我到目前为止所做的:

@EnableIntegration
@IntegrationComponentScan
@Configuration
public class TcpConfiguration {

    private static final String REQUEST_OBJECT_CHANNEL = "REQUEST_OBJECT_CHANNEL";
    private static final String REQUEST_JSON_CHANNEL = "REQUEST_JSON_CHANNEL";
    private static final String RESPONSE_JSON_CHANNEL = "RESPONSE_JSON_CHANNEL";

    @Value(value = "${ip}")
    private String ip;
    @Value(value = "${port}")
    private Integer port;

    @Bean
    public AbstractClientConnectionFactory clientConnectionFactory() {
        return new TcpNetClientConnectionFactory(this.ip, this.port);
    }

    @Bean
    @Transformer(inputChannel = REQUEST_OBJECT_CHANNEL, outputChannel = REQUEST_JSON_CHANNEL)
    public ObjectToJsonTransformer objectToJsonTransformer() {
        return new ObjectToJsonTransformer();
    }

    @Bean
    @ServiceActivator(inputChannel = REQUEST_JSON_CHANNEL)
    public MessageHandler tcpOutputGateway(final AbstractClientConnectionFactory connectionFactory) {
        final var tcpOutboundGateway = new TcpOutboundGateway();
        tcpOutboundGateway.setConnectionFactory(connectionFactory);
        tcpOutboundGateway.setNotPropagatedHeaders(JsonHeaders.HEADERS.toArray(new String[0]));
        tcpOutboundGateway.setOutputChannelName(RESPONSE_JSON_CHANNEL);
        return tcpOutboundGateway;
    }

    @Bean
    @Transformer(inputChannel = RESPONSE_JSON_CHANNEL)
    public JsonToObjectTransformer jsonToObjectTransformer() {
        return new JsonToObjectTransformer(MyResponse.class);
    }

    @MessagingGateway
    public interface StandaloneGateway {

        @Gateway(requestChannel = REQUEST_OBJECT_CHANNEL)
        MyResponse sendRequestAndGetResponse(MyRequest request);

    }
}

使用此代码,我可以正确反序列化对MyResponse 的响应,但如果我删除此行

tcpOutboundGateway.setNotPropagatedHeaders(JsonHeaders.HEADERS.toArray(new String[0]));

然后将响应反序列化为MyRequest

有没有更好的方法来处理这个流程?

【问题讨论】:

    标签: json spring spring-integration


    【解决方案1】:

    默认情况下,网关始终复制入站标头。

    您的解决方案是正确的,但还有一个替代方案。

    new JsonToObjectTransformer(MyResponse.class);
    

    该类型是不存在标头时的后备类型。

    首先咨询valueTypeExpression(从版本 5.2.6 开始),默认使用标头。

    另一种方法是设置不同的表达式:

    ResolvableType type = ResolvableType.forClass(TestPerson.class);
    transformer.setValueTypeExpression(new ValueExpression<>(type));
    

    然后标题将被忽略。

    【讨论】:

    猜你喜欢
    • 2013-11-13
    • 2012-07-14
    • 1970-01-01
    • 1970-01-01
    • 2013-11-28
    • 1970-01-01
    • 2012-03-03
    • 1970-01-01
    • 1970-01-01
    相关资源
    最近更新 更多