Help needed with CURL/JSON

General Help regarding HMG, Compilation, Linking, Samples

Moderator: Rathinagiri

Post Reply
User avatar
serge_girard
Posts: 2139
Joined: Sun Nov 25, 2012 2:44 pm
DBs Used: 1 MySQL - MariaDB
2 DBF
Location: Belgium
Has thanked: 449 times
Been thanked: 102 times
Contact:

Help needed with CURL/JSON

Post by serge_girard » Mon Oct 15, 2018 8:39 am

Hello All !

I need to transfer large volumes of files and so I decided to use the WeTransfer API.

First you need to register etc. and afterwards you will get an API-key. This I have.
With the API-key you can call the authorization for a 'token'.

In DOS this works fine but in my program I receive: "message":"Unauthorized"

I attach a short working demo but you will need to a valid API-key: this I can provide.

Demo:

Code: Select all

#include "hmg.ch"
#include "hbcurl.ch"

 

FUNCTION MAIN()
/***************/
PUBLIC cCurrentSRT   := GetStartUpFolder()  
PUBLIC cURL          := ''
PUBLIC cApiUrl       := "https://dev.wetransfer.com/"
PUBLIC cAPIKey       := "my_key"   
PUBLIC cPOSTdata
PUBLIC h, curlHandle, i, ahResp
/*
DOS ok 
C:\curl-7.53.1-win32-mingw\bin> 
curl -i -X POST "https://dev.wetransfer.com/v2/authorize"   -H "Content-Type: application/json"   -H "x-api-key: my_key" 

RESPONSE:
{
   "success": true,
   "token": "some_token"
}

 OR:
{
   "message":"Unauthorized"
}
*/
SET PRINTER TO C:\TEST\TEST_WT.TXT 
SET PRINTER ON 
SET CONSOLE OFF
 
Get_WETR_Authorization()

SET PRINTER TO  
SET PRINTER OFF 
SET CONSOLE ON
  
RETURN NIL


FUNCTION Get_WETR_Authorization()
/**********************************************************/
LOCAL cURL, i,  h 

? 'Get_WETR_Authorization: Authorization for WETRANSFER'

cURL        := cApiUrl + 'v2/authorize'
curlHandle  := curl_easy_init()
IF EMPTY(curlHandle)
	? "Error while init cURL lib."
	MsgStop("Error while init cURL lib.")
	RETURN 
ENDIF

// see https://developers.wetransfer.com/documentation

// Authorization
h                       := { => }    
h [ "x-api-key" ]       := cAPIKey
h [ "Content-Type" ]    := "application/json"

cPOSTdata         := hb_jsonEncode( h , .T. ) 
cResp             := Send_WeTransfer( cUrl, cPOSTdata, curlHandle )
 
? 'cURL',      cURL
? 'cPOSTdata', cPOSTdata
? 'cResp',     cResp
? 'cAPIKey',   cAPIKey

hb_jsonDecode( cResp , @ahResp)
? 'ahResp' ,   ahResp 
? 'cResp ',    cResp 
? 'LEN( ahResp )', LEN( ahResp )

RETURN



FUNCTION Send_WeTransfer (cUrl, cPOSTdata, curlHandle)
/****************************************************/
Local curlErr, cReturn

curl_easy_reset( curlHandle )

curl_easy_setopt( curlHandle, HB_CURLOPT_URL, cUrl )
curl_easy_setopt( curlHandle, HB_CURLOPT_FOLLOWLOCATION, .T. )
curl_easy_setopt( curlHandle, HB_CURLOPT_SSL_VERIFYPEER, .F. )

curl_easy_setopt( curlHandle, HB_CURLOPT_DOWNLOAD )
curl_easy_setopt( curlHandle, HB_CURLOPT_DL_BUFF_SETUP )
	
curl_easy_setopt( curlHandle, HB_CURLOPT_USERAGENT, "WeTransfer-Curl/1.0")  
curl_easy_setopt( curlHandle, HB_CURLOPT_POST, .T. )
curl_easy_setopt( curlHandle, HB_CURLOPT_POSTFIELDSIZE, LEN( cPOSTdata ) )
curl_easy_setopt( curlHandle, HB_CURLOPT_POSTFIELDS, cPOSTdata )

curlErr := curl_easy_perform( curlHandle )		/* Do everything */

IF !EMPTY( curlErr )	/* Report any errors */
	cReturn := "!ERROR!" + CRLF + curl_easy_strerror(curlErr)
ELSE
	cReturn := curl_easy_dl_buff_get( curlHandle )
ENDIF

RETURN cReturn
Anybody has an idea what's going wrong?

Thanks, Serge

mlnr
Posts: 81
Joined: Fri Aug 28, 2015 1:52 pm
DBs Used: DBF
Location: Hungary
Has thanked: 26 times
Been thanked: 9 times

Post by mlnr » Tue Oct 16, 2018 12:41 pm

Hi Serge,


Try to add the next lines in the Send_Wetransfer()

Code: Select all

  headers:={}
  AADD(headers,"Content-Type: application/json")
  AADD(headers,"x-api-key: my_key")

  curl_easy_setopt(curl, HB_CURLOPT_HTTPHEADER, headers)
Best regards,
Gabor

User avatar
serge_girard
Posts: 2139
Joined: Sun Nov 25, 2012 2:44 pm
DBs Used: 1 MySQL - MariaDB
2 DBF
Location: Belgium
Has thanked: 449 times
Been thanked: 102 times
Contact:

Post by serge_girard » Tue Oct 16, 2018 1:03 pm

Gabor,

Thanks, I allready tried that with this as result:

Code: Select all

Failure when receiving data from the peer
Should I comment these lines:?

Code: Select all

//curl_easy_setopt( curlHandle, HB_CURLOPT_POSTFIELDSIZE, LEN( cPOSTdata ) )
//curl_easy_setopt( curlHandle, HB_CURLOPT_POSTFIELDS, cPOSTdata )
Serge

mlnr
Posts: 81
Joined: Fri Aug 28, 2015 1:52 pm
DBs Used: DBF
Location: Hungary
Has thanked: 26 times
Been thanked: 9 times

Post by mlnr » Tue Oct 16, 2018 1:03 pm

Code: Select all

FUNCTION Curl_Func(params, postRequest, resultFile)
    LOCAL curl
    LOCAL requestParams := ""
    LOCAL param
    LOCAL result
    LOCAL _cURL:="https://dev.wetransfer.com/v2/authorize"
    LOCAL headers:={}
    
    AADD(headers,"Content-Type: application/json")
    AADD(headers,"x-api-key: your_api_key")

    // Default
    IF(params == NIL); params := {}; ENDIF
    IF(postRequest == NIL); postRequest := .F.; ENDIF

    // Init cURL
    curl_global_init()
    curl := curl_easy_init()

    // Do NOT include header in output
    curl_easy_setopt(curl, HB_CURLOPT_HEADER, .F.)

    // Parameters
    FOR EACH param IN params
        requestParams += param[1] + "=" + curl_easy_escape(curl, AllTrim(HB_ValToStr(param[2]))) + "&"
    NEXT

    // Removes trailing &
    IF(LEN(requestParams) > 0)
        requestParams := LEFT(requestParams, LEN(requestParams) - 1)
    ENDIF

    IF(postRequest)
        // POST request
        curl_easy_setopt(curl, HB_CURLOPT_NOSIGNAL, 1)
        curl_easy_setopt(curl, HB_CURLOPT_TIMEOUT_MS, 2000) // no default
        curl_easy_setopt(curl, HB_CURLOPT_POST, .T.)
        curl_easy_setopt(curl, HB_CURLOPT_POSTFIELDS, requestParams)
        curl_easy_setopt(curl, HB_CURLOPT_HTTPHEADER, headers)
        curl_easy_setopt(curl, HB_CURLOPT_URL, _cURL)
    ELSE
        curl_easy_setopt(curl, HB_CURLOPT_URL, _cURL + "?" + requestParams)
    ENDIF

    // Save result to file?
    IF(resultFile != NIL)
        curl_easy_setopt(curl, HB_CURLOPT_DL_FILE_SETUP, resultFile)
        result := .T.
    ELSE
        curl_easy_setopt(curl, HB_CURLOPT_DL_BUFF_SETUP)
    ENDIF

    // Execute
    curl_easy_perform(curl)

    // Load result from buffer into variable
    IF(result == NIL)
        result := curl_easy_dl_buff_get(curl)
    ENDIF

    curl_easy_cleanup(curl)
    curl_global_cleanup()

RETURN result
Best regards,
Gabor

mlnr
Posts: 81
Joined: Fri Aug 28, 2015 1:52 pm
DBs Used: DBF
Location: Hungary
Has thanked: 26 times
Been thanked: 9 times

Post by mlnr » Tue Oct 16, 2018 1:21 pm

And the call function

Code: Select all

  fpParams:={}
  cText:=Curl_Func(fpParams, .T.,,)
Best regards,
Gabor

User avatar
serge_girard
Posts: 2139
Joined: Sun Nov 25, 2012 2:44 pm
DBs Used: 1 MySQL - MariaDB
2 DBF
Location: Belgium
Has thanked: 449 times
Been thanked: 102 times
Contact:

Post by serge_girard » Tue Oct 16, 2018 5:28 pm

Thanks Gabor,

Result is empty, so something is wrong!

Serge

mlnr
Posts: 81
Joined: Fri Aug 28, 2015 1:52 pm
DBs Used: DBF
Location: Hungary
Has thanked: 26 times
Been thanked: 9 times

Post by mlnr » Wed Oct 17, 2018 7:45 am

Hi Serge,

I'm not test, but i will check the example.

Try this.

Code: Select all

    oHttp := CreateObject( 'MSXML2.XMLHTTP' )
    oHttp:Open( 'POST', "https://dev.wetransfer.com/v2/authorize", .F. )
    ohttp:SetRequestHeader( "Content-Type" , "application/json" )  
    oHttp:SetRequestHeader( "x-api-key","api_key")
    oHttp:Send()
    cText:=alltrim(ohttp:responseText)

Edit: It's work too.
Last edited by mlnr on Wed Oct 17, 2018 8:13 am, edited 1 time in total.
Best regards,
Gabor

mlnr
Posts: 81
Joined: Fri Aug 28, 2015 1:52 pm
DBs Used: DBF
Location: Hungary
Has thanked: 26 times
Been thanked: 9 times

Post by mlnr » Wed Oct 17, 2018 8:10 am

This is the full code with result. It's work.

Code: Select all

FUNCTION Curl_Func(params, postRequest, resultFile)
    LOCAL curl
    LOCAL requestParams := ""
    LOCAL param
    LOCAL result
    LOCAL _cURL:="https://dev.wetransfer.com/v2/authorize"
    LOCAL headers:={}
    
    AADD(headers,"Content-Type: application/json")
    AADD(headers,"x-api-key: your_api_key")

    // Default
    IF(params == NIL); params := {}; ENDIF
    IF(postRequest == NIL); postRequest := .F.; ENDIF

    // Init cURL
    curl_global_init()
    curl := curl_easy_init()

    // Do NOT include header in output
    curl_easy_setopt(curl, HB_CURLOPT_HEADER, .F.)

    // Parameters
    FOR EACH param IN params
        requestParams += param[1] + "=" + curl_easy_escape(curl, AllTrim(HB_ValToStr(param[2]))) + "&"
    NEXT

    // Removes trailing &
    IF(LEN(requestParams) > 0)
        requestParams := LEFT(requestParams, LEN(requestParams) - 1)
    ENDIF

    IF(postRequest)
        // POST request
        curl_easy_setopt(curl, HB_CURLOPT_NOSIGNAL, 1)
        curl_easy_setopt(curl, HB_CURLOPT_TIMEOUT_MS, 2000) // no default
        curl_easy_setopt(curl, HB_CURLOPT_POST, .T.)
        curl_easy_setopt(curl, HB_CURLOPT_POSTFIELDS, requestParams)
        curl_easy_setopt(curl, HB_CURLOPT_HTTPHEADER, headers)
        curl_easy_setopt(curl, HB_CURLOPT_URL, _cURL)
    ELSE
        curl_easy_setopt(curl, HB_CURLOPT_URL, _cURL + "?" + requestParams)
    ENDIF

    // Save result to file?
    IF(resultFile != NIL)
        curl_easy_setopt(curl, HB_CURLOPT_DL_FILE_SETUP, resultFile)
        result := .T.
    ELSE
        curl_easy_setopt(curl, HB_CURLOPT_DL_BUFF_SETUP)
    ENDIF

    // Execute
    curl_easy_perform(curl)

    // Load result from buffer into variable
    IF(result == NIL)
        result := curl_easy_dl_buff_get(curl)
    ENDIF

    curl_easy_cleanup(curl)
    curl_global_cleanup()

RETURN result
Best regards,
Gabor

User avatar
serge_girard
Posts: 2139
Joined: Sun Nov 25, 2012 2:44 pm
DBs Used: 1 MySQL - MariaDB
2 DBF
Location: Belgium
Has thanked: 449 times
Been thanked: 102 times
Contact:

Post by serge_girard » Wed Oct 17, 2018 8:31 am

Hi Gabor,

Thanks for helping!

The 'oHttp := CreateObject( 'MSXML2.XMLHTTP' )...' works fine and returns token, the other sample I can't get it working.
Do you want my API-key to test? Mail me at sg AT pass-sys DOT be

Serge

mlnr
Posts: 81
Joined: Fri Aug 28, 2015 1:52 pm
DBs Used: DBF
Location: Hungary
Has thanked: 26 times
Been thanked: 9 times

Post by mlnr » Wed Oct 17, 2018 9:29 am

ok, i wrote to you.
Best regards,
Gabor

Post Reply