on 2022 Aug 01 3:57 AM
Hello SAP developers,
So the problem I am trying to solve involves connecting to MS Graph API in ABAP (cloud foundry) where the classes are slightly different to normal on-premise systems.
I can connect to open APIs in ABAP cloud that don't require authentication, many examples online of this, however not what I need.
How do you connect using refresh tokens and client secret using abap cloud, and finally display the payload in a z-table? Do you use destinations or is it better to set it all manually in the abap class/program?
I have already been through the following;
OAuth Credentials
https://help.sap.com/docs/CP_CONNECTIVITY/cca91383641e40ffbe03bdc78f00f681/4e1d742a3d45472d83b411e14...
Destination connection in abap cloud from BTP
https://developers.sap.com/tutorials/abap-environment-external-api.html#237e1bf4-668e-4c95-871e-4258...
SAP BTP and Azure integration
https://blogs.sap.com/2021/07/08/sap-btp-integration-with-microsoft-azure/
Connect MS Graph to Destination in BTP
https://blogs.sap.com/2020/10/12/consuming-microsoft-365-api-in-the-cloud-application-programming-ca...
Consume REST API in ABAP Cloud
https://blogs.sap.com/2020/10/27/consuming-rest-apis-with-cloud-abap/
Also, this connection in POSTMAN works fine, can see the payload no worries and all the data I need. So from the Azure side it is set-up fine.
Thanks so much,
Paul
Request clarification before answering.
Hi Paul,
I don't get why you try to implement your own OAuth client. Haven't you tried the HTTP Communication via Destination Service (Deprecated)? Even if it's deprecated it seems to be the solution working out of the box. Please use this destination template: MicrosoftGraph, adjust it with your Tenant and Client ID. Then import it into your BTP Subaccount where the ABAP Environment is provisioned to. I've tried that in my Free Tier ABAP Environment. Not sure if it would work in BTP Trial.
Then try this Code:
CLASS zcl_ms_graph DEFINITION
PUBLIC
FINAL
CREATE PUBLIC .
PUBLIC SECTION.
INTERFACES if_oo_adt_classrun.
PROTECTED SECTION.
PRIVATE SECTION.
ENDCLASS.
CLASS zcl_ms_graph IMPLEMENTATION.
METHOD if_oo_adt_classrun~main.
DATA lo_http_destination TYPE REF TO if_http_destination.
DATA lo_http_client TYPE REF TO if_web_http_client.
DATA lo_http_response TYPE REF TO if_web_http_response.
TRY.
" create HTTP destination by cloud destination
lo_http_destination = cl_http_destination_provider=>create_by_cloud_destination(
i_name = 'MSGraph'
i_authn_mode = if_a4c_cp_service=>service_specific ).
" create HTTP client by HTTP destination
lo_http_client = cl_web_http_client_manager=>create_by_http_destination( lo_http_destination ).
" adding header fields
lo_http_client->get_http_request( )->set_header_fields(
VALUE #( ( name = if_web_http_header=>content_type value = if_web_http_header=>accept_application_json )
( name = if_web_http_header=>accept value = if_web_http_header=>accept_application_json ) ) ).
" request users - would be great if the path would be added to the URL provided in the service
lo_http_client->get_http_request( )->set_uri_path(
i_uri_path = '/beta/6f8c8b13-6c5b-42e2-8a42-e4ef99e7ff48/users' ).
" execute HTTP GET-request and store response
lo_http_response = lo_http_client->execute( if_web_http_client=>get ).
" print response text to console
DATA(ls_status) = lo_http_response->get_status( ).
out->write( |Response is: { ls_status-code } { ls_status-reason }.| ).
out->write( lo_http_response->get_text( ) ).
CATCH cx_http_dest_provider_error cx_web_http_client_error INTO DATA(lx_error).
" display error details
out->write( lx_error->get_text( ) ).
ENDTRY.
ENDMETHOD.
ENDCLASS.
The output I've got in the console was:
Response is: 200 OK.
{"@odata.context":"https://graph.microsoft.com/beta/$metadata#users","value":[{"id":"b6815529
Two Question to florian.wahl:
Best Regards
Gregor
You must be a registered user to add a comment. If you've already registered, sign in. Otherwise, register and sign in.
Thanks Gregor,
This was an excellent response and fixed our issue. The oData is coming through now with a 200 success code, the problem was in our destination set up. This was why I originally abandoned it and tried to hard code in all in abap steampunk.
Turns out our destination had some sort of bug in it. Even though we set it up identical to yours, one of the errors I was getting in the console was that the Token Service URL Type was not set to dedicated. Even though it was. I exported the destination config and compared it to yours and could see the difference. I then remade a new destination importing your one from github, changed the clientID and secret etc. works perfectly!
thanks so much
So the problem is connecting from Steampunk, right? I have not tried this yet, but since you are saying the calls are working from Postman you have already figured out all the steps for the "authentication dance".
Can you share more insights on where you are facing the problems? Are some of your HTTP calls going through? Are you able to connect to any other external API that requires authentication?
- Holger.
You must be a registered user to add a comment. If you've already registered, sign in. Otherwise, register and sign in.
Hi Holger,
thanks for replying. So today I managed to get some success however I am having trouble getting the access token into a variable that I can use for the actual header request to MS Graph and get the data I need.
I am doing 2 calls, one for the token, then one to use that token to get the data. I have moved away from BTP destinations and instead am hard coding a destination in steampunk using if_web_http_client and then setting the header and form-fields using variables from postman.
See screen shots, first 2 are from postman where I can get the access token fine with the 4 main form values (clientID, clientSecret grant-type and scope). I can call this as many times as I like and I get a new token. Also, the second screenshot shows that the token will work successfully to get the data I need. Again, this is in postman and I need this to be done in steampunk.
I do get a 200 code return in my abap console output when I use if_web_http_client->get_headers() however the if_web_http_client->get_text() does not show the token, therefore I cannot use the response for the next call in the header to get the actual data I need.
This is where I am stuck?
Token GET in postman - working.
GET user entity request in postman - working
I haven't noticed that you're using Steampunk in my initial response. Have you tried to follow HTTP Communication via Communication Arrangements?
You must be a registered user to add a comment. If you've already registered, sign in. Otherwise, register and sign in.
Yes, funny you mention that, we are currently looking through that option now to see if it helps with making the API call in cloud-foundry. Will update here if we have any success.
I guess another option is to use on-premise to do the API calling to MSGraph, then use cloud connector to link up with our steampunk environment?
Are you aware of the ABAP SDK for Azure?
You must be a registered user to add a comment. If you've already registered, sign in. Otherwise, register and sign in.
Hi Gregor,
Yes, I have looked through your posts on this topic, we didn't pursue as it looked like you needed the SAP GUI. Do you know if there is a way to use ABAP SDK for Azure using the Cloud BTP?
We will try the SDK on our 2020 on premise system to see how it goes but our deployment is in the cloud foundry. Otherwise SDK would have been perfect for us.
Unless I am missing something?
User | Count |
---|---|
72 | |
30 | |
8 | |
7 | |
6 | |
6 | |
6 | |
4 | |
4 | |
4 |
You must be a registered user to add a comment. If you've already registered, sign in. Otherwise, register and sign in.