Page 1 of 1

HTTP Plugin - Need help with GET

PostPosted: Thu Nov 13, 2014 7:02 am
by kwpsd
Servoy Versio: 7.4.2 - build 2033
Java version "1.7.0_71

I need help.

Using the http plugin, I am attempting to download data from a remote server that uses DotNet. I am assured by the owner of the remote server that the url (with obfuscated IP address) in the below code snippet is correct. However, whenever the code is executed, the returned status is always 500, and the XML response is always an error message. I use the exact same url in a Visual FoxPro implementation and valid data is returned. Also, the server owner sent a test program of theirs that also returns the expected data. Can anyone explain why the Servoy implementation does not work?


Code: Select all
var url = 'http://xxx.xxx.xxx.xxx/EAM.Outbound.WebServices/OutBoundService.asmx?op=GetTodayXML'

var httpClient = plugins.http.createNewHttpClient()

var httpGet = httpClient.createGetRequest( url )

var httpResponse = httpGet.executeRequest()

var httpStatus = httpResponse.getStatusCode()
   
var xml = httpResponse.getResponseBody()



Also, is there a way to 'see' what the http plugin is emitting/sending to the remote server? I tried using the Wireshark network protocol analyzer, however, it doesn't show the url in its entirety (as in the code).

Re: HTTP Plugin - Need help with GET

PostPosted: Thu Nov 13, 2014 10:45 am
by ROCLASI
Hi Kim,

Status code 500 means a server error. You should ask the owner of the remote server to look inside their server logs to see what the error is.
You code is a simple GET request like any browser would do. Can you put the exact URL in a browser on the machine you try to run Servoy on and see if you can recreate the problem?
In any case the remote server logs should provide some more insight in what goes wrong.

Hope this helps.

Re: HTTP Plugin - Need help with GET

PostPosted: Thu Nov 13, 2014 5:07 pm
by kwpsd
Hi, Robert. Thanks for the reply!

When I use the url in a browser, I get a web page that contains the following:

http_wsdl_soap.png
http_wsdl_soap.png (52.13 KiB) Viewed 10547 times


Working with the server owner today...

The 'OutBoundService.asmx' method in the url is never being called (from the log file). Additionally, the server owner thinks Servoy's http plugin implementation is not compatible with WSDL/SOAP which is what they use. He provided the following link to a YouTube video showing how to do this in Java:

http://www.youtube.com/watch?v=KZkW1X6y39I

but, I am not certain I know how do this in Servoy. Any suggestions?

Re: HTTP Plugin - Need help with GET

PostPosted: Thu Nov 13, 2014 11:02 pm
by sbutler
Servoy works fine with SOAP web services. They are just picky. Your missing some stuff in your headers likely.
Every SOAP services I've worked with always requires 4 headers to be passed in:
Host, User-Agent, Content-Type, and SOAPAction

Try this:

Code: Select all
var url = 'http://xxx.xxx.xxx.xxx/EAM.Outbound.WebServices/OutBoundService.asmx?op=GetTodayXML'

var httpClient = plugins.http.createNewHttpClient()

var httpGet = httpClient.createGetRequest( url )

//add your headers!
httpGet.addHeader ('Host', 'xxx.xxx.xxx.xxx')
httpGet.addHeader ('User-Agent', 'Agent')
httpGet.addHeader ('Content-Type','text/xml; charset=utf-8')
httpGet.addHeader ('SOAPAction', 'GetTodayXML')

var httpResponse = httpGet.executeRequest()

var httpStatus = httpResponse.getStatusCode()
   
var xml = httpResponse.getResponseBody()


Obviously xxx.xxx.xxx.xxx should be the hostname or ip, like 'www.restfulwebservices.net'

Re: HTTP Plugin - Need help with GET

PostPosted: Fri Nov 14, 2014 8:12 pm
by kwpsd
Hi, Scott.

Thanks for the tip regarding SOAP headers as it helped me to understand what I was seeing when the server responds with its error page (graphic below).

http_header_info.png
http_header_info.png (24.27 KiB) Viewed 10490 times


Following your lead and using the information in the graphic, I changed the code from a GET to a POST as follows:


Code: Select all
    var httpPost = httpClient.createPostRequest( url )
   
    if ( httpPost )
    {
        var sxml = '<?xml version="1.0" encoding="utf-8"?>' +
                   '<soap:Envelope xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xmlns:xsd="http://www.w3.org/2001/XMLSchema" xmlns:soap="http://schemas.xmlsoap.org/soap/envelope/">' +
                   '<soap:Body>' +
                   '<GetTodayXml xmlns="http://tempuri.org/" />' +
                   '</soap:Body>' +
                   '</soap:Envelope>'   
       
        httpPost.addParameter( 'op', 'GetTodayXML' )
       
        httpPost.addHeader( 'Host', serverAddr )
        httpPost.addHeader( 'User-Agent', 'Agent' )
        httpPost.addHeader( 'Content-Type', 'text/xml; charset=utf-8' )
        httpPost.addHeader( 'Content-Length', sxml.length.toString( 10 ) )
        httpPost.addHeader( 'SOAPAction', 'http://tempuri.org/GetTodayXml' )
       
        httpPost.setBodyContent( sxml )
    }
   
    var httpResponse = httpPost.executeRequest()



When I run the code, the line containing httpPost.executeRequest() returns a null.

One by one, I commented out each of the 'httpPost.addXXXXX' lines and found that the line containing 'Content-Length' was the offender. Even if I hard-code a number string for the 'Content-Length', executeRequest() always returns a null. What is it about 'Content-Length' that prevents Servoy from executing the POST?


With the 'Content-Length' line commented out, instead of getting a null response, the following response is returned from the server:

{X-AspNet-Version:[2.0.50727],Date:[Fri, 14 Nov 2014 17:46:47 GMT],Content-Length:[0],X-Powered-By:[ASP.NET],Server:[Microsoft-IIS/7.5],Cache-Control:[private]}
400: Bad Request

which may be due to missing requiste 'Content-Length' header information.

Do you have any suggestions regarding the 'Content-Length' problem, or any other suggestions in general?

Re: HTTP Plugin - Need help with GET

PostPosted: Fri Nov 14, 2014 8:22 pm
by ptalbot
You are adding a parameter here
httpPost.addParameter( 'op', 'GetTodayXML' )

In a get request, parameters will be added to the URL, but in a POST request, they are added to the body. Possibly since you have both a body and post parameters, the query is sent as a multipart, so it's Content-Length is more than what you imagine.

What you could try is to call your URL + "?op=GetTodayXML' (if you really need that parameter), or omit the added parameter and use the header to pass the action target (SOAPAction)

Re: HTTP Plugin - Need help with GET

PostPosted: Fri Nov 14, 2014 8:42 pm
by sbutler
In SOAP services I've seen, parameters never get passed via the URL. They are always header values or in the XML of the body. So your URL would be 'http://xxx.xxx.xxx.xxx/EAM.Outbound.WebServices/OutBoundService.asmx'

Here is an example connecting to a sample SOAP weather service. Notice the use of E4X XML and using the {country} parameters in the XML (not required, but ensures valid XML instead of building a string of XML)


Code: Select all
   var url = "http://www.restfulwebservices.net/wcf/WeatherForecastService.svc"
   var soapaction = "GetCitiesByCountry"
   var host = "www.restfulwebservices.net"
   
   var country = "USA"
   var xml = <soapenv:Envelope xmlns:soapenv="http://schemas.xmlsoap.org/soap/envelope/" xmlns:ns="http://www.restfulwebservices.net/ServiceContracts/2008/01">
      <soapenv:Header/>
      <soapenv:Body>
         <ns:GetCitiesByCountry>
            <ns:Country>{country}</ns:Country>
         </ns:GetCitiesByCountry>
      </soapenv:Body>
   </soapenv:Envelope>
   
   var client = plugins.http.createNewHttpClient()
   var poster = client.createPostRequest(url)
   poster.addHeader ('Host',host)
   poster.addHeader ('User-Agent', 'Agent')
   poster.addHeader ('Content-Type','text/xml; charset=utf-8')
   poster.addHeader ('SOAPAction',soapaction)
   poster.setBodyContent(xml.toXMLString())
   
   var response = poster.executeRequest()
   var httpCode = response.getStatusCode()
   var result = response.getResponseBody()

Re: HTTP Plugin - Need help with GET

PostPosted: Fri Nov 14, 2014 8:55 pm
by kwpsd
Hi, Patrick.

It's good to hear from you!

Removing the httpPost.addParameter( 'op', 'GetTodayXML' ) got things working. I did not have to add '?op=GetTodayXML' to the url (even though its in the server owner's specification).

Thanks for your help, and thanks to the others for their input as well!

Re: HTTP Plugin - Need help with GET

PostPosted: Thu Aug 11, 2016 4:06 pm
by dfernandez
Hi Scott,

Your sample on how to invoke a soap ws from Servoy works fantastic.

How do you just get the values for the cities in an array?