Subject: | XML::Compile::WSDL11::Operation::compileClient fails to extract response message content, on service that works fine with several other clients |
The attached script jacop_test.pl is a test script for a public-facing
web service.
The service in question returns valid results when queried with SoapUI,
or the Java toolkits Axis2 or CXF. In addition, when we build
client-side proxies for it with the wsdl2perl.pl script in SOAP::WSDL,
it works fine.
However, its output doesn't seem to be parseable by
XML::Compile::WSDL11::Operation::compileClient(), as jacop_test.pl will
demonstrate if you run it.
The hash returned by executing the code ref provided by compileClient
has no element called 'parameters', which is the part name defined in
the WSDL and returned by the service. The data dump provided by the
script will verify this.
The service in question is described here:
WSDL: http://myhits.isb-sib.ch/doc/FuncNet.wsdl
Service: JacopService
Port: JacopPort
Binding: JacopBinding
Operation: ScorePairwiseRelations
Interestingly, we have several services that use basically the same WSDL
at different sites, which XML::Compile can handle fine. For example:
http://cathdb.info:8080/BioMiner-war/services/GecoService?wsdl
Service: GecoService
Port: GecoPort
Binding: GecoBinding
Operation: ScorePairwiseRelations
I have also attached a script called geco_registry_test.pl which hits
this latter service using the same method as in jacop_test.pl -- only
geco_registry_test.pl works as expected. We have been unable to figure
out what differences between the two services would cause XML::Compile
to fail, especially as they both work with other clients.
Perl version 5.8.6
XML::Compile 0.96
Centos 5 (basically Redhat Enterprise Linux 5)
Linux kernel 2.6.18
Subject: | jacop_test.pl |
#!/usr/bin/perl -w
# FuncNet predictor testing tool for EMBRACE registry at http://embraceregistry.net/
#
# Put some query and reference proteins in the $parameters hash.
#
# For each expected prediction, add a $expectedN string containing the query
# protein ID, reference protein ID and p-value, separated by tabs, e.g.:
#
# my $expected1 = "O75865\tP22676\t0.893313";
#
# Put these in alphabetical order.
#
# See also http://funcnet.eu/
use strict;
use Data::Dumper;
use LWP::UserAgent;
use XML::Compile::WSDL11;
use XML::Compile::Transport::SOAPHTTP;
use XML::Compile::Schema;
# Download local copy of WSDL
my $ua = LWP::UserAgent->new;
my $wsdl_url = "http://myhits.isb-sib.ch/doc/FuncNet.wsdl";
my $response = $ua->get( $wsdl_url );
unless( $response->is_success )
{
warn "Could not retrieve $wsdl_url: ", $response->status_line, "\n";
exit 1;
}
unless( open WSDL, ">jacop_temp.wsdl" )
{
warn "Could not open temporary local file: $1\n";
exit 1;
}
unless( print WSDL $response->content )
{
warn "Could not write WSDL to temporary local file: $!\n";
exit 1;
}
close WSDL;
# Parse WSDL
my $wsdl = XML::LibXML->new->parse_file( "jacop_temp.wsdl" );
unless( $wsdl )
{
warn "Attempt to parse WSDL returned null\n";
exit 1;
}
# Clean up local temp copy
unlink "jacop_temp.wsdl";
# Not sure what would happen if two copies of this script ran simultaneously...
print "Retrieved and parsed WSDL OK.\n";
# Build SOAP proxy object
my $proxy = XML::Compile::WSDL11->new( $wsdl );
my @op_defs = $proxy->operations();
my $op = $proxy->operation(
operation => 'ScorePairwiseRelations',
port => "JacopPort",
service => "{http://cathdb.info/FuncNet_0_1/}JacopService",
binding => "{http://cathdb.info/FuncNet_0_1/}JacopBinding"
);
my $op_call = $op->compileClient();
# Build request object -- proteins1 is query set, proteins2 is reference set
my $parameters = {
proteins1 => { p => [ 'A8K8U9', 'P27797', 'B1B0W0' ] },
proteins2 => { p => [ 'O75925', 'P10321', 'P48034' ] }
};
# Send request
my ( $answer, $trace ) = $op_call->( parameters => $parameters );
unless( exists( $answer->{ parameters } ) )
{
warn "No parameters element found! Trace:\n", Dumper( $trace ), "\nAnswer:\n", Dumper( $answer ), "\n";
exit 1;
}
print "Prot 1\tProt 2\tP-value\n";
my @lines;
foreach my $result ( @{ $answer->{ parameters }->{ s } } )
{
my $line = $result->{ p1 } . "\t" . $result->{ p2 } . "\t" . $result->{ pv };
print $line . "\n";
push @lines, $line;
}
if( @lines != 2 )
{
warn "Expected 2 results in output, got " . scalar( @lines ) . "\n";
exit 2;
}
# Predictions expected for this request -- make sure these are in alphabetical order
my $expected1 = "A8K8U9\tO75925\t0.843698";
my $expected2 = "P27797\tP10321\t0.721078";
my @sorted = sort @lines;
if( $sorted[ 0 ] ne $expected1 )
{
warn "Expected result '$expected1' != actual result '$lines[ 0 ]'\n";
exit 2;
}
if( $sorted[ 1 ] ne $expected2 )
{
warn "Expected result '$expected2' != actual result '$lines[ 1 ]'\n";
exit 2;
}
# Success if we've reached here
print "All tests passed.\n";
exit 0;
Subject: | geco_registry_test.pl |
#!/usr/bin/perl -w
# FuncNet predictor testing tool for EMBRACE registry at http://embraceregistry.net/
#
# The service to test is set in the $SVC string.
#
# Put some query and reference proteins in the $parameters hash.
#
# For each expected prediction, add a $expectedN string containing the query
# protein ID, reference protein ID and p-value, separated by tabs, e.g.:
#
# my $expected1 = "O75865\tP22676\t0.893313";
#
# Put these in alphabetical order.
#
# See also http://funcnet.eu/
use strict;
use Data::Dumper;
use LWP::UserAgent;
use XML::Compile::WSDL11;
use XML::Compile::Transport::SOAPHTTP;
use XML::Compile::Schema;
my $SVC = 'Geco';
# Download local copy of WSDL
my $ua = LWP::UserAgent->new;
my $wsdl_url = "http://cathdb.info:8080/BioMiner-war/services/${SVC}Service?wsdl";
my $response = $ua->get( $wsdl_url );
unless( $response->is_success )
{
warn "Could not retrieve $wsdl_url: ", $response->status_line, "\n";
exit 1;
}
unless( open WSDL, ">${SVC}_temp.wsdl" )
{
warn "Could not open temporary local file: $1\n";
exit 1;
}
unless( print WSDL $response->content )
{
warn "Could not write WSDL to temporary local file: $!\n";
exit 1;
}
close WSDL;
# Parse WSDL
my $wsdl = XML::LibXML->new->parse_file( "${SVC}_temp.wsdl" );
unless( $wsdl )
{
warn "Attempt to parse WSDL returned null\n";
exit 1;
}
# Clean up local temp copy
unlink "${SVC}_temp.wsdl";
# Not sure what would happen if two copies of this script ran simultaneously...
print "Retrieved and parsed WSDL OK.\n";
# Build SOAP proxy object
my $proxy = XML::Compile::WSDL11->new( $wsdl );
my @op_defs = $proxy->operations();
my $op = $proxy->operation(
operation => 'ScorePairwiseRelations',
port => "${SVC}Port",
service => "{http://cathdb.info/FuncNet_0_1/}${SVC}Service",
binding => "{http://cathdb.info/FuncNet_0_1/}${SVC}Binding"
);
my $op_call = $op->compileClient();
# Build request object -- proteins1 is query set, proteins2 is reference set
my $parameters = {
proteins1 => { p => [ 'A3EXL0', 'Q8NFN7', 'O75865' ] },
proteins2 => { p => [ 'Q5SR05', 'Q9H8H3', 'P22676' ] }
};
# Send request
my ( $answer, $trace ) = $op_call->( parameters => $parameters );
unless( exists( $answer->{ parameters } ) )
{
warn "No parameters element found! Trace:\n", Dumper( $trace ), "\n";
exit 1;
}
print "Prot 1\tProt 2\tP-value\n";
my @lines;
foreach my $result ( @{ $answer->{ parameters }->{ s } } )
{
my $line = $result->{ p1 } . "\t" . $result->{ p2 } . "\t" . $result->{ pv };
print $line . "\n";
push @lines, $line;
}
if( @lines != 2 )
{
warn "Expected 2 results in output, got " . scalar( @lines ) . "\n";
exit 2;
}
# Predictions expected for this request -- make sure these are in alphabetical order
my $expected1 = "O75865\tP22676\t0.893313";
my $expected2 = "O75865\tQ9H8H3\t0.445814";
my @sorted = sort @lines;
if( $sorted[ 0 ] ne $expected1 )
{
warn "Expected result '$expected1' != actual result '$lines[ 0 ]'\n";
exit 2;
}
if( $sorted[ 1 ] ne $expected2 )
{
warn "Expected result '$expected2' != actual result '$lines[ 1 ]'\n";
exit 2;
}
# Success if we've reached here
print "All tests passed.\n";
exit 0;