如何将 Spring 集成 HTTP 网关响应解析为 Bean?
How to parse Spring Integration HTTP gateway response into a Bean?
我一直在尝试获得一个简单的集成工作流程以供练习。问题是我刚开始使用 Spring,我很难理解集成及其工作原理。
现在我有一个非常简单的后端应用程序 Spring MVC returns
[
{"id":1,"name":"Series test","synopsis":"Testing reading items from JSON.","imageUrl":"http://some.where/images/some_image.png"},
{"id":2,"name":"Arrow","synopsis":"Some guy in a hood shooting arrows to some guys with superpowers.","imageUrl":"http://some.where/images/some_image.png"},
{"id":3,"name":"Primeval","synopsis":"Some guys with guns killing dinosaurs and lots of infidelity.","imageUrl":"http://some.where/images/some_image.png"},
{"id":4,"name":"Dr. Who","synopsis":"It's bigger on the inside.","imageUrl":"http://some.where/images/some_image.png"},
{"id":5,"name":"Fringe","synopsis":"Weird things happen.","imageUrl":"http://some.where/images/some_image.png"},
{"id":6,"name":"Monster Hunter Freedom Unite","synopsis":"Wait. This is a game.","imageUrl":"http://some.where/images/some_image.png"}
]
到 http://localhost:9000/api/series/findAll
和一个可运行的 Spring 项目,该项目通过集成尝试恢复该数据并将其转换为 Series
(具有与 JSON) 数组。
如果我不向 outbound-gateway
添加 reply-channel
,一切正常。但是当我将它发送到另一个频道以将其解析为 Series
对象时,我开始在新频道上获得 "Dispatcher has no subscribers" 。说的有道理,但是现在我不知道怎么办了。
我的项目文件,除了 Series,现在看起来是这样的:
Startup.java
package com.txus.integration;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.context.annotation.Configuration;
import org.springframework.context.support.ClassPathXmlApplicationContext;
import java.util.List;
import java.util.concurrent.Future;
public class Startup {
@Autowired
RequestGateway requestGateway;
public static void main(String[] args) throws Exception {
ClassPathXmlApplicationContext context = new ClassPathXmlApplicationContext("/META-INF/spring/integration-components.xml");
RequestGateway requestGateway = context.getBean(RequestGateway.class);
Future<String> promise = requestGateway.getSeries("");
while (!promise.isDone()) {
Thread.sleep(1000);
}
String response = promise.get();
printReadable(response);
context.close();
System.exit(0);
}
public static void printReadable(String string) {
String separator = "= = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = =";
System.out.println("\n" + separator + "\n" + string + "\n" + separator + "\n");
}
public static void printReadable(List<String> strings) {
for (String string : strings) printReadable(string);
}
}
请求网关
package com.txus.integration;
import com.txus.entities.Series;
import org.springframework.integration.annotation.Gateway;
import java.util.concurrent.Future;
public interface RequestGateway {
@Gateway(requestChannel="responseChannel")
Future<String> getSeries(String jsonString);
@Gateway(requestChannel="responseChannel")
Future<String> getSeries(Series series);
}
积分-components.xml
<beans:beans
xmlns="http://www.springframework.org/schema/integration"
xmlns:beans="http://www.springframework.org/schema/beans"
xmlns:context="http://www.springframework.org/schema/context"
xmlns:http="http://www.springframework.org/schema/integration/http"
xmlns:task="http://www.springframework.org/schema/task"
xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
xsi:schemaLocation="
http://www.springframework.org/schema/beans http://www.springframework.org/schema/beans/spring-beans.xsd
http://www.springframework.org/schema/context http://www.springframework.org/schema/context/spring-context-3.1.xsd
http://www.springframework.org/schema/integration http://www.springframework.org/schema/integration/spring-integration.xsd
http://www.springframework.org/schema/integration/http http://www.springframework.org/schema/integration/http/spring-integration-http.xsd
http://www.springframework.org/schema/task http://www.springframework.org/schema/task/spring-task.xsd">
<context:annotation-config/>
<context:component-scan base-package="com.txus"/>
<!-- START: Spring Integration -->
<!-- Integration: Channels -->
<channel id="requestChannel"/>
<channel id="responseChannel"/>
<channel id="failedChannel"/>
<!-- Integration: Loggers -->
<logging-channel-adapter
id="payloadLogger" level="DEBUG" expression="'### Message [' + headers.id + '] payload: ' + payload"/>
<logging-channel-adapter
id="headersLogger" level="DEBUG" expression="'### Message [' + headers.id + '] headers: ' + headers"/>
<!-- Integration: Flow -->
<gateway
service-interface="com.txus.integration.RequestGateway"
default-request-timeout="5000" async-executor="executor">
<method name="getSeries" request-channel="inputChannel"/>
</gateway>
<task:executor id="executor" pool-size="100"/>
<payload-type-router input-channel="inputChannel" default-output-channel="failedChannel">
<mapping type="java.lang.String" channel="requestChannel"/>
<mapping type="com.txus.entities.Series" channel="objectToJSONChannel"/>
</payload-type-router>
<object-to-json-transformer
id="objectToJsonTransformer" input-channel="objectToJSONChannel" output-channel="requestChannel"/>
<http:outbound-gateway
http-method="GET"
expected-response-type="java.lang.String"
url="http://localhost:9000/api/series/findAll"
request-channel="requestChannel"
reply-channel="jsonToSeries"
reply-timeout="30000"/>
<map-to-object-transformer
input-channel="jsonToSeries" output-channel="responseChannel" type="com.txus.entities.Series"/>
<!-- END: Spring Integration -->
</beans:beans>
配置 output-channel="responseChannel"
的最后一个组件有问题。没有订阅该频道的内容。
我看到了你的 @Gateway
配置,但是有点不对。 XML 配置优先于注释。因此最后的 requestChannel
正好是 inputChannel
.
如果您想将 <map-to-object-transformer>
的结果发送到 responseChannel
并接受来自 RequestGateway
调用的 return
,您应该指定responseChannel
作为网关配置的 reply-channel
。
从另一边看,您根本不需要它,而 TemporaryReplyChannel
可以提供帮助。
请参阅 Spring 集成 Manual 的更多信息。
我一直在尝试获得一个简单的集成工作流程以供练习。问题是我刚开始使用 Spring,我很难理解集成及其工作原理。
现在我有一个非常简单的后端应用程序 Spring MVC returns
[
{"id":1,"name":"Series test","synopsis":"Testing reading items from JSON.","imageUrl":"http://some.where/images/some_image.png"},
{"id":2,"name":"Arrow","synopsis":"Some guy in a hood shooting arrows to some guys with superpowers.","imageUrl":"http://some.where/images/some_image.png"},
{"id":3,"name":"Primeval","synopsis":"Some guys with guns killing dinosaurs and lots of infidelity.","imageUrl":"http://some.where/images/some_image.png"},
{"id":4,"name":"Dr. Who","synopsis":"It's bigger on the inside.","imageUrl":"http://some.where/images/some_image.png"},
{"id":5,"name":"Fringe","synopsis":"Weird things happen.","imageUrl":"http://some.where/images/some_image.png"},
{"id":6,"name":"Monster Hunter Freedom Unite","synopsis":"Wait. This is a game.","imageUrl":"http://some.where/images/some_image.png"}
]
到 http://localhost:9000/api/series/findAll
和一个可运行的 Spring 项目,该项目通过集成尝试恢复该数据并将其转换为 Series
(具有与 JSON) 数组。
如果我不向 outbound-gateway
添加 reply-channel
,一切正常。但是当我将它发送到另一个频道以将其解析为 Series
对象时,我开始在新频道上获得 "Dispatcher has no subscribers" 。说的有道理,但是现在我不知道怎么办了。
我的项目文件,除了 Series,现在看起来是这样的:
Startup.java
package com.txus.integration;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.context.annotation.Configuration;
import org.springframework.context.support.ClassPathXmlApplicationContext;
import java.util.List;
import java.util.concurrent.Future;
public class Startup {
@Autowired
RequestGateway requestGateway;
public static void main(String[] args) throws Exception {
ClassPathXmlApplicationContext context = new ClassPathXmlApplicationContext("/META-INF/spring/integration-components.xml");
RequestGateway requestGateway = context.getBean(RequestGateway.class);
Future<String> promise = requestGateway.getSeries("");
while (!promise.isDone()) {
Thread.sleep(1000);
}
String response = promise.get();
printReadable(response);
context.close();
System.exit(0);
}
public static void printReadable(String string) {
String separator = "= = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = = =";
System.out.println("\n" + separator + "\n" + string + "\n" + separator + "\n");
}
public static void printReadable(List<String> strings) {
for (String string : strings) printReadable(string);
}
}
请求网关
package com.txus.integration;
import com.txus.entities.Series;
import org.springframework.integration.annotation.Gateway;
import java.util.concurrent.Future;
public interface RequestGateway {
@Gateway(requestChannel="responseChannel")
Future<String> getSeries(String jsonString);
@Gateway(requestChannel="responseChannel")
Future<String> getSeries(Series series);
}
积分-components.xml
<beans:beans
xmlns="http://www.springframework.org/schema/integration"
xmlns:beans="http://www.springframework.org/schema/beans"
xmlns:context="http://www.springframework.org/schema/context"
xmlns:http="http://www.springframework.org/schema/integration/http"
xmlns:task="http://www.springframework.org/schema/task"
xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
xsi:schemaLocation="
http://www.springframework.org/schema/beans http://www.springframework.org/schema/beans/spring-beans.xsd
http://www.springframework.org/schema/context http://www.springframework.org/schema/context/spring-context-3.1.xsd
http://www.springframework.org/schema/integration http://www.springframework.org/schema/integration/spring-integration.xsd
http://www.springframework.org/schema/integration/http http://www.springframework.org/schema/integration/http/spring-integration-http.xsd
http://www.springframework.org/schema/task http://www.springframework.org/schema/task/spring-task.xsd">
<context:annotation-config/>
<context:component-scan base-package="com.txus"/>
<!-- START: Spring Integration -->
<!-- Integration: Channels -->
<channel id="requestChannel"/>
<channel id="responseChannel"/>
<channel id="failedChannel"/>
<!-- Integration: Loggers -->
<logging-channel-adapter
id="payloadLogger" level="DEBUG" expression="'### Message [' + headers.id + '] payload: ' + payload"/>
<logging-channel-adapter
id="headersLogger" level="DEBUG" expression="'### Message [' + headers.id + '] headers: ' + headers"/>
<!-- Integration: Flow -->
<gateway
service-interface="com.txus.integration.RequestGateway"
default-request-timeout="5000" async-executor="executor">
<method name="getSeries" request-channel="inputChannel"/>
</gateway>
<task:executor id="executor" pool-size="100"/>
<payload-type-router input-channel="inputChannel" default-output-channel="failedChannel">
<mapping type="java.lang.String" channel="requestChannel"/>
<mapping type="com.txus.entities.Series" channel="objectToJSONChannel"/>
</payload-type-router>
<object-to-json-transformer
id="objectToJsonTransformer" input-channel="objectToJSONChannel" output-channel="requestChannel"/>
<http:outbound-gateway
http-method="GET"
expected-response-type="java.lang.String"
url="http://localhost:9000/api/series/findAll"
request-channel="requestChannel"
reply-channel="jsonToSeries"
reply-timeout="30000"/>
<map-to-object-transformer
input-channel="jsonToSeries" output-channel="responseChannel" type="com.txus.entities.Series"/>
<!-- END: Spring Integration -->
</beans:beans>
配置 output-channel="responseChannel"
的最后一个组件有问题。没有订阅该频道的内容。
我看到了你的 @Gateway
配置,但是有点不对。 XML 配置优先于注释。因此最后的 requestChannel
正好是 inputChannel
.
如果您想将 <map-to-object-transformer>
的结果发送到 responseChannel
并接受来自 RequestGateway
调用的 return
,您应该指定responseChannel
作为网关配置的 reply-channel
。
从另一边看,您根本不需要它,而 TemporaryReplyChannel
可以提供帮助。
请参阅 Spring 集成 Manual 的更多信息。