如何在 WSO2 ESB 中操作原生 Json?
How to manipulate native Json in WSO2 ESB?
我正在尝试在 json-request-reply 场景中为 REST-API 操作数据。
为了简化我的问题,假设我想用负载中的 'd' 替换所有 'b' 个字符。
有没有办法让我在本地处理 json 数据,而不是先将数据转换为 XML?
我正在尝试构建自定义 class 调解器以放入我的 OutSequence,但由于我只能访问将有效负载视为 XML 的 MessageContext,我 运行 遇到问题。
问题是 json 无法与 XML 相互转换。
它的结构中有这个部分:
"Destination": {
"name": "abc",
"type": "ST",
"$": "\n"
}
“$”属性 有效 json,但由于 WSO2 ESB 始终在其 MessageContext 中将数据处理为 XML,因此它无法转换 属性显然要标记,所以每当我这样做时
MessageContext.getEnvelope().getBody()
在我的 class 调解器中,响应是:
<Destination>
<name>abc</name>
<type>ST</type>
</Destination>
缺少 $属性。
我正在使用消息生成器:org.apache.synapse.commons.json.JsonStreamBuilder 和格式化程序:org.apache.synapse.commons.json.JsonStreamFormatter
正常情况下要通过内容(否则会在XML到JSON处理步骤中失败)。但是我必须有一种方法可以将数据作为本机 JSON(或作为本机字符串?)进行操作,也许能够获取 InputStream 并从中操作数据?但是我找不到从消息上下文访问 InputStream 的方法?
事实证明,WSO2 本身已经编写了处理 $-characters 的逻辑。
来自他们的支持文档 (https://docs.wso2.com/display/ESB481/JSON+Support):
When building XML elements, the ESB handles the ‘$’ character and
digits in a special manner when they appear as the first character of
a JSON key.
$ 字符在 XML 表示中被替换为“_JsonReader_PS_”。但是,我查看了这方面的代码(喜欢开源),这是处理这种情况的代码:
// "$a" replace with "_JsonReader_PS_a"
private String replaceInvalidCharacters(String keyString){
if(Pattern.compile("^[0-9]").matcher(keyString).find()) {
return "_JsonReader_PD_" + keyString;
} else if (keyString.startsWith("$")){
return "_JsonReader_PS_" + keyString.substring(1);
} else
return keyString;
}
如我们所见,代码假定 属性 将以 $ 字符开头并且至少有一个其他字符。在我们的例子中这不是真的,这就是为什么我们的代码失败并且 属性 是 "lost".
为了避免这种情况,我编写了一个自定义 JSONStreamBuilder 来替换实际 InputStream 中的所有 $-characters,以确保对话得到正确处理。
import java.io.BufferedReader;
import java.io.ByteArrayInputStream;
import java.io.IOException;
import java.io.InputStream;
import java.io.InputStreamReader;
import org.apache.axiom.om.OMElement;
import org.apache.axis2.AxisFault;
import org.apache.axis2.builder.Builder;
import org.apache.axis2.context.MessageContext;
import org.apache.commons.logging.Log;
import org.apache.commons.logging.LogFactory;
import org.apache.synapse.commons.json.JsonStreamBuilder;
/*
* As WSO2 JSON parser can't handle single $ properties when converting between JSON and XML
* This custom JSON Stream builder replaces all $ signs with the constant '_JsonReader_PS_',
* which the WSO2 parser treats as a $ sign when transforming.
*/
public class CustomJsonStreamBuilder implements Builder {
private static final Log logger = LogFactory.getLog(CustomJsonStreamBuilder.class.getName());
JsonStreamBuilder jsonStreamBuilder = new JsonStreamBuilder();
public OMElement processDocument(InputStream arg0, String arg1, MessageContext arg2) throws AxisFault {
logger.debug("Processing input stream for custom JSON stream builder");
BufferedReader br = null;
StringBuilder sb = new StringBuilder();
String line;
try {
br = new BufferedReader(new InputStreamReader(arg0));
while ((line = br.readLine()) != null) {
sb.append(line);
}
String input = sb.toString();
/*
* WSO2 JSON parser treats _JsonReader_PS_ as $ in JSON structure
*/
input = input.replace("$", "_JsonReader_PS_");
InputStream is = new ByteArrayInputStream(input.getBytes("utf-8"));
if (br != null) {
try {
br.close();
} catch (IOException e) {
e.printStackTrace();
}
}
return jsonStreamBuilder.processDocument(is, arg1, arg2);
} catch (Exception e) {
e.printStackTrace();
logger.error("Problem processing input stream for custom JSON stream builder", e);
}
return jsonStreamBuilder.processDocument(arg0, arg1, arg2);
}
}
在我替换了 axis2 配置中的 JSON 流构建器后,我可以愉快地对序列中的有效负载执行任何脚本技术并保留 $-character 属性.
我希望这对遇到与我相同问题的人有所帮助。
我正在尝试在 json-request-reply 场景中为 REST-API 操作数据。
为了简化我的问题,假设我想用负载中的 'd' 替换所有 'b' 个字符。
有没有办法让我在本地处理 json 数据,而不是先将数据转换为 XML?
我正在尝试构建自定义 class 调解器以放入我的 OutSequence,但由于我只能访问将有效负载视为 XML 的 MessageContext,我 运行 遇到问题。
问题是 json 无法与 XML 相互转换。
它的结构中有这个部分:
"Destination": {
"name": "abc",
"type": "ST",
"$": "\n"
}
“$”属性 有效 json,但由于 WSO2 ESB 始终在其 MessageContext 中将数据处理为 XML,因此它无法转换 属性显然要标记,所以每当我这样做时
MessageContext.getEnvelope().getBody()
在我的 class 调解器中,响应是:
<Destination>
<name>abc</name>
<type>ST</type>
</Destination>
缺少 $属性。
我正在使用消息生成器:org.apache.synapse.commons.json.JsonStreamBuilder 和格式化程序:org.apache.synapse.commons.json.JsonStreamFormatter
正常情况下要通过内容(否则会在XML到JSON处理步骤中失败)。但是我必须有一种方法可以将数据作为本机 JSON(或作为本机字符串?)进行操作,也许能够获取 InputStream 并从中操作数据?但是我找不到从消息上下文访问 InputStream 的方法?
事实证明,WSO2 本身已经编写了处理 $-characters 的逻辑。
来自他们的支持文档 (https://docs.wso2.com/display/ESB481/JSON+Support):
When building XML elements, the ESB handles the ‘$’ character and digits in a special manner when they appear as the first character of a JSON key.
$ 字符在 XML 表示中被替换为“_JsonReader_PS_”。但是,我查看了这方面的代码(喜欢开源),这是处理这种情况的代码:
// "$a" replace with "_JsonReader_PS_a"
private String replaceInvalidCharacters(String keyString){
if(Pattern.compile("^[0-9]").matcher(keyString).find()) {
return "_JsonReader_PD_" + keyString;
} else if (keyString.startsWith("$")){
return "_JsonReader_PS_" + keyString.substring(1);
} else
return keyString;
}
如我们所见,代码假定 属性 将以 $ 字符开头并且至少有一个其他字符。在我们的例子中这不是真的,这就是为什么我们的代码失败并且 属性 是 "lost".
为了避免这种情况,我编写了一个自定义 JSONStreamBuilder 来替换实际 InputStream 中的所有 $-characters,以确保对话得到正确处理。
import java.io.BufferedReader;
import java.io.ByteArrayInputStream;
import java.io.IOException;
import java.io.InputStream;
import java.io.InputStreamReader;
import org.apache.axiom.om.OMElement;
import org.apache.axis2.AxisFault;
import org.apache.axis2.builder.Builder;
import org.apache.axis2.context.MessageContext;
import org.apache.commons.logging.Log;
import org.apache.commons.logging.LogFactory;
import org.apache.synapse.commons.json.JsonStreamBuilder;
/*
* As WSO2 JSON parser can't handle single $ properties when converting between JSON and XML
* This custom JSON Stream builder replaces all $ signs with the constant '_JsonReader_PS_',
* which the WSO2 parser treats as a $ sign when transforming.
*/
public class CustomJsonStreamBuilder implements Builder {
private static final Log logger = LogFactory.getLog(CustomJsonStreamBuilder.class.getName());
JsonStreamBuilder jsonStreamBuilder = new JsonStreamBuilder();
public OMElement processDocument(InputStream arg0, String arg1, MessageContext arg2) throws AxisFault {
logger.debug("Processing input stream for custom JSON stream builder");
BufferedReader br = null;
StringBuilder sb = new StringBuilder();
String line;
try {
br = new BufferedReader(new InputStreamReader(arg0));
while ((line = br.readLine()) != null) {
sb.append(line);
}
String input = sb.toString();
/*
* WSO2 JSON parser treats _JsonReader_PS_ as $ in JSON structure
*/
input = input.replace("$", "_JsonReader_PS_");
InputStream is = new ByteArrayInputStream(input.getBytes("utf-8"));
if (br != null) {
try {
br.close();
} catch (IOException e) {
e.printStackTrace();
}
}
return jsonStreamBuilder.processDocument(is, arg1, arg2);
} catch (Exception e) {
e.printStackTrace();
logger.error("Problem processing input stream for custom JSON stream builder", e);
}
return jsonStreamBuilder.processDocument(arg0, arg1, arg2);
}
}
在我替换了 axis2 配置中的 JSON 流构建器后,我可以愉快地对序列中的有效负载执行任何脚本技术并保留 $-character 属性.
我希望这对遇到与我相同问题的人有所帮助。