[SOLVED] Using WINHTTPREQUEST

Author: knut.dybendahl@gmail.com (Knut)

Happy New Year to all! - and the title should have been edited too - but I cannot get to it! Due to some return value size limitations in our current Uniface version (9.6.04) we've had to look at using the "WINHTTPREQUEST" object available in Windows7. The call(s) to the "WINHTTPREQUEST" object works fine - the challenge occurs when the return data is anything else but text.... We need to return a pdf file from a request, and automatically store the pdf file on disk without prompting the user (via filebox). When we take the output and store it (either as text, raw or image) - the file cannot be opened in a PdfReader as the file is corrupted. Amongst others, the number of bytes stored on disk is different from what's in the header below; Content-Length: 1703 Content-Type: application/pdf Server: Microsoft-HTTPAPI/2.0 X-AspNet-Version: 2.0.50727 FileExtension: pdf Content-Disposition: attachment; filename="abc.pdf" When the 'get_responsebody' operation / method is imported to Uniface, the return value is declared as a basic type of string, and the interface is the Microsoft VT_VARIANT. When the 'get_responsestream' operation / method is imported to Uniface, the return value is declared as a basic type of string, and the interface is the Microsoft VT_VARIANT. Does anyone have any experience(s) with this that you'd be willing and able to share? Regards, Knut

6 Comments

  1. Not exactly the same problem, but potentially similar.  We interface with Crystal reports, and use a function in there to export a PDF to an in memory variable which we pass back to Uniface. In this case the parameter in the signature had to be set up as :- Data Type = Basic, Raw Interface = VT_ARRAY|VT_UI1 (array of bytes) We then execute this operation using a local proc variable of type raw, before storing that in a string in the database. However, you should be able to load the data to the variable and then filedump/raw.....  Iain


    Author: Iain Sharp (i.sharp@pcisystems.co.uk)
  2. Iain Sharp said Not exactly the same problem, but potentially similar.  We interface with Crystal reports, and use a function in there to export a PDF to an in memory variable which we pass back to Uniface. In this case the parameter in the signature had to be set up as :- Data Type = Basic, Raw Interface = VT_ARRAY|VT_UI1 (array of bytes) We then execute this operation using a local proc variable of type raw, before storing that in a string in the database. However, you should be able to load the data to the variable and then filedump/raw.....  Iain

    This should work fine for the ‘get_responsebody’ operation - although it is also possible to use the "Basic, Raw" data type in combination with the "VT_VARIANT" interface. The ‘get_responsestream’ operation is a different story. It will not return the (binary) data itself, but a pointer to the IStream object. Hope this helps. Daniel


    Author: diseli (daniel.iseli@uniface.com)
  3. Hi Iain, Yep, that did the trick - thank you. Only caveat I found - I had to duplicate the WINHTTPREQUEST in order to have the specific RAW return - so now we have two WINHTTPREQUEST signatures. Cheers, Knut


    Author: Knut (knut.dybendahl@gmail.com)
  4. You don't necessarily have to duplicate the entire signature. You can have several operations (with different names of course) that map to the same DLL function name but have different data type definitions for the parameters. I've done that in the past for similar instances where functions can return longs or strings (e.g. libcurl)   Andy


    Author: Andy Heydon (andy@heydon.org)
  5. Hi Andy, I agree for a 3gl, since we have access to the function/method name. For a COM object - I didn't see a way to (re)define the function/method name - hence the duplication. Knut


    Author: Knut (knut.dybendahl@gmail.com)
  6. Knut said Hi Andy, I agree for a 3gl, since we have access to the function/method name. For a COM object - I didn't see a way to (re)define the function/method name - hence the duplication. Knut

    Why do you want to "(re)define the function/method name"? You could create a operation called 'get_responsebodyasraw' operation (in WINHTTPREQUEST), define the output parameter (RESULT_) as Raw, and set the the literal name of the operation to 'ResponseBody.get' (see "Details of 'COM'" in the "Define Operation" screen). That should work. Hope this helps. Daniel


    Author: diseli (daniel.iseli@uniface.com)