最近项目要调用第三方接口来获取json数据,并解析数据入库。这里用到了kettle作为数据抽取工具。Kettle 除了常规的数据处理之外,还可以模拟发送HTTP client/post ,REST client。

这里顺便讲一下这三个组件的区别之处,省的下次绕迷糊。
1.HTTP Post组件
”post“顾名思义应该就是http请求方式为post,这里查看源码也得到证实,是引入的org.apache.commons.httpclient.methods里面的方法。
try {
if ( isDetailed() ) {
logDetailed( BaseMessages.getString( PKG, "HTTPPOST.Log.ConnectingToURL", data.realUrl ) );
}
HttpClient httpPostClient = SlaveConnectionManager.getInstance().createHttpClient();
PostMethod post = new PostMethod( data.realUrl );

下面我用代码模拟了一个get方式的请求,在kettle中使用该组件调用该请求,未获取到结果集。返回结果中提示“系统发生异常”,可想而知,该组件并不支持get方式的请求。(这里顺便提示一下,由于HTTP Client和Post都是查询菜单里的组件,并不是输入流组件,所以使用该组件前面必须要配合输入流的组件使用,否则执行的时候,由于你并没有输入流传入,所以程序自动判断你的转换没有源数据流入,自动结束运行,程序会自动退出,不会执行后面的流程。所以,要切记,使用该组件之前一定要有输入组件,可以将url或者请求参数作为输入流)。
@RequestMapping(value = "/infoTrans", method = GET, produces = "application/json")
public Object infoTrans(HttpServletRequest request, HttpServletResponse response) throws IOException {
String attribute = (String)request.getAttribute("p2");
result = "{\r\n" +
"\"BasicResponse\": {\r\n" +
"\"succeeded\": 1\r\n" +
"},\r\n" +
"\"RTDataSets\": [\r\n" +
"{\r\n" +
"\"kksCode\": \"EB002HP4MKA01MK001BN01J1CB001BB02\",\r\n" +
"\"RTDataValues\": [\r\n" +
"{\r\n" +
"\"Value\": 5.5944,\r\n" +
"\"Time\": 1446184512000\r\n" +
"},\r\n" +
"{\r\n" +
"}\r\n" +
"]\r\n" +
"}";
return result;
}
 

所以。使用该组件的时候,一定要知道你请求的接口请求方式是什么类型的。接下来,那你一定会问,如果HTTP Post是请求Post方式的,那Get方式的怎么请求呢,没错,就是Http Client组件了,不知道官方为什么把组件名命名为这样,而不是叫做HTTP Get,可能命名不好听吧....额,反正我是圆不下去了,管他呢,everything 有毒....,然后我用Client组件请求该接口,ok,一切顺利。

接下来,讲一讲剩下的那两个组件,REST Client和Json数据解析,REST Client是针对RestFul风格的http请求获取其数据的,这里你可以支持多种请求方式,如Post,Get,Put,Delete等。这一个组件等同于前两个组件的集合吧。http post 和 http Client 这两个都可以利用Rest Client来替代。下面来说说Rest Client 怎么使用:



这样就完成了调用接口获取token值了。
还有一个说明一下:

一、对于json数据的解析
简介
- JSONPath - 是xpath在json的应用。
类似于XPath在xml文档中的定位,JsonPath表达式通常是用来路径检索或设置Json的。其表达式可以接受“dot–notation”和“bracket–notation”格式,例如$.store.book[0].title、$[‘store’][‘book’][0][‘title’]
- JSONPaht 用一个抽象的名字$来表示最外层对象。
- 使用.符号:$.store.book[0].title
- 使用[]:$['store']['book'][0]['title']
- 数组索引
1)JSONPath 允许使用通配符 * 表示所以的子元素名和数组索引。还允许使用 '..' 从E4X参照过来的和数组切分语法[start:end:step]
2 ) $.store.book[(@.length-1)].title
3)使用'@'符号表示当前的对象,?(<判断表达式>) 使用逻辑表达式来过滤
$.store.book[?(@.price < 10)].title
二、JSONPath语法元素和对应XPath元素的对比
XPath
|
JSONPath
|
Description
|
/
|
$
|
表示根元素
|
.
|
@
|
当前元素
|
/
|
. or []
|
子元素
|
..
|
n/a
|
父元素
|
//
|
..
|
递归下降,JSONPath是从E4X借鉴的。
|
*
|
*
|
通配符,表示所有的元素
|
@
|
n/a
|
属性访问字符
|
[]
|
[]
|
子元素操作符
|
|
|
[,]
|
连接操作符在XPath 结果合并其它结点集合。JSONP允许name或者数组索引。
|
n/a
|
[start:end:step]
|
数组分割操作从ES4借鉴。
|
[]
|
?()
|
应用过滤表示式
|
n/a
|
()
|
脚本表达式,使用在脚本引擎下面。
|
()
|
n/a
|
Xpath分组
|
三、jsonpath使用举例
接口返回:
- [{
- "id": "PRIMARY",
- "name": "小学",
- "front_id": "PRIMARY",
- "front_name": "小学"
- }, {
- "id": "JUNIOR",
- "name": "初中",
- "front_id": "JUNIOR",
- "front_name": "初中"
- }, {
- "id": "HIGH",
- "name": "高中",
- "front_id": "HIGH",
- "front_name": "高中"
- }, {
- "id": "TECHNICAL",
- "name": "中专/技校",
- "front_id": "TECHNICAL",
- "front_name": "中专/技校"
- }, {
- "id": "COLLEGE",
- "name": "大专",
- "front_id": "COLLEGE",
- "front_name": "大专"
- }, {
- "id": "BACHELOR",
- "name": "本科",
- "front_id": "BACHELOR",
- "front_name": "本科"
- }, {
- "id": "MASTER",
- "name": "硕士",
- "front_id": "MASTER",
- "front_name": "硕士"
- }, {
- "id": "DOCTOR",
- "name": "博士",
- "front_id": "DOCTOR",
- "front_name": "博士"
- }]
|
JSONPath
|
结果
|
|
$.[*].name
|
所有学历的name
|
|
$.[*].id
|
所有的id
|
|
$.[*]
|
所有元素
|
|
$.[(@.length-2)].name
|
倒数第二个元素的name
|
|
$.[2]
|
第三个元素
|
|
$.[(@.length-1)]
|
最后一个元素
|
|
$.[0,1]
$.[:2]
|
前面的两个元素
|
|
$.[? (@.name =~ /.*中/i)]
|
过滤出所有的name包含“中”的书。
|
|
$..book[?(@.price<10)]
|
过滤出价格低于10的书。
|
|
$.[*]. length()
|
所有元素的个数
|
接口返回:
- {
- "store": {
- "book": [
- {
- "category": "reference",
- "author": "Nigel Rees",
- "title": "Sayings of the Century",
- "price": 8.95
- },
- {
- "category": "fiction",
- "author": "Evelyn Waugh",
- "title": "Sword of Honour",
- "price": 12.99
- },
- {
- "category": "fiction",
- "author": "Herman Melville",
- "title": "Moby Dick",
- "isbn": "0-553-21311-3",
- "price": 8.99
- },
- {
- "category": "fiction",
- "author": "J. R. R. Tolkien",
- "title": "The Lord of the Rings",
- "isbn": "0-395-19395-8",
- "price": 22.99
- }
- ],
- "bicycle": {
- "color": "red",
- "price": 19.95
- }
- },
- "expensive": 10
- }
JsonPath表达式
|
结果
|
$.store.book[*].author
或
$..author
|
[
“Nigel Rees”,
“Evelyn Waugh”,
“Herman Melville”,
“J. R. R. Tolkien”
]
|
$.store.* 显示所有叶子节点值
|
[
[
{
”category” : “reference”,
”author” : “Nigel Rees”,
”title” : “Sayings of the Century”,
”price” : 8.95
},
{
”category” : “fiction”,
”author” : “Evelyn Waugh”,
”title” : “Sword of Honour”,
”price” : 12.99
},
{
”category” : “fiction”,
”author” : “Herman Melville”,
”title” : “Moby Dick”,
”isbn” : “0-553-21311-3”,
”price” : 8.99
},
{
”category” : “fiction”,
”author” : “J. R. R. Tolkien”,
”title” : “The Lord of the Rings”,
”isbn” : “0-395-19395-8”,
”price” : 22.99
}
],
{
”color” : “red”,
”price” : 19.95
}
]
|
$.store..price
|
[
8.95,
12.99,
8.99,
22.99,
19.95
]
|
$..book[0,1]
或
$..book[:2]
|
[
{
”category” : “reference”,
”author” : “Nigel Rees”,
”title” : “Sayings of the Century”,
”price” : 8.95
},
{
”category” : “fiction”,
”author” : “Evelyn Waugh”,
”title” : “Sword of Honour”,
”price” : 12.99
}
]
|
$..book[-2:]
|
获取最后两本书
|
$..book[2:]
|
[
{
”category” : “fiction”,
”author” : “Herman Melville”,
”title” : “Moby Dick”,
”isbn” : “0-553-21311-3”,
”price” : 8.99
},
{
”category” : “fiction”,
”author” : “J. R. R. Tolkien”,
”title” : “The Lord of the Rings”,
”isbn” : “0-395-19395-8”,
”price” : 22.99
}
]
|
$..book[?(@.isbn)]
|
所有具有isbn属性的书
|
$.store.book[?(@.price < 10)]
|
所有价格小于10的书
|
$..book[?(@.price <= $[‘expensive’])]
|
所有价格低于expensive字段的书
|
$..book[?(@.author =~ /.*REES/i)]
|
所有符合正则表达式的书
[
{
”category” : “reference”,
”author” : “Nigel Rees”,
”title” : “Sayings of the Century”,
”price” : 8.95
}
]
|
$..*
|
返回所有
|
$..book.length()
|
[
4
]
|
四、过滤器
操作符
|
描述
|
==
|
等于符号,但数字1不等于字符1(note that 1 is not equal to ‘1’)
|
!=
|
不等于符号
|
<
|
小于符号
|
<=
|
小于等于符号
|
>
|
大于符号
|
>=
|
大于等于符号
|
=~
|
判断是否符合正则表达式,例如[?(@.name =~ /foo.*?/i)]
|
in
|
所属符号,例如[?(@.size in [‘S’, ‘M’])]
|
nin
|
排除符号
|
size
|
size of left (array or string) should match right
|
empty
|
判空符号
|
例如:
1)所有具有isbn属性的书
$.store.book[?(@.isbn)].author
2)所有价格大于10的书
$.store.book[?(@.price > 10)]
3)查询xxx==3的所有对象
$.result.list[?(@.xxx ==3)]
4)可以自定义过滤器来获取想要的任何元素,可以多条件查询
五、在线解析器
http://jsonpath.com/
https://jsonpath.curiousconcept.com/
在这里,你可以将你的json格式的数据拷贝上去,自己手动写表达式解析查看。
|