use xbase to communicate with a rest API

Xbase++ 2.0 Build 554 or later
Post Reply
Message
Author
User avatar
PedroAlex
Posts: 229
Joined: Tue Feb 09, 2010 3:06 am

use xbase to communicate with a rest API

#1 Post by PedroAlex »

Hello!

I'm trying to communicate with a rest API.
I have no experience with this type of procedure.
I need to do this in xbase:

Code: Select all

Request:
1POST https://dcn-solution.saphety.com/Dcn.Sandbox.WebApi/api/Account/GetToken
2Content-Type: application/json
3
4{
5     "Username": "comercial@algarbytes.pt",
6     "Password": "ab917007041**"
7}
must get this response:

Code: Select all

Response:
1HTTP/1.1 200 OK
2Content-Type: application/json
3
4{
5     "CorrelationId": "58b6f620-6167-4506-aec7-df4de92ecfa1",
6     "IsValid": true,
7     "Errors": [],
8     "Data": "eyJhbGciOiJIUzI1NiIsInR5cCI6IkpXVCJ9.eyJuYW1laWQiOiJjb21lcmNpYWxAYWxnYXJieXRlcy5wdCIsInVuaXF1ZV9uYW1lIjoiY29tZXJjaWFsQGFsZ2FyYnl0ZXMucHQiLCJzeXN0ZW1fYWRtaW4iOiJGYWxzZSIsInNlc3Npb25faWQiOiJhODZkODdhOS1mZDA5LTRhNjktOGIyMC1mZTIwODYyYTY5OWIiLCJjcCI6ImNvbWVyY2lhbEBhbGdhcmJ5dGVzLnB0IiwicmwiOiJEZXZlbG9wZXIiLCJuYmYiOjE2NTcyMDgyMDgsImV4cCI6MTY1NzIzNzAwOCwiaWF0IjoxNjU3MjA4MTQ4LCJpc3MiOiJodHRwczovL3d3dy5zYXBoZXR5LmNvbS8iLCJhdWQiOiJodHRwczovL3d3dy5zYXBoZXR5LmNvbS9EY25TYW5kYm94In0.QX-Bc7Qfm4mmYCheZhyFvV9K0rQdy4yUs0JFJ0H6X0s"
9}
My xBase code is this. but it does not work. Someone with experience in this can help.

Code: Select all

Function Teste_SAPHETY()
LOCAL oPost
LOCAL cResult

// Process the SOAP request
oPost := HttpClient():new( "https://dcn-solution.saphety.com/Dcn.Sandbox.WebApi/api/Account/GetToken" )
oPost:httpRequest:setParameter( "Username", "comercial@algarbytes.pt" )
oPost:httpRequest:setParameter( "Password", "ab917007041**" )
oPost:httpRequest:setContentType("application/json")
oPost:httpRequest:setMethod( "POST" )
cResult := oPost:send()

Sleep(50)

IF oPost:getStatusCode() == 200
	Msgbox( "ok" )
Else
	MsgBox( "failed: " + oPost:httpResponse:statusText, 'Falhou!' )
Endif

IF oPost:getStatusCode() != 200
	IF oPost:getStatusCode() ==-1
    	MsgBox( Var2Char(oPost:getLastError()) + Chr(13) + Var2Char(oPost:getLastMessage()), "Non HTTP protocol error:" )
	ELSE
    	MsgBox( Var2Char(oPost:getLastError()) + Chr(13) + Var2Char(oPost:getLastMessage()), "HTTP protocol error:" )
	ENDIF
ENDIF

MsgBox( cResult, 'Token' )

RETURN NIL
Note :
the user and the pass are authentic to be able to test.
It is a test server.

any tips would be important
Pedro Alexandre

User avatar
rdonnay
Site Admin
Posts: 4722
Joined: Wed Jan 27, 2010 6:58 pm
Location: Boise, Idaho USA
Contact:

Re: use xbase to communicate with a rest API

#2 Post by rdonnay »

What response are you getting?
The eXpress train is coming - and it has more cars.

skiman
Posts: 1183
Joined: Thu Jan 28, 2010 1:22 am
Location: Sijsele, Belgium
Contact:

Re: use xbase to communicate with a rest API

#3 Post by skiman »

Hi,

You send the username and password as a parameter and not as a json in the body? Is this allowed by the server?

With most rest-API you need to send the username and password as a base64encoded string for basic authentication.

What tells the documentation of the rest-api about the authentication?
Best regards,

Chris.
www.aboservice.be

User avatar
PedroAlex
Posts: 229
Joined: Tue Feb 09, 2010 3:06 am

Re: use xbase to communicate with a rest API

#4 Post by PedroAlex »

rdonnay wrote: Thu Jul 07, 2022 11:24 am What response are you getting?
Error Code 400 - Bad request
"A Non-Empty Request is required!"
Pedro Alexandre

User avatar
PedroAlex
Posts: 229
Joined: Tue Feb 09, 2010 3:06 am

Re: use xbase to communicate with a rest API

#5 Post by PedroAlex »

skiman wrote: Fri Jul 08, 2022 12:25 am Hi,

You send the username and password as a parameter and not as a json in the body? Is this allowed by the server?

With most rest-API you need to send the username and password as a base64encoded string for basic authentication.

What tells the documentation of the rest-api about the authentication?
I made this change but it's the same

Code: Select all

oPost:httpRequest:setParameter( "Username", Bin2Base64("comercial@algarbytes.pt") )
oPost:httpRequest:setParameter( "Password", Bin2Base64("ab917007041**") )
I found this information:
https://dcn-solution.saphety.com/Dcn.Sa ... quest.html

Do you have any sample how build a request like this?
Pedro Alexandre

User avatar
PedroAlex
Posts: 229
Joined: Tue Feb 09, 2010 3:06 am

Re: use xbase to communicate with a rest API

#6 Post by PedroAlex »

I made these changes but I still don't get the first step.

Code: Select all

//============================================================================
Function Teste_SAPHETY()
LOCAL oPost
LOCAL cResult
LOCAL cFile := 'Token.txt'

payload = { {'Username', "comercial@algarbytes.pt"}, {'Password', "ab917007041**"} }

JS_User := Dc_Array2JS( payload )

// Process the SOAP request
oPost := HttpClient():new( "https://dcn-solution.saphety.com/Dcn.Sandbox.WebApi/api/Account/GetToken" )
oPost:httpRequest:setHeader( 'content-type', 'application/json' )
oPost:httpRequest:setContent( JS_User )
oPost:httpRequest:setContentType("application/json")
oPost:httpRequest:setMethod( "POST" )
cResult := oPost:send()

Sleep(50)


IF oPost:getStatusCode() == 200
	Msgbox( "ok" )
Else
	MsgBox( "failed Code: " + Var2Char(oPost:getStatusCode()) +', '+oPost:httpResponse:statusText, 'Falhou!' )
Endif

IF oPost:getStatusCode() != 200
	IF oPost:getStatusCode() ==-1
    	MsgBox( Var2Char(oPost:getLastError()) + Chr(13) + Var2Char(oPost:getLastMessage()), "Non HTTP protocol error:" )
	ELSE
    	MsgBox( Var2Char(oPost:getLastError()) + Chr(13) + Var2Char(oPost:getLastMessage()), "HTTP protocol error:" )
	ENDIF
ENDIF


set device to printer
set printer on
set printer to ( cFile )
set console off

? cResult

Set device to screen
Set printer off
Set printer to
Set console on

runshell( ( cFile ) , "notepad.exe" , .t. )
//MsgBox( cResult, 'Token' )

RETURN NIL

The server send this response:
{"type":"https://tools.ietf.org/html/rfc7231#sec ... itle":"One or more validation errors occurred.","status":400,"traceId":"|5db76691-429579d0f8520bb1.","errors":{"$":["The JSON value could not be converted to Dcn.Sandbox.Application.Contracts.Dto.Account.UsernameAndPasswordInputDto. Path: $ | LineNumber: 0 | BytePositionInLine: 1."]}}
Pedro Alexandre

skiman
Posts: 1183
Joined: Thu Jan 28, 2010 1:22 am
Location: Sijsele, Belgium
Contact:

Re: use xbase to communicate with a rest API

#7 Post by skiman »

Hi,

I didn't test this, but maybe the code below will work. You need to send the json string in the body. I don't know what the content of your JS_User is? Is this a string with the complete json string in it?

Code: Select all

Function Teste_SAPHETY()
LOCAL oPost
LOCAL cResult
LOCAL cFile := 'Token.txt'
Local cpayload = '{"Username":"comercial@algarbytes.pt", "Password": "ab917007041**"}'

// Process the SOAP request  -> REST API isn't a SOAP request!!!
oPost := HttpClient():new( "https://dcn-solution.saphety.com/Dcn.Sandbox.WebApi/api/Account/GetToken" )
// oPost:httpRequest:setHeader( 'content-type', 'application/json' )
oPost:httpRequest:setContent( cPayload)
oPost:httpRequest:setContentType("application/json")  
oPost:httpRequest:setMethod( "POST" )
cResult := oPost:send()
Best regards,

Chris.
www.aboservice.be

User avatar
rdonnay
Site Admin
Posts: 4722
Joined: Wed Jan 27, 2010 6:58 pm
Location: Boise, Idaho USA
Contact:

Re: use xbase to communicate with a rest API

#8 Post by rdonnay »

The response implies there is a problem with the username and password.

Sometimes, servers require that these values must be in the header.

oPost:httpRequest:setHeader( "Username", "comercial@algarbytes.pt" )
oPost:httpRequest:setHeader( "Password","ab917007041**" )
The eXpress train is coming - and it has more cars.

User avatar
PedroAlex
Posts: 229
Joined: Tue Feb 09, 2010 3:06 am

Re: use xbase to communicate with a rest API

#9 Post by PedroAlex »

Roger and Chris.

both are right: The username and password must be in the header and in JSON format
I will continue to try to find a solution.

Thanks!
Pedro Alexandre

Post Reply