2017 Dec 12 9:52 PM
Hi Folks,
I am calling a REST API from ABAP code. I am able to get the HTTP response. But the response from REST API is coming in JSON format. Is there a way to convert the JSON response which has nested deep structures to ABAP Internal table?
I need to convert it to ABAP table to loop across the information before processing it.
Regards,
Narayan
2017 Dec 12 10:12 PM
Hi Narayan,
SAP has an API class CL_FDT_JSON which allows to convert the JSON response to ABAP structure. I noticed this class is better than /UI2/CL_JSON. The CL_FDT_JSON converts the deep table structure without field names and just values as well to ABAP structure. Had to use CL_REST_HTTP_CLIENT to obtain the string information from REST API.
Note: The ABAP SE11 structure should exactly match the JSON response received from the REST API. Only then the conversion works.
I have attached a sample code below which was used by me to achieve the JSON to ABAP conversion.
* Declarations
DATA lo_client TYPE REF TO if_http_client.
DATA lo_conv TYPE REF TO cl_abap_conv_in_ce.
DATA lo_rest_client TYPE REF TO cl_rest_http_client.
DATA lo_response TYPE REF TO if_rest_entity.
DATA lv_result_url TYPE string.
DATA lv_url TYPE string.
DATA lv_json TYPE string.
DATA lv_response TYPE string.
DATA lv_httpcode TYPE i.
DATA lv_reason TYPE string.
DATA lv_message TYPE string.
DATA lv_index TYPE i.
DATA lt_data_json TYPE zxyz_geocode_response. "Exact structure of JSON response created in SE11
DATA response TYPE string.
CALL METHOD cl_http_client=>create_by_destination
EXPORTING
destination = 'ZXYZ_GEOCODE'
IMPORTING
client = lo_client
EXCEPTIONS
argument_not_found = 1
destination_not_found = 2
destination_no_authority = 3
plugin_not_active = 4
internal_error = 5
OTHERS = 6.
IF sy-subrc <> 0.
ENDIF.
IF lo_client IS BOUND.
lo_client->request->set_method( if_http_request=>co_request_method_get ).
* Construct the URL
CONCATENATE '?housenumber=' im_address-house_num1
'&street=' im_address-street
'&city=' im_address-city1
'&postalcode=' im_address-post_code1
'&state=' im_address-region
'&country=' im_address-country
INTO lv_result_url.
* Set URL to request
cl_http_utility=>set_request_uri( request = lo_client->request uri = lv_result_url ).
* Send the HTTP request
CALL METHOD lo_client->send
EXCEPTIONS
http_communication_failure = 1
http_invalid_state = 2
http_processing_failed = 3
http_invalid_timeout = 4
OTHERS = 5.
IF sy-subrc <> 0.
ENDIF.
* HTTP call receive
CALL METHOD lo_client->receive
EXCEPTIONS
http_communication_failure = 1
http_invalid_state = 2
http_processing_failed = 3
OTHERS = 4.
IF sy-subrc <> 0.
ENDIF.
* get status of the response
CALL METHOD lo_client->response->get_status
IMPORTING
code = lv_httpcode
reason = lv_reason.
* Instantiate REST client
CREATE OBJECT lo_rest_client
EXPORTING
io_http_client = lo_client.
* Get Response data
lo_response = lo_rest_client->if_rest_client~get_response_entity( ).
* Get string data
response = lo_response->get_string_data( ).
* Convert string to Abap structures (better than /UI2/CL_JSON, converts even tables without field names and just values)
CALL METHOD cl_fdt_json=>json_to_data
EXPORTING
iv_json = response
CHANGING
ca_data = lt_data_json.
CALL METHOD lo_client->close
EXCEPTIONS
http_invalid_state = 1
OTHERS = 2.
IF sy-subrc <> 0.
ENDIF.
ENDIF.
Joseph M
2022 Feb 24 9:15 AM
It does converts a json string into abap internal table. but it is skipping any blank space inside the values. I need to process the name.
TYPES: BEGIN OF ty_result,
status TYPE string,
vpa TYPE string,
isvpavalid TYPE i,
payeraccountname TYPE string,
END OF ty_result.
DATA: it_result type TABLE OF ty_result,
wa_result TYPE ty_result.
data: result TYPE string.
result = '{"status":"SUCCESS FUL","vpa":"","isVpaValid" = "0", "payerAccountName":"FRANCIS CASIMIR S"}'.
CALL METHOD cl_fdt_json=>json_to_data
EXPORTING
iv_json = result
CHANGING
ca_data = wa_result.
Need Immedeiate assistance here.
2017 Dec 13 5:52 AM