Calling functions with parameters using SOAP with Perl

function, parameters, perl, soap, web-services

Solution

Use SOAP::WSDL to consume the service wsdl, it also marshals from and (optionally) to plain perl data structures for you. Highly recommended module.

Something like the following:

use SOAP::WSDL;
use Data::Dumper;

my $soap = SOAP::WSDL->new(
  wsdl => 'http://server/pathtoservice?WSDL',
  outputhash => 1
);
my $res = $soap->call('method', { foo => 1, bar =>2 });
die $res->faultstring if $res->fault;
print Dumper($res->result);

Problem

I am attempting to access a web service using SOAP through Perl and am having issues calling the service's functions that require parameters. The XSD that dictates the SOAP call says, ``` <xs:complexType name="getVersion"> <xs:sequence/> </xs:complexType> <xs:complexType name="getVersionResponse"> <xs:sequence> <xs:element minOccurs="0" name="return" type="xs:string"/> </xs:sequence> </xs:complexType> ... <xs:complexType name="enumerateEntities"> <xs:sequence> <xs:element name="entityId" type="xs:int"/> <xs:element minOccurs="0" name="entityType" type="tns:entityType"/> </xs:sequence> </xs:complexType> <xs:complexType name="enumerateEntitiesResponse"> <xs:sequence> <xs:element maxOccurs="unbounded" minOccurs="0" name="return" nillable="true" type="xs:int"/> </xs:sequence> </xs:complexType> ``` According to the docs for the service, the signatures for the two functions are: ``` String getVersion () int[] enumerateEntities (int entityId, EntityType entityType) ``` I am able to call the first function, which requires no input parameters, using: ``` #!/usr/bin/perl use SOAP::Lite; my $uri = 'http://wsdl.mydomain.com/'; my $service = SOAP::Lite -> uri($uri) -> on_action(sub { sprintf '"Call by on_action: %s"',shift}) -> proxy('http://192.168.1.100:8688/MyService/services/MyService.MyServicePort/'); $method = SOAP::Data->name("MyService")->attr({xmlns => $uri}); $getVersion = SOAP::Data->name("getVersion")->attr({xmlns=>$uri});#line 11 my $theResult = $service->getVersion; unless ($theResult->fault){ print "Version: "; print $theResult->result;} else {print $theResult->faultstring;} ``` ...but my attempt (below) at calling a function with parameters by changing line 11 on have been futile. ``` ... @entityId = SOAP::Data->type('int')->name('entityId')->value(0); @entityType = SOAP::Data->type('EntityType')->name('entityType')->value(NODE); $enumerateEntities = SOAP::Data->name("enumerateEntities",@entityId,@entityType)->attr({xmlns=>$uri}); my $result2 = $service->enumerateEntities; print $result2->result; ``` What am I doing wrong that is preventing me from calling functions of the service with parameters? Edit: Here's the updated sample code with using SOAP::WSDL ``` #!/usr/bin/perl use SOAP::WSDL; use Data::Dumper; my $service = SOAP::WSDL->new( wsdl => 'http://192.168.1.100:8688/MyService/services/MyService.MyServicePort?wsdl', outputhash => 1 ); ```

Original source