此版本仍在开发中,尚未被视为稳定版本。对于最新的稳定版本,请使用 Spring Integration 6.3.1Spring中文文档

此版本仍在开发中,尚未被视为稳定版本。对于最新的稳定版本,请使用 Spring Integration 6.3.1Spring中文文档

Spring Integration 提供了命名空间和相应的模式定义。 若要将其包含在配置中,请在应用程序上下文配置文件中提供以下命名空间声明:httpSpring中文文档

<?xml version="1.0" encoding="UTF-8"?>
<beans xmlns="http://www.springframework.org/schema/beans"
  xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
  xmlns:int="http://www.springframework.org/schema/integration"
  xmlns:int-http="http://www.springframework.org/schema/integration/http"
  xsi:schemaLocation="
    http://www.springframework.org/schema/beans
    https://www.springframework.org/schema/beans/spring-beans.xsd
    http://www.springframework.org/schema/integration
    https://www.springframework.org/schema/integration/spring-integration.xsd
    http://www.springframework.org/schema/integration/http
    https://www.springframework.org/schema/integration/http/spring-integration-http.xsd">
    ...
</beans>

入境

XML 命名空间提供了两个用于处理 HTTP 入站请求的组件:和 。 要在不返回专用响应的情况下处理请求,请使用 . 以下示例演示如何配置一个:inbound-channel-adapterinbound-gatewayinbound-channel-adapterSpring中文文档

<int-http:inbound-channel-adapter id="httpChannelAdapter" channel="requests"
    supported-methods="PUT, DELETE"/>

若要处理需要响应的请求,请使用 . 以下示例演示如何配置一个:inbound-gatewaySpring中文文档

<int-http:inbound-gateway id="inboundGateway"
    request-channel="requests"
    reply-channel="responses"/>

请求映射支持

Spring Integration 3.0 通过引入 IntegrationRequestMappingHandlerMapping 改进了 REST 支持。 该实现依赖于 Spring Framework 3.1 或更高版本提供的增强的 REST 支持。

HTTP 入站网关或 HTTP 入站通道适配器的解析会注册一个 IntegrationRequestMappingHandlerMapping 类型的 Bean,以防尚未注册。 HandlerMapping 的这种特定实现将其逻辑委托给 RequestMappingInfoHandlerMapping。 该实现提供的功能类似于 Spring MVC 中的 org.springframework.web.bind.annotation.RequestMapping 注解。integrationRequestMappingHandlerMappingSpring中文文档

有关更多信息,请参阅使用 @RequestMapping 映射请求

为此,Spring Integration 3.0 引入了该元素。 您可以将此可选元素添加到 和 中。 它与 和 属性结合使用。 以下示例演示如何在入站网关上配置它:<request-mapping><http:inbound-channel-adapter><http:inbound-gateway>pathsupported-methodsSpring中文文档

<inbound-gateway id="inboundController"
    request-channel="requests"
    reply-channel="responses"
    path="/foo/{fooId}"
    supported-methods="GET"
    view-name="foo"
    error-code="oops">
   <request-mapping headers="User-Agent"
     params="myParam=myValue"
     consumes="application/json"
     produces="!text/plain"/>
</inbound-gateway>

根据上述配置,命名空间解析器将创建一个 (如果不存在)和一个 Bean 的实例,并将 RequestMapping 的实例与它相关联。 此实例又转换为 Spring MVC RequestMappingInfoIntegrationRequestMappingHandlerMappingHttpRequestHandlingControllerRequestMappingSpring中文文档

该元素提供以下属性:<request-mapping>Spring中文文档

使用 和 的 和 属性 或 ,属性直接转换为 Spring MVC 中注解提供的相应选项。pathsupported-methods<http:inbound-channel-adapter><http:inbound-gateway><request-mapping>org.springframework.web.bind.annotation.RequestMappingSpring中文文档

该元素允许您将多个Spring Integration HTTP入站端点配置为相同(甚至相同),并允许您根据传入的HTTP请求提供不同的下游消息流。<request-mapping>pathsupported-methodsSpring中文文档

或者,您也可以只声明一个 HTTP 入站端点,并在 Spring Integration 流中应用路由和过滤逻辑以实现相同的结果。 这使您可以尽早进入流程。 以下示例演示如何执行此操作:MessageSpring中文文档

<int-http:inbound-gateway request-channel="httpMethodRouter"
    supported-methods="GET,DELETE"
    path="/process/{entId}"
    payload-expression="#pathVariables.entId"/>

<int:router input-channel="httpMethodRouter" expression="headers.http_requestMethod">
    <int:mapping value="GET" channel="in1"/>
    <int:mapping value="DELETE" channel="in2"/>
</int:router>

<int:service-activator input-channel="in1" ref="service" method="getEntity"/>

<int:service-activator input-channel="in2" ref="service" method="delete"/>

有关处理程序映射的更多信息,请参阅 Spring Framework Web Servlet 文档Spring Framework Web Reactive 文档Spring中文文档

扩展了 Spring MVC 类,继承了它的大部分逻辑,特别是 ,当映射由于某种原因不匹配时,它会为 HTTP 响应抛出特定错误,从而阻止对应用程序上下文中任何剩余映射处理程序的调用。 因此,为 Spring Integration 和 Spring MVC 请求映射配置相同的路径(例如 在一个和另一个中)不受支持;找不到 MVC 映射。IntegrationRequestMappingHandlerMappingRequestMappingHandlerMappinghandleNoMatch(Set, String, HttpServletRequest)4xxPOSTGET
Spring Integration 3.0 通过引入 IntegrationRequestMappingHandlerMapping 改进了 REST 支持。 该实现依赖于 Spring Framework 3.1 或更高版本提供的增强的 REST 支持。
有关更多信息,请参阅使用 @RequestMapping 映射请求
扩展了 Spring MVC 类,继承了它的大部分逻辑,特别是 ,当映射由于某种原因不匹配时,它会为 HTTP 响应抛出特定错误,从而阻止对应用程序上下文中任何剩余映射处理程序的调用。 因此,为 Spring Integration 和 Spring MVC 请求映射配置相同的路径(例如 在一个和另一个中)不受支持;找不到 MVC 映射。IntegrationRequestMappingHandlerMappingRequestMappingHandlerMappinghandleNoMatch(Set, String, HttpServletRequest)4xxPOSTGET

跨域资源共享 (CORS) 支持

从版本 4.2 开始,您可以使用元素配置 and。 它表示与Spring MVC相同的注释选项,并允许为Spring Integration HTTP端点配置跨域资源共享(CORS):<http:inbound-channel-adapter><http:inbound-gateway><cross-origin>@CrossOrigin@ControllerSpring中文文档

  • origin:允许的来源列表。 意味着允许所有来源。 这些值都放在预检响应和实际响应的标头中。 默认值为 。*Access-Control-Allow-Origin*Spring中文文档

  • allowed-headers:指示在实际请求期间可以使用哪些请求标头。 表示允许客户端请求的所有标头。 此属性控制预检响应标头的值。 默认值为 。*Access-Control-Allow-Headers*Spring中文文档

  • exposed-headers:用户代理允许客户端访问的响应标头列表。 此属性控制实际响应标头的值。Access-Control-Expose-HeadersSpring中文文档

  • method:允许的HTTP请求方法:、、、。 此处指定的方法将覆盖 中的方法。GETPOSTHEADOPTIONSPUTPATCHDELETETRACEsupported-methodsSpring中文文档

  • allow-credentials:设置为浏览器是否应包含与请求域关联的任何 Cookie,或者是否不应包含。 空字符串 (“”) 表示未定义。 如果 ,则预检响应包括标头。 默认值为 。truefalsetrueAccess-Control-Allow-Credentials=truetrueSpring中文文档

  • max-age:控制预检响应的缓存持续时间。 将此值设置为合理值可以减少浏览器所需的预检请求-响应交互次数。 此属性控制预检响应中标头的值。 值 均值未定义。 默认值为 1800 秒(30 分钟)。Access-Control-Max-Age-1Spring中文文档

CORS Java 配置由类表示,其实例可以注入到 Bean 中。org.springframework.integration.http.inbound.CrossOriginHttpRequestHandlingEndpointSupportSpring中文文档

响应状态代码

从版本 4.1 开始,您可以配置 with a 以覆盖默认状态。 表达式必须返回一个可转换为枚举值的对象。 从版本 5.1 开始,具有 and 作为根对象提供。 例如,在运行时解析返回状态代码值的某些作用域 Bean。 但是,最有可能的是,它被设置为固定值,例如 (无内容) 或 . 默认情况下,为 null,表示返回正常的“200 OK”响应状态。 使用 as root 对象,状态代码可以是有条件的,例如请求方法、某些标头、URI 内容甚至请求正文。 以下示例演示如何将状态代码设置为:<http:inbound-channel-adapter>status-code-expression200 OKorg.springframework.http.HttpStatusevaluationContextBeanResolverRequestEntity<?>status-code=expression="204"status-code-expression="T(org.springframework.http.HttpStatus).NO_CONTENT"status-code-expressionRequestEntity<?>ACCEPTEDSpring中文文档

<http:inbound-channel-adapter id="inboundController"
       channel="requests" view-name="foo" error-code="oops"
       status-code-expression="T(org.springframework.http.HttpStatus).ACCEPTED">
   <request-mapping headers="BAR"/>
</http:inbound-channel-adapter>

从回复的标题中解析“状态代码”。 从版本 4.2 开始,当 中未收到回复时,默认响应状态代码为 。 有两种方法可以修改此行为:<http:inbound-gateway>http_statusCodeMessagereply-timeout500 Internal Server ErrorSpring中文文档

  • 添加 . 这与入站适配器具有相同的语义。reply-timeout-status-code-expressionstatus-code-expressionSpring中文文档

  • 添加并返回带有 HTTP 状态代码标头的相应消息,如以下示例所示:error-channelSpring中文文档

    <int:chain input-channel="errors">
        <int:header-enricher>
            <int:header name="http_statusCode" value="504" />
        </int:header-enricher>
        <int:transformer expression="payload.failedMessage" />
    </int:chain>

的有效负载是 . 它必须转换为可由网关转换的内容,例如 . 一个很好的候选对象是异常的消息属性,这是使用该技术时使用的值。ErrorMessageMessageTimeoutExceptionStringexpressionSpring中文文档

如果错误流在主流超时后超时,则返回错误流,或者,如果存在错误流,则评估错误流。500 Internal Server Errorreply-timeout-status-code-expressionSpring中文文档

以前,超时的默认状态代码为 。 若要恢复该行为,请设置 。200 OKreply-timeout-status-code-expression="200"

同样从 V5.4 开始,准备请求消息时遇到的错误将发送到错误通道(如果提供)。 应通过检查异常在错误流中决定是否引发适当的异常。 以前,任何异常都只是简单地抛出,导致 HTTP 500 服务器错误响应状态,但在某些情况下,问题可能是由不正确的请求参数引起的,因此应抛出具有 4xx 客户端错误状态的异常。 有关详细信息,请参阅。 发送到此错误通道包含原始异常作为分析的有效负载。ResponseStatusExceptionResponseStatusExceptionErrorMessageSpring中文文档

以前,超时的默认状态代码为 。 若要恢复该行为,请设置 。200 OKreply-timeout-status-code-expression="200"

URI 模板变量和表达式

通过将该属性与属性和元素结合使用,可以高度灵活地映射入站请求数据。pathpayload-expressionheaderSpring中文文档

在以下示例配置中,入站通道适配器配置为使用以下 URI 接受请求:Spring中文文档

/first-name/{firstName}/last-name/{lastName}

使用该属性时,URI 模板变量映射为有效负载,而 URI 模板变量映射到消息标头,如以下示例中所定义:payload-expression{firstName}Message{lastName}lnameSpring中文文档

<int-http:inbound-channel-adapter id="inboundAdapterWithExpressions"
    path="/first-name/{firstName}/last-name/{lastName}"
    channel="requests"
    payload-expression="#pathVariables.firstName">
    <int-http:header name="lname" expression="#pathVariables.lastName"/>
</int-http:inbound-channel-adapter>

有关 URI 模板变量的更多信息,请参阅 Spring 参考手册中的 uri 模板模式Spring中文文档

从 Spring Integration 3.0 开始,除了 payload 和 header 表达式中可用的现有变量和变量外,我们还添加了其他有用的表达式变量:#pathVariables#requestParamsSpring中文文档

  • #requestParams:来自 .MultiValueMapServletRequestparameterMapSpring中文文档

  • #pathVariables:from URI 模板占位符及其值。MapSpring中文文档

  • #matrixVariables:根据 Spring MVC 规范的 of。 请注意,这需要 Spring MVC 3.2 或更高版本。MapMultiValueMap#matrixVariablesSpring中文文档

  • #requestAttributes:与当前请求关联的。org.springframework.web.context.request.RequestAttributesSpring中文文档

  • #requestHeaders:当前请求中的对象。org.springframework.http.HttpHeadersSpring中文文档

  • #cookies:当前请求中的实例。MultiValueMap<String, Cookie>jakarta.servlet.http.CookieSpring中文文档

请注意,如果该消息流是单线程的并且位于请求线程中,则可以通过该变量在下游消息流的表达式中访问所有这些值(以及其他值)。 下面的示例配置使用属性的转换器:ThreadLocalorg.springframework.web.context.request.RequestAttributesexpressionSpring中文文档

<int-:transformer
    expression="T(org.springframework.web.context.request.RequestContextHolder).
                  requestAttributes.request.queryString"/>

出境

若要配置出站网关,可以使用命名空间支持。 以下代码片段显示了出站 HTTP 网关的可用配置选项:Spring中文文档

<int-http:outbound-gateway id="example"
    request-channel="requests"
    url="http://localhost/test"
    http-method="POST"
    extract-request-payload="false"
    expected-response-type="java.lang.String"
    charset="UTF-8"
    request-factory="requestFactory"
    reply-timeout="1234"
    reply-channel="replies"/>

最重要的是,请注意提供了“http-method”和“expected-response-type”属性。 这是两个最常配置的值。 默认值为 ,默认响应类型为 null。 对于 null 响应类型,只要其 HTTP 状态为 成功(不成功的状态代码会引发异常),回复的有效负载就包含 。 如果需要其他类型(如 ,请将其作为完全限定的类名提供)(在前面的示例中)。 另请参阅有关 HTTP 出站组件中空响应正文的说明。http-methodPOSTMessageResponseEntityStringjava.lang.StringSpring中文文档

从 Spring Integration 2.1 开始,HTTP 出站网关的属性被重命名,以更好地反映其意图。request-timeoutreply-timeout

从 Spring Integration 2.2 开始,默认情况下不再启用基于 HTTP 的 Java 序列化。 以前,将属性设置为对象时,标头未正确设置。 从 Spring Integration 2.2 开始,现在已经更新了标头,将标头设置为 。expected-response-typeSerializableAcceptSerializingHttpMessageConverterAcceptapplication/x-java-serialized-objectSpring中文文档

但是,由于这可能会导致与现有应用程序不兼容,因此决定不再自动将此转换器添加到 HTTP 终结点。 如果要使用 Java 序列化,可以使用属性(使用 XML 配置时)或使用方法(在 Java 配置中)将 添加到相应的端点。 或者,您可能希望考虑改用 JSON,这是通过在类路径上放置 Jackson 库来启用的。SerializingHttpMessageConvertermessage-converterssetMessageConverters()Spring中文文档

从 Spring Integration 2.2 开始,您还可以使用 SpEL 和属性动态确定 HTTP 方法。 请注意,此属性与 互斥。 您还可以使用该属性来代替并提供任何确定响应类型的有效 SpEL 表达式。 以下配置示例使用:http-method-expressionhttp-methodexpected-response-type-expressionexpected-response-typeexpected-response-type-expressionSpring中文文档

<int-http:outbound-gateway id="example"
    request-channel="requests"
    url="http://localhost/test"
    http-method-expression="headers.httpMethod"
    extract-request-payload="false"
    expected-response-type-expression="payload"
    charset="UTF-8"
    request-factory="requestFactory"
    reply-timeout="1234"
    reply-channel="replies"/>

如果要以单向方式使用出站适配器,则可以改用 。 这意味着成功的响应在执行时不会向回复通道发送任何消息。 如果响应状态代码不成功,则会引发异常。 配置看起来与网关非常相似,如以下示例所示:outbound-channel-adapterSpring中文文档

<int-http:outbound-channel-adapter id="example"
    url="http://localhost/example"
    http-method="GET"
    channel="requests"
    charset="UTF-8"
    extract-payload="false"
    expected-response-type="java.lang.String"
    request-factory="someRequestFactory"
    order="3"
    auto-startup="false"/>

要指定 URL,您可以使用“url”属性或“url-expression”属性。 “url”属性采用一个简单的字符串(带有 URI 变量的占位符,如下所述)。 “url-expression”是一个 SpEL 表达式,以 the 作为根对象,用于启用动态 url。 表达式计算结果的 URL 仍可以具有 URI 变量的占位符。MessageSpring中文文档

在以前的版本中,一些用户使用占位符将整个 URL 替换为 URI 变量。 Spring 3.1 中的更改可能会导致转义字符出现一些问题,例如“?”。 因此,如果您希望完全在运行时生成 URL,我们建议您使用“url-expression”属性。Spring中文文档

从 Spring Integration 2.1 开始,HTTP 出站网关的属性被重命名,以更好地反映其意图。request-timeoutreply-timeout

从 Spring Integration 2.2 开始,默认情况下不再启用基于 HTTP 的 Java 序列化。 以前,将属性设置为对象时,标头未正确设置。 从 Spring Integration 2.2 开始,现在已经更新了标头,将标头设置为 。expected-response-typeSerializableAcceptSerializingHttpMessageConverterAcceptapplication/x-java-serialized-objectSpring中文文档

但是,由于这可能会导致与现有应用程序不兼容,因此决定不再自动将此转换器添加到 HTTP 终结点。 如果要使用 Java 序列化,可以使用属性(使用 XML 配置时)或使用方法(在 Java 配置中)将 添加到相应的端点。 或者,您可能希望考虑改用 JSON,这是通过在类路径上放置 Jackson 库来启用的。SerializingHttpMessageConvertermessage-converterssetMessageConverters()Spring中文文档

要指定 URL,您可以使用“url”属性或“url-expression”属性。 “url”属性采用一个简单的字符串(带有 URI 变量的占位符,如下所述)。 “url-expression”是一个 SpEL 表达式,以 the 作为根对象,用于启用动态 url。 表达式计算结果的 URL 仍可以具有 URI 变量的占位符。MessageSpring中文文档

在以前的版本中,一些用户使用占位符将整个 URL 替换为 URI 变量。 Spring 3.1 中的更改可能会导致转义字符出现一些问题,例如“?”。 因此,如果您希望完全在运行时生成 URL,我们建议您使用“url-expression”属性。Spring中文文档

映射 URI 变量

如果 URL 包含 URI 变量,则可以使用该元素映射它们。 此元素可用于 HTTP 出站网关和 HTTP 出站通道适配器。 以下示例将 URI 变量映射到表达式:uri-variablezipCodeSpring中文文档

<int-http:outbound-gateway id="trafficGateway"
    url="https://local.yahooapis.com/trafficData?appid=YdnDemo&amp;zip={zipCode}"
    request-channel="trafficChannel"
    http-method="GET"
    expected-response-type="java.lang.String">
    <int-http:uri-variable name="zipCode" expression="payload.getZip()"/>
</int-http:outbound-gateway>

该元素定义了两个属性:和 。 该属性标识 URI 变量的名称,而该属性用于设置实际值。 通过使用该属性,您可以利用 Spring 表达式语言 (SpEL) 的全部功能,它使您可以完全动态访问消息有效负载和消息标头。 例如,在前面的配置中,该方法在 的有效负载对象上调用,该方法的结果用作名为“zipCode”的 URI 变量的值。uri-variablenameexpressionnameexpressionexpressiongetZip()MessageSpring中文文档

从 Spring Integration 3.0 开始,HTTP 出站端点支持该属性来指定应评估的属性,从而在 URL 模板中生成所有 URI 变量占位符。 它提供了一种机制,您可以在其中根据出站消息使用不同的变量表达式。 此属性与元素互斥。 下面的示例演示如何使用该属性:uri-variables-expressionexpressionMap<uri-variable/>uri-variables-expressionSpring中文文档

<int-http:outbound-gateway
     url="https://foo.host/{foo}/bars/{bar}"
     request-channel="trafficChannel"
     http-method="GET"
     uri-variables-expression="@uriVariablesBean.populate(payload)"
     expected-response-type="java.lang.String"/>

uriVariablesBean可以定义如下:Spring中文文档

public class UriVariablesBean {
    private static final ExpressionParser EXPRESSION_PARSER = new SpelExpressionParser();

    public Map<String, ?> populate(Object payload) {
        Map<String, Object> variables = new HashMap<String, Object>();
        if (payload instanceOf String.class)) {
            variables.put("foo", "foo"));
        }
        else {
            variables.put("foo", EXPRESSION_PARSER.parseExpression("headers.bar"));
        }
        return variables;
    }

}
必须计算为 . 的值必须是 或 的实例。 通过在出站的上下文中使用这些表达式,将其提供给 URI 变量占位符的进一步解析。uri-variables-expressionMapMapStringExpressionMapExpressionEvalMapMessage

重要 该属性提供了一种非常强大的机制来计算 URI 变量。 我们预计人们大多使用简单的表达式,例如前面的示例。 但是,您也可以配置一些内容,例如在返回的映射中将表达式设置为 ,其中表达式在名为 的消息头中动态提供。 由于标头可能来自不受信任的源,因此 HTTP 出站终结点在评估这些表达式时使用。 仅使用 SpEL 功能的子集。 如果您信任消息源并希望使用受限制的 SpEL 构造,请将出站终结点的属性设置为 。uriVariablesExpression"@uriVariablesBean.populate(#root)"variables.put("thing1", EXPRESSION_PARSER.parseExpression(message.getHeaders().get("thing2", String.class)));thing2SimpleEvaluationContextSimpleEvaluationContexttrustedSpeltrueSpring中文文档

通过使用自定义和一些实用程序来构建和编码 URL 参数,可以实现需要基于每条消息提供一组动态 URI 变量的方案。 以下示例演示如何执行此操作:url-expressionSpring中文文档

url-expression="T(org.springframework.web.util.UriComponentsBuilder)
                           .fromHttpUrl('https://HOST:PORT/PATH')
                           .queryParams(payload)
                           .build()
                           .toUri()"

该方法需要 a 作为参数,因此您可以在执行请求之前提前构建一组真实的 URL 查询参数。queryParams()MultiValueMap<String, String>Spring中文文档

整体也可以表示为 ,如以下示例所示:queryStringuri-variableSpring中文文档

<int-http:outbound-gateway id="proxyGateway" request-channel="testChannel"
              url="http://testServer/test?{queryString}">
    <int-http:uri-variable name="queryString" expression="'a=A&amp;b=B'"/>
</int-http:outbound-gateway>

在这种情况下,您必须手动提供 URL 编码。 例如,您可以将 用于此目的。 如前所述,可以使用以下 Java Streams 代码段将手动构建的参数转换为 method 参数:org.apache.http.client.utils.URLEncodedUtils#format()MultiValueMap<String, String>List<NameValuePair>format()Spring中文文档

List<NameValuePair> nameValuePairs =
    params.entrySet()
            .stream()
            .flatMap(e -> e
                    .getValue()
                    .stream()
                    .map(v -> new BasicNameValuePair(e.getKey(), v)))
            .collect(Collectors.toList());
必须计算为 . 的值必须是 或 的实例。 通过在出站的上下文中使用这些表达式,将其提供给 URI 变量占位符的进一步解析。uri-variables-expressionMapMapStringExpressionMapExpressionEvalMapMessage

控制 URI 编码

默认情况下,在发送请求之前,URL 字符串将编码为 URI 对象(请参阅 UriComponentsBuilder)。 在某些具有非标准 URI(例如 RabbitMQ REST API)的方案中,不需要执行编码。 和 提供属性。 若要禁用对 URL 的编码,请将此属性设置为(默认情况下为 )。 如果要对 URL 的某些部分进行部分编码,请在 中使用 ,如以下示例所示:<http:outbound-gateway/><http:outbound-channel-adapter/>encoding-modeNONETEMPLATE_AND_VALUESexpression<uri-variable/>Spring中文文档

<http:outbound-gateway url="https://somehost/%2f/fooApps?bar={param}" encoding-mode="NONE">
          <http:uri-variable name="param"
            expression="T(org.apache.commons.httpclient.util.URIUtil)
                                             .encodeWithinQuery('Hello World!')"/>
</http:outbound-gateway>

使用 Java DSL,此选项可以通过该选项进行控制。 相同的配置适用于 WebFlux 模块Web 服务模块中的类似出站组件。 对于许多复杂的场景,建议在外部提供 ;或者在 WebFlux 的情况下 - 使用它.BaseHttpMessageHandlerSpec.encodingMode()UriTemplateHandlerRestTemplateWebClientUriBuilderFactorySpring中文文档