话不多说,先上代码
*&---------------------------------------------------------------------*
*& Report ZWEBAPI_TEST
*&
*&---------------------------------------------------------------------*
*&
*&
*&---------------------------------------------------------------------*
REPORT ZWEBAPI_TEST.
DATA: gv_service TYPE string,
gr_http_client TYPE REF TO if_http_client,
gv_json_send TYPE string,
gv_json_receive TYPE string.
DATA:lv_sign TYPE string,
lv_timestep TYPE string,
Pv_subrc TYPE sy-subrc,
Pv_message TYPE string.
"复制后只要修改这个对方系统提供的接口地址和接口json/XML参数即可
gv_service = 'http://192.168.254.191:1029/api/dataportal/invoke' .
gv_json_send = '{"ApiType":"SmomWebApiController","Parameters":[{"Value":[{"UnitCode":null,"SpecificationModel":null,"Sta ' &&
'te":0,"Description":null,"DrawingNo":null,"Version":null,"BaseModel":null,"Person":null,"MrpPerson":null,"UpperWeight":0.0,' &&
'LowerWeight":0.0,"MinPackingQty":null,"EnglishDescription":null,"ShortDescription":null,"Len' &&
'gth":null,"Width":null,"Height":null,"Volume":null,"Weight":null,"PurchasingAgent":null,"Precision":null,"GoodsB' &&
'arcode":null,"Type":0,"CategoryCode":null,' &&
'"IsVirtualPart":null,"InvOrgId":0,"ItemSourceType":null,"ProductFamilyId":0,"PurchasingGroupId":0,"UnitId":null,"Erp' &&
'Key":null,"Code":null,"Name":null,"Infkey":null,"IsDelete":false,"LastUp' &&
'dateDate":"0001-01-01T00:00:00+08:00"}]},{"Value":1}],' &&
'"Method":"SaveItems","Context":{"InvOrgId":1}}' .
"通过esb给的服务地址创建http客户端
CALL METHOD cl_http_client=>create_by_url
EXPORTING
url = gv_service
IMPORTING
client = gr_http_client
EXCEPTIONS
argument_not_found = 1
plugin_not_active = 2
internal_error = 3
OTHERS = 4.
gr_http_client->request->set_content_type( content_type = 'application/json; charset=utf-8' ).
gr_http_client->request->set_method( if_http_request=>co_request_method_post ).
"设置待传输内容
DATA:lv_len TYPE i."发送报文长度
lv_len = strlen( gv_json_send ).
CALL METHOD gr_http_client->request->set_cdata
EXPORTING
data = gv_json_send
offset = 0
length = lv_len.
"发送
CALL METHOD gr_http_client->send
EXCEPTIONS
http_communication_failure = 1
http_invalid_state = 2.
"接收
CALL METHOD gr_http_client->receive
EXCEPTIONS
http_communication_failure = 1
http_invalid_state = 2
http_processing_failed = 3.
IF sy-subrc NE 0.
pv_subrc = sy-subrc.
CALL METHOD gr_http_client->get_last_error
IMPORTING
code = pv_subrc
message = pv_message.
" CALL METHOD gr_http_client->close.
ENDIF.
"提取返回字符串
CLEAR gv_json_receive.
gv_json_receive = gr_http_client->response->get_cdata( ).
"关闭http服务
CALL METHOD gr_http_client->close.
WRITE : pv_message .
WRITE : gv_json_receive .
基本框架如下,只要修改外部系统的通讯地址gv_service和传输的json字符串gv_json_send就好了
同时,分享三种构造json字符串的方式
1.调用类cl_trex_json_serializer 的方法serialize。代码如下
data: json_ser type ref to cl_trex_json_serializer.
create object json_ser
exporting
data = GS_JSON_SEND.
call method json_ser->serialize.
call method json_ser->get_data
receiving
rval = GV_JSON_SEND.
GS_JSON_SEND是一个结构,按照外部系统的结构定义,然后赋值,赋值后用该方法转换得到GV_JSON_SEND就是json字符串,由于转换出来的字段名都是小写,后续还需要转换,这个方法不太好用,不建议使用
2.调用类/UI2/CL_JSON 的方法SERIALIZE。代码如下
gv_json_send = /ui2/cl_json=>serialize( data = ls_data
compress = abap_true
pretty_name = /ui2/cl_json=>pretty_mode-camel_case ).
这样和方法1一样转换后也需要调整格式,而且低版本sap系统没有该类
3.自定义宏,自己构造JSON,同样给出参考代码如下,这个大家可以根据自己的特点情况修改
宏定义
DEFINE %BUILD_JSON. "自动转json字符串的类不适用,自己利用宏来转json
GV_TXT = &5 .
IF &7 = 'X'. "是否带引号
GV_TXT = '"' && GV_TXT && '"' .
ENDIF.
&1 = &1 && &2 && &3 && &4 && GV_TXT && &6.
END-OF-DEFINITION.
构造调用
FORM FRM_BUILE_PO_JSON .
DATA LV_MENGE TYPE P LENGTH 16 DECIMALS 3 .
CLEAR:GV_JSON_SEND .
%BUILD_JSON GV_JSON_SEND '{"ApiType": "SmomWebApiController","Parameters": [{"Value": [{' '' '' '' '' '' .
%BUILD_JSON GV_JSON_SEND '' '"No"' ':' GS_EKKOH-EBELN ',' 'X' .
%BUILD_JSON GV_JSON_SEND '' '"BillDate"' ':' GS_EKKOH-BillDate ',' 'X' .
%BUILD_JSON GV_JSON_SEND '' '"BillerId"' ':' GS_EKKOH-ERNAM ',' 'X' .
%BUILD_JSON GV_JSON_SEND '' '"OrderType"' ':' '0' ',' '' .
%BUILD_JSON GV_JSON_SEND '' '"WarehouseCode"' ':' '"ARVI"' ',' '' .
%BUILD_JSON GV_JSON_SEND '' '"SupplierCode"' ':' GS_EKKOH-LIFNR ',' 'X' .
%BUILD_JSON GV_JSON_SEND '' '"Contacts"' ':' 'null' ',' '' .
%BUILD_JSON GV_JSON_SEND '' '"ContactNumber"' ':' 'null' ',' '' .
* %BUILD_JSON GV_JSON_SEND '' '"IsFreeze"' ':' GS_EKKOH-ISFREEZE ',' '' .
%BUILD_JSON GV_JSON_SEND '' '"DetailList"' ':' '[{' '' '' . "行项目数据开始
LOOP AT GT_EKKO INTO GS_EKKO .
IF SY-TABIX <> 1.
%BUILD_JSON GV_JSON_SEND ',{' '' '' '' '' '' . "如果行项目有多行,从第二行开始用逗号隔开并用大括号开始
ENDIF.
%BUILD_JSON GV_JSON_SEND '' '"PoNo"' ':' 'null' ',' '' .
%BUILD_JSON GV_JSON_SEND '' '"LineNo"' ':' GS_EKKO-EBELP ',' 'X' .
IF GS_EKKO-MATNR IS INITIAL.
GS_EKKO-MATNR = 'XN001' .
ENDIF.
%BUILD_JSON GV_JSON_SEND '' '"ItemCode"' ':' GS_EKKO-MATNR ',' 'X' .
LV_MENGE = GS_EKKO-PEINH * GS_EKKO-MENGE .
%BUILD_JSON GV_JSON_SEND '' '"Quantity"' ':' GS_EKKO-MENGE ',' '' .
%BUILD_JSON GV_JSON_SEND '' '"UnitPrice"' ':' GS_EKKO-NETWR ',' '' .
%BUILD_JSON GV_JSON_SEND '' '"DeliveryDate"' ':' GS_EKKO-DeliveryDate ',' 'X' .
%BUILD_JSON GV_JSON_SEND '' '"UnitCode"' ':' 'null' ',' '' .
%BUILD_JSON GV_JSON_SEND '' '"IsFreeze"' ':' GS_EKKO-ISFREEZEP ',' '' .
CLEAR:GV_STR . GV_STR = GS_EKKO-TXZ01 .
PERFORM FRM_Remove_special_characters CHANGING GV_STR . "转译特殊字符串
%BUILD_JSON GV_JSON_SEND '' '"Remark"' ':' GV_STR ',' 'X' .
%BUILD_JSON GV_JSON_SEND '' '"EkknKostl"' ':' GS_EKKO-KOSTL ',' 'X' .
%BUILD_JSON GV_JSON_SEND '' '"EkknWempf"' ':' GS_EKKO-WEMPF ',' 'X' .
%BUILD_JSON GV_JSON_SEND '' '"EkpoKnttp"' ':' GS_EKKO-KNTTP ',' 'X' .
%BUILD_JSON GV_JSON_SEND '' '"ErpKey"' ':' 'null' ',' '' .
%BUILD_JSON GV_JSON_SEND '' '"Code"' ':' 'null' ',' '' .
%BUILD_JSON GV_JSON_SEND '' '"Name"' ':' 'null' ',' '' .
%BUILD_JSON GV_JSON_SEND '' '"Infkey"' ':' 'null' ',' '' .
%BUILD_JSON GV_JSON_SEND '' '"IsDelete"' ':' GS_EKKO-IsDelteP ',' '' .
%BUILD_JSON GV_JSON_SEND '' '"LastUpdateDate"' ':' '0001-01-01T00:00:00+08:00' '}' 'X' .
ENDLOOP.
%BUILD_JSON GV_JSON_SEND '],' '' '' '' '' '' . "行项目数据结束
%BUILD_JSON GV_JSON_SEND '' '"ErpKey"' ':' 'null' ',' '' .
%BUILD_JSON GV_JSON_SEND '' '"Code"' ':' 'null' ',' '' .
%BUILD_JSON GV_JSON_SEND '' '"Name"' ':' 'null' ',' '' .
%BUILD_JSON GV_JSON_SEND '' '"Infkey"' ':' 'null' ',' '' .
* %BUILD_JSON GV_JSON_SEND '' '"IsDelete"' ':' GS_EKKOH-IsDelte ',' '' .
%BUILD_JSON GV_JSON_SEND '' '"LastUpdateDate"' ':' '0001-01-01T00:00:00+08:00' ',' 'X' .
%BUILD_JSON GV_JSON_SEND '' '"Plant"' ':' GS_EKKOH-WERKS '' 'X' .
%BUILD_JSON GV_JSON_SEND '}]},{"Value": 1}],"Method": "SavePurchaseOrders","Context": {"InvOrgId": 1}}' '' '' '' '' '' .
* CONDENSE GV_JSON_SEND NO-GAPS .
GS_JSON-JSON = GV_JSON_SEND .
APPEND GS_JSON TO GT_JSON .
ENDFORM .
我最推荐第三种方法,再外部系统给出要求明确的情况下,这样更快
最好分享我常用的字符串转换未JSON的网站JSON在线校验格式化工具(Be JSON)