Trying to send a soap message directly at a server


#1

I’ve now tried 2 different methods of sending a soap message (read in
from a file) at a server, one using the net/http library the other a
socket.

require ‘soap/wsdlDriver’
require ‘rexml/document’
#require ‘net/http’
require ‘socket’
include Socket::Constants

file = File.new(“PDSUpdate.xml”)
doc = REXML::Document.new(file)
#puts doc
#http.post(“http://inpsesrh02.inpses.co.uk:7778”, doc)

socket = Socket.new( AF_INET, SOCK_STREAM, 0 )
sockaddr = Socket.pack_sockaddr_in( 7779,
inpsesrh02.inpses.co.uk/orabpel/default/’ )
socket.connect( sockaddr )
socket.puts doc
socket.close

Can anyone please tell me the simplest way of sending a SOAP message
directly at an address and port. I don’t need the WSDL as I already know
the available methods, and just want to write a test stub.


#2

On Fri, 02 Feb 2007 22:46:17 +0900, Max R. wrote:

I’ve now tried 2 different methods of sending a soap message (read in
from a file) at a server, one using the net/http library the other a
socket.

Have you tried SOAP4r?

http://dev.ctor.org/soap4r

Mid


#3

mid wrote:

On Fri, 02 Feb 2007 22:46:17 +0900, Max R. wrote:

I’ve now tried 2 different methods of sending a soap message (read in
from a file) at a server, one using the net/http library the other a
socket.

Have you tried SOAP4r?

http://dev.ctor.org/soap4r

Mid

I have had a look previously, what I’m needing is a howto I suppose. The
documentation around some of this stuff is a bit flaky…


#4

On Fri, 02 Feb 2007 22:46:17 +0900, Max R. wrote:

Can anyone please tell me the simplest way of sending a SOAP message
directly at an address and port. I don’t need the WSDL as I already know
the available methods, and just want to write a test stub.

Here’s what I do in the console (for testing purposes):

require “soap/wsdlDriver”
wsdl_url =
http://webservices.globaladdress.net/globaladdress.asmx?WSDL
factory = SOAP::WSDLDriverFactory.new(wsdl_url)
driver = factory.create_rpc_driver

This allows me to use the SOAP services available on the GlobalAddress
server.

I can do a driver.methods to find out what methods (services) are
available but in reality I already know what methods are available to
me.

Do you have a WSDL file to reference?

Disclosure: I’m new to all this too so this may be a case of the blind
leading the blind but I am successfully consuming services except I’ve
also hit a snag too but that’s the topic of another thread :slight_smile:


#5

On Fri, Feb 02, 2007 at 10:46:17PM +0900, Max R. wrote:

I’ve now tried 2 different methods of sending a soap message (read in
from a file) at a server, one using the net/http library the other a
socket.

So what happens when you try these methods?

What does tcpdump (Linux) or ethereal (Windows) show at the network
level?

tcpdump -i eth0 -n -s1500 -vX tcp port 80

require ‘soap/wsdlDriver’
require ‘rexml/document’

Why require these libraries? AFAICT you’re just trying to send a
pre-existing XML file over HTTP.

#require ‘net/http’
require ‘socket’
include Socket::Constants

file = File.new(“PDSUpdate.xml”)
doc = REXML::Document.new(file)
#puts doc
#http.post(“http://inpsesrh02.inpses.co.uk:7778”, doc)

I’d suggest you don’t parse the document using REXML. Just read it in as
a
file, and then squirt it out over the HTTP connection. I’m not sure how
http.post will cope with being given an REXML::Document object.

Try “ri Net::HTTP” for some samples of how to do a HTTP POST.
(or “ri1.8 Net::HTTP” under Ubuntu).

Capture the result in a variable, e.g. res = http.post …
and inspect it.

Perhaps you should be posting to a more specific URL, e.g.
http.post(“http://inpsesrh02.inpses.co.uk:7778/foo/myapp”, doc)

socket = Socket.new( AF_INET, SOCK_STREAM, 0 )
sockaddr = Socket.pack_sockaddr_in( 7779,
inpsesrh02.inpses.co.uk/orabpel/default/’ )
socket.connect( sockaddr )
socket.puts doc
socket.close

Doing it this way you’d want a TCPSocket.
See http://www.rubycentral.com/book/lib_network.html
for some examples.

HTH,

Brian.


#6

Brian C. wrote:

So what happens when you try these methods?

What does tcpdump (Linux) or ethereal (Windows) show at the network
level?

tcpdump -i eth0 -n -s1500 -vX tcp port 80

That nothing was going out over HTTP at all.

require ‘soap/wsdlDriver’
require ‘rexml/document’

Why require these libraries? AFAICT you’re just trying to send a
pre-existing XML file over HTTP.

The soap/wsdlDriver was a hangover from my hacking (in vain) session…

#require ‘net/http’
require ‘socket’
include Socket::Constants

file = File.new(“PDSUpdate.xml”)
doc = REXML::Document.new(file)
#puts doc
#http.post(“http://inpsesrh02.inpses.co.uk:7778”, doc)

I’d suggest you don’t parse the document using REXML. Just read it in as
a
file, and then squirt it out over the HTTP connection. I’m not sure how
http.post will cope with being given an REXML::Document object.

Try “ri Net::HTTP” for some samples of how to do a HTTP POST.
(or “ri1.8 Net::HTTP” under Ubuntu).

I’ve had a look at this documentation, the sections pertaining to POST
all refer to form data (e.g. looking at a search box and posting info,
setting dates and posting etc.) , rather than an individual POST of a
file.

Capture the result in a variable, e.g. res = http.post …
and inspect it.

Perhaps you should be posting to a more specific URL, e.g.
http.post(“http://inpsesrh02.inpses.co.uk:7778/foo/myapp”, doc)

socket = Socket.new( AF_INET, SOCK_STREAM, 0 )
sockaddr = Socket.pack_sockaddr_in( 7779,
inpsesrh02.inpses.co.uk/orabpel/default/’ )
socket.connect( sockaddr )
socket.puts doc
socket.close

Doing it this way you’d want a TCPSocket.
See http://www.rubycentral.com/book/lib_network.html
for some examples.

Think I’d prefer to avoid the socket route if possible anyway.


#7

On Wed, Feb 07, 2007 at 08:54:43PM +0900, Max R. wrote:

setting dates and posting etc.) , rather than an individual POST of a
file.

It looks easy enough to me:

require ‘net/http’

doc = <<EOS

bar!

EOS

res = nil
Net::HTTP.start(“rubyforge.org”, 80) do |http|
res = http.post(’/wibble/wobble’, doc)
end
puts res.inspect


#8

Brian C. wrote:

On Wed, Feb 07, 2007 at 08:54:43PM +0900, Max R. wrote:

setting dates and posting etc.) , rather than an individual POST of a
file.

It looks easy enough to me:

require ‘net/http’

doc = <<EOS

bar!

EOS

res = nil
Net::HTTP.start(“rubyforge.org”, 80) do |http|
res = http.post(’/wibble/wobble’, doc)
end
puts res.inspect

I’ll try that, thanks. RI didn’t turn up anything like that example. It
has sections on posting form data, but nothing with a simple post.

ta