Spring Integration多PathVariable在payloadExpression中的配置问题
嘿,我看你在尝试用Spring Integration的payloadExpression传递多个路径变量时踩坑了,直接拼接字符串的方式肯定走不通,下面给你讲清楚正确的实现方法和注意点:
1. 正确传递多个PathVariable到Payload
你之前的写法把两个路径变量拼成了一个字符串,导致下游没法拆分出单独的参数。正确的做法是把这些变量封装成一个结构化的对象(比如Map或者自定义DTO),这样后续可以轻松提取单个值:
方案一:直接复用#pathVariables Map
最省事的方式就是直接用Spring Integration提供的#pathVariables——它本身就是一个包含所有路径参数的Map,直接把它作为payload传递即可:
public IntegrationFlow getContraindicationsByDrugcodeAndIcd10WorkFlow() { return IntegrationFlows .from(Http.inboundGateway("/drug/{code}/icd10/{icd10}/contraindications") .payloadExpression("#pathVariables") // 直接传递所有路径变量的Map .requestMapping(m -> m.methods(HttpMethod.GET)) .errorChannel(IntegrationConfiguration.CHANNEL_ERROR_REST)) .handle(Http.outboundGateway(url + "/{code}/V22?format=json") .httpMethod(HttpMethod.GET) .uriVariable("code", "payload.code") // 从Map中提取code参数 // 如果后续需要用到icd10,只需添加这一行: // .uriVariable("icd10", "payload.icd10") .expectedResponseType(String.class)) .get(); }
方案二:用自定义DTO封装参数
如果需要更严格的类型约束,可以创建一个简单的DTO类来封装路径变量:
// 先定义一个DTO类 public class DrugIcd10Request { private String code; private String icd10; // 带参构造方法、Getter方法都要加上 public DrugIcd10Request(String code, String icd10) { this.code = code; this.icd10 = icd10; } // Getters... } // 然后在IntegrationFlow中使用 public IntegrationFlow getContraindicationsByDrugcodeAndIcd10WorkFlow() { return IntegrationFlows .from(Http.inboundGateway("/drug/{code}/icd10/{icd10}/contraindications") // 用SpEL创建DTO实例作为payload .payloadExpression("new com.yourpackage.DrugIcd10Request(#pathVariables.code, #pathVariables.icd10)") .requestMapping(m -> m.methods(HttpMethod.GET)) .errorChannel(IntegrationConfiguration.CHANNEL_ERROR_REST)) .handle(Http.outboundGateway(url + "/{code}/V22?format=json") .httpMethod(HttpMethod.GET) .uriVariable("code", "payload.code") .expectedResponseType(String.class)) .get(); }
2. 关于.uriVariable的额外配置
完全不需要额外配置!.uriVariable的作用就是告诉Spring Integration:从当前Message的payload或headers里,用SpEL表达式提取对应的值,替换URI模板里的变量。只要你的payload(或headers)能提供对应的属性/键,直接写SpEL表达式就行——比如针对Map用payload.code或payload['code'],针对自定义对象用payload.code都可以。
为什么你原来的写法不生效?
你之前写的payloadExpression("#pathVariables.code" + ',' + "#pathVariables.icd10")犯了一个小错误:Java会先把字符串拼接成"#pathVariables.code,#pathVariables.icd10",然后SpEL解析器会把整个字符串当作字面量处理,最终payload变成了类似"ABC123,Z99.8"的纯字符串,而不是包含两个变量的结构化数据。下游的.uriVariable("code", "payload")只能拿到这个拼接后的字符串,自然没法正确传递参数。
内容的提问来源于stack exchange,提问作者Nick Stepka

