Compare commits

...

3 Commits

Author SHA1 Message Date
Martin Kutter
745ce925c1 import SOAP-WSDL 2.00.01 from CPAN
git-cpan-module:   SOAP-WSDL
git-cpan-version:  2.00.01
git-cpan-authorid: MKUTTER
git-cpan-file:     authors/id/M/MK/MKUTTER/SOAP-WSDL-2.00.01.tar.gz
2009-12-12 19:48:32 -08:00
Martin Kutter
0cbf981665 import SOAP-WSDL 2.00_33 from CPAN
git-cpan-module:   SOAP-WSDL
git-cpan-version:  2.00_33
git-cpan-authorid: MKUTTER
git-cpan-file:     authors/id/M/MK/MKUTTER/SOAP-WSDL-2.00_33.tar.gz
2009-12-12 19:48:28 -08:00
Martin Kutter
51db446428 import SOAP-WSDL 2.00_32 from CPAN
git-cpan-module:   SOAP-WSDL
git-cpan-version:  2.00_32
git-cpan-authorid: MKUTTER
git-cpan-file:     authors/id/M/MK/MKUTTER/SOAP-WSDL-2.00_32.tar.gz
2009-12-12 19:48:24 -08:00
199 changed files with 4542 additions and 1755 deletions

View File

@@ -2,10 +2,10 @@ use Module::Build;
use version;
$build = Module::Build->new(
dist_author => 'Martin Kutter <martin.kutter@fen-net.de>',
create_makefile_pl => 'passthrough',
create_makefile_pl => 'small',
dist_abstract => 'SOAP with WSDL support',
dist_name => 'SOAP-WSDL',
dist_version => '2.00_31',
dist_version => '2.00.01',
module_name => 'SOAP::WSDL',
license => 'artistic',
requires => {
@@ -13,7 +13,7 @@ $build = Module::Build->new(
# for us. SOAP-WSDL relies on unicode (WS-I demands it)
# and triggers several 5.6 bugs...
'perl' => q(5.8.0),
'Class::Std::Fast' => qv(0.0.5),
'Class::Std::Fast' => q(0.0.5),
'Data::Dumper' => 0,
'Date::Parse' => 0,
'Date::Format' => 0,
@@ -27,14 +27,15 @@ $build = Module::Build->new(
'URI' => 0,
'XML::Parser::Expat' => 0,
},
buildrequires => {
'Class::Std::Fast' => qv(0.0.5),
build_requires => {
'Class::Std::Fast' => q(0.0.5),
'Cwd' => 0,
'Date::Parse' => 0,
'Date::Format' => 0,
'Getopt::Long' => 0,
'List::Util' => 0,
'LWP::UserAgent' => 0,
'Module::Build' => 0,
'File::Basename' => 0,
'File::Path' => 0,
'File::Spec' => 0,

105
Changes
View File

@@ -1,7 +1,7 @@
Release notes for SOAP::WSDL 2.00_31
Release notes for SOAP::WSDL 2.00.01
-------
I'm proud to present a new pre-release version of SOAP::WSDL.
I'm proud to present a new release of SOAP::WSDL.
SOAP::WSDL is a toolkit for creating WSDL-based SOAP client interfaces in perl.
@@ -15,6 +15,8 @@ Features:
* Easy-to use API
o Automatically encodes perl data structures as message data
o Automatically sets HTTP headers right
o Datatypes provide hints on method names on calls to non-existant
methods
* Efficient documentation
o SOAP::WSDL::Manual guides you at getting your work done, not at
the module's internals
@@ -23,17 +25,112 @@ Features:
over 95% (excluding documentation - you wouldn't want to read
through it all).
* SOAP::Lite like look and feel
o Where possible, SOAP::WSDL mimics SOAP::Lite's API to allow easy migrations
o Where possible, SOAP::WSDL mimics SOAP::Lite's API to allow easy migration
* XML schema based class library for creating data objects
* High-performance XML parser
* Plugin support. SOAP::WSDL can be extended through plugins in various aspects.
The following plugins are supported:
o Transport plugins via SOAP::WSDL::Factory::Transport
o Serializer plugins via SOAP::WSDL::Factory::Serializer
o Deserializer plugins via SOAP::WSDL::Factory::Serializer
o Deserializer plugins via SOAP::WSDL::Factory::Deserializer
The following changes have been made:
2.00.01
The following features were added (the numbers in square brackets are the
tracker IDs from https://sourceforge.net/tracker/?group_id=111978&atid=660924):
* [ 1941134 ] Server for mod_perl2. Thanks to Noah Robin for contributing.
The following bugs have been fixed (the numbers in square brackets are the
tracker IDs from https://sourceforge.net/tracker/?group_id=111978&atid=660921):
The numbers with # are CPAN RT IDs (http://rt.cpan.org/).
* [ 1944368 ] SOAP/WSDL/XSD/Typelib/SimpleType.pm spelling
* [ 1944367 ] SOAP/WSDL/XSD/Typelib/ComplexType.pm spelling
* [ 1944364 ] SOAP/WSDL/XSD/Typelib/Builtin.pm spelling
* [ 1944362 ] SOAP/WSDL/SOAP/Typelib/Fault11.pm spelling
* [ 1944361 ] SOAP/WSDL/Generator/Visitor.pm spelling
* [ 1944360 ] SOAP/WSDL/Generator/Iterator/WSDL11.pm spelling
* [ 1944359 ] SOAP::WSDL::Factory::Transport spelling
* [ 1944355 ] SOAP::WSDL::Deserializer::XSD.pm spelling
Thanks to "nobody" for correcting these errors.
* [ 1942576 ] SOAP/WSDL/Deserializer/SOM.pm spelling.
* [ 1942568 ] SOAP/WSDL/Client.pm minor spelling/grammar/style cleanup.
* [ 1942562 ] WSDL.pm spelling corrections.
Thanks to Noah Robin for providing patches for these errors.
* #34642 booleans in WSDL attributes don't get converted to perl's
representation (for now - not all attributes covered yet)
* #34714: MessageParser misses character data in elements just below SOAP-ENV:Body
* #34688: wsdl2perl.pl croaks when WSDL operation uses a header
The following uncategorized improvements have been made:
* Storable freeze/thaw speedup in conjunction with upcoming version of
Class::Std::Fast
* improved server doc generation
* improved xsi:nil handling
* serializing an attribute from http://www.w3.org/XML/1998/namespace now
serializes it with xml: prefix. This should probably be moved into the
generator, to avoid testing every attribute
2.00_33 - Mar 30 2008
The following features were added (the numbers in square brackets are the
tracker IDs from https://sourceforge.net/tracker/?group_id=111978&atid=660924):
* [ 1925336 ] Create a Prefix Resolver Plugin Interface for Code Generator
* [ 1898591 ] object stringify returns undef
* [ 1906753 ] Hypens in MyTypes/* cause runtime syntax errors
Hypens and dots in variable and method names are now replaced by _
The following bugs have been fixed (the numbers in square brackets are the
tracker IDs from https://sourceforge.net/tracker/?group_id=111978&atid=660921):
The numbers with # are CPAN RT IDs (http://rt.cpan.org/).
* #33616: Bugs in the META.yml file
* [ 1892895 ] Test failures on RHEL4
* [ 1844956 ] t/SOAP/WSDL/XSD/Typelib/Builtin/NMTOKENS fails test on OS X
* #33376: HTTP Authentication (not implemented or not documented)
The following uncategorized improvements have been made:
* Some minor performance improvements have been made
* The XSD generator now asserts the soap:operation style is "document"
* <wsdl:import> and <xsd:import> now import namespace declarations, too
* The XSD generator now uses the relevant <wsdl:portType>'s
targetNamespace for finding operation messages, not the <wsdl:definition>
element's targetNamespace
* Attribute handling has been improved so it could possibly work.
Attributes from different namespaces are probably still broken.
* Attribute ref handling has been added (though probably broken on
ref cascades).
* <xsd:attributeGroup> elements are now parsed, but have no effect yet.
* <xsd:enumeration> elements are now parsed, but have no effect yet.
2.00_32 - Feb 14 2008
The following features were added (the numbers in square brackets are the
tracker IDs from https://sourceforge.net/tracker/?group_id=111978&atid=660924):
The following bugs have been fixed (the numbers in square brackets are the
tracker IDs from https://sourceforge.net/tracker/?group_id=111978&atid=660921):
The numbers with # are CPAN RT IDs (http://rt.cpan.org/).
* [ 1893147 ] Segfault on 2.0.0_31
The following uncategorized improvements have been made:
* changed SOAP::WSDL::XSD::ComplexType's set_/get_flavor methods to
set_/get_variety to reflect the XML standard more closely.
get_flavor is retained for compatibility reasons.
* added initial support for complexType/simpleContent definitions. Right
now, only restriction derivations are supported.
* fixed an error in the generator_test.wsdl
2.00_31 - Feb 11 2007
The following features were added (the numbers in square brackets are the

View File

@@ -3,6 +3,7 @@ benchmark/hello.pl
benchmark/person.pl
benchmark/person.xml
benchmark/person_profile.pl
benchmark/person_single.pl
benchmark/XSD/01_anyType.t
benchmark/XSD/02_anySimpleType.t
benchmark/XSD/03_string.t
@@ -92,9 +93,12 @@ lib/SOAP/WSDL/Factory/Deserializer.pm
lib/SOAP/WSDL/Factory/Generator.pm
lib/SOAP/WSDL/Factory/Serializer.pm
lib/SOAP/WSDL/Factory/Transport.pm
lib/SOAP/WSDL/Generator/Iterator/WSDL11.pm
lib/SOAP/WSDL/Generator/PrefixResolver.pm
lib/SOAP/WSDL/Generator/Template.pm
lib/SOAP/WSDL/Generator/Template/Plugin/XSD.pm
lib/SOAP/WSDL/Generator/Template/XSD.pm
lib/SOAP/WSDL/Generator/Template/XSD/_type_class.tt
lib/SOAP/WSDL/Generator/Template/XSD/attribute.tt
lib/SOAP/WSDL/Generator/Template/XSD/complexType.tt
lib/SOAP/WSDL/Generator/Template/XSD/complexType/all.tt
lib/SOAP/WSDL/Generator/Template/XSD/complexType/atomicTypes.tt
@@ -103,13 +107,23 @@ lib/SOAP/WSDL/Generator/Template/XSD/complexType/complexContent.tt
lib/SOAP/WSDL/Generator/Template/XSD/complexType/contentModel.tt
lib/SOAP/WSDL/Generator/Template/XSD/complexType/extension.tt
lib/SOAP/WSDL/Generator/Template/XSD/complexType/POD/all.tt
lib/SOAP/WSDL/Generator/Template/XSD/complexType/POD/attributeSet.tt
lib/SOAP/WSDL/Generator/Template/XSD/complexType/POD/choice.tt
lib/SOAP/WSDL/Generator/Template/XSD/complexType/POD/complexContent.tt
lib/SOAP/WSDL/Generator/Template/XSD/complexType/POD/content_model.tt
lib/SOAP/WSDL/Generator/Template/XSD/complexType/POD/restriction.tt
lib/SOAP/WSDL/Generator/Template/XSD/complexType/POD/simpleContent.tt
lib/SOAP/WSDL/Generator/Template/XSD/complexType/POD/simpleContent/extension.tt
lib/SOAP/WSDL/Generator/Template/XSD/complexType/POD/simpleContent/restriction.tt
lib/SOAP/WSDL/Generator/Template/XSD/complexType/POD/structure.tt
lib/SOAP/WSDL/Generator/Template/XSD/complexType/POD/structure/restriction.tt
lib/SOAP/WSDL/Generator/Template/XSD/complexType/POD/structure/simpleContent.tt
lib/SOAP/WSDL/Generator/Template/XSD/complexType/restriction.tt
lib/SOAP/WSDL/Generator/Template/XSD/complexType/simpleContent.tt
lib/SOAP/WSDL/Generator/Template/XSD/complexType/simpleContent/extension.tt
lib/SOAP/WSDL/Generator/Template/XSD/complexType/variety.tt
lib/SOAP/WSDL/Generator/Template/XSD/element.tt
lib/SOAP/WSDL/Generator/Template/XSD/element/POD/contentModel.tt
lib/SOAP/WSDL/Generator/Template/XSD/element/POD/structure.tt
lib/SOAP/WSDL/Generator/Template/XSD/Interface.tt
lib/SOAP/WSDL/Generator/Template/XSD/Interface/Body.tt
@@ -121,6 +135,7 @@ lib/SOAP/WSDL/Generator/Template/XSD/Interface/POD/method_info.tt
lib/SOAP/WSDL/Generator/Template/XSD/Interface/POD/Operation.tt
lib/SOAP/WSDL/Generator/Template/XSD/Interface/POD/Part.tt
lib/SOAP/WSDL/Generator/Template/XSD/Interface/POD/Type.tt
lib/SOAP/WSDL/Generator/Template/XSD/POD/annotation.tt
lib/SOAP/WSDL/Generator/Template/XSD/Server.tt
lib/SOAP/WSDL/Generator/Template/XSD/Server/POD/Message.tt
lib/SOAP/WSDL/Generator/Template/XSD/Server/POD/method_info.tt
@@ -130,10 +145,13 @@ lib/SOAP/WSDL/Generator/Template/XSD/simpleType.tt
lib/SOAP/WSDL/Generator/Template/XSD/simpleType/atomicType.tt
lib/SOAP/WSDL/Generator/Template/XSD/simpleType/contentModel.tt
lib/SOAP/WSDL/Generator/Template/XSD/simpleType/list.tt
lib/SOAP/WSDL/Generator/Template/XSD/simpleType/POD/contentModel.tt
lib/SOAP/WSDL/Generator/Template/XSD/simpleType/POD/list.tt
lib/SOAP/WSDL/Generator/Template/XSD/simpleType/POD/restriction.tt
lib/SOAP/WSDL/Generator/Template/XSD/simpleType/POD/structure.tt
lib/SOAP/WSDL/Generator/Template/XSD/simpleType/POD/union.tt
lib/SOAP/WSDL/Generator/Template/XSD/simpleType/restriction.tt
lib/SOAP/WSDL/Generator/Template/XSD/simpleType/union.tt
lib/SOAP/WSDL/Generator/Template/XSD/Typemap.tt
lib/SOAP/WSDL/Generator/Visitor.pm
lib/SOAP/WSDL/Generator/Visitor/Typelib.pm
@@ -166,13 +184,27 @@ lib/SOAP/WSDL/Transport/Loopback.pm
lib/SOAP/WSDL/Transport/Test.pm
lib/SOAP/WSDL/TypeLookup.pm
lib/SOAP/WSDL/Types.pm
lib/SOAP/WSDL/XSD/Annotation.pm
lib/SOAP/WSDL/XSD/Attribute.pm
lib/SOAP/WSDL/XSD/AttributeGroup.pm
lib/SOAP/WSDL/XSD/Builtin.pm
lib/SOAP/WSDL/XSD/ComplexType.pm
lib/SOAP/WSDL/XSD/Element.pm
lib/SOAP/WSDL/XSD/Enumeration.pm
lib/SOAP/WSDL/XSD/FractionDigits.pm
lib/SOAP/WSDL/XSD/Group.pm
lib/SOAP/WSDL/XSD/Length.pm
lib/SOAP/WSDL/XSD/MaxExclusive.pm
lib/SOAP/WSDL/XSD/MaxInclusive.pm
lib/SOAP/WSDL/XSD/MaxLength.pm
lib/SOAP/WSDL/XSD/MinExclusive.pm
lib/SOAP/WSDL/XSD/MinInclusive.pm
lib/SOAP/WSDL/XSD/MinLength.pm
lib/SOAP/WSDL/XSD/Pattern.pm
lib/SOAP/WSDL/XSD/Schema.pm
lib/SOAP/WSDL/XSD/Schema/Builtin.pm
lib/SOAP/WSDL/XSD/SimpleType.pm
lib/SOAP/WSDL/XSD/TotalDigits.pm
lib/SOAP/WSDL/XSD/Typelib/Attribute.pm
lib/SOAP/WSDL/XSD/Typelib/AttributeSet.pm
lib/SOAP/WSDL/XSD/Typelib/Builtin.pm
@@ -225,12 +257,14 @@ lib/SOAP/WSDL/XSD/Typelib/Builtin/unsignedShort.pm
lib/SOAP/WSDL/XSD/Typelib/ComplexType.pm
lib/SOAP/WSDL/XSD/Typelib/Element.pm
lib/SOAP/WSDL/XSD/Typelib/SimpleType.pm
lib/SOAP/WSDL/XSD/WhiteSpace.pm
LICENSE
Makefile.PL
MANIFEST This list of files
META.yml
MIGRATING
README
SOAP-WSDL-2.00_32.tar
t/001_use.t
t/002_parse_wsdl.t
t/003_wsdl_based_serializer.t
@@ -282,16 +316,22 @@ t/acceptance/wsdl/generator_test.wsdl
t/acceptance/wsdl/generator_test_dot_names.wsdl
t/acceptance/wsdl/generator_unsupported_test.wsdl
t/acceptance/wsdl/import.xsd
t/acceptance/wsdl/import_loop.xsd
t/acceptance/wsdl/message_gateway.wsdl
t/acceptance/wsdl/nested_complextype.wsdl
t/acceptance/wsdl/WSDLParser-import.wsdl
t/acceptance/wsdl/WSDLParser-imported.wsdl
t/acceptance/wsdl/WSDLParser.wsdl
t/acceptance/wsdl/WSDLParser_import_loop.wsdl
t/contributed.wsdl
t/Expat/03_wsdl.t
t/lib/MyComplexType.pm
t/lib/MyElement.pm
t/lib/MySimpleType.pm
t/lib/Test/SOAPMessage.pm
t/lib/Test/SOAP/WSDL/Expat/WSDLParser.pm
t/lib/Test/SOAP/WSDL/Generator/Iterator/WSDL11.pm
t/lib/Test/SOAP/WSDL/Generator/Visitor/Typemap.pm
t/lib/Test/SOAP/WSDL/Tester.pm
t/lib/Typelib/Base.pm
t/lib/Typelib/TEnqueueMessage.pm
t/lib/Typelib/TMessage.pm
@@ -326,12 +366,13 @@ t/SOAP/WSDL/Expat/WSDLParser.t
t/SOAP/WSDL/Factory/Deserializer.t
t/SOAP/WSDL/Factory/Serializer.t
t/SOAP/WSDL/Factory/Transport.t
t/SOAP/WSDL/Generator/attr.pl
t/SOAP/WSDL/Generator/Template.t
t/SOAP/WSDL/Generator/Visitor.t
t/SOAP/WSDL/Generator/Visitor/Typemap.t
t/SOAP/WSDL/Generator/XCS.t
t/SOAP/WSDL/Generator/XSD.t
t/SOAP/WSDL/Generator/XSD_dot_names.t
t/SOAP/WSDL/Generator/XSD_nested_complextype.t
t/SOAP/WSDL/Generator/XSD_unsupported.t
t/SOAP/WSDL/Part.t
t/SOAP/WSDL/PortType.t
@@ -343,9 +384,13 @@ t/SOAP/WSDL/Transport/02_HTTP.t
t/SOAP/WSDL/Transport/acceptance/test2.xml
t/SOAP/WSDL/Transport/acceptance/test3.xml
t/SOAP/WSDL/Typelib/Fault11.t
t/SOAP/WSDL/Types.t
t/SOAP/WSDL/XSD/Attribute.t
t/SOAP/WSDL/XSD/AttributeGroup.t
t/SOAP/WSDL/XSD/Builtin.t
t/SOAP/WSDL/XSD/ComplexType.t
t/SOAP/WSDL/XSD/Element.t
t/SOAP/WSDL/XSD/Enumeration.t
t/SOAP/WSDL/XSD/Schema.t
t/SOAP/WSDL/XSD/SimpleType.t
t/SOAP/WSDL/XSD/Typelib/Attribute.t

175
META.yml
View File

@@ -1,6 +1,6 @@
---
name: SOAP-WSDL
version: 2.00_31
version: 2.00.01
author:
- 'Martin Kutter <martin.kutter@fen-net.de>'
abstract: SOAP with WSDL support
@@ -8,13 +8,7 @@ license: artistic
resources:
license: http://opensource.org/licenses/artistic-license.php
requires:
Class::Std::Fast: !!perl/hash:version
original: v0.0.5
qv: 1
version:
- 0
- 0
- 5
Class::Std::Fast: 0.0.5
Data::Dumper: 0
Date::Format: 0
Date::Parse: 0
@@ -28,149 +22,233 @@ requires:
URI: 0
XML::Parser::Expat: 0
perl: 5.8.0
build_requires:
Class::Std::Fast: 0.0.5
Cwd: 0
Date::Format: 0
Date::Parse: 0
File::Basename: 0
File::Path: 0
File::Spec: 0
Getopt::Long: 0
LWP::UserAgent: 0
List::Util: 0
Module::Build: 0
Storable: 0
Template: 0
Test::More: 0
XML::Parser::Expat: 0
provides:
SOAP::WSDL:
file: lib/SOAP/WSDL.pm
version: 2.00_31
version: 2.00.01
SOAP::WSDL::Base:
file: lib/SOAP/WSDL/Base.pm
version: 2.00_27
version: 2.00.01
SOAP::WSDL::Binding:
file: lib/SOAP/WSDL/Binding.pm
version: 2.00.01
SOAP::WSDL::Client:
file: lib/SOAP/WSDL/Client.pm
version: 2.00_27
version: 2.00.01
SOAP::WSDL::Client::Base:
file: lib/SOAP/WSDL/Client/Base.pm
version: 2.00_25
version: 2.00.01
SOAP::WSDL::Definitions:
file: lib/SOAP/WSDL/Definitions.pm
version: 2.00_27
version: 2.00.01
SOAP::WSDL::Deserializer::Hash:
file: lib/SOAP/WSDL/Deserializer/Hash.pm
version: 2.00_25
version: 2.00.01
SOAP::WSDL::Deserializer::SOM:
file: lib/SOAP/WSDL/Deserializer/SOM.pm
version: 2.00_24
version: 2.00.01
SOAP::WSDL::Deserializer::XSD:
file: lib/SOAP/WSDL/Deserializer/XSD.pm
version: 2.00_25
version: 2.00.01
SOAP::WSDL::Expat::Base:
file: lib/SOAP/WSDL/Expat/Base.pm
version: 2.00_27
version: 2.00.01
SOAP::WSDL::Expat::Message2Hash:
file: lib/SOAP/WSDL/Expat/Message2Hash.pm
version: 2.00_27
version: 2.00.01
SOAP::WSDL::Expat::MessageParser:
file: lib/SOAP/WSDL/Expat/MessageParser.pm
version: 2.00_27
version: 2.00.01
SOAP::WSDL::Expat::MessageStreamParser:
file: lib/SOAP/WSDL/Expat/MessageStreamParser.pm
version: 2.00_24
version: 2.00.01
SOAP::WSDL::Factory::Deserializer:
file: lib/SOAP/WSDL/Factory/Deserializer.pm
version: 2.00_24
version: 2.00.01
SOAP::WSDL::Factory::Generator:
file: lib/SOAP/WSDL/Factory/Generator.pm
version: 2.00_24
version: 2.00.01
SOAP::WSDL::Factory::Serializer:
file: lib/SOAP/WSDL/Factory/Serializer.pm
version: 2.00_24
version: 2.00.01
SOAP::WSDL::Factory::Transport:
file: lib/SOAP/WSDL/Factory/Transport.pm
version: 2.00_31
version: 2.00.01
SOAP::WSDL::Generator::Iterator::WSDL11:
file: lib/SOAP/WSDL/Generator/Iterator/WSDL11.pm
version: 2.00.01
SOAP::WSDL::Generator::PrefixResolver:
file: lib/SOAP/WSDL/Generator/PrefixResolver.pm
version: 2.00.01
SOAP::WSDL::Generator::Template:
file: lib/SOAP/WSDL/Generator/Template.pm
version: 2.00_25
version: 2.00.01
SOAP::WSDL::Generator::Template::Plugin::XSD:
file: lib/SOAP/WSDL/Generator/Template/Plugin/XSD.pm
version: 2.00.01
SOAP::WSDL::Generator::Template::XSD:
file: lib/SOAP/WSDL/Generator/Template/XSD.pm
version: 2.00_27
version: 2.00.01
SOAP::WSDL::Generator::Visitor:
file: lib/SOAP/WSDL/Generator/Visitor.pm
version: 2.00_25
version: 2.00.01
SOAP::WSDL::Generator::Visitor::Typelib:
file: lib/SOAP/WSDL/Generator/Visitor/Typelib.pm
version: 2.00.01
SOAP::WSDL::Generator::Visitor::Typemap:
file: lib/SOAP/WSDL/Generator/Visitor/Typemap.pm
version: 2.00_25
version: 2.00.01
SOAP::WSDL::Message:
file: lib/SOAP/WSDL/Message.pm
version: 2.00.01
SOAP::WSDL::OpMessage:
file: lib/SOAP/WSDL/OpMessage.pm
version: 2.00.01
SOAP::WSDL::Operation:
file: lib/SOAP/WSDL/Operation.pm
version: 2.00.01
SOAP::WSDL::Part:
file: lib/SOAP/WSDL/Part.pm
version: 2.00.01
SOAP::WSDL::Port:
file: lib/SOAP/WSDL/Port.pm
version: 2.00.01
SOAP::WSDL::PortType:
file: lib/SOAP/WSDL/PortType.pm
version: 2.00.01
SOAP::WSDL::SOAP::Address:
file: lib/SOAP/WSDL/SOAP/Address.pm
version: 2.00.01
SOAP::WSDL::SOAP::Body:
file: lib/SOAP/WSDL/SOAP/Body.pm
version: 2.00.01
SOAP::WSDL::SOAP::Header:
file: lib/SOAP/WSDL/SOAP/Header.pm
version: 2.00.01
SOAP::WSDL::SOAP::HeaderFault:
file: lib/SOAP/WSDL/SOAP/HeaderFault.pm
version: 2.00.01
SOAP::WSDL::SOAP::Operation:
file: lib/SOAP/WSDL/SOAP/Operation.pm
version: 2.00_25
version: 2.00.01
SOAP::WSDL::SOAP::Typelib::Fault11:
file: lib/SOAP/WSDL/SOAP/Typelib/Fault11.pm
version: 2.00_25
version: 2.00.01
SOAP::WSDL::Serializer::XSD:
file: lib/SOAP/WSDL/Serializer/XSD.pm
version: 2.00_27
version: 2.00.01
SOAP::WSDL::Server:
file: lib/SOAP/WSDL/Server.pm
version: 2.00_27
version: 2.00.01
SOAP::WSDL::Server::CGI:
file: lib/SOAP/WSDL/Server/CGI.pm
version: 2.00_27
version: 2.00.01
SOAP::WSDL::Service:
file: lib/SOAP/WSDL/Service.pm
version: 2.00.01
SOAP::WSDL::Transport::HTTP:
file: lib/SOAP/WSDL/Transport/HTTP.pm
version: 2.00.01
SOAP::WSDL::Transport::Loopback:
file: lib/SOAP/WSDL/Transport/Loopback.pm
version: 2.00_25
version: 2.00.01
SOAP::WSDL::Transport::Test:
file: lib/SOAP/WSDL/Transport/Test.pm
version: 2.00_25
version: 2.00.01
SOAP::WSDL::TypeLookup:
file: lib/SOAP/WSDL/TypeLookup.pm
version: 2.00_31
version: 2.00.01
SOAP::WSDL::Types:
file: lib/SOAP/WSDL/Types.pm
version: 2.00.01
SOAP::WSDL::XSD::Annotation:
file: lib/SOAP/WSDL/XSD/Annotation.pm
version: 2.00.01
SOAP::WSDL::XSD::Attribute:
file: lib/SOAP/WSDL/XSD/Attribute.pm
version: 2.00_29
version: 2.00.01
SOAP::WSDL::XSD::AttributeGroup:
file: lib/SOAP/WSDL/XSD/AttributeGroup.pm
version: 2.00.01
SOAP::WSDL::XSD::Builtin:
file: lib/SOAP/WSDL/XSD/Builtin.pm
version: 2.00.01
SOAP::WSDL::XSD::ComplexType:
file: lib/SOAP/WSDL/XSD/ComplexType.pm
version: 2.00_29
version: 2.00.01
SOAP::WSDL::XSD::Element:
file: lib/SOAP/WSDL/XSD/Element.pm
version: 2.00_25
version: 2.00.01
SOAP::WSDL::XSD::Enumeration:
file: lib/SOAP/WSDL/XSD/Enumeration.pm
version: 2.00.01
SOAP::WSDL::XSD::FractionDigits:
file: lib/SOAP/WSDL/XSD/FractionDigits.pm
version: 2.00.01
SOAP::WSDL::XSD::Group:
file: lib/SOAP/WSDL/XSD/Group.pm
version: 2.00.01
SOAP::WSDL::XSD::Length:
file: lib/SOAP/WSDL/XSD/Length.pm
version: 2.00.01
SOAP::WSDL::XSD::MaxExclusive:
file: lib/SOAP/WSDL/XSD/MaxExclusive.pm
version: 2.00.01
SOAP::WSDL::XSD::MaxInclusive:
file: lib/SOAP/WSDL/XSD/MaxInclusive.pm
version: 2.00.01
SOAP::WSDL::XSD::MaxLength:
file: lib/SOAP/WSDL/XSD/MaxLength.pm
version: 2.00.01
SOAP::WSDL::XSD::MinExclusive:
file: lib/SOAP/WSDL/XSD/MinExclusive.pm
version: 2.00.01
SOAP::WSDL::XSD::MinInclusive:
file: lib/SOAP/WSDL/XSD/MinInclusive.pm
version: 2.00.01
SOAP::WSDL::XSD::MinLength:
file: lib/SOAP/WSDL/XSD/MinLength.pm
version: 2.00.01
SOAP::WSDL::XSD::Pattern:
file: lib/SOAP/WSDL/XSD/Pattern.pm
version: 2.00.01
SOAP::WSDL::XSD::Schema:
file: lib/SOAP/WSDL/XSD/Schema.pm
version: 2.00_25
version: 2.00.01
SOAP::WSDL::XSD::Schema::Builtin:
file: lib/SOAP/WSDL/XSD/Schema/Builtin.pm
version: 2.00.01
SOAP::WSDL::XSD::SimpleType:
file: lib/SOAP/WSDL/XSD/SimpleType.pm
version: 2.00_25
version: 2.00.01
SOAP::WSDL::XSD::TotalDigits:
file: lib/SOAP/WSDL/XSD/TotalDigits.pm
version: 2.00.01
SOAP::WSDL::XSD::Typelib::Attribute:
file: lib/SOAP/WSDL/XSD/Typelib/Attribute.pm
version: 2.00_29
version: 2.00.01
SOAP::WSDL::XSD::Typelib::AttributeSet:
file: lib/SOAP/WSDL/XSD/Typelib/AttributeSet.pm
version: 2.00_29
version: 2.00.01
SOAP::WSDL::XSD::Typelib::Builtin:
file: lib/SOAP/WSDL/XSD/Typelib/Builtin.pm
version: 2.00_25
version: 2.00.01
SOAP::WSDL::XSD::Typelib::Builtin::ENTITY:
file: lib/SOAP/WSDL/XSD/Typelib/Builtin/ENTITY.pm
SOAP::WSDL::XSD::Typelib::Builtin::ID:
@@ -268,14 +346,19 @@ provides:
file: lib/SOAP/WSDL/XSD/Typelib/Builtin/unsignedShort.pm
SOAP::WSDL::XSD::Typelib::ComplexType:
file: lib/SOAP/WSDL/XSD/Typelib/ComplexType.pm
version: 2.00_31
version: 2.00.01
SOAP::WSDL::XSD::Typelib::Element:
file: lib/SOAP/WSDL/XSD/Typelib/Element.pm
version: 2.00_29
version: 2.00.01
SOAP::WSDL::XSD::Typelib::SimpleType:
file: lib/SOAP/WSDL/XSD/Typelib/SimpleType.pm
version: 2.00.01
SOAP::WSDL::XSD::Typelib::SimpleType::restriction:
file: lib/SOAP/WSDL/XSD/Typelib/SimpleType.pm
version: 2.00.01
SOAP::WSDL::XSD::WhiteSpace:
file: lib/SOAP/WSDL/XSD/WhiteSpace.pm
version: 2.00.01
generated_by: Module::Build version 0.2808
meta-spec:
url: http://module-build.sourceforge.net/META-spec-v1.2.html

View File

@@ -1,5 +1,18 @@
MIGRATING
---------
MIGRATING FROM PRE-2.00_33
--------------------------
The handling of stringification of SOAP::WSDL::XSD simpleType objects with
undef values changed in 2.00_33.
While 2.00_32 and before returned undef on stringification of a undef value,
>=2.00_33 now returns an empty string.
This is due to common usage in templates or the like, where undef is likely
to produce a warning, and the unreliable behavior of
$obj eq undef
which behaves differently in different versions of perl.
MIGRATING FROM PRE-2.00_29
--------------------------
@@ -9,7 +22,7 @@ require the class SOAP::WSDL::XSD::Typelib::Attribute introduced in the same
pre-release.
While interfaces generated with pre-releases back to 2.00_25 work without
change, this does not hold true vice versa: Interfaces generated with
change, this does not hold true vice versa: Interfaces generated with
2.00_29 and above won't work with older pre-releases.
You'll have to update SOAP::WSDL on all your machines.
@@ -17,7 +30,7 @@ You'll have to update SOAP::WSDL on all your machines.
MIGRATING FROM PRE-2.00_24
--------------------------
This section describes how to migrate from 2.00_24 and before versions to
This section describes how to migrate from 2.00_24 and before versions to
2.00_25.
Migrating from 2.00_xx
@@ -25,9 +38,9 @@ Migrating from 2.00_xx
Background
SOAP::WSDL 2.00_xx has used Class::Std as base for its inside out objects
SOAP::WSDL 2.00_xx has used Class::Std as base for its inside out objects
up to 2.00_24. For performance reasons, now Class::Std::Fast is used.
As Class::Std::Fast is a drop-in replacement for Class::Std, there should be
As Class::Std::Fast is a drop-in replacement for Class::Std, there should be
no need to change anything in your (handwritten) code.
Generated interfaces
@@ -42,8 +55,8 @@ Typemaps
SOAP::WSDL now tries to load all typemap classes at once from 2.00_25 on.
If you use __SKIP__ in your typemaps, you'll have to comment out all
path deeper than the path marked with __SKIP__ - if you don't, SOAP::WSDL
If you use __SKIP__ in your typemaps, you'll have to comment out all
paths deeper than the path marked with __SKIP__ - if you don't, SOAP::WSDL
will try to load all correspondent classes.
Migrating from 1.xx
@@ -55,7 +68,7 @@ SOAP::WSDL uses a custom WSDL parser and serializer. It does not rely on XPath
for on the fly WSDL processing, nor does it use SOAP::Data objects for
encoding any more.
You should be able to use your wxisting code under most circumstances.
You should be able to use your existing code under most circumstances.
SOAP::WSDL is the compatibility module for old interfaces.
Overloading

View File

@@ -1,30 +1,5 @@
# Note: this file was auto-generated by Module::Build::Compat version 0.03
unless (eval "use Module::Build::Compat 0.02; 1" ) {
print "This module requires Module::Build to install itself.\n";
require ExtUtils::MakeMaker;
my $yn = ExtUtils::MakeMaker::prompt
(' Install Module::Build now from CPAN?', 'y');
unless ($yn =~ /^y/i) {
die " *** Cannot install without Module::Build. Exiting ...\n";
}
require Cwd;
require File::Spec;
require CPAN;
# Save this 'cause CPAN will chdir all over the place.
my $cwd = Cwd::cwd();
CPAN::Shell->install('Module::Build::Compat');
CPAN::Shell->expand("Module", "Module::Build::Compat")->uptodate
or die "Couldn't install Module::Build, giving up.\n";
chdir $cwd or die "Cannot chdir() back to $cwd: $!";
}
eval "use Module::Build::Compat 0.02; 1" or die $@;
use Module::Build::Compat 0.02;
Module::Build::Compat->run_build_pl(args => \@ARGV);
require Module::Build;

26
README
View File

@@ -3,7 +3,25 @@ INTRO
SOAP-WSDL provides a SOAP client with WSDL support.
This is a developer release - everything may (and most things will) change.
SUBCLASSING
-----------
SOAP-WSDL is still under very active development. Please don't build
applications using the following modules directly:
- SOAP::WSDL::Definitions
- SOAP::WSDL::Port
- SOAP::WSDL::PortType
- SOAP::WSDL::Binding
- SOAP::WSDL::Message
- SOAP::WSDL::Operation
- SOAP::WSDL::OpMessage
- SOAP::WSDL::Part
- SOAP::WSDL::Service
- SOAP::WSDL::Types
- SOAP::WSDL::XSD::Schema
Those will be replaced some time in the future.
INSTALLING
----------
@@ -15,12 +33,12 @@ Use the following mantra:
perl Build test
perl Build install
If you don't have Module::Build installed, you may also use
If you don't have Module::Build installed, you may also use
perl Makefile.PL
make
make
make test
make install
Note that Module::Build is the recommended installer - make will not run
Note that Module::Build is the recommended installer - make will not run
all tests provided with SOAP-WSDL.

BIN
SOAP-WSDL-2.00_32.tar Normal file

Binary file not shown.

View File

@@ -1,11 +1,17 @@
# Unfortunately, Build testcover reports test coverage wrong.
#
# To get a complete coverage report, just run this file as a shell script
# To get a complete coverage report, just run this file as a shell script
# on a linux box (or execute the equivalent commands on another OS):
#
# Note that this shell script requires Devel::CoverX::Covered - if you
# don't have it, comment out the line noted below
#
cd t/
cover -delete
find . -type f -name '*.t' | xargs -n 1 /usr/bin/perl -MDevel::Cover=-silent,1,-summary,0 -I../lib
# Devel::CoverX::Covered
covered runs
cover -ignore_re \.t$ -ignore_re ^lib -coverage="statement" -coverage=condition -coverage=subroutine -coverage="branch"

5
TODO
View File

@@ -1,10 +1,5 @@
TODO list for SOAP::WSDL
2.00 Pre-releases
--------
* Act as SOAP Server [ 1842436 ]
2.1 release
--------
* Support namespaces in SOAP message payload [ 1809057 ]

View File

@@ -1,15 +1,17 @@
#!/usr/bin/perl -w
%DB::packages=(SOAP::WSDL::Expat::MessageParser => 1);
use strict;
use warnings;
use lib '../lib';
use lib '../../Class-Std-Fast/lib';
use lib '/home/martin/workspace/SOAP-WSDL_XS/blib/lib';
use lib '/home/martin/workspace/SOAP-WSDL_XS/blib/arch';
use lib '../t/lib';
# use SOAP::WSDL::SAX::MessageHandler;
use Benchmark qw(cmpthese timethese);
use SOAP::WSDL::Expat::MessageParser;
use SOAP::WSDL::Expat::Message2Hash;
use SOAP::WSDL::Expat::MessageParser_XS;
use SOAP::Lite;
use XML::Simple;
use XML::LibXML;
@@ -17,24 +19,50 @@ use MyComplexType;
use MyElement;
use MySimpleType;
my $xml = q{<SOAP-ENV:Envelope xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
my $xml = q{<SOAP-ENV:Envelope xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
xmlns:SOAP-ENV="http://schemas.xmlsoap.org/soap/envelope/" >
<SOAP-ENV:Body>
<MyAtomicComplexTypeElement xmlns="urn:Test" >
<test>
<test2 >Test2</test2>
<test2 >Test2</test2>
<test2 >Test2</test2>
<test2 >Test2</test2>
<test2 >Test2</test2>
<test2 >Test2</test2>
<test2 >Test2</test2>
<test2 >Test2</test2>
<test2 >Test2</test2>
<test2 >Test2</test2>
<test2 >Test2</test2>
<test2 >Test2</test2>
<test2 >Test55</test2>
<test2 >Test2</test2>
<test2 >Test3</test2>
<test2 >Test4</test2>
<test2 >Test5</test2>
<test2 >Test6</test2>
<test2 >Test7</test2>
<test2 >Test8</test2>
<test2 >Test9</test2>
<test2 >Test10</test2>
<test2 >Test11</test2>
<test2 >Test12</test2>
<test2 >Test13</test2>
<test2 >Test55</test2>
<test2 >Test14</test2>
<test2 >Test15</test2>
<test2 >Test16</test2>
<test2 >Test17</test2>
<test2 >Test18</test2>
<test2 >Test19</test2>
<test2 >Test20</test2>
<test2 >Test21</test2>
<test2 >Test22</test2>
<test2 >Test23</test2>
<test2 >Test24</test2>
<test2 >Test25</test2>
<test2 >Test565</test2>
<test2 >Test27</test2>
<test2 >Test28</test2>
<test2 >Test29</test2>
<test2 >Test30</test2>
<test2 >Test31</test2>
<test2 >Test32</test2>
<test2 >Test33</test2>
<test2 >Test34</test2>
<test2 >Test35</test2>
<test2 >Test36</test2>
<test2 >Test37</test2>
<test2 >Test38</test2>
<test2 >Test55</test2>
</test>
</MyAtomicComplexTypeElement>
</SOAP-ENV:Body></SOAP-ENV:Envelope>};
@@ -57,13 +85,17 @@ my @data;
my $deserializer = SOAP::Deserializer->new();
sub libxml_test {
my $parser_xs = SOAP::WSDL::Expat::MessageParser_XS->new({
class_resolver => 'FakeResolver'
});
sub libxml_test {
my $dom = $libxml->parse_string( $xml );
push @data, dom2hash( $dom->firstChild );
};
sub dom2hash {
for ($_[0]->childNodes) {
for ($_[0]->childNodes) {
if (exists $_[1]->{ $_->nodeName }) {
if (ref $_[1]->{ $_->nodeName } eq 'ARRAY') {
if ($_->nodeName eq '#text') {
@@ -78,7 +110,7 @@ sub dom2hash {
$_[1] = [ $_[1], $_->textContent() ];
}
else {
$_[1]->{ $_->nodeName } = [ $_[1]->{ $_->nodeName } ,
$_[1]->{ $_->nodeName } = [ $_[1]->{ $_->nodeName } ,
dom2hash( $_, {} ) ];
}
}
@@ -94,11 +126,11 @@ sub dom2hash {
}
return $_[1];
}
cmpthese 5000,
cmpthese 5000,
{
'SOAP::WSDL (Hash)' => sub { push @data, $hash_parser->parse( $xml ) },
'SOAP::WSDL (XSD)' => sub { push @data, $parser->parse( $xml ) },
'SOAP::WSDL_XS (XSD)' => sub { push @data, $parser_xs->parse_string( $xml ) },
'XML::Simple (Hash)' => sub { push @data, XMLin $xml },
'XML::LibXML (DOM)' => sub { push @data, $libxml->parse_string( $xml ) },
'XML::LibXML (Hash)' => \&libxml_test,
@@ -128,3 +160,18 @@ BEGIN {
};
};
};
__END__
Output on my machine:
xml length: 641 bytes
Rate SOAP::Lite XML::Simple (Hash) SOAP::WSDL (XSD) XML::LibXML (Hash) SOAP::WSDL (Hash) SOAP::WSDL_XS (XSD) XML::LibXML (DOM)
SOAP::Lite 446/s -- -54% -72% -73% -80% -95% -96%
XML::Simple (Hash) 963/s 116% -- -39% -41% -57% -89% -91%
SOAP::WSDL (XSD) 1587/s 256% 65% -- -3% -29% -81% -86%
XML::LibXML (Hash) 1629/s 265% 69% 3% -- -27% -81% -85%
SOAP::WSDL (Hash) 2222/s 398% 131% 40% 36% -- -74% -80%
SOAP::WSDL_XS (XSD) 8475/s 1798% 780% 434% 420% 281% -- -24%
XML::LibXML (DOM) 11111/s 2389% 1053% 600% 582% 400% 31% --

View File

@@ -11,7 +11,7 @@ my $obj = SOAP::WSDL::XSD::Typelib::Builtin::anySimpleType->new();
timethese 10000, {
'new' => sub { SOAP::WSDL::XSD::Typelib::Builtin::anySimpleType->new() },
'new + params' => sub { SOAP::WSDL::XSD::Typelib::Builtin::anySimpleType->new({
value => 'Teststring'
value => 'Teststring',
}) },
'set_FOO' => sub { $obj->set_value('Test') },
};

View File

@@ -11,8 +11,9 @@ my $obj = SOAP::WSDL::XSD::Typelib::Builtin::string->new();
timethese 20000, {
'new' => sub { SOAP::WSDL::XSD::Typelib::Builtin::string->new() },
'new + params' => sub { SOAP::WSDL::XSD::Typelib::Builtin::string->new({
value => 'Teststring'
}) },
value => 'Teststring',
})
},
};
$obj->set_value('Foobar');
@@ -36,7 +37,7 @@ new + params: 1 wallclock secs ( 0.53 usr + 0.01 sys = 0.54 CPU) @ 37037.04/s
Benchmark: timing 1000000 iterations of get_FOO, set_FOO...
get_FOO: 2 wallclock secs ( 1.43 usr + 0.01 sys = 1.44 CPU) @ 694444.44/s (n=1000000)
set_FOO: 0 wallclock secs ( 1.43 usr + 0.01 sys = 1.44 CPU) @ 694444.44/s (n=1000000)
::Fast
---
@@ -47,7 +48,7 @@ Benchmark: timing 1000000 iterations of get_FOO, set_FOO...
get_FOO: 0 wallclock secs ( 0.81 usr + 0.00 sys = 0.81 CPU) @ 1234567.90/s (n=1000000)
set_FOO: 2 wallclock secs ( 0.87 usr + 0.01 sys = 0.88 CPU) @ 1136363.64/s (n=1000000)
::Fast with inlined ID
::Fast with inlined ID
Benchmark: timing 20000 iterations of new, new + params...
new: 0 wallclock secs ( 0.41 usr + 0.00 sys = 0.41 CPU) @ 48780.49/s (n=20000)
new + params: 1 wallclock secs ( 0.52 usr + 0.00 sys = 0.52 CPU) @ 38461.54/s (n=20000)

View File

@@ -1,29 +1,43 @@
#!/usr/bin/perl -w
use strict;
use warnings;
use diagnostics;
use lib '../example/lib';
use lib '/home/martin/workspace/SOAP-WSDL-Fast_XS/blib/lib';
use lib '/home/martin/workspace/SOAP-WSDL-Fast_XS/blib/arch';
use lib '../../SOAP-Lite-0.71/lib';
use lib '/home/martin/workspace/SOAP-WSDL_XS/blib/lib';
use lib '/home/martin/workspace/SOAP-WSDL_XS/blib/arch';
use Data::Dumper;
use SOAP::Lite;
use XML::Compile::WSDL11;
use XML::Compile::Transport::SOAPHTTP;
use MyInterfaces::HelloWorld::HelloWorldSoap;
use SOAP::WSDL::Deserializer::XSD_XS;
use Benchmark qw(cmpthese);
use Benchmark qw(cmpthese timethese);
use SOAP::WSDL::Transport::HTTP;
use SOAP::WSDL::Factory::Transport;
SOAP::WSDL::Factory::Transport->register('http', 'SOAP::WSDL::Transport::HTTP');
#my $proxy = 'http://localhost:81/soap-wsdl-test/helloworld.pl';
my $proxy = 'http://localhost:81/soap-wsdl-test/helloworld';
my $lite = SOAP::Lite->new(
proxy => 'http://localhost:81/soap-wsdl-test/helloworld.pl'
proxy => $proxy
);
$lite->on_action( sub { "urn:HelloWorld#sayHello" });
$lite->autotype(0);
my $soap = MyInterfaces::HelloWorld::HelloWorldSoap->new();
my $soap = MyInterfaces::HelloWorld::HelloWorldSoap->new({
proxy => $proxy,
});
my $soap_xs = MyInterfaces::HelloWorld::HelloWorldSoap->new();
my $soap_xs = MyInterfaces::HelloWorld::HelloWorldSoap->new({
proxy => $proxy,
});
$soap_xs->set_deserializer( SOAP::WSDL::Deserializer::XSD_XS->new() );
my @result;
my @result = ();;
sub wsdl_bench {
push @result, $soap->sayHello({
@@ -40,7 +54,12 @@ sub wsdl_xs_bench {
}
my $wsdl = XML::Compile::WSDL11->new('../example/wsdl/11_helloworld.wsdl');
my $call = $wsdl->compileClient('sayHello');
my $call = $wsdl->compileClient('sayHello',
sloppy_integers => 1,
check_values => 0,
check_values => 0,
validation => 0,
);
sub compile_bench {
push @result, $call->(
@@ -58,12 +77,16 @@ sub lite_bench {
);
}
# give all a chance to perform first-run initializations
compile_bench();
lite_bench();
wsdl_bench();
wsdl_xs_bench();
cmpthese 150, {
timethese 150, {
'SOAP::WSDL' => \&wsdl_bench,
'SOAP::WSDL_XS' => \&wsdl_xs_bench,
'XML::Compile' => \&compile_bench,
# 'SOAP::Lite' => \&lite_bench,
}
'SOAP::Lite' => \&lite_bench,
};

View File

@@ -1,5 +1,7 @@
use lib '../lib';
use lib '../example/lib';
use lib '../../Class-Std-Fast/lib';
use lib '../../SOAP-Lite-0.71/lib';
use lib '../../SOAP-WSDL_XS/blib/lib';
use lib '../../SOAP-WSDL_XS/blib/arch';
use strict;
@@ -11,15 +13,80 @@ use XML::Compile::Util;
use XML::Compile::WSDL11;
use XML::Simple;
use SOAP::Lite;
use MyInterfaces::TestService::TestPort;
use SOAP::WSDL::Deserializer::XSD_XS;
use SOAP::WSDL::Factory::Deserializer;
#
# register SOAP::WSDL's transport as default for SOAP::WSDL and SOAP::WSDL_XS
# - they use SOAP::Lite's SOAP::Transport::* if available
#
use SOAP::WSDL::Transport::HTTP;
use SOAP::WSDL::Factory::Transport;
SOAP::WSDL::Factory::Transport->register('http', 'SOAP::WSDL::Transport::HTTP');
$XML::Simple::PREFERRED_PARSER = 'XML::Parser';
use SOAP::Lite;
use MyInterfaces::TestService::TestPort;
my $person = {
PersonID => { # MyTypes::PersonID
ID => 1, # int
},
Salutation => 'Salutation0', # string
Name => 'Name0', # string
GivenName => 'Martin', # string
DateOfBirth => '1970-01-01', # date
HomeAddress => { # MyTypes::Address
Street => 'Street 0', # string
ZIP => '00000', # string
City => 'City0', # string
Country => 'Country0', # string
PhoneNumber => '++499131123456', # PhoneNumber
MobilePhoneNumber => '++49150123456', # PhoneNumber
},
WorkAddress => { # MyTypes::Address
Street => 'Somestreet 23', # string
ZIP => '12345', # string
City => 'SomeCity', # string
Country => 'Germany', # string
PhoneNumber => '++499131123456', # PhoneNumber
MobilePhoneNumber => '++49150123456', # PhoneNumber
},
Contracts => { # MyTypes::ArrayOfContract
Contract => [
{ # MyTypes::Contract
ContractID => 100000, # long
ContractName => 'SomeContract0', # string
},
{ # MyTypes::Contract
ContractID => 100001, # long
ContractName => 'SomeContract1', # string
},
{ # MyTypes::Contract
ContractID => 100002, # long
ContractName => 'SomeContract2', # string
},
{ # MyTypes::Contract
ContractID => 100003, # long
ContractName => 'SomeContract3', # string
},
],
},
}
;
#
# compile XML::Compile client with the options suggested by Mark Overmeer
# for maximum speedup
#
my $compile = XML::Compile::WSDL11->new('../example/wsdl/Person.wsdl',
sloppy_integers => 1,
check_values => 0,
check_values => 0,
validation => 0,
ignore_facets => 1,
);
my $compile = XML::Compile::WSDL11->new('../example/wsdl/Person.wsdl');
my $call = $compile->compileClient('ListPerson');
$call->({ in => undef});
@@ -39,8 +106,7 @@ $lite->on_action( sub { 'http://www.example.org/benchmark/ListPerson' } );
SOAP::WSDL::Factory::Deserializer->register('1.1' => 'SOAP::WSDL::Deserializer::XSD_XS' );
my $wsdl_xs = MyInterfaces::TestService::TestPort->new();
# trigger loading of XML Data
my $count = 100;
my $count = 70;
my @data = ();
my $n = 0;
print "Benchmark conducted with
@@ -53,34 +119,45 @@ Benchmark $n: Store result in private variable and destroy it
";
$n++;
cmpthese $count, {
# 'XML::Simple' => sub { my $result = XMLin( MyData::xml() )},
'SOAP::WSDL' => sub { my $result = $soap->ListPerson({}) },
'XML::Compile' => sub { my $result = $call->() },
'SOAP::WSDL_XS' => sub { my $result = $wsdl_xs->ListPerson({}) },
# 'SOAP::Lite' => sub { my $result = $deserializer->deserialize( MyData::xml() )},
'SOAP::Lite' => sub { my $som = $lite->call('ListPerson') },
};
print "\nBenchmark $n: Push result on list\n";
$n++;
cmpthese $count, {
# 'XML::Simple' => sub { push @data, XMLin( MyData::xml() )},
'SOAP::WSDL' => sub { push @data, $soap->ListPerson({}) },
'XML::Compile' => sub { push @data, $call->() },
'SOAP::WSDL' => sub { push @data, $soap->ListPerson({}) },
'XML::Compile' => sub { push @data, $call->() },
'SOAP::WSDL_XS' => sub { push @data, $wsdl_xs->ListPerson({}) },
# 'SOAP::Lite' => sub { push @data, $deserializer->deserialize( MyData::xml() )}
'SOAP::Lite' => sub { push @data, $lite->call('ListPerson') },
'SOAP::Lite' => sub { push @data, $lite->call('ListPerson') },
};
@data = ();
print "\nBenchmark $n: Play it again, Sam\n";
$n++;
cmpthese $count, {
# 'XML::Simple' => sub { push @data, XMLin( MyData::xml() )},
'SOAP::WSDL' => sub { push @data, $soap->ListPerson({}) },
'SOAP::WSDL' => sub { push @data, $soap->ListPerson({}) },
'SOAP::WSDL_XS' => sub { push @data, $wsdl_xs->ListPerson({}) },
'XML::Compile' => sub { push @data, $call->() },
# 'SOAP::Lite' => sub { push @data, $deserializer->deserialize( MyData::xml() )}
'SOAP::Lite' => sub { push @data, $lite->call('ListPerson') },
'XML::Compile' => sub { push @data, $call->() },
'SOAP::Lite' => sub { push @data, $lite->call('ListPerson') },
};
print "\nBenchmark $n: ca. 1kB request - result destroyed immediately\n";
$n++;
cmpthese $count, {
'SOAP::WSDL' => sub { my $result = $soap->ListPerson({ in => $person }) },
'SOAP::WSDL_XS' => sub { my $result = $wsdl_xs->ListPerson({ in => $person }) },
'XML::Compile' => sub { my $result = $call->({ in => $person }) },
};
print "\nBenchmark $n: ca. 1kB request - push result on list\n";
$n++;
cmpthese $count, {
'SOAP::WSDL' => sub { push @data, $soap->ListPerson({ in => $person }) },
'SOAP::WSDL_XS' => sub { push @data, $wsdl_xs->ListPerson({ in => $person }) },
'XML::Compile' => sub { push @data, $call->({ in => $person }) },
};

View File

@@ -3,9 +3,17 @@ use lib '../example/lib';
use lib '../../SOAP-WSDL_XS/blib/lib';
use lib '../../SOAP-WSDL_XS/blib/arch';
use strict;
# use Benchmark;
use SOAP::WSDL::Deserializer::XSD_XS;
use SOAP::WSDL::Factory::Deserializer;
# # register for SOAP 1.1
SOAP::WSDL::Factory::Deserializer->register('1.1' => 'SOAP::WSDL::Deserializer::XSD_XS' );
use MyInterfaces::TestService::TestPort;
my $soap = MyInterfaces::TestService::TestPort->new();
# Load all classes - XML::Compile has created everything before, too
for (1..100) { $soap->ListPerson({}) };
if (@ARGV) { print $soap->ListPerson({}) }
else {
$soap->ListPerson({})
}

File diff suppressed because one or more lines are too long

View File

@@ -19,6 +19,7 @@ my %opt = (
proxy => undef,
generator => 'XSD',
server => 0,
namespace => 0,
);
{ # a block just to scope "no warnings"
@@ -34,12 +35,14 @@ my %opt = (
ReadMode 1;
$user = ReadLine();
ReadMode 0;
chomp $user;
};
if (not $password = delete $opt{password}) {
print 'Password:';
ReadMode 2;
$user = ReadLine;
$password = ReadLine;
ReadMode 0;
chomp $password;
};
return ($user, $password);
};
@@ -61,6 +64,7 @@ GetOptions(\%opt,
password=s
generator=s
server
namespaces|n
)
);

View File

@@ -1,4 +1,5 @@
#!/usr/bin/perl -w
package main;
use strict;
use warnings;
use lib '../../lib';
@@ -33,7 +34,7 @@ in examples/wsdl/helloworld.wsdl
Before using this script, you should secure your webserver. The easiest way
to do so is to let it listen to 127.0.0.1 only.
Then make a ScriptAlias named /soap-wsdl-test/ pointing at the directory
Then make a ScriptAlias named /soap-wsdl-test/ pointing at the directory
this file lies in.
For my apache, it looks like this:

View File

@@ -2,7 +2,7 @@
package main;
use strict;
use warnings;
#use lib qw(../lib ../../lib);
use lib qw(../lib ../../lib);
use MyElements::ListPersonResponse;
use MyServer::TestService::TestPort;
my $server = MyServer::TestService::TestPort->new({

View File

@@ -15,12 +15,11 @@ my %dispatch_to :ATTR(:name<dispatch_to>);
my $action_map_ref = {
'urn:HelloWorld#sayHello' => 'sayHello',
};
sub START {
my ($self, $ident, $arg_ref) = @_;
eval "require $transport_class_of{ $ident }"
eval "require $transport_class_of{ $ident }"
or die "Cannot load transport class $transport_class_of{ $ident }: $@";
$transport_of{ $ident } = $transport_class_of{ $ident }->new({
action_map_ref => $action_map_ref,
@@ -30,7 +29,7 @@ sub START {
}
sub handle {
$transport_of{ ${ $_[0] } }->handle();
$transport_of{ ${ $_[0] } }->handle(@_[1..$#_]);
}
1;
@@ -76,7 +75,7 @@ located at http://localhost:81/soap-wsdl-test/helloworld.pl.
Constructor.
The C<dispatch_to> argument is mandatory. It must be a class or object
The C<dispatch_to> argument is mandatory. It must be a class or object
implementing the SOAP Service methods listed below.
=head2 SOAP Service methods
@@ -94,9 +93,9 @@ class.
my ($self, $body, $header) = @_;
# body is a ??? object - sorry, POD not implemented yet
# header is a ??? object - sorry, POD not implemented yet
# do something with body and header...
return MyElements::sayHelloResponse->new( {
sayHelloResult => $some_value, # string
},

View File

@@ -14,7 +14,7 @@ use Class::Std::Fast;
use SOAP::WSDL::XSD::Typelib::Builtin::anySimpleType;
use LWP::UserAgent;
our $VERSION= '2.00_31';
use version; our $VERSION= qv('2.00.01');
my %no_dispatch_of :ATTR(:name<no_dispatch>);
my %wsdl_of :ATTR(:name<wsdl>);
@@ -330,6 +330,17 @@ read L<SOAP::WSDL::Manual>.
For using an interpreting (thus slow and somewhat troublesome) WSDL based
SOAP client, which mimics L<SOAP::Lite|SOAP::Lite>'s API, read on.
Creating Interface classes is the recommended usage.
Did I say you should create interface classes following the steps in
L<SOAP::WSDL::Manual>?
If you're migrating from earlier versions of SOAP::WSDL, you should read the
MIGRATING documentation.
The stuff below is for users of the 1.2x SOAP::WSDL series. All others,
please refer to L<SOAP::WSDL::Manual>
=head1 SYNOPSIS
my $soap = SOAP::WSDL->new(
@@ -501,7 +512,7 @@ it's content.
The object tree has two main functions: It knows how to serialize data passed
as hash ref, and how to render the WSDL elements found into perl classes.
Yup your're right, there's a builting code generation facility. Read
Yup you're right; there's a builtin code generation facility. Read
L<SOAP::WSDL::Manual> for using it.
=item * no_dispatch
@@ -522,6 +533,28 @@ You may pass the servicename and portname as attributes to wsdlinit, though.
=back
=head1 Differences to previous versions
The following functionality is no longer supported:
=head2 Operation overloading
The SOAP standard allows operation overloading - that is, you may specify
SOAP operations with more than one message. The client/server than can
choose which message to send. This SOAP feature is usually used similar
to the use of methods with different argument lists in C++.
Operation overloading is no longer supported. The WS-I Basic profile does
not operation overloading. The same functionality as operation overloading
can be obtained by using a choice declaration in the XML Schema.
=head2 readable
Readable has no effect any more. If you need readable debug output, copy the
SOAP message to your favorite XML editor and run the source format command.
Outputting readable XML requires lots of programming for little use: The
resulting XMl is still quite unreadable.
=head1 Differences to SOAP::Lite
=head2 readable
@@ -562,7 +595,7 @@ See L<class_resolver|class_resolver> above.
=item * Hash refs
This is for convnience: A single hash ref containing the content of the
This is for convenience: A single hash ref containing the content of the
SOAP body.
=item * xml
@@ -604,6 +637,18 @@ details.
=over
=item * $obj == undef does not work in perl 5.8.6 and perl 5.8.7
Due to some strange behaviour in perl 5.8.6 and perl 5.8.7, stringification
overloading is not triggered during comparison with undef.
While this is probably harmless in most cases, it's important to know that
you need to do
defined( $obj->get_value() )
to check for undef values in simpleType objects.
=item * perl 5.8.0 or higher required
SOAP::WSDL needs perl 5.8.0 or higher. This is due to a bug in perls
@@ -617,24 +662,26 @@ If you want this changed, email me a copy of the specs, please.
=item * Incomplete XML Schema definitions support
XML Schema attribute definitions are not supported yet.
This section describes the limitations of SOAP::WSDL, that is the interpreting
SOAP client. For limitations of L<wsdl2perl.pl|wsdl2perl.pl> generated
SOAP clients, see L<SOAP::WSDL::Manual::XSD>.
Importing external definitions is not supported yet.
XML Schema attribute definitions are not supported in interpreting mode.
The following XML Schema definitions varieties are not supported:
The following XML Schema definitions varieties are not supported in
interpreting mod:
group
union
simpleContent
The following XML Schema definition content model is only partially
supported:
supported in interpreting mode:
complexContent - only restriction variety supported
See L<SOAP::WSDL::Manual::XSD> for details.
=item * Serialization of hash refs dos not work for ambiguos values
=item * Serialization of hash refs does not work for ambiguous values
If you have list elements with multiple occurences allowed, SOAP::WSDL
has no means of finding out which variant you meant.
@@ -644,17 +691,17 @@ Passing in item => [1,2,3] could serialize to
<item>1 2</item><item>3</item>
<item>1</item><item>2 3</item>
Ambiguos data can be avoided by providing data as objects.
Ambiguous data can be avoided by providing data as objects.
=item * XML Schema facets
Almost no XML schema facets are implemented yet. The only facets
Almost no XML schema facets are implemented. The only facets
currently implemented are:
fixed
default
The following facets have no influence yet:
The following facets have no influence:
minLength
maxLength
@@ -678,10 +725,10 @@ The following facets have no influence yet:
Full featured SOAP-library, little WSDL support. Supports rpc-encoded style
only. Many protocols supported.
=item * L<XML::Compile::WSDL|XML::Compile::WSDL> / L<XML::Compile::SOAP|XML::Compile::SOAP>
=item * L<XML::Compile::SOAP|XML::Compile::SOAP>
Creates parser/generator functions for SOAP messages. Includes SOAP Client
and Server implementatios.
and Server implementations. Can validate XML messages.
You might want to give it a try, especially if you need to adhere very
closely to the XML Schema / WSDL specs.
@@ -712,20 +759,33 @@ became v1.23)
David Bussenschutt, Damian A. Martinez Gelabert, Dennis S. Hennen, Dan Horne,
Peter Orvos, Mark Overmeer, Jon Robens, Isidro Vila Verde and Glenn Wood
spotted bugs and/or suggested improvements in the 1.2x releases.
(in alphabetical order) spotted bugs and/or suggested improvements in
the 1.2x releases.
Noah Robin contirbuted lots of documentation fixes, and the mod_perl server.
JT Justman and Noah Robin provided early feedback and bug reports for
the 2.xx pre-releases.
Adam Kennedy checked and suggested improvements on metadata and dependencies
in the 2.xx pre-releases.
Andreas 'ac0v' Specht constantly asked for better performance.
JT Justman provided early feedback for the 2.xx pre-releases.
Matt S. Trout encouraged me "to get a non-dev-release out."
CPAN Testers provided most valuable (automated) feedback. Thanks a lot.
Numerous people sent me their real-world WSDL files for testing. Thank you.
Paul Kulchenko and Byrne Reese wrote and maintained SOAP::Lite and
thus provided a base (and counterpart) for SOAP::WSDL.
Mark Overmeer wrote XML::Compile::SOAP - competition is good for business.
=head1 LICENSE AND COPYRIGHT
Copyright 2004-2007 Martin Kutter.
Copyright 2004-2008 Martin Kutter.
This file is part of SOAP-WSDL. You may distribute/modify it under
the same terms as perl itself
@@ -736,10 +796,9 @@ Martin Kutter E<lt>martin.kutter fen-net.deE<gt>
=head1 REPOSITORY INFORMATION
$Rev: 524 $
$Rev: 616 $
$LastChangedBy: kutterma $
$Id: WSDL.pm 524 2008-02-10 23:24:43Z kutterma $
$Id: WSDL.pm 616 2008-04-22 21:51:49Z kutterma $
$HeadURL: http://soap-wsdl.svn.sourceforge.net/svnroot/soap-wsdl/SOAP-WSDL/trunk/lib/SOAP/WSDL.pm $
=cut

View File

@@ -5,18 +5,30 @@ use Class::Std::Fast::Storable;
use List::Util qw(first);
use Carp qw(croak carp confess);
our $VERSION='2.00_27';
use version; our $VERSION = qv('2.00.01');
my %id_of :ATTR(:name<id> :default<()>);
my %name_of :ATTR(:name<name> :default<()>);
my %documentation_of :ATTR(:name<documentation> :default<()>);
my %targetNamespace_of :ATTR(:name<targetNamespace> :default<()>);
my %xmlns_of :ATTR(:name<xmlns> :default<{}>);
my %parent_of :ATTR(:name<parent> :default<()>);
my %id_of :ATTR(:name<id> :default<()>);
my %lang_of :ATTR(:name<lang> :default<()>);
my %name_of :ATTR(:name<name> :default<()>);
my %documentation_of :ATTR(:name<documentation> :default<()>);
my %annotation_of :ATTR(:name<annotation> :default<()>);
my %targetNamespace_of :ATTR(:name<targetNamespace> :default<()>);
my %xmlns_of :ATTR(:name<xmlns> :default<{}>);
my %parent_of :ATTR(:name<parent> :default<()>);
my %namespaces_of :ATTR(:default<{}>);
sub namespaces {
return shift->get_xmlns();
}
sub START {
my ($self, $ident, $arg_ref) = @_;
$xmlns_of{ $ident }->{ '#default' } = $self->get_xmlns()->{ '#default' };
$xmlns_of{ $ident }->{ 'xml' } = 'http://www.w3.org/XML/1998/namespace';
$namespaces_of{ $ident }->{ '#default' } = $self->get_xmlns()->{ '#default' };
$namespaces_of{ $ident }->{ 'xml' } = 'http://www.w3.org/XML/1998/namespace';
}
sub DEMOLISH {
@@ -87,7 +99,12 @@ sub AUTOMETHOD {
return $result_ref->[0];
};
}
confess "$subname not found in class " . ref $self;
# return if called from can();
my @caller = caller(2);
return if ($caller[3] eq 'Class::Std::Fast::__ANON__');
# confess "$subname not found in class " . ref $self;
return;
}
sub init {
@@ -109,8 +126,8 @@ sub init {
}
sub expand {
my ($self, , $qname) = @_;
my $ns_of = $self->get_xmlns();
my ($self, $qname) = @_;
my $ns_of = $self->namespaces();
if (not $qname=~m{:}xm) {
die "un-prefixed element name <$qname> found, but no default namespace set\n"
if not defined $ns_of->{ '#default' };

View File

@@ -5,6 +5,8 @@ use Class::Std::Fast::Storable;
use List::Util qw(first);
use base qw(SOAP::WSDL::Base);
use version; our $VERSION = qv('2.00.01');
my %operation_of :ATTR(:name<operation> :default<()>);
my %type_of :ATTR(:name<type> :default<()>);
my %transport_of :ATTR(:name<transport> :default<()>);

View File

@@ -11,7 +11,7 @@ use SOAP::WSDL::Factory::Serializer;
use SOAP::WSDL::Factory::Transport;
use SOAP::WSDL::Expat::MessageParser;
our $VERSION = '2.00_27';
use version; our $VERSION = qv('2.00.01');
my %class_resolver_of :ATTR(:name<class_resolver> :default<()>);
my %no_dispatch_of :ATTR(:name<no_dispatch> :default<()>);
@@ -259,10 +259,10 @@ You probably should not use a character encoding different from utf8:
SOAP::WSDL::Client will not convert the request into a different encoding
(yet).
To leave out the encoding, just set the content type without appendet charset
like in
To leave out the encoding, just set the content type without appending charset
like this:
text/xml
$soap->set_content_type('text/xml');
Default:
@@ -271,7 +271,7 @@ Default:
=head2 Features different from SOAP::Lite
SOAP::WSDL does not aim to be a complete replacement for SOAP::Lite - the
SOAP::Lite module has it's strengths and weaknesses and SOAP::WSDL is
SOAP::Lite module has its strengths and weaknesses and SOAP::WSDL is
designed as a cure for the weakness of little WSDL support - nothing more,
nothing less.
@@ -283,7 +283,7 @@ A few things are quite different from SOAP::Lite, though:
=head3 SOAP request data
SOAP request data may either be given as message object, or as hash ref (in
SOAP request data may either be given as message object, or as a hash ref (in
which case it will automatically be encoded into a message object).
=head3 Return values
@@ -303,7 +303,7 @@ The fault object is a SOAP1.1 fault object of the following
C<SOAP::WSDL::SOAP::Typelib::Fault11>.
SOAP::WSDL::SOAP::Typelib::Fault11 objects are false in boolean context, so
you can just do something like
you can just do something like:
my $result = $soap->call($method, $data);
@@ -360,9 +360,9 @@ Martin Kutter E<lt>martin.kutter fen-net.deE<gt>
=head1 REPOSITORY INFORMATION
$Rev: 455 $
$Rev: 616 $
$LastChangedBy: kutterma $
$Id: Client.pm 455 2007-12-14 15:50:16Z kutterma $
$Id: Client.pm 616 2008-04-22 21:51:49Z kutterma $
$HeadURL: http://soap-wsdl.svn.sourceforge.net/svnroot/soap-wsdl/SOAP-WSDL/trunk/lib/SOAP/WSDL/Client.pm $
=cut

View File

@@ -4,21 +4,21 @@ use warnings;
use base 'SOAP::WSDL::Client';
use Scalar::Util qw(blessed);
our $VERSION = '2.00_25';
use version; our $VERSION = qv('2.00.01');
sub call {
my ($self, $method, $body, $header) = @_;
# Treat non-objects special
if (not blessed $body) {
# make sure there's something sensible in our body data
$body = {} if not defined $body;
$body = ref $body eq 'ARRAY' ? $body : [ $body ];
my @body_from = @{ $body }; # make a copy
# build list of parts as objects initialized with
# build list of parts as objects initialized with
# parameters given
my @part_from = ();
foreach my $class (@{ $method->{ body }->{ parts } }) {
@@ -78,9 +78,9 @@ Martin Kutter E<lt>martin.kutter fen-net.deE<gt>
=head1 REPOSITORY INFORMATION
$Rev: 501 $
$Rev: 616 $
$LastChangedBy: kutterma $
$Id: Base.pm 501 2008-01-26 20:23:32Z kutterma $
$Id: Base.pm 616 2008-04-22 21:51:49Z kutterma $
$HeadURL: http://soap-wsdl.svn.sourceforge.net/svnroot/soap-wsdl/SOAP-WSDL/trunk/lib/SOAP/WSDL/Client/Base.pm $
=cut

View File

@@ -9,22 +9,22 @@ use List::Util qw(first);
use Class::Std::Fast::Storable;
use base qw(SOAP::WSDL::Base);
our $VERSION='2.00_27';
use version; our $VERSION = qv('2.00.01');
my %types_of :ATTR(:name<types> :default<[]>);
my %message_of :ATTR(:name<message> :default<()>);
my %portType_of :ATTR(:name<portType> :default<()>);
my %binding_of :ATTR(:name<binding> :default<()>);
my %service_of :ATTR(:name<service> :default<()>);
my %namespace_of :ATTR(:name<namespace> :default<()>);
my %types_of :ATTR(:name<types> :default<[]>);
my %message_of :ATTR(:name<message> :default<[]>);
my %portType_of :ATTR(:name<portType> :default<[]>);
my %binding_of :ATTR(:name<binding> :default<[]>);
my %service_of :ATTR(:name<service> :default<[]>);
my %namespace_of :ATTR(:name<namespace> :default<()>);
# must be attr for Class::Std::Fast::Storable
my %attributes_of :ATTR();
%attributes_of = (
binding => \%binding_of,
message => \%message_of,
portType => \%portType_of,
service => \%service_of,
binding => \%binding_of,
message => \%message_of,
portType => \%portType_of,
service => \%service_of,
);
# Function factory - we could be writing this method for all %attribute
@@ -118,9 +118,9 @@ Martin Kutter E<lt>martin.kutter fen-net.deE<gt>
=head1 REPOSITORY INFORMATION
$Rev: 477 $
$Rev: 616 $
$LastChangedBy: kutterma $
$Id: Definitions.pm 477 2007-12-24 10:23:52Z kutterma $
$Id: Definitions.pm 616 2008-04-22 21:51:49Z kutterma $
$HeadURL: http://soap-wsdl.svn.sourceforge.net/svnroot/soap-wsdl/SOAP-WSDL/trunk/lib/SOAP/WSDL/Definitions.pm $
=cut

View File

@@ -8,7 +8,7 @@ use SOAP::WSDL::Expat::Message2Hash;
use SOAP::WSDL::Factory::Deserializer;
SOAP::WSDL::Factory::Deserializer->register( '1.1', __PACKAGE__ );
our $VERSION='2.00_25';
use version; our $VERSION = qv('2.00.01');
sub BUILD {
my ($self, $ident, $args_of_ref) = @_;
@@ -54,7 +54,7 @@ SOAP::WSDL::Deserializer::Hash - Deserializer SOAP messages into perl hash refs
use SOAP::WSDL;
use SOAP::WSDL::Deserializer::Hash;
=head1 DESCRIPTION
Deserializer for creating perl hash refs as result of a SOAP call.
@@ -152,9 +152,9 @@ Martin Kutter E<lt>martin.kutter fen-net.deE<gt>
=head1 REPOSITORY INFORMATION
$Rev: 427 $
$Rev: 616 $
$LastChangedBy: kutterma $
$Id: Hash.pm 427 2007-12-02 22:20:24Z kutterma $
$Id: Hash.pm 616 2008-04-22 21:51:49Z kutterma $
$HeadURL: http://soap-wsdl.svn.sourceforge.net/svnroot/soap-wsdl/SOAP-WSDL/trunk/lib/SOAP/WSDL/Deserializer/Hash.pm $
=cut

View File

@@ -2,7 +2,7 @@ package SOAP::WSDL::Deserializer::SOM;
use strict;
use warnings;
our $VERSION = '2.00_24';
use version; our $VERSION = qv('2.00.01');
our @ISA;
eval {
@@ -37,7 +37,7 @@ SOAP::WSDL::Deserializer::SOM - Deserializer SOAP messages into SOM objects
use SOAP::WSDL::Deserializer::SOM;
use SOAP::WSDL::Factory::Deserializer;
SOAP::WSDL::Factory::Deserializer->register( '1.1', __PACKAGE__ );
=head1 DESCRIPTION
Deserializer for creating SOAP::Lite's SOM object as result of a SOAP call.
@@ -68,11 +68,11 @@ from the L<SOAP::Lite|SOAP::Lite> package.
=head1 USAGE
SOAP::WSDL::Deserializer will not auroregister itself - to use it for a particular
SOAP::WSDL::Deserializer will not autoregister itself - to use it for a particular
SOAP version just use the following lines:
my $soap_version = '1.1'; # or '1.2', further versions may appear.
use SOAP::WSDL::Deserializer::SOM;
use SOAP::WSDL::Factory::Deserializer;
SOAP::WSDL::Factory::Deserializer->register( $soap_version, __PACKAGE__ );
@@ -114,9 +114,9 @@ Martin Kutter E<lt>martin.kutter fen-net.deE<gt>
=head1 REPOSITORY INFORMATION
$Rev: 391 $
$Rev: 616 $
$LastChangedBy: kutterma $
$Id: SOM.pm 391 2007-11-17 21:56:13Z kutterma $
$Id: SOM.pm 616 2008-04-22 21:51:49Z kutterma $
$HeadURL: http://soap-wsdl.svn.sourceforge.net/svnroot/soap-wsdl/SOAP-WSDL/trunk/lib/SOAP/WSDL/Deserializer/SOM.pm $
=cut

View File

@@ -5,7 +5,7 @@ use Class::Std::Fast::Storable;
use SOAP::WSDL::SOAP::Typelib::Fault11;
use SOAP::WSDL::Expat::MessageParser;
our $VERSION='2.00_25';
use version; our $VERSION = qv('2.00.01');
my %class_resolver_of :ATTR(:name<class_resolver> :default<()>);
@@ -72,7 +72,7 @@ Usually you don't need to do anything to use this package - it's the default
deserializer for SOAP::WSDL::Client and interface classes generated by
SOAP::WSDL.
Is you want to use the XSD serializer from SOAP::WSDL, set the outputtree()
If you want to use the XSD serializer from SOAP::WSDL, set the outputtree()
property and provide a class_resolver.
=head1 METHODS
@@ -99,9 +99,9 @@ Martin Kutter E<lt>martin.kutter fen-net.deE<gt>
=head1 REPOSITORY INFORMATION
$Rev: 501 $
$Rev: 616 $
$LastChangedBy: kutterma $
$Id: XSD.pm 501 2008-01-26 20:23:32Z kutterma $
$Id: XSD.pm 616 2008-04-22 21:51:49Z kutterma $
$HeadURL: http://soap-wsdl.svn.sourceforge.net/svnroot/soap-wsdl/SOAP-WSDL/trunk/lib/SOAP/WSDL/Deserializer/XSD.pm $
=cut

View File

@@ -6,29 +6,56 @@ use XML::Parser::Expat;
# TODO: convert to Class::Std::Fast based class - hash based classes suck.
our $VERSION = '2.00_27';
use version; our $VERSION = qv('2.00.01');
sub new {
my ($class, $arg_ref) = @_;
my $self = {};
my $self = {
data => undef,
};
bless $self, $class;
$self->set_user_agent($arg_ref->{ user_agent })
if $arg_ref->{ user_agent };
$self->{ parsed } = $arg_ref->{ parsed } if $arg_ref->{ parsed };
return $self;
}
sub clone {
my $self = shift;
my $class = ref $self;
my $clone = $class->new($self);
return $clone;
}
sub set_uri { $_[0]->{ uri } = $_[1]; }
sub get_uri { return $_[0]->{ uri }; }
sub set_user_agent { $_[0]->{ user_agent } = $_[1]; }
sub get_user_agent { return $_[0]->{ user_agent }; }
sub set_parsed {
my ($self, $uri) = @_;
$self->{ parsed }->{ $uri } = 1;
return;
}
sub is_parsed {
my ($self, $uri) = @_;
return exists $self->{ parsed }->{ $uri };
}
sub parse_uri {
my $self = shift;
my $uri = shift;
if ($self->is_parsed($uri)){
warn "$uri already imported. Ignoring it\n";
return;
}
$self->set_parsed($uri);
$self->set_uri( $uri );
if (not $self->{ user_agent }) {
@@ -37,7 +64,6 @@ sub parse_uri {
}
my $response = $self->{ user_agent }->get($uri);
die $response->message() if $response->code() ne '200';
return $self->parse( $response->content() );
}

View File

@@ -4,7 +4,7 @@ use strict;
use warnings;
use base qw(SOAP::WSDL::Expat::Base);
our $VERSION = '2.00_27';
use version; our $VERSION = qv('2.00.01');
sub _initialize {
my ($self, $parser) = @_;
@@ -21,7 +21,7 @@ sub _initialize {
my ($_element, $_method,
$_class, $_parser, %_attrs) = ();
no strict qw(refs);
# no strict qw(refs);
$parser->setHandlers(
Start => sub {
push @$list, $current;

View File

@@ -4,7 +4,7 @@ use strict;
use warnings;
use Carp qw(croak confess);
our $VERSION = q{2.00_27};
use version; our $VERSION = qv('2.00.01');
use SOAP::WSDL::XSD::Typelib::Builtin;
use SOAP::WSDL::XSD::Typelib::Builtin::anySimpleType;
@@ -24,7 +24,12 @@ sub new {
};
bless $self, $class;
$self->load_classes() if ($args->{ class_resolver });
# could be written as && - but Devel::Cover doesn't like that
if ($args->{ class_resolver }) {
$self->load_classes()
if ! exists $LOADED_OF{ $self->{ class_resolver } };
}
return $self;
}
@@ -32,7 +37,8 @@ sub class_resolver {
my $self = shift;
if (@_) {
$self->{ class_resolver } = shift;
$self->load_classes();
$self->load_classes()
if ! exists $LOADED_OF{ $self->{ class_resolver } };
}
return $self->{ class_resolver };
}
@@ -40,8 +46,6 @@ sub class_resolver {
sub load_classes {
my $self = shift;
return if $LOADED_OF{ $self->{ class_resolver } };
for (values %{ $self->{ class_resolver }->get_typemap }) {
no strict qw(refs);
my $class = $_;
@@ -162,6 +166,9 @@ sub _initialize {
# (circumventing constructor) here.
# That's dirty, but fast.
#
# TODO: check whether this is faster under all perls - there's
# strange benchmark results...
#
# The alternative would read:
# $current = $_class->new({ @_[2..$#_] });
#
@@ -172,8 +179,20 @@ sub _initialize {
}
# set attributes if there are any
$current->attr({ @_[2..$#_] }) if (@_ > 2);
ATTR: {
if (@_ > 2) {
# die Data::Dumper::Dumper(@_[2..$#_]);
my %attr = @_[2..$#_];
if (my $nil = delete $attr{nil}) {
# TODO: check namespace
if ($nil && $nil ne 'false') {
undef $characters;
last ATTR if not (%attr);
}
}
$current->attr(\%attr);
}
}
$depth++;
return;
},
@@ -194,13 +213,6 @@ sub _initialize {
$depth--;
# return if there's only one elment - can't set it in parent ;-)
# but set as root element if we don't have one already.
if (not defined $list->[-1]) {
$self->{ data } = $current if (not exists $self->{ data });
return;
};
# we only set character values in leaf nodes
if ($_leaf) {
# Use dirty but fast access via global variables.
@@ -210,12 +222,20 @@ sub _initialize {
# $current->set_value( $characters ) if (length($characters));
#
$SOAP::WSDL::XSD::Typelib::Builtin::anySimpleType::___value
->{ $$current } = $characters if $characters =~m{ [^\s] }xms;
->{ $$current } = $characters
if defined $characters && defined $current; # =~m{ [^\s] }xms;
}
# empty characters
$characters = q{};
# return if there's only one elment - can't set it in parent ;-)
# but set as root element if we don't have one already.
if (not defined $list->[-1]) {
$self->{ data } = $current if (not exists $self->{ data });
return;
};
# set appropriate attribute in last element
# multiple values must be implemented in base class
# $_method = "add_$_localname";
@@ -295,8 +315,8 @@ the same terms as perl itself
$Id: $
$LastChangedDate: 2008-02-02 10:19:45 +0100 (Sa, 02 Feb 2008) $
$LastChangedRevision: 516 $
$LastChangedDate: 2008-04-22 23:51:49 +0200 (Di, 22 Apr 2008) $
$LastChangedRevision: 616 $
$LastChangedBy: kutterma $
$HeadURL: http://soap-wsdl.svn.sourceforge.net/svnroot/soap-wsdl/SOAP-WSDL/trunk/lib/SOAP/WSDL/Expat/MessageParser.pm $

View File

@@ -6,7 +6,7 @@ use XML::Parser::Expat;
use SOAP::WSDL::Expat::MessageParser;
use base qw(SOAP::WSDL::Expat::MessageParser);
our $VERSION = '2.00_24';
use version; our $VERSION = qv('2.00.01');
sub parse_start {
my $self = shift;
@@ -43,7 +43,7 @@ SOAP::WSDL::Expat::MessageStreamParser - Convert SOAP messages to custom object
# process response while it comes in, trying to read 32k chunks.
$lwp->request( $request, sub { $chunk_parser->parse_more($_[0]) } , 32468 );
$chunk_parser->parse_done();
my $obj = $parser->get_data();
=head1 DESCRIPTION
@@ -69,9 +69,9 @@ the same terms as perl itself
=head1 REPOSITORY INFORMATION
$Rev: 477 $
$Rev: 616 $
$LastChangedBy: kutterma $
$Id: MessageStreamParser.pm 477 2007-12-24 10:23:52Z kutterma $
$Id: MessageStreamParser.pm 616 2008-04-22 21:51:49Z kutterma $
$HeadURL: http://soap-wsdl.svn.sourceforge.net/svnroot/soap-wsdl/SOAP-WSDL/trunk/lib/SOAP/WSDL/Expat/MessageStreamParser.pm $
=cut

View File

@@ -5,16 +5,21 @@ use Carp;
use SOAP::WSDL::TypeLookup;
use base qw(SOAP::WSDL::Expat::Base);
our $VERSION = q{2.00_31};
use version; our $VERSION = qv('2.00.01');
sub _import_children {
my ($self, $name, $imported, $importer, $import_namespace) = @_;
return if not $imported;
my $targetNamespace = $importer->get_targetNamespace();
my $push_method = "push_$name";
my $get_method = "get_$name";
no strict qw(refs);
my $value_ref = $imported->$get_method();
if ($value_ref) {
#print $self->get_uri(), "\n";
#use Data::Dumper;
#print Data::Dumper::Dumper $value_ref;
$value_ref = [ $value_ref ] if (not ref $value_ref eq 'ARRAY');
# set xmlns - can be different from parent
for (@{ $value_ref }) {
@@ -23,37 +28,70 @@ sub _import_children {
if ( ($import_namespace ne $targetNamespace) && ! $_->get_targetNamespace);
# update parent...
$_->set_parent( $importer );
$importer->$push_method($_);
}
# push elements into importing WSDL
$importer->$push_method(@{ $value_ref });
#$importer->$push_method(@{ $value_ref })
# if @{ $value_ref };
}
}
sub _import_namespace_definitions {
my $self = shift;
my $arg_ref = shift;
my $importer = $arg_ref->{ importer };
my $imported = $arg_ref->{ imported };
# import namespace definitions, too
my $importer_ns_of = $importer->get_xmlns();
my %xmlns_of = %{ $imported->get_xmlns() };
while (my ($prefix, $url) = each %xmlns_of) {
$importer_ns_of->{ $prefix } = $url;
}
}
sub xml_schema_import {
my $self = shift;
my $schema = shift;
my $parser = ref($self)->new();
my $parser = $self->clone();
my %attr_of = @_;
my $import_namespace = $attr_of{ namespace };
my $uri = URI->new_abs($attr_of{schemaLocation}, $self->get_uri() );
my $import = $parser->parse_uri($uri);
my $imported = $parser->parse_uri($uri);
for my $name ( qw(type element group) ) {
$self->_import_children( $name, $import, $schema, $import_namespace);
# might already be imported - parse_uri just returns in this case
return if not defined $imported;
$self->_import_namespace_definitions({
importer => $schema,
imported => $imported,
});
for my $name ( qw(type element group attribute attributeGroup) ) {
$self->_import_children( $name, $imported, $schema, $import_namespace);
}
}
sub wsdl_import {
my $self = shift;
my $definitions = shift;
my $parser = ref($self)->new();
my $parser = $self->clone();
my %attr_of = @_;
my $import_namespace = $attr_of{ namespace };
my $uri = URI->new_abs($attr_of{location}, $self->get_uri() );
my $import = $parser->parse_uri($uri);
my $imported = $parser->parse_uri($uri);
# might already be imported - parse_uri just returns in this case
return if not defined $imported;
$self->_import_namespace_definitions({
importer => $definitions,
imported => $imported,
});
for my $name ( qw(types message binding portType service) ) {
$self->_import_children( $name, $import, $definitions, $import_namespace);
$self->_import_children( $name, $imported, $definitions, $import_namespace);
}
}
@@ -241,10 +279,10 @@ the same terms as perl itself
=head1 Repository information
$Id: $
$Id: WSDLParser.pm 616 2008-04-22 21:51:49Z kutterma $
$LastChangedDate: 2008-02-11 00:14:27 +0100 (Mo, 11 Feb 2008) $
$LastChangedRevision: 522 $
$LastChangedDate: 2008-04-22 23:51:49 +0200 (Di, 22 Apr 2008) $
$LastChangedRevision: 616 $
$LastChangedBy: kutterma $
$HeadURL: http://soap-wsdl.svn.sourceforge.net/svnroot/soap-wsdl/SOAP-WSDL/trunk/lib/SOAP/WSDL/Expat/WSDLParser.pm $

View File

@@ -2,7 +2,7 @@ package SOAP::WSDL::Factory::Deserializer;
use strict;
use warnings;
our $VERSION = '2.00_24';
use version; our $VERSION = qv('2.00.01');
my %DESERIALIZER = (
'1.1' => 'SOAP::WSDL::Deserializer::XSD',
@@ -47,10 +47,10 @@ SOAP::WSDL::Factory::Deserializer - Factory for retrieving Deserializer objects
# in deserializer class:
package MyWickedDeserializer;
use SOAP::WSDL::Factory::Deserializer;
# register class as deserializer for SOAP1.2 messages
SOAP::WSDL::Factory::Deserializer->register( '1.2' , __PACKAGE__ );
=head1 DESCRIPTION
SOAP::WSDL::Factory::Deserializer serves as factory for retrieving
@@ -150,5 +150,5 @@ Martin Kutter E<lt>martin.kutter fen-net.deE<gt>
$LastChangedBy: kutterma $
$Id: Serializer.pm 176 2007-08-31 15:28:29Z kutterma $
$HeadURL: https://soap-wsdl.svn.sourceforge.net/svnroot/soap-wsdl/SOAP-WSDL/trunk/lib/SOAP/WSDL/Factory/Serializer.pm $
=cut

View File

@@ -2,7 +2,7 @@ package SOAP::WSDL::Factory::Generator;
use strict;
use warnings;
our $VERSION='2.00_24';
use version; our $VERSION = qv('2.00.01');
my %GENERATOR = (
'XSD' => 'SOAP::WSDL::Generator::Template::XSD',
@@ -49,10 +49,10 @@ SOAP::WSDL::Factory:Generator - Factory for retrieving generator objects
# in generator class:
package MyWickedGenerator;
use SOAP::WSDL::Factory::Generator;
# register as generator for SOAP1.2 messages
SOAP::WSDL::Factory::Generator->register( '1.2' , __PACKAGE__ );
=head1 DESCRIPTION
SOAP::WSDL::Factory::Generator serves as factory for retrieving
@@ -168,5 +168,5 @@ Martin Kutter E<lt>martin.kutter fen-net.deE<gt>
$LastChangedBy: kutterma $
$Id: Serializer.pm 176 2007-08-31 15:28:29Z kutterma $
$HeadURL: https://soap-wsdl.svn.sourceforge.net/svnroot/soap-wsdl/SOAP-WSDL/trunk/lib/SOAP/WSDL/Factory/Serializer.pm $
=cut

View File

@@ -2,7 +2,7 @@ package SOAP::WSDL::Factory::Serializer;
use strict;
use warnings;
our $VERSION='2.00_24';
use version; our $VERSION = qv('2.00.01');
my %SERIALIZER = (
'1.1' => 'SOAP::WSDL::Serializer::XSD',
@@ -46,10 +46,10 @@ SOAP::WSDL::Factory::Serializer - Factory for retrieving serializer objects
# in serializer class:
package MyWickedSerializer;
use SOAP::WSDL::Factory::Serializer;
# register as serializer for SOAP1.2 messages
SOAP::WSDL::Factory::Serializer->register( '1.2' , __PACKAGE__ );
=head1 DESCRIPTION
SOAP::WSDL::Factory::Serializer serves as factory for retrieving
@@ -138,9 +138,9 @@ Martin Kutter E<lt>martin.kutter fen-net.deE<gt>
=head1 REPOSITORY INFORMATION
$Rev: 510 $
$Rev: 616 $
$LastChangedBy: kutterma $
$Id: Serializer.pm 510 2008-01-29 08:03:46Z kutterma $
$Id: Serializer.pm 616 2008-04-22 21:51:49Z kutterma $
$HeadURL: http://soap-wsdl.svn.sourceforge.net/svnroot/soap-wsdl/SOAP-WSDL/trunk/lib/SOAP/WSDL/Factory/Serializer.pm $
=cut

View File

@@ -1,10 +1,8 @@
package SOAP::WSDL::Factory::Transport;
use strict;
use warnings;
use version; our $VERSION = qv('2.00.01');
our $VERSION='2.00_31';
# class data
my %registered_transport_of = ();
# Local constants
@@ -12,7 +10,7 @@ my %registered_transport_of = ();
my %SOAP_LITE_TRANSPORT_OF = (
ftp => 'SOAP::Transport::FTP',
http => 'SOAP::Transport::HTTP',
https => 'SOAP::Transport::HTTPS',
https => 'SOAP::Transport::HTTP',
mailto => 'SOAP::Transport::MAILTO',
'local' => 'SOAP::Transport::LOCAL',
jabber => 'SOAP::Transport::JABBER',
@@ -32,14 +30,17 @@ sub register {
}
sub get_transport {
my ($class, $scheme, %attrs) = @_;
my ($class, $url, %attrs) = @_;
$scheme =~s{ \A ([^\:]+) \: .+ }{$1}x;
if ($registered_transport_of{ $scheme }) {
my $scheme = $url;
$scheme =~s{ \:.+$ }{}xm;
if (defined $registered_transport_of{ $scheme }) {
no strict qw(refs);
defined %{ "$registered_transport_of{ $scheme }::" }
or eval "require $registered_transport_of{ $scheme }"
defined %{ "$registered_transport_of{ $scheme }::" } or
eval "require $registered_transport_of{ $scheme }"
or die "Cannot load transport class $registered_transport_of{ $scheme } : $@";
# try "foo::Client" class first - SOAP::Tranport always requires
@@ -50,28 +51,30 @@ sub get_transport {
# sparse resource ...
# ... but we've decided to mimic SOAP::Lite...
# my $protocol_class = $SOAP_LITE_TRANSPORT_OF{ $scheme } . '::Client';
# my $transport;
# eval {
# $transport = $protocol_class->new( %attrs );
# };
# return $transport if not $@;
return $registered_transport_of{ $scheme }->new( %attrs );
}
# try SOAP::Lite's Transport module - just skip if not require'able
SOAP_Lite: {
if (exists $SOAP_LITE_TRANSPORT_OF{ $scheme }) {
eval "require $SOAP_LITE_TRANSPORT_OF{ $scheme }"
or last SOAP_Lite;
my $protocol_class = $SOAP_LITE_TRANSPORT_OF{ $scheme } . '::Client';
return $protocol_class->new( %attrs );
}
if (exists $SOAP_LITE_TRANSPORT_OF{ $scheme }) {
no strict qw(refs);
# behaves interestingly different under different versions of perl
# maybe true even if it's not available
defined %{ "$SOAP_LITE_TRANSPORT_OF{ $scheme }::" }
or eval "require $SOAP_LITE_TRANSPORT_OF{ $scheme }"
or last SOAP_Lite;
my $protocol_class = $SOAP_LITE_TRANSPORT_OF{ $scheme } . '::Client';
# may fail if it's not available
my $transport = eval { $protocol_class->new( %attrs ) }
or last SOAP_Lite;
return $transport;
}
}
if (exists $SOAP_WSDL_TRANSPORT_OF{ $scheme }) {
no strict qw(refs);
defined %{ "$SOAP_WSDL_TRANSPORT_OF{ $scheme }::" }
defined %{ "$SOAP_WSDL_TRANSPORT_OF{ $scheme }::"}
or eval "require $SOAP_WSDL_TRANSPORT_OF{ $scheme }"
or die "Cannot load transport class $SOAP_WSDL_TRANSPORT_OF{ $scheme } : $@";
return $SOAP_WSDL_TRANSPORT_OF{ $scheme }->new( %attrs );
@@ -159,7 +162,7 @@ the class should be used for, and $module is the class' module name.
To auto-register your transport class on loading, execute register() in your
tranport class (see L<SYNOPSIS|SYNOPSIS> above).
Multiple protocols ore multiple classes are registered by multiple calls to
Multiple protocols or multiple classes are registered by multiple calls to
register().
=head2 Transport plugin package layout
@@ -240,9 +243,9 @@ Martin Kutter E<lt>martin.kutter fen-net.deE<gt>
=head1 REPOSITORY INFORMATION
$Rev: 524 $
$Rev: 616 $
$LastChangedBy: kutterma $
$Id: Transport.pm 524 2008-02-10 23:24:43Z kutterma $
$Id: Transport.pm 616 2008-04-22 21:51:49Z kutterma $
$HeadURL: http://soap-wsdl.svn.sourceforge.net/svnroot/soap-wsdl/SOAP-WSDL/trunk/lib/SOAP/WSDL/Factory/Transport.pm $
=cut

View File

@@ -0,0 +1,270 @@
package SOAP::WSDL::Generator::Iterator::WSDL11;
use strict; use warnings;
use Class::Std::Fast;
use version; our $VERSION = qv('2.00.01');
my %definitions_of :ATTR(:name<definitions> :default<[]>);
my %nodes_of :ATTR(:name<nodes> :default<[]>);
# memoization attributes
my %portType_of :ATTR();
my %types_of :ATTR();
my %METHOD_OF = (
'SOAP::WSDL::Definitions' => 'get_service',
'SOAP::WSDL::Service' => 'get_port',
'SOAP::WSDL::Port' => sub {
my ($self, $node) = @_;
return if ! $node->first_address()
or ! $node->first_address()->isa('SOAP::WSDL::SOAP::Address');
return [ $self->get_definitions()
->find_binding( $node->expand( $node->get_binding() ) ) || () ];
},
'SOAP::WSDL::Binding' => sub {
my ($self, $node) = @_;
# remember referenced portType
$portType_of{ ident $self } = $self->get_definitions()
->find_portType( $node->expand( $node->get_type ) )
or return [];
return $node->get_operation();
},
'SOAP::WSDL::Operation' => sub {
my ($self, $node) = @_;
my $name = $node->get_name();
# get the equally named operation from the portType
my ($op) = grep { $_->get_name() eq $name }
@{ $portType_of{ ident $self }->get_operation() }
or return [];
return [ @{ $op->get_input }, @{ $op->get_output }, @{ $op->get_fault } ]
},
'SOAP::WSDL::OpMessage' => sub {
my ($self, $node) = @_;
return if ( ref $node->get_parent() eq 'SOAP::WSDL::Binding' ); # we're in binding
# TODO maybe allow more messages && overloading by specifying name
return [ $self->get_definitions()->find_message(
$node->expand( $node->get_message() )
) || () ];
},
'SOAP::WSDL::Message' => 'get_part',
'SOAP::WSDL::Part' => sub {
my ($self, $node) = @_;
my $ident = ident $self;
my $types = $types_of{ $ident } = $definitions_of{ $ident }->get_types()->[0]
or return [];
return [
# If we have a type, this type is to be used in document/literal
# as global type. However this is forbidden, at least by WS-I.
# We should store the style/encoding somewhere, and regard it.
# TODO: auto-generate element for RPC bindings
$node->get_type()
? do {
die "unsupported global type <"
. $node->get_type . "> found in part ". $node->get_name();
$types->find_type( $node->expand($node->get_type) )
}
: (),
$node->get_element()
? $types->find_element( $node->expand($node->get_element) )
: (),
];
},
);
sub init {
my ($self, $arg_of) = @_;
my $ident = ident $self;
undef $portType_of{ $ident };
undef $types_of{ $ident };
$nodes_of{ $ident } = [
exists($arg_of->{ node })
? $arg_of->{ node }
: $definitions_of{ ident $self }
];
}
sub get_next {
my $self = shift;
my $ident = ident $self;
my $node = shift @{ $nodes_of{ $ident }};
return if ! defined $node;
unshift @{ $nodes_of{ $ident }}, @{ $self->get_nextNodes( $node ) || [] };
return $node;
}
sub get_nextNodes {
my ($self, $node) = @_;
my $method = $METHOD_OF{ ref $node }
or return [];
return (ref($method) eq 'CODE')
? $method->( $self, $node )
: $node->can($method)->( $node );
}
1;
__END__
=pod
=head1 NAME
SOAP::WSDL::Generator::Iterator::WSDL11 - WSDL 1.1 Iterator
=head1 SYNOPSIS
my $iter = SOAP::WSDL::Generator::Iterator::WSDL11->new({
definitions => $wsdl
});
$iter->init();
while (my $node = $iter->get_next()) {
# do something with node - possibly call _accept with a visitor on it...
}
=head1 DESCRIPTION
Iterator for walking a WSDL 1.1 definition.
The iterator performs a depth-first search along the following path:
service
port
binding
operation
input/output/fault of operation in portType
message
part
type/element in XML schema
If you wonder about this path: This is how to look up which XML Schema element
is associated with a operation from a service/port.
=head2 Example
The nodes are returned in the order denoted in the following example:
<?xml version="1.0" encoding="UTF-8"?>
<!-- 1 -->
<definitions xmlns:http="http://schemas.xmlsoap.org/wsdl/http/"
xmlns:soap="http://schemas.xmlsoap.org/wsdl/soap/"
xmlns:s="http://www.w3.org/2001/XMLSchema" xmlns:s0="urn:HelloWorld"
targetNamespace="urn:HelloWorld"
xmlns="http://schemas.xmlsoap.org/wsdl/">
<types>
<s:schema elementFormDefault="qualified" targetNamespace="urn:HelloWorld">
<!-- 9 -->
<s:element name="sayHello">
<s:complexType>
<s:sequence>
<s:element minOccurs="0" maxOccurs="1" name="name" type="s:string" />
<s:element minOccurs="0" maxOccurs="1" name="givenName" type="s:string" nillable="1" />
</s:sequence>
<s:attribute name="testAttr" type="s:string" use="optional"></s:attribute>
</s:complexType>
</s:element>
<!-- 13 -->
<s:element name="sayHelloResponse">
<s:complexType>
<s:sequence>
<s:element minOccurs="0" maxOccurs="1"
name="sayHelloResult" type="s:string" />
</s:sequence>
</s:complexType>
</s:element>
</s:schema>
</types>
<!-- 7 -->
<message name="sayHelloSoapIn">
<!-- 8 -->
<part name="parameters" element="s0:sayHello" />
</message>
<!-- 11 -->
<message name="sayHelloSoapOut">
<!-- 12 -->
<part name="parameters" element="s0:sayHelloResponse" />
</message>
<portType name="Service1Soap">
<operation name="sayHello">
<!-- 6 -->
<input message="s0:sayHelloSoapIn" />
<!-- 10 -->
<output message="s0:sayHelloSoapOut" />
</operation>
</portType>
<!-- 4 -->
<binding name="Service1Soap" type="s0:Service1Soap">
<soap:binding transport="http://schemas.xmlsoap.org/soap/http"
style="document" />
<!-- 5 -->
<operation name="sayHello">
<soap:operation soapAction="urn:HelloWorld#sayHello"
style="document" />
<input>
<soap:body use="literal" />
</input>
<output>
<soap:body use="literal" />
</output>
</operation>
</binding>
<!-- 2 -->
<service name="Service1">
<!-- 3 -->
<port name="Service1Soap" binding="s0:Service1Soap">
<soap:address
location="http://localhost:81/soap-wsdl-test/helloworld.pl" />
</port>
</service>
</definitions>
You should not rely too much on this order - it may change. Even though the
current order will probably remain, the nodes currently skipped might
be returned somewhere along the path.
=head1 LICENSE AND COPYRIGHT
Copyright 2004-2008 Martin Kutter.
This file is part of SOAP-WSDL. You may distribute/modify it under
the same terms as perl itself
=head1 AUTHOR
Martin Kutter E<lt>martin.kutter fen-net.deE<gt>
=head1 REPOSITORY INFORMATION
$Rev: 239 $
$LastChangedBy: kutterma $
$Id: Client.pm 239 2007-09-11 09:45:42Z kutterma $
$HeadURL: https://soap-wsdl.svn.sourceforge.net/svnroot/soap-wsdl/SOAP-WSDL/trunk/lib/SOAP/WSDL/Client.pm $
=cut

View File

@@ -0,0 +1,145 @@
package SOAP::WSDL::Generator::PrefixResolver;
use strict; use warnings;
use Class::Std::Fast::Storable;
use version; our $VERSION = qv('2.00.01');
my %namespace_prefix_map_of :ATTR(:name<namespace_prefix_map> :default<{}>);
my %namespace_map_of :ATTR(:name<namespace_map> :default<{}>);
my %prefix_of :ATTR(:name<prefix> :default<{}>);
sub resolve_prefix {
my ($self, $type, $namespace, $element) = @_;
my $prefix;
if (not defined($namespace)) {
$prefix = $prefix_of{ $$self }->{ $type }
}
else {
$prefix = $namespace_prefix_map_of{ $$self }->{ $namespace }
|| ( ($namespace_map_of{ $$self }->{ $namespace })
? join ('::', $prefix_of{ $$self }->{ $type }, $namespace_map_of{ $$self }->{ $namespace })
: $prefix_of{ $$self }->{ $type }
);
}
return "${prefix}::";
}
1;
__END__
=pod
=head1 NAME
SOAP::WSDL::Generator::PrefixResolver - prefixes for different classes
=head1 SYNOPSIS
If you want to create your custom prefix resolver:
package MyPrefixResolver;
use strict; use warnings;
use base qw(SOAP::WSDL::Generator::PrefixResolver);
sub resolve_prefix {
my ($self, $type, $namespace, $node) = @_;
# return something special
return $self->SUPER::resolve_prefix($type, $namespace, $node);
}
When generating code:
use MyPrefixResolver;
use SOAP::WSDL::Generator::XSD;
my $generator = SOAP::WSDL::Generator::Template::XSD->new({
prefix_resolver_class => 'MyPrefixResolver',
});
=head1 DESCRIPTION
Prefix resolver class for SOAP::WSDL's code generator. You may subclass it to
apply some custom prefix resolving logic.
Subclasses must implement the following methods:
=over
=item * resolve_prefix
sub resolve_prefix {
my ($self, $namespace, $node) = @_;
# ...
}
resolve_prefix is expected to return a (perl class) prefix. It is called with
the following parameters:
NAME DESCRIPTION
-----------------------------------------------------------------------------
type One of (server|interface|typemap|type|element|attribute)
namespace The targetNamespace of the node to generate a prefix for.
node The node to generate a prefix for
You usually just need type and namespace for prefix resolving. node is
provided for rather funky setups, where you have to choose different prefixes
based on type names or whatever.
Node may be of any of the following classes:
SOAP::WSDL::Service
SOAP::WSDL::XSD::Attribute
SOAP::WSDL::XSD::Element
SOAP::WSDL::XSD::Type
Note that both namespace and node may be undef - you should test for
definedness before doing anything fancy with them.
If you want your prefixes to represent perl class hierarchies, they should
end with '::'.
Example:
Imagine you're generating interfaces for the Acme Pet Shop. Acme Corp. has
set up their datatypes to be global across all interfaces (and products), while
elements are local to the product (the Pet Shop in the example).
All elements are in the urn:Acme namespace.
In addition, there are types in the namespace urn:Acme:Goods, which should go
into the same namespace as types, but be prefixed with 'Goods_'
You may want prefixes (roughly) like this:
Interfaces: Acme::Client::PetShop::
Server: Acme::Server::PetShop::
Types: Acme::Types::
Types (Goods): Acme::Types::Goods_
Elements: Acme::Elements::PetShop::
Typemaps: Acme::Typemaps::PetShop::
=back
=head1 BUGS AND LIMITATIONS
You cannot suffix your types by some rule yet...
=head1 LICENSE AND COPYRIGHT
Copyright 2008 Martin Kutter.
This library is free software. You may distribute/modify it under
the same terms as perl itself
=head1 AUTHOR
Martin Kutter E<lt>martin.kutter fen-net.deE<gt>
=head1 REPOSITORY INFORMATION
$Rev: 583 $
$LastChangedBy: kutterma $
$Id: $
$HeadURL: $
=cut

View File

@@ -2,20 +2,25 @@ package SOAP::WSDL::Generator::Template;
use strict;
use Template;
use Class::Std::Fast::Storable;
use Carp;
use SOAP::WSDL::Generator::PrefixResolver;
our $VERSION=q{2.00_25};
use version; our $VERSION = qv('2.00.01');
my %tt_of :ATTR(:get<tt>);
my %definitions_of :ATTR(:name<definitions> :default<()>);
my %server_prefix_of :ATTR(:name<server_prefix> :default<MyServer>);
my %interface_prefix_of :ATTR(:name<interface_prefix> :default<MyInterfaces>);
my %typemap_prefix_of :ATTR(:name<typemap_prefix> :default<MyTypemaps>);
my %type_prefix_of :ATTR(:name<type_prefix> :default<MyTypes>);
my %element_prefix_of :ATTR(:name<element_prefix> :default<MyElements>);
my %INCLUDE_PATH_of :ATTR(:name<INCLUDE_PATH> :default<()>);
my %EVAL_PERL_of :ATTR(:name<EVAL_PERL> :default<0>);
my %RECURSION_of :ATTR(:name<RECURSION> :default<0>);
my %OUTPUT_PATH_of :ATTR(:name<OUTPUT_PATH> :default<.>);
my %definitions_of :ATTR(:name<definitions> :default<()>);
my %server_prefix_of :ATTR(:name<server_prefix> :default<MyServer>);
my %interface_prefix_of :ATTR(:name<interface_prefix> :default<MyInterfaces>);
my %typemap_prefix_of :ATTR(:name<typemap_prefix> :default<MyTypemaps>);
my %type_prefix_of :ATTR(:name<type_prefix> :default<MyTypes>);
my %element_prefix_of :ATTR(:name<element_prefix> :default<MyElements>);
my %attribute_prefix_of :ATTR(:name<attribute_prefix> :default<MyAttributes>);
my %INCLUDE_PATH_of :ATTR(:name<INCLUDE_PATH> :default<()>);
my %EVAL_PERL_of :ATTR(:name<EVAL_PERL> :default<0>);
my %RECURSION_of :ATTR(:name<RECURSION> :default<0>);
my %OUTPUT_PATH_of :ATTR(:name<OUTPUT_PATH> :default<.>);
my %prefix_resolver_class_of :ATTR(:name<prefix_resolver_class> :default<SOAP::WSDL::Generator::PrefixResolver>);
sub START {
my ($self, $ident, $arg_ref) = @_;
@@ -25,29 +30,42 @@ sub _process :PROTECTED {
my ($self, $template, $arg_ref, $output) = @_;
my $ident = ident $self;
$tt_of{$ident} = Template->new(
# always create a new Template object to
# force re-loading of plugins.
my $tt = Template->new(
DEBUG => 1,
EVAL_PERL => $EVAL_PERL_of{ $ident },
RECURSION => $RECURSION_of{ $ident },
INCLUDE_PATH => $INCLUDE_PATH_of{ $ident },
OUTPUT_PATH => $OUTPUT_PATH_of{ $ident },
)
if (not $tt_of{ $ident });
PLUGIN_BASE => 'SOAP::WSDL::Generator::Template::Plugin',
);
$tt_of{ $ident }->process( $template,
$tt->process( $template,
{
context => {
prefix_resolver => $prefix_resolver_class_of{ $$self }->new({
namespace_prefix_map => {
'http://www.w3.org/2001/XMLSchema' => 'SOAP::WSDL::XSD::Typelib::Builtin',
},
namespace_map => {
},
prefix => {
interface => $self->get_interface_prefix,
element => $self->get_element_prefix,
attribute => $self->get_attribute_prefix,
server => $self->get_server_prefix,
type => $self->get_type_prefix,
typemap => $self->get_typemap_prefix,
}
}),
},
definitions => $self->get_definitions,
interface_prefix => $self->get_interface_prefix,
server_prefix => $self->get_server_prefix,
type_prefix => $self->get_type_prefix,
typemap_prefix => $self->get_typemap_prefix,
TYPE_PREFIX => $self->get_type_prefix,
element_prefix => $self->get_element_prefix,
NO_POD => delete $arg_ref->{ NO_POD } ? 1 : 0 ,
%{ $arg_ref }
},
$output)
or die $INCLUDE_PATH_of{ $ident }, '\\', $template, ' ', $tt_of{ $ident }->error();
or croak $INCLUDE_PATH_of{ $ident }, '\\', $template, ' ', $tt->error();
}
1;

View File

@@ -0,0 +1,179 @@
package SOAP::WSDL::Generator::Template::Plugin::XSD;
use strict;
use warnings;
use Carp qw(confess);
use Class::Std::Fast::Storable constructor => 'none';
use version; our $VERSION = qv('2.00.01');
my %namespace_prefix_map_of :ATTR(:name<namespace_prefix_map> :default<{}>);
my %namespace_map_of :ATTR(:name<namespace_map> :default<{}>);
my %prefix_of :ATTR(:name<prefix> :default<()>);
my %prefix_resolver_of :ATTR(:name<prefix_resolver> :default<()>);
# create a singleton
sub load { # called as MyPlugin->load($context)
my ($class, $context, @arg_from) = @_;
my $stash = $context->stash();
my $self = bless \do { my $o = Class::Std::Fast::ID() }, $class;
$self->set_prefix_resolver( $stash->{ context }->{ prefix_resolver });
return $self; # returns 'MyPlugin'
}
sub new {
return shift if ref $_[0];
my ($class, $arg_ref) = @_;
my $self = bless \do { my $o = Class::Std::Fast::ID() }, $class;
$self->set_prefix_resolver( $arg_ref->{ prefix_resolver });
return $self; # returns 'MyPlugin'
}
sub _get_prefix {
my ($self, $type, $node) = @_;
my $namespace = defined ($node)
? ref($node)
? $node->get_targetNamespace()
: $node
: undef;
return $self->get_prefix_resolver()->resolve_prefix(
$type,
$namespace,
ref($node)
? $node
: undef
);
}
sub create_xsd_name {
my ($self,$node) = @_;
my $name = $self->_resolve_prefix($node) #. '::'
. $node->get_name();
return $self->perl_name( $name );
}
sub create_typemap_name {
my ($self, $node) = @_;
my $name = $self->_get_prefix('typemap') #. '::'
. $node->get_name();
return $self->perl_name( $name );
}
sub create_server_name {
my ($self, $server, $port) = @_;
my $port_name = $port->get_name();
$port_name =~s{\A (?:.+)\. ([^\.]+) \z}{$1}x;
my $name = join( q{},
$self->_get_prefix('server', $server),
join( '::', $server->get_name(), $port_name)
);
return $self->perl_name( $name );
}
sub create_interface_name {
my ($self, $server, $port) = @_;
my $port_name = $port->get_name();
$port_name =~s{\A (?:.+)\. ([^\.]+) \z}{$1}x;
my $name = join( q{},
$self->_get_prefix('interface', $server),
join( '::', $server->get_name(), $port_name )
);
return $self->perl_name( $name );
}
sub _resolve_prefix {
my ($self, $node) = @_;
confess "no node" if not $node;
if ($node->isa('SOAP::WSDL::XSD::Builtin')) {
return $self->_get_prefix('type', $node)
}
if ( $node->isa('SOAP::WSDL::XSD::SimpleType')
or $node->isa('SOAP::WSDL::XSD::ComplexType')
) {
return $self->_get_prefix('type', $node);
}
if ( $node->isa('SOAP::WSDL::XSD::Element') ) {
return $self->_get_prefix('element', $node);
}
if ( $node->isa('SOAP::WSDL::XSD::Attribute') ) {
return $self->_get_prefix('attribute', $node);
}
}
sub perl_name {
my $self = shift;
my $name = shift;
$name =~s{\-}{_}xmsg;
$name =~s{\.}{::}xmsg;
return $name;
}
sub create_subpackage_name {
my $self = shift;
my $arg_ref = shift;
my $type = ref $arg_ref eq 'HASH' ? $arg_ref->{ value } : $arg_ref;
my @name_from = $type->get_name() || (); ;
my $parent = $type;
my $top_node = $parent;
if (! $parent->get_parent()->isa('SOAP::WSDL::XSD::Schema') ) {
NAMES: while ($parent = $parent->get_parent()) {
$top_node = $parent;
last NAMES if $parent->get_parent()->isa('SOAP::WSDL::XSD::Schema');
# skip empty names - atomic types have no name...
unshift @name_from, $parent->get_name()
if $parent->get_name();
}
}
# create name for top node
my $top_node_name = $self->create_xsd_name($top_node);
my $package_name = join('::_', $top_node_name , (@name_from) ? join('::', @name_from) : () );
return $package_name;
}
sub create_xmlattr_name {
return join '::', shift->create_subpackage_name(shift), 'XmlAttr';
}
1;
=pod
=head1 NAME
SOAP::WSDL::Generator::Template::Plugin::XSD - Template plugin for the XSD generator
=head1 METHODS
=head2 perl_name
XSD.perl_name(element.get_name);
Converts a XML name into a valid perl name (valid for subroutines, variables
or the like).
perl_name takes a crude approach by just replacing . and - (dot and dash)
with a underscore. This may or may not be sufficient, and may or may not
provoke collisions in your XML names.
=head1 LICENSE AND COPYRIGHT
Copyright 2008 Martin Kutter.
This file is part of SOAP-WSDL. You may distribute/modify it under the same
terms as perl itself
=head1 AUTHOR
Martin Kutter E<lt>martin.kutter fen-net.deE<gt>
=head1 REPOSITORY INFORMATION
$Rev: 564 $
$LastChangedBy: kutterma $
$Id: ComplexType.pm 564 2008-02-23 13:31:39Z kutterma $
$HeadURL: http://soap-wsdl.svn.sourceforge.net/svnroot/soap-wsdl/SOAP-WSDL/trunk/lib/SOAP/WSDL/XSD/Typelib/ComplexType.pm $
=cut

View File

@@ -5,14 +5,15 @@ use Class::Std::Fast::Storable;
use File::Basename;
use File::Spec;
our $VERSION = q{2.00_27};
use version; our $VERSION = qv('2.00.01');
use SOAP::WSDL::Generator::Visitor::Typemap;
use SOAP::WSDL::Generator::Visitor::Typelib;
use SOAP::WSDL::Generator::Template::Plugin::XSD;
use base qw(SOAP::WSDL::Generator::Template);
my %output_of :ATTR(:name<output> :default<()>);
my %typemap_of :ATTR(:name<typemap> :default<({})>);
my %output_of :ATTR(:name<output> :default<()>);
my %typemap_of :ATTR(:name<typemap> :default<({})>);
sub BUILD {
my ($self, $ident, $arg_ref) = @_;
@@ -46,93 +47,104 @@ sub BUILD {
);
}
# construct object on call to allow late binding of prefix_resolver class
# and namespace maps (not used yet)
sub get_name_resolver {
my $self = shift;
return SOAP::WSDL::Generator::Template::Plugin::XSD->new({
prefix_resolver => $self->get_prefix_resolver_class()->new({
namespace_prefix_map => {
'http://www.w3.org/2001/XMLSchema' => 'SOAP::WSDL::XSD::Typelib::Builtin',
},
namespace_map => {
},
prefix => {
attribute => $self->get_attribute_prefix,
interface => $self->get_interface_prefix,
element => $self->get_element_prefix,
server => $self->get_server_prefix,
type => $self->get_type_prefix,
typemap => $self->get_typemap_prefix,
}
})
});
}
sub generate {
my $self = shift;
my $opt = shift;
$self->generate_typelib( $opt );
# $self->generate_interface( $opt );
$self->generate_typemap( $opt );
}
sub generate_typelib {
my ($self, $arg_ref) = @_;
# $output_of{ ident $self } = "";
my @schema = exists $arg_ref->{ schema }
? @{ $arg_ref->{schema} }
: @{ $self->get_definitions()->first_types()->get_schema() };
for my $type (map { @{ $_->get_type() } , @{ $_->get_element() } } @schema[1..$#schema] ) {
for my $type (map {
@{ $_->get_type() } ,
@{ $_->get_element() },
@{ $_->get_attribute() }
} @schema[1..$#schema] ) {
$type->_accept( $self );
}
# return $output_of{ ident $self };
return;
}
sub _generate_interface {
my $self = shift;
my $arg_ref = shift;
my $template_name = delete $arg_ref->{ template_name };
my $name_method = delete $arg_ref->{ name_method };
for my $service (@{ $self->get_definitions->get_service }) {
for my $port (@{ $service->get_port() }) {
# Skip ports without (known) address
next if not $port->first_address;
next if not $port->first_address->isa('SOAP::WSDL::SOAP::Address');
my $port_name = $port->get_name;
$port_name =~s{ \A .+\. }{}xms;
my $output = $arg_ref->{ output }
? $arg_ref->{ output }
: $self->_generate_filename(
$self->get_name_resolver()->can($name_method)->(
$self->get_name_resolver(),
$service,
$port,
));
print "Creating interface class $output\n";
$self->_process($template_name,
{
service => $service,
port => $port,
NO_POD => $arg_ref->{ NO_POD } ? 1 : 0 ,
},
$output, binmode => ':utf8');
}
}
}
sub generate_server {
my $self = shift;
my $ident = ident $self;
my $arg_ref = shift;
for my $service (@{ $self->get_definitions->get_service }) {
for my $port (@{ $service->get_port() }) {
# Skip ports without (known) address
next if not $port->first_address;
next if not $port->first_address->isa('SOAP::WSDL::SOAP::Address');
my $port_name = $port->get_name;
$port_name =~s{ \A .+\. }{}xms;
my $output = $arg_ref->{ output }
? $arg_ref->{ output }
: $self->_generate_filename(
$self->get_server_prefix(),
$service->get_name(),
$port_name,
);
print "Creating interface class $output\n";
$self->_process('Server.tt',
{
service => $service,
port => $port,
NO_POD => $arg_ref->{ NO_POD } ? 1 : 0 ,
},
$output, binmode => ':utf8');
}
}
my ($self, $arg_ref) = @_;
$arg_ref->{ template_name } = 'Server.tt';
$arg_ref->{ name_method } = 'create_server_name';
$self->_generate_interface($arg_ref);
}
sub generate_interface {
my $self = shift;
my $ident = ident $self;
my $arg_ref = shift;
for my $service (@{ $self->get_definitions->get_service }) {
for my $port (@{ $service->get_port() }) {
# Skip ports without (known) address
next if not $port->first_address;
next if not $port->first_address->isa('SOAP::WSDL::SOAP::Address');
my $port_name = $port->get_name;
$port_name =~s{ \A .+\. }{}xms;
my $output = $arg_ref->{ output }
? $arg_ref->{ output }
: $self->_generate_filename(
$self->get_interface_prefix(),
$service->get_name(),
$port_name,
);
print "Creating interface class $output\n";
$self->_process('Interface.tt',
{
service => $service,
port => $port,
NO_POD => $arg_ref->{ NO_POD } ? 1 : 0 ,
},
$output, binmode => ':utf8');
}
}
sub generate_client {
my ($self, $arg_ref) = @_;
$arg_ref->{ template_name } = 'Interface.tt';
$arg_ref->{ name_method } = 'create_interface_name';
$self->_generate_interface($arg_ref);
}
sub generate_interface;
*generate_interface = \&generate_client;
sub generate_typemap {
my ($self, $arg_ref) = @_;
my $visitor = SOAP::WSDL::Generator::Visitor::Typemap->new({
type_prefix => $self->get_type_prefix(),
element_prefix => $self->get_element_prefix(),
@@ -144,13 +156,23 @@ sub generate_typemap {
'Fault/faultstring' => 'SOAP::WSDL::XSD::Typelib::Builtin::string',
'Fault/detail' => 'SOAP::WSDL::XSD::Typelib::Builtin::string',
%{ $typemap_of{ident $self }},
}
},
resolver => $self->get_name_resolver(),
});
use SOAP::WSDL::Generator::Iterator::WSDL11;
my $iterator = SOAP::WSDL::Generator::Iterator::WSDL11->new({
definitions => $self->get_definitions });
for my $service (@{ $self->get_definitions->get_service }) {
$visitor->visit_Service( $service );
$iterator->init({ node => $service });
while (my $node = $iterator->get_next()) {
$node->_accept( $visitor );
}
my $output = $arg_ref->{ output }
? $arg_ref->{ output }
: $self->_generate_filename( $self->get_typemap_prefix(), $service->get_name() );
: $self->_generate_filename( $self->get_name_resolver()->create_typemap_name($service) );
print "Creating typemap class $output\n";
$self->_process('Typemap.tt',
{
@@ -163,19 +185,26 @@ sub generate_typemap {
}
sub _generate_filename :PRIVATE {
my ($self, @parts) = @_;
my $name = join '::', @parts;
my ($self, $name) = @_;
$name =~s{ \. }{::}xmsg;
$name =~s{ \- }{_}xmsg;
$name =~s{ :: }{/}xmsg;
return "$name.pm";
}
sub visit_XSD_Attribute {
my ($self, $attribute) = @_;
my $output = defined $output_of{ ident $self }
? $output_of{ ident $self }
: $self->_generate_filename( $self->get_name_resolver()->create_xsd_name($attribute) );
$self->_process('attribute.tt', { attribute => $attribute } , $output);
}
sub visit_XSD_Element {
my ($self, $element) = @_;
my $output = defined $output_of{ ident $self }
? $output_of{ ident $self }
: $self->_generate_filename( $self->get_element_prefix(), $element->get_name() );
: $self->_generate_filename( $self->get_name_resolver()->create_xsd_name($element) );
$self->_process('element.tt', { element => $element } , $output);
}
@@ -183,7 +212,7 @@ sub visit_XSD_SimpleType {
my ($self, $type) = @_;
my $output = defined $output_of{ ident $self }
? $output_of{ ident $self }
: $self->_generate_filename( $self->get_type_prefix(), $type->get_name() );
: $self->_generate_filename( $self->get_name_resolver()->create_xsd_name($type) );
$self->_process('simpleType.tt', { simpleType => $type } , $output);
}
@@ -191,8 +220,8 @@ sub visit_XSD_ComplexType {
my ($self, $type) = @_;
my $output = defined $output_of{ ident $self }
? $output_of{ ident $self }
: $self->_generate_filename( $self->get_type_prefix(), $type->get_name() );
: $self->_generate_filename( $self->get_name_resolver()->create_xsd_name($type) );
$self->_process('complexType.tt', { complexType => $type } , $output);
}
1;
1;

View File

@@ -1,7 +1,5 @@
[% interface_name = interface_prefix _ '::'
_ service.get_name.replace('\.', '::') _ '::'
_ port.get_name.replace('^.+\.','');
interface_name = interface_name.replace('-','_'); -%]
[% USE XSD -%]
[% interface_name = XSD.create_interface_name(service, port) -%]
package [% interface_name %];
use strict;
use warnings;
@@ -10,20 +8,20 @@ use Scalar::Util qw(blessed);
use base qw(SOAP::WSDL::Client::Base);
# only load if it hasn't been loaded before
require [% typemap_prefix %]::[% service.get_name.replace('\.', '::').replace('-', '_') %]
if not [% typemap_prefix %]::[% service.get_name.replace('\.', '::').replace('-', '_') %]->can('get_class');
require [% XSD.create_typemap_name(service) %]
if not [% XSD.create_typemap_name(service) %]->can('get_class');
sub START {
$_[0]->set_proxy('[% port.first_address.get_location %]') if not $_[2]->{proxy};
$_[0]->set_class_resolver('[% typemap_prefix %]::[% service.get_name.replace('\.', '::').replace('-', '_') %]')
$_[0]->set_class_resolver('[% XSD.create_typemap_name(service) %]')
if not $_[2]->{class_resolver};
}
[% binding = definitions.find_binding( port.expand( port.get_binding ) );
FOREACH operation = binding.get_operation;
%][% INCLUDE Interface/Operation.tt %]
[%
[%
END;
%]
@@ -48,12 +46,12 @@ __END__
use [% interface_name %];
my $interface = [% interface_name %]->new();
my $response;
[% FOREACH operation = binding.get_operation;
%] $response = $interface->[% operation.get_name %]();
[% END %]
[% head1 %] DESCRIPTION
@@ -82,7 +80,6 @@ All arguments are forwarded to L<SOAP::WSDL::Client|SOAP::WSDL::Client>.
[% INCLUDE Interface/POD/method_info.tt %]
[% FOREACH operation = binding.get_operation;
%][% INCLUDE Interface/POD/Operation.tt %]
[% END %]

View File

@@ -1,14 +1,12 @@
[% RETURN IF NOT item;
type = definitions.find_portType( binding.expand( binding.get_type ) );
port_op = type.find_operation( definitions.get_targetNamespace, operation.get_name );
port_op = type.find_operation( type.get_targetNamespace, operation.get_name );
message = definitions.find_message( port_op.first_input.expand( port_op.first_input.get_message ) );
part_from = message.get_part;
PERL %]
my $item = $stash->{ item };
my $def = $stash->{ definitions };
my $part_from = $stash->{ part_from };
my $type_prefix = $stash->{ type_prefix };
my $element_prefix = $stash->{ element_prefix };
my $part_from = $stash->{ message }->get_part();
my @body_part_from = split m{\s}, $item->get_parts;
@@ -17,22 +15,25 @@
@parts = map {
my $part = $_;
(grep {
my ($ns, $lname) = $def->expand( $_ );
($lname eq $part->get_name)
# my ($ns, $lname) = $def->expand( $_ );
($_ eq $part->get_name)
} @body_part_from
)
? do {
my $name;
($name = $part->get_element)
? do {
$name =~s{ ^[^:]+: }{}xms;
$element_prefix . '::' . $name;
}
my $element = $def->first_types->find_element($part->expand($name));
my $resolver = $context->plugin('XSD');
$resolver->create_xsd_name($element);
}
: ($name = $part->get_type)
? do {
$name =~s{ ^[^:]+: }{}xms;
$type_prefix . '::' . $name;
}
my $element = $def->first_types->find_type($part->expand($name));
my $resolver = $context->plugin('XSD');
$resolver->create_xsd_name($element);
}
: die "input must have either type or element"
}
: ()
@@ -44,13 +45,15 @@
my $name;
($name = $part->get_element)
? do {
$name =~s{ ^[^:]+: }{}xms;
"$element_prefix\::$name"
}
my $element = $def->first_types->find_element($part->expand($name));
my $resolver = $context->plugin('XSD');
$resolver->create_xsd_name($element);
}
: ($name = $part->get_type)
? do {
$name =~s{ ^[^:]+: }{}xms;
"$type_prefix\::$name"
my $element = $def->first_types->find_type($part->expand($name));
my $resolver = $context->plugin('XSD');
$resolver->create_xsd_name($element);
}
: die "input must have either type or element";
} @{ $part_from };
@@ -63,7 +66,10 @@
$stash->{ parts } = \@parts;
[% END %]
'use' => '[% item.get_use %]',
namespace => '[% item.get_namespace %]',
encodingStyle => '[% item.get_encodingStyle %]',
parts => [qw( [% parts.join(' ') %] )],
[% IF item.get_use != 'literal';
THROW NOT_SUPPORTED "Body: SOAP::WSDL supports literal encoding only - ${ item.get_use } found";
END %]
'use' => '[% item.get_use %]',
namespace => '[% item.get_namespace %]',
encodingStyle => '[% item.get_encodingStyle %]',
parts => [qw( [% parts.join(' ') %] )],

View File

@@ -11,27 +11,34 @@
my $def = $stash->{ definitions };
my $type_prefix = $stash->{ type_prefix };
my $element_prefix = $stash->{ element_prefix };
my ($ns, $lname) = $def->expand( $item->get_part() );
#my ($ns, $lname) = $def->expand( $item->get_part() );
my $part_name = $item->get_part();
my ($part) = grep {
$_->get_name eq $lname
&& $_->get_targetNamespace eq $ns } @{ $message->get_part( ) };
$_->get_name eq $part_name
} @{ $message->get_part( ) };
my $part_class = do {
my $name;
($name = $part->get_element)
? do {
$name =~s{ ^[^:]+: }{}xms;
$element_prefix . '::' . $name;
my $element = $def->first_types->find_element($part->expand($name));
my $resolver = $context->plugin('XSD');
$resolver->create_xsd_name($element);
}
: ($name = $part->get_type)
? do {
$name =~s{ ^[^:]+: }{}xms;
$type_prefix . '::' . $name;
}
my $element = $def->first_types->find_type($part->expand($name));
my $resolver = $context->plugin('XSD');
$resolver->create_xsd_name($element);
}
: die "input must have either type or element"
};
$stash->{ part_class } = $part_class;
[% END;
%]
%]
[% IF item.get_use != 'literal';
THROW NOT_SUPPORTED "Header: SOAP::WSDL supports literal encoding only - ${ item.get_use } found";
END %]
'use' => '[% item.get_use %]',
namespace => '[% item.get_namespace %]',
encodingStyle => '[% item.get_encodingStyle %]',

View File

@@ -4,7 +4,12 @@ sub [% operation.get_name %] {
return $self->SUPER::call({
operation => '[% operation.get_name %]',
soap_action => '[% operation.first_operation.get_soapAction %]',
style => '[% operation.get_style || binding.get_style %]',
style => [% style = operation.first_operation.get_style || binding.get_style;
IF style != "document";
THROW NOT_SUPPORTED "SOAP::WSDL supports document encoding only - $style found";
END;
-%]
'[% style %]',
body => {
[% INCLUDE Interface/Body.tt( item = operation.first_input.first_body ); %]
},

View File

@@ -7,4 +7,3 @@
port_op.get_documentation %]
$interface->[% operation.get_name %]([% INCLUDE Interface/POD/Message.tt %] );

View File

@@ -5,3 +5,12 @@ of the corresponding class can be passed instead of the marked hash ref.
You may pass any combination of objects, hash and list refs to these
methods, as long as you meet the structure.
List items (i.e. multiple occurences) are not displayed in the synopsis.
You may generally pass a list ref of hash refs (or objects) instead of a hash
ref - this may result in invalid XML if used improperly, though. Note that
SOAP::WSDL always expects list references at maximum depth position.
XML attributes are not displayed in this synopsis and cannot be set using
hash refs. See the respective class' documentation for additional information.

View File

@@ -0,0 +1,2 @@
[% node.get_annotation.0.get_documentation %]

View File

@@ -1,7 +1,6 @@
[% server_name = server_prefix _ '::'
_ service.get_name.replace('\.', '::') _ '::'
_ port.get_name.replace('^.+\.','');
server_name = server_name.replace('-','_'); -%]
[% USE XSD;
server_name = XSD.create_server_name(service, port);
-%]
package [% server_name %];
use strict;
use warnings;
@@ -10,8 +9,8 @@ use Scalar::Util qw(blessed);
use base qw(SOAP::WSDL::Client::Base);
# only load if it hasn't been loaded before
require [% typemap_prefix %]::[% service.get_name.replace('\.', '::') %]
if not [% typemap_prefix %]::[% service.get_name.replace('\.', '::') %]->can('get_class');
require [% XSD.create_typemap_name(service) %]
if not [% XSD.create_typemap_name(service) %]->can('get_class');
my %transport_class_of :ATTR(:name<transport_class> :default<SOAP::WSDL::Server::CGI>);
my %transport_of :ATTR(:name<transport> :default<()>);
@@ -31,13 +30,13 @@ sub START {
or die "Cannot load transport class $transport_class_of{ $ident }: $@";
$transport_of{ $ident } = $transport_class_of{ $ident }->new({
action_map_ref => $action_map_ref,
class_resolver => '[% typemap_prefix %]::[% service.get_name.replace('\.', '::') %]',
class_resolver => '[% XSD.create_typemap_name(service) %]',
dispatch_to => $dispatch_to{ $ident },
});
}
sub handle {
$transport_of{ ${ $_[0] } }->handle();
$transport_of{ ${ $_[0] } }->handle(@_[1..$#_]);
}
1;
@@ -103,4 +102,4 @@ implementing the SOAP Service methods listed below.
Generated by SOAP::WSDL on [% PERL %]print scalar localtime() [% END %]
=pod
=cut

View File

@@ -3,15 +3,48 @@
[% head3 %] [% operation.get_name %]
[% type = definitions.find_portType( binding.expand( binding.get_type ) );
port_op = type.find_operation( definitions.get_targetNamespace, operation.get_name );
port_op.get_documentation %]
[% type = definitions.find_portType( binding.expand( binding.get_type ) );
port_op = '';
FOREACH port_op = type.get_operation();
IF (port_op.get_name == operation.get_name);
LAST;
END;
END;
input_message_name = port_op.first_input.get_message();
output_message_name = port_op.first_output.get_message();
input_message = definitions.find_message(port_op.first_input.expand(input_message_name));
output_message = definitions.find_message(port_op.first_output.expand(output_message_name));
input_parts = input_message.get_part();
output_parts = output_message.get_part();
# port_op.get_documentation
%]
sub [% operation.get_name %] {
my ($self, $body, $header) = @_;
# body is a ??? object - sorry, POD not implemented yet
# header is a ??? object - sorry, POD not implemented yet
[%
IF (input_parts.size() > 1); -%]
# body is a list ref of the following objects:
# [
# sorry - POD support not implemented yet
# ]
[% ELSE;
input_element = definitions.first_types.find_element(input_parts.0.expand(input_parts.0.get_element));
IF (input_element);
class = XSD.create_xsd_name( input_element );
ELSE;
input_type = definitions.first_types.find_type(input_parts.0.expand(input_parts.0.get_type));
class = XSD.create_xsd_name( input_type );
END;
-%]
# body is a [% class %] object
[%-
END;
%]
# header is a ??? object - sorry, POD support not implemented yet
# do something with body and header...
return [% INCLUDE Server/POD/Message.tt %]

View File

@@ -3,7 +3,7 @@
#element;
#STOP;
-%]
[% element_prefix %]::[% element.get_name.replace('\.', '::') %]->new([%
[% XSD.create_xsd_name(element) %]->new([%
type = element.first_complexType || element.first_simpleType || definitions.first_types.find_type(
element.expand( element.get_type ) );
INCLUDE Interface/POD/Type.tt; %]

View File

@@ -1,4 +1,5 @@
package [% typemap_prefix %]::[% service.get_name.replace('\.','::') %];
[% USE XSD %]
package [% XSD.create_typemap_name(service) %];
use strict;
use warnings;
@@ -27,7 +28,7 @@ __END__
[% head1 %] NAME
[% typemap_prefix %]::[% service.get_name.replace('\.','::').replace('-', '_') %]; - typemap for ::[% service.get_name %];
[% XSD.create_typemap_name(service) %] - typemap for [% service.get_name %]
[% head1 %] DESCRIPTION

View File

@@ -1,6 +0,0 @@
[% type_name = node.expand( type );
IF (type_name.0 == 'http://www.w3.org/2001/XMLSchema'); -%]
SOAP::WSDL::XSD::Typelib::Builtin::[% type_name.1 %]
[% ELSE -%]
[% type_prefix %]::[% type_name.1 %]
[% END -%]

View File

@@ -0,0 +1,83 @@
[% USE XSD(context) %]
package [% XSD.create_xsd_name(attribute) %];
use strict;
use warnings;
{ # BLOCK to scope variables
sub get_xmlns { '[% attribute.get_targetNamespace %]' }
__PACKAGE__->__set_name('[% attribute.get_name %]');
__PACKAGE__->__set_ref([% IF attribute.get_ref; %]'[% attribute.get_ref %]'[% END %]);
[%- IF (type_name = attribute.get_type); -%]
use base qw(
SOAP::WSDL::XSD::Typelib::Attribute
[% type = definitions.get_types.0.find_type(attribute.expand(type_name));
IF ! type;
THROW NOT_FOUND "type " _ type_name _ " not found in attribute " _ attribute.get_name;
END;
XSD.create_xsd_name(type) %]
);
}
[%- ELSIF (ref = attribute.get_ref);
ref_from = ref.split(':');
-%]
# attribute ref="[% ref %]"
use base qw(
[% ref_element = definitions.get_types.0.find_attribute(attribute.expand(ref));
XSD.create_xsd_name( ref_element ); %]
);
}
[%- ELSIF (simpleType = attribute.first_simpleType) %]
# atomic simpleType: <attribute><simpleType
use base qw(
SOAP::WSDL::XSD::Typelib::Attribute
);
[% INCLUDE simpleType/contentModel.tt -%]
}
[% END %]
1;
[%# work around for CPAN's indexer, which gets disturbed by pod in templates -%]
[% pod = BLOCK %]=pod[% END -%]
[% head1 = BLOCK %]=head1[% END -%]
[% head2 = BLOCK %]=head2[% END -%]
[% head3 = BLOCK %]=head3[% END -%]
[% pod %]
[% head1 %] NAME
[% XSD.create_xsd_name(attribute) %]
[% head1 %] DESCRIPTION
Perl data type class for the XML Schema defined attribute
[% attribute.get_name %] from the namespace [% attribute.get_targetNamespace %].
[% INCLUDE POD/annotation.tt(node = attribute) %]
[% INCLUDE element/POD/contentModel.tt(element = attribute) %]
[% head1 %] METHODS
[% head2 %] new
my $element = [% XSD.create_xsd_name(attribute) %]->new($data);
Constructor. The following data structure may be passed to new():
{ value => $value }
[% head1 %] AUTHOR
Generated by SOAP::WSDL
=cut

View File

@@ -1,14 +1,15 @@
package [% type_prefix %]::[% complexType.get_name.replace('\.','::').replace('-','_') %];
[% USE XSD -%]
package [% XSD.create_xsd_name(complexType) %];
use strict;
use warnings;
[% INCLUDE complexType/contentModel.tt %]
[%#
# Don't include any perl source here - there may be sub-packages...
# Don't include any perl source for this package below this line - there
# may be sub-packages...
#-%]
package [% type_prefix %]::[% complexType.get_name.replace('\.','::').replace('-','_') %]::_ATTR;
use base qw(SOAP::WSDL::XSD::Typelib::AttributeSet);
[% INCLUDE complexType/attributeSet.tt %]
[% INCLUDE complexType/contentModel.tt %]
1;
[%# work around for CPAN's indexer, which gets disturbed by pod in templates -%]
@@ -21,22 +22,35 @@ use base qw(SOAP::WSDL::XSD::Typelib::AttributeSet);
[% head1 %] NAME
[% type_prefix %]::[% complexType.get_name.replace('\.','::').replace('-','_') %]
[% XSD.create_xsd_name(complexType) %]
[% head1 %] DESCRIPTION
Perl data type class for the XML Schema defined complextype
Perl data type class for the XML Schema defined complexType
[% complexType.get_name %] from the namespace [% complexType.get_targetNamespace %].
[% INCLUDE POD/annotation.tt(node = complexType) %]
[% IF (complexType.get_element); %]
[% head2 %] PROPERTIES
The following properties may be accessed using get_PROPERTY / set_PROPERTY
methods:
=over
[% FOREACH element = complexType.get_element -%]
[% element.get_name %]
=item * [% element.get_name %]
[% IF element.get_annotation.get_documentation; %]
[% element.get_annotation.get_documentation %]
[% END -%]
[% END %]
=back
[% END -%]
[% head1 %] METHODS
[% head2 %] new
@@ -45,6 +59,8 @@ Constructor. The following data structure may be passed to new():
[% indent = ' '; INCLUDE complexType/POD/structure.tt %]
[% INCLUDE complexType/POD/attributeSet.tt %]
[% head1 %] AUTHOR
Generated by SOAP::WSDL

View File

@@ -1,5 +1,5 @@
[% indent %]{
[%- IF complexType.get_name %] # [% type_prefix %]::[% complexType.get_name %][% END %]
{
[%- IF complexType.get_name %] # [% XSD.create_xsd_name(complexType) %][% END %]
[%- indent = indent _ ' ';
FOREACH element = complexType.get_element %]
[% indent %][% element.get_name %] => [% INCLUDE element/POD/structure.tt -%]

View File

@@ -0,0 +1,37 @@
[% head2 = BLOCK %]=head2[% END -%]
[% IF (complexType.get_attribute.size) %]
[% head2 %] attr
NOTE: Attribute documentation is experimental, and may be inaccurate.
See the correspondent WSDL/XML Schema if in question.
This class has additional attributes, accessibly via the C<attr()> method.
attr() returns an object of the class [% XSD.create_xmlattr_name(complexType) %].
The following attributes can be accessed on this object via the corresponding
get_/set_ methods:
=over
[% FOREACH element = complexType.get_attribute;
WHILE element.get_ref;
element = definitions.first_types.find_attribute(element.expand( element.get_ref ));
END; -%]
=item * [% element.get_name %]
[%- IF (element.get_annotation && element.get_annotation.0.get_documentation) %]
[% element.get_annotation.0.get_documentation %]
[% END; %]
[% IF (type_name=element.get_type);
type = definitions.get_types.0.find_type(element.expand(type_name));
IF (! type);
THROW NOT_FOUND "type " _ type_name _ " for attribute " _ element.get_name _ " not found";
END; %]
This attribute is of type L<[% XSD.create_xsd_name(type) %]|[% XSD.create_xsd_name(type) %]>.
[% END %]
[%- END -%]
[% END %]

View File

@@ -1,5 +1,5 @@
[% indent %]{
[%- IF complexType.get_name %] # [% type_prefix %]::[% complexType.get_name %][% END %]
[%- IF complexType.get_name %] # [% XSD.create_xsd_name(complexType) %][% END %]
[%- indent = indent _ ' ' %]
[% indent %]# One of the following elements.
[% indent %]# No occurance checks yet, so be sure to pass just one...

View File

@@ -1,7 +1,10 @@
[% IF (complexType.get_variety == 'restriction');
INCLUDE complexType/POD/restriction.tt(complexType = complexType);
ELSIF (complexType.get_variety == 'sequence');
THROW NOT_IMPLEMENTED, "${ complexType.get_name } - complexType complexContent extension not implemented yet";
ELSIF (complexType.get_variety == 'extension');
#THROW NOT_IMPLEMENTED, "${ complexType.get_name } - complexType complexContent extension not implemented yet";
%]
# No documentation generated for complexContent / extension yet
[%
ELSE;
THROW UNKNOWN, "unknown variety ${ complexType.get_variety }";
END;

View File

@@ -1,5 +1,5 @@
[% indent %]{
[%- IF complexType.get_name %] # [% type_prefix %]::[% complexType.get_name %][% END %]
[%- IF complexType.get_name %] # [% XSD.create_xsd_name(complexType) %][% END %]
[%- indent = indent _ ' ';
FOREACH element = complexType.get_element %]
[% indent %][% element.get_name %] => [% INCLUDE element/POD/structure.tt -%]

View File

@@ -0,0 +1,9 @@
[% IF (complexType.get_variety == 'restriction');
INCLUDE complexType/POD/simpleContent/restriction.tt(complexType = complexType);
ELSIF (complexType.get_variety == 'extension');
INCLUDE complexType/POD/simpleContent/restriction.tt(complexType = complexType);
ELSE;
THROW UNKNOWN, "unknown variety ${ complexType.get_variety }";
END;
%]

View File

@@ -0,0 +1 @@
# No documentation generated for simpleContent / extension yet

View File

@@ -0,0 +1,46 @@
{
value => $some_value, # simple perl scalar. See below for restrictions
}
NOTE: This type is derived by restriction as complexType with simpleContent.
Documentation generation for this derivation method is experimental and may
be erroneous/incomplete.
This clase is derived from [%-
IF (name = complexType.get_base);
# type_name = complexType.expand( name );
-%]
[% XSD.create_xsd_name(complexType) %]
[% ELSE;
%] an atomic base type. Unfortunately there's no documentation generated
on atomic base types' base type yet.[%
END -%]
SOAP::WSDL's schema implementation does not validate data yet - however, the
following restrictions apply for this type's value:
[%- FOREACH facet = [
'length',
'minLength',
'maxLength',
'totalDigits',
'fractionDigits',
'minInclusive',
'maxInclusive',
'minExclusive',
'maxExclusive',
'pattern',
'enumeration'
];
IF (facet_method = complexType.can( "get_" _ facet ));
facet_value = facet_method( complexType );
IF (facet_value.size());
%]
[% IF (facet == 'enumeration');
%]valid values (enumeration)
[%- ELSE;
facet;
END -%]:[% FOREACH value = facet_value %] [% value.get_value; END -%]
[% END;
END;
END %]

View File

@@ -7,7 +7,7 @@ ELSIF (complexType.get_variety == 'group');
ELSIF (complexType.get_variety == 'choice');
INCLUDE complexType/POD/choice.tt(complexType = complexType);
ELSIF (complexType.get_contentModel == 'simpleContent');
THROW NOT_IMPLEMENTED, "${ element.get_name } - complexType simpleContent not implemented yet";
INCLUDE complexType/POD/structure/simpleContent.tt(complexType = complexType);
ELSIF (complexType.get_contentModel == 'complexContent');
INCLUDE complexType/POD/complexContent.tt(complexType = complexType);
END %],
END -%],

View File

@@ -0,0 +1,7 @@
{
[%- IF complexType.get_name %] # [% XSD.create_xsd_name(complexType) %][% END %]
[%- indent = indent _ ' ';
FOREACH element = complexType.get_element %]
[% indent %][% element.get_name %] => [% INCLUDE element/POD/structure.tt -%]
[% END %]
[% indent.replace('\s{2}$', ''); %]}

View File

@@ -0,0 +1 @@
{ value => $some_value }

View File

@@ -8,7 +8,7 @@ Class::Std::initialize();
atomic_types = {};
FOREACH element = complexType.get_element %]
my %[% element.get_name %]_of :ATTR(:get<[% element.get_name %]>);
my %[% XSD.perl_name(element.get_name) %]_of :ATTR(:get<[% XSD.perl_name(element.get_name) %]>);
[%- END %]
__PACKAGE__->_factory(
@@ -18,27 +18,23 @@ __PACKAGE__->_factory(
) ],
{
[% FOREACH element = complexType.get_element -%]
[% element.get_name %] => \%[% element.get_name %]_of,
'[% element.get_name %]' => \%[% XSD.perl_name(element.get_name) %]_of,
[% END -%]
},
{
[% FOREACH element = complexType.get_element;
IF (type = element.get_type);
element_type = complexType.expand( type );
IF (element_type.0 == 'http://www.w3.org/2001/XMLSchema'); -%]
[% element.get_name %] => 'SOAP::WSDL::XSD::Typelib::Builtin::[% element_type.1 %]',
[% ELSE -%]
[% element.get_name %] => '[% type_prefix %]::[% element_type.1 %]',
[% END;
ELSE;
element_type = definitions.first_types.find_type(complexType.expand( type )); -%]
'[% element.get_name %]' => '[% XSD.create_xsd_name(element_type) %]',
[% ELSE;
IF (element.first_simpleType);
atomic_types.${ element.get_name } = element.first_simpleType;
ELSIF (element.first_complexType);
atomic_types.${ element.get_name } = element.first_complexType;
ELSE;
THROW NOT_IMPLEMENTED , "Neither simple nor complex atomic type - don't know what to do with it";
THROW NOT_IMPLEMENTED , "Neither simple nor complex atomic type for element ${ element.get_name } - don't know what to do with it";
END; %]
[% element.get_name %] => '[% type_prefix %]::[% complexType.get_name %]::_[% element.get_name %]',
'[% element.get_name %]' => '[% XSD.create_subpackage_name({ value => element }) %]',
[% END;
END -%]
}

View File

@@ -1,7 +1,7 @@
[% FOREACH type IN atomic_types; %]
package [% type_prefix %]::[% complexType.get_name %]::_[% type.key %];
[%# TODO generate name create_name method %]
package [% XSD.create_subpackage_name(type); %];
use strict;
use warnings;
{

View File

@@ -1,40 +1,54 @@
{ # BLOCK to scope variables
[%
[% IF (complexType.get_attribute.size) -%]
package [% XSD.create_xmlattr_name(complexType) %];
use base qw(SOAP::WSDL::XSD::Typelib::AttributeSet);
FOREACH element = complexType.get_attribute %]
{ # BLOCK to scope variables
[% FOREACH element = complexType.get_attribute;
WHILE element.get_ref;
element = definitions.first_types.find_attribute(element.expand( element.get_ref ));
END; %]
my %[% element.get_name %]_of :ATTR(:get<[% element.get_name %]>);
[%- END %]
__PACKAGE__->_factory(
[ qw([% FOREACH element = complexType.get_attribute %]
[ qw(
[%- FOREACH element = complexType.get_attribute;
WHILE element.get_ref;
element = definitions.first_types.find_attribute(element.expand( element.get_ref ));
END; %]
[% element.get_name -%]
[% END %]
) ],
{
[% FOREACH element = complexType.get_attribute -%]
[% FOREACH element = complexType.get_attribute;
WHILE element.get_ref;
element = definitions.first_types.find_attribute(element.expand( element.get_ref ));
END; %]
[% element.get_name %] => \%[% element.get_name %]_of,
[% END -%]
},
{
[% FOREACH element = complexType.get_attribute;
IF (type = element.get_type);
element_type = complexType.expand( type );
IF (element_type.0 == 'http://www.w3.org/2001/XMLSchema'); -%]
[% element.get_name %] => 'SOAP::WSDL::XSD::Typelib::Builtin::[% element_type.1 %]',
[% ELSE -%]
[% element.get_name %] => '[% type_prefix %]::[% element_type.1 %]',
[% END;
ELSE;
IF (element.first_simpleType);
element_type = definitions.first_types.find_type(complexType.expand( type ));
-%]
[% element.get_name %] => '[% XSD.create_xsd_name(element_type) %]',
[%
ELSIF (ref = element.get_ref);
WHILE element.get_ref;
element = definitions.first_types.find_attribute(element.expand( element.get_ref ));
END;
%]
[% element.get_name %] => '[% XSD.create_xsd_name(element) %]',
[% ELSIF (element.first_simpleType);
THROW NOT_IMPLEMENTED , "Attributes with atomic simpleType definition are not implemented yet";
atomic_types.${ element.get_name } = element.first_simpleType;
ELSE;
THROW NOT_IMPLEMENTED , "Neither simple nor complex atomic type - don't know what to do with it";
END; %]
[% element.get_name %] => '[% type_prefix %]::[% complexType.get_name %]::_[% element.get_name %]',
[% END;
ELSE;
THROW NOT_IMPLEMENTED , "Neither simple nor complex atomic type for attribute ${ element.get_name } in ${ complexType.get_name } - don't know what to do with it";
END;
END -%]
}
);
} # end BLOCK
[% END %]

View File

@@ -2,6 +2,8 @@
INCLUDE complexType/restriction.tt(complexType = complexType);
ELSIF (complexType.get_variety == 'sequence');
INCLUDE complexType/extension.tt(complexType = complexType);
ELSIF (complexType.get_variety == 'all');
INCLUDE complexType/extension.tt(complexType = complexType);
ELSE;
THROW UNKNOWN, "unknown variety ${ complexType.get_variety }";
END;

View File

@@ -1,7 +1,19 @@
[% IF (complexType.get_attribute.size) -%]
our $XML_ATTRIBUTE_CLASS = '[% XSD.create_xmlattr_name(complexType) %]';
[% ELSE -%]
our $XML_ATTRIBUTE_CLASS;
undef $XML_ATTRIBUTE_CLASS;
[% END %]
sub __get_attr_class {
return $XML_ATTRIBUTE_CLASS;
}
[% IF (complexType.get_contentModel == 'simpleContent');
THROW NOT_IMPLEMENTED, "${ element.get_name } - complexType simpleContent not implemented yet";
INCLUDE complexType/simpleContent.tt(complexType = complexType);
ELSIF (complexType.get_contentModel == 'complexContent');
INCLUDE complexType/complexContent.tt(complexType = complexType);
ELSE;
INCLUDE complexType/variety.tt(complexType = complexType);
END %]
END -%]
[% INCLUDE complexType/attributeSet.tt %]

View File

@@ -20,7 +20,7 @@ END;
complexType.set_element( element_list );
-%]
use base qw([% type_prefix %]::[% base_name.1.replace('\.', '::') %]);
use base qw([% XSD.create_xsd_name( base_type ) %]);
[%
INCLUDE complexType/variety.tt(complexType = complexType);

View File

@@ -1,7 +1,7 @@
[% IF (base=complexType.get_base);
base_name=complexType.expand(base);
base_type=definitions.get_types.0.find_type(complexType.expand(base));
-%]
use base qw([% type_prefix %]::[% base_name.1.replace('\.', '::') %]);
use base qw([% XSD.create_xsd_type(base_type) %]);
[%
ELSE;
THROW NOT_IMPLEMENTED, "restriction without base not supported";

View File

@@ -0,0 +1,9 @@
[% IF (complexType.get_variety == 'restriction');
INCLUDE complexType/restriction.tt(complexType = complexType);
ELSIF (complexType.get_variety == 'extension');
INCLUDE complexType/simpleContent/extension.tt(complexType = complexType);
# THROW NOT_IMPLEMENTED, "${ complexType.get_name } - complexType simpleContent extension not implemented yet";
ELSE;
THROW UNKNOWN, "unknown variety ${ complexType.get_variety } in complexType name='${complexType.get_name}'";
END;
%]

View File

@@ -0,0 +1,11 @@
[% IF (base=complexType.get_base);
base_type=definitions.get_types.0.find_type(complexType.expand(base));
-%]
use base qw(
SOAP::WSDL::XSD::Typelib::ComplexType
[% XSD.create_xsd_name(base_type) %]
);
[%
ELSE;
THROW NOT_IMPLEMENTED, "extension without base not supported";
END %]

View File

@@ -1,4 +1,5 @@
package [% element_prefix %]::[% element.get_name.replace('\.','::') %];
[% USE XSD(context) %]
package [% XSD.create_xsd_name(element) %];
use strict;
use warnings;
@@ -7,22 +8,29 @@ use warnings;
sub get_xmlns { '[% element.get_targetNamespace %]' }
__PACKAGE__->__set_name('[% element.get_name %]');
__PACKAGE__->__set_nillable([% element.get_nillable %]);
__PACKAGE__->__set_nillable([% IF (element.get_nillable);
IF (element.get_nillable != 'false'); %]1[% ELSE %]0[% END;
END;
%]);
__PACKAGE__->__set_minOccurs([% element.get_minOccurs %]);
__PACKAGE__->__set_maxOccurs([% element.get_maxOccurs %]);
__PACKAGE__->__set_ref([% IF element.get_ref; %]'[% element.get_ref %]'[% END %]);
[%- IF (type = element.get_type); -%]
[%- IF (type_name = element.get_type); -%]
use base qw(
SOAP::WSDL::XSD::Typelib::Element
[% INCLUDE _type_class.tt( type = type, node = element ) %]
[% type = definitions.get_types.0.find_type(element.expand(type_name));
XSD.create_xsd_name(type) %]
);
}
[%- ELSIF (ref = element.get_ref); -%]
[%- ELSIF (ref = element.get_ref);
ref_from = ref.split(':');
-%]
# element ref="[% ref %]"
use base qw(
[% element_prefix %]::[% ref.split(':').1 %]
[% ref_element = definitions.get_types.0.find_element(element.expand(ref));
XSD.create_xsd_name( ref_element ); %]
);
}
@@ -40,16 +48,9 @@ use base qw(
SOAP::WSDL::XSD::Typelib::Element
SOAP::WSDL::XSD::Typelib::ComplexType
);
[% INCLUDE complexType/contentModel.tt -%]
}
package [% element_prefix %]::[% element.get_name.replace('\.','::').replace('-','_') %]::_ATTR;
use base qw(SOAP::WSDL::XSD::Typelib::AttributeSet);
[% INCLUDE complexType/attributeSet.tt %]
[% ELSE %]
} # end of BLOCK
[% END %]
@@ -66,18 +67,20 @@ use base qw(SOAP::WSDL::XSD::Typelib::AttributeSet);
[% head1 %] NAME
[% element_prefix %]::[% element.get_name %]
[% XSD.create_xsd_name(element) %]
[% head1 %] DESCRIPTION
Perl data type class for the XML Schema defined element
[% element.get_name %] from the namespace [% element.get_targetNamespace %].
[% INCLUDE POD/annotation.tt(node = element) %]
[% head1 %] METHODS
[% head2 %] new
my $element = [% element_prefix %]::[% element.get_name %]->new($data);
my $element = [% XSD.create_xsd_name(element) %]->new($data);
Constructor. The following data structure may be passed to new():

View File

@@ -0,0 +1,8 @@
[% IF (type = element.get_type);
ELSIF (simpleType = element.get_simpleType) %]
This XML element type class has a atomic simpleType as it's base:
[%
INCLUDE simpleType/POD/contentModel.tt(simpleType = simpleType);
ELSIF (simpleType = element.get_complexType);
ELSIF (ref_element = element.get_ref);
END %]

View File

@@ -1,4 +1,5 @@
package [% type_prefix %]::[% simpleType.get_name.replace('\.','::').replace('-','_') %];
[% USE XSD(context) -%]
package [% XSD.create_xsd_name(simpleType) %];
use strict;
use warnings;
@@ -20,20 +21,18 @@ __END__
[% pod %]
[% head1 %] [% type_prefix %]::[% simpleType.get_name.replace('\.','::').replace('-','_') %]
[% head1 %] NAME
[% XSD.create_name(simpleType) %]
[% head1 %] DESCRIPTION
Perl data type class for the XML Schema defined simpleType
[% simpleType.get_name %] from the namespace [% simpleType.get_targetNamespace %].
[% IF (simpleType.get_variety == 'list');
INCLUDE simpleType/POD/list.tt;
ELSIF (simpleType.get_variety == 'restriction');
INCLUDE simpleType/POD/restriction.tt;
ELSE;
THROW NOT_IMPLEMENTED "simpleType union not implemented yet in $simpleType.get_name";
END %]
[% INCLUDE POD/annotation.tt(node = simpleType) %]
[% INCLUDE simpleType/POD/contentModel.tt(simpleType = simpleType) %]
[% head1 %] METHODS

View File

@@ -0,0 +1,9 @@
[% IF (simpleType.get_variety == 'list');
INCLUDE simpleType/POD/list.tt;
ELSIF (simpleType.get_variety == 'restriction');
INCLUDE simpleType/POD/restriction.tt;
ELSIF (simpleType.get_variety == 'union');
INCLUDE simpleType/POD/union.tt;
ELSE;
# THROW NOT_IMPLEMENTED "simpleType " _ simpleType.get_variety _ "not implemented yet in $simpleType.get_name";
END %]

View File

@@ -1,13 +1,9 @@
This clase is derived from
[%-
IF (name = simpleType.get_itemType);
type_name = simpleType.expand( name );
IF (type_name.0 == 'http://www.w3.org/2001/XMLSchema'); -%]
SOAP::WSDL::XSD::Typelib::Builtin::[% type_name.1 %]
[% ELSE -%]
[% type_prefix %]::[% type_name.1 %]
[% END;
ELSE;
type = definitions.get_types.0.find_type(simpleType.expand( name )); %]
[% XSD.create_xsd_name(type) %]
[% ELSE;
# THROW NOT_IMPLEMENTED "atomic simpleType list not implemented yet in $simpleType.get_name";
%] a atomic base type. Unfortunately there's no documenatation generation for atomic base types yet. [%
END -%].

View File

@@ -1,12 +1,8 @@
This clase is derived from [%-
IF (name = simpleType.get_base);
type_name = simpleType.expand( name );
IF (type_name.0 == 'http://www.w3.org/2001/XMLSchema'); -%]
SOAP::WSDL::XSD::Typelib::Builtin::[% type_name.1 %]
[% ELSE -%]
[% type_prefix %]::[% type_name.1 %]
[% END;
ELSE;
type = definitions.get_types.0.find_type(simpleType.expand(name)); %]
[% XSD.create_xsd_name(type); %]
[% ELSE;
# THROW NOT_IMPLEMENTED "atomic simpleType restriction not implemented yet in $simpleType.get_name";
%] a atomic base type. Unfortunately there's no documenatation generation for atomic base types yet. [%
END -%]

View File

@@ -0,0 +1,8 @@
This type class is derived by union.
Derivation by union is not fully supported yet - value space constraints are
not checked yet.
The current implementation of union resorts to inheriting from the base type,
which means (quoted from the XML Schema specs): "If the <list> or <union>
alternative is chosen, then the simple ur-type definition·."

View File

@@ -2,6 +2,8 @@
INCLUDE simpleType/list.tt(simpleType = simpleType);
ELSIF (simpleType.get_variety == 'restriction');
INCLUDE simpleType/restriction.tt(type = simpleType);
ELSIF (simpleType.get_variety == 'union');
INCLUDE simpleType/union.tt(type = simpleType);
ELSE;
THROW NOT_IMPLEMENTED "${ element.get_name } - ${ simpleType.get_variety } not supported yet";
END %]

View File

@@ -1,17 +1,13 @@
[% USE XSD %]
# list derivation
use base qw(
SOAP::WSDL::XSD::Typelib::Builtin::list
[%
IF (name = simpleType.get_itemType);
type_name = simpleType.expand( name );
IF (type_name.0 == 'http://www.w3.org/2001/XMLSchema'); -%]
SOAP::WSDL::XSD::Typelib::Builtin::[% type_name.1 %]
type = definitions.get_types.0.find_type(simpleType.expand( name )); -%]
[% XSD.create_xsd_name(type) %]
);
[% ELSE -%]
[% type_prefix %]::[% type_name.1 %]
);
[% END;
ELSIF (type = simpleType.first_simpleType); %]
[% ELSIF (type = simpleType.first_simpleType); %]
);
[% INCLUDE simpleType/atomicType.tt(type = type);

View File

@@ -1,9 +1,14 @@
# derivation by restriction
[% IF (base = simpleType.get_base) -%]
use base qw(
[% INCLUDE _type_class.tt(type = base, node=simpleType) %]);
[%
base_type = definitions.get_types.0.find_type(simpleType.expand(base));
IF ! base_type;
THROW NOT_FOUND "No base type in " _ simpleType.get_parent.get_name;
END;
XSD.create_xsd_name(base_type) %]);
[% ELSIF (type = simpleType.first_simpleType() );
INCLUDE simpleType/atomicType.tt(type = type);
ELSE;
THROW "neither base nor atomic type - don't know what to do" %]
[% END %]
[% END %]

View File

@@ -0,0 +1,11 @@
# derivation by union
# union is not fully supported yet - value space constraints are not
# checked yet.
# This implementation of union resorts to the simplest possible base, which
# is: "If the <list> or <union> alternative is chosen, then the
# simple ur-type definition·."
#
use base qw(
SOAP::WSDL::XSD::Typelib::Builtin::anySimpleType
);

View File

@@ -3,7 +3,7 @@ use strict;
use warnings;
use Class::Std::Fast::Storable;
our $VERSION = q{2.00_25};
use version; our $VERSION = qv('2.00.01');
my %definitions_of :ATTR(:name<definitions> :default<()>);
my %type_prefix_of :ATTR(:name<type_prefix> :default<()>);
@@ -66,35 +66,35 @@ tree of objects.
A Visitor's methods are called using the so-called double dispatch technique.
To allow double dispatching, the Visitor implements one method for every class
ro be handled, whereas every class implements just one method (commonly named
to be handled, whereas every class implements just one method (commonly named
"access"), which does nothing more than calling a method on the reference
given, with the self object as parameter.
If all this sounds strange, maybe an example helps. Imagine you had a list of
person objects and wanted to print out a list of their names (or address
stamps or everything elseyou like). This can easily be implemented with a
stamps or everything else you like). This can easily be implemented with a
Visitor:
package PersonVisitor;
use Class::Std; # handles all basic stuff like constructors etc.
sub visit_Person {
my ( $self, $object ) = @_;
print "Person name is ", $object->get_name(), "\n";
}
package Person;
use Class::Std;
my %name : ATTR(:name<name> :default<anonymous>);
sub accept { $_[1]->visit_Person( $_[0] ) }
package main;
my @person_from = ();
for (qw(Gamma Helm Johnson Vlissides)) {
push @person_from, Person->new( { name => $_ } );
}
my $visitor = PersonVisitor->new();
for (@person_from) {
$_->accept($visitor);
@@ -107,7 +107,7 @@ Visitor:
Person name is Vlissides
While using this pattern for just printing a list may look a bit over-sized,
but it may become handy if you need multiple output formats and different
it may become handy if you need multiple output formats and different
classes to operate on.
The main benefits using visitors are:
@@ -188,8 +188,8 @@ mimicing .NET's .asmx example pages.
All these behaviours could well be (and have historically been) implemented in
the classes holding the WSDL data. This made these classes rather bloated, and
made it hard to change behaviour (like, supporting SOAP Headers,
supporting atomic types and other features which were missing from early
made it hard to change behaviour (like supporting SOAP Headers,
supporting atomic types, and other features which were missing from early
versions of SOAP::WSDL).
Implementing these behaviours in Visitor classes eases adding new behaviours,
@@ -203,7 +203,7 @@ schema implementation.
SOAP::WSDL::Base defines an accept method which expects a Visitor as only
parameter.
The method visit_Foo_Bar is called on the visitor, whith the self object as
The method visit_Foo_Bar is called on the visitor, with the self object as
parameter.
The actual method name is constructed this way:
@@ -224,7 +224,7 @@ visit_XSD_ComplexType is called on the visitor.
=head2 Writing your own visitor
SOAP::WSDL eases writing your own visitor. This might be required if you need
some special output format from a WSDL file, or want to feed your own
some special output format from a WSDL file or want to feed your own
serializer/deserializer pair with custom configuration data. Or maybe you want
to generate C# code from it...
@@ -269,19 +269,22 @@ SOAP::WSDL data classes:
In your Visitor, you must implement visit_Foo methods for all classes you wish
to visit.
Currently, all SOAP::WSDL::Generator::Visitor implementations include their own
The SOAP::WSDL::Generator::Visitor implementations include part of their own
Iterator (which means they know how to find the next objects to visit). You
may or may not choose to implement a separate Iterator.
Letting a visitor implementing it's own Iterator visit a WSDL definition is as
Letting a visitor implementing its own Iterator visit a WSDL definition is as
easy as writing something like this:
my $visitor = MyVisitor->new();
my $parser = SOAP::WSDL::Expat::WSDLParser->new();
my $definitions = $parser->parse_file('my.wsdl'):
$definitions->_accept( $visitor );
If you need an iterator following the somewhat crude path of dependencies in
a WSDL1.1 definition, you might want to look at L<SOAP::WSDL::Generator::Iterator::WSDL11>.
=head1 REFERENCES
=over
@@ -296,10 +299,10 @@ Addison-Wesley Longman, Amsterdam.
=head1 LICENSE AND COPYRIGHT
Copyright 2004-2007 Martin Kutter.
Copyright 2004-2008 Martin Kutter.
This file is part of SOAP-WSDL. You may distribute/modify it under
the same terms as perl itself
This file is part of SOAP-WSDL. You may distribute/modify it under the same
terms as perl itself
=head1 AUTHOR
@@ -307,9 +310,9 @@ Martin Kutter E<lt>martin.kutter fen-net.deE<gt>
=head1 REPOSITORY INFORMATION
$Rev: 239 $
$Rev: 391 $
$LastChangedBy: kutterma $
$Id: Client.pm 239 2007-09-11 09:45:42Z kutterma $
$Id: Client.pm 391 2007-11-17 21:56:13Z kutterma $
$HeadURL: https://soap-wsdl.svn.sourceforge.net/svnroot/soap-wsdl/SOAP-WSDL/trunk/lib/SOAP/WSDL/Client.pm $
=cut

View File

@@ -5,6 +5,7 @@ use base qw(SOAP::WSDL::Generator::Visitor
SOAP::WSDL::Generator::Template
);
use version; our $VERSION = qv('2.00.01');
1;

View File

@@ -5,17 +5,15 @@ use Class::Std::Fast::Storable;
use base qw(SOAP::WSDL::Generator::Visitor);
our $VERSION = q{2.00_25};
use version; our $VERSION = qv('2.00.01');
my %path_of :ATTR(:name<path> :default<[]>);
my %typemap_of :ATTR(:name<typemap> :default<()>);
my %type_prefix_of :ATTR(:name<type_prefix> :default<()>);
my %element_prefix_of :ATTR(:name<element_prefix> :default<()>);
my %resolver_of :ATTR(:name<resolver> :default<()>);
sub START {
my ($self, $ident, $arg_ref) = @_;
$type_prefix_of{ $ident } ||= 'MyTypes';
$element_prefix_of{ $ident } ||= 'MyElements';
$resolver_of { $ident } = $arg_ref->{ resolver };
}
sub set_typemap_entry {
@@ -41,126 +39,22 @@ sub add_element_path {
# . $element->get_name();
}
sub visit_Definitions {
my ( $self, $ident, $definitions ) = ( $_[0], ident $_[0], $_[1] );
$self->set_definitions( $definitions );
for ( @{ $definitions->get_service() } ){
$_->_accept($self);
}
}
sub visit_Service {
my ( $self, $service ) = ( $_[0], $_[1] );
for ( @{ $service->get_port() } ) { $_->_accept($self); }
}
sub visit_Port {
my ( $self, $ident, $port ) = ( $_[0], ident $_[0], $_[1] );
# This is a false assumption - typemaps may be valid for non-soap
# bindings as well.
# TODO check and correct
return if not $port->first_address();
return if not $port->first_address()->isa('SOAP::WSDL::SOAP::Address');
my $binding = $self->get_definitions()
->find_binding( $port->expand( $port->get_binding() ) )
or die 'binding ' . $port->get_binding() . ' not found!';
$binding->_accept($self);
}
sub visit_Binding {
my ( $self, $ident, $binding ) = ( $_[0], ident $_[0], $_[1] );
my $portType = $self->get_definitions()
->find_portType( $binding->expand( $binding->get_type ) )
or die 'portType not found: ' . $binding->binding_type;
for my $operation ( @{ $binding->get_operation() } ) {
my $name = $operation->get_name();
# get the equally named operation from the portType
my ($op) = grep { $_->get_name eq $name }
@{ $portType->get_operation() }
or die "operation <$name> not found";
# visit every input, output and fault message...
for ( @{ $op->get_input }, @{ $op->get_output }, @{ $op->get_fault } ) {
$_->_accept($self);
}
}
}
sub visit_OpMessage {
my ( $self, $ident, $operation_message ) = ( $_[0], ident $_[0], $_[1] );
return if not( $operation_message->get_message() ); # we're in binding
# TODO maybe allow more messages && overloading by specifying name
# find message referenced in operation
my $message = $self->get_definitions()->find_message(
$operation_message->expand( $operation_message->get_message() ) );
for my $part ( @{ $message->get_part() } ) {
$part->_accept($self);
}
}
sub visit_Part {
my ( $self, $ident, $part ) = ( $_[0], ident $_[0], $_[1] );
my $types_ref = $self->get_definitions()->first_types()
or warn "Empty part" . $part->get_name();
# resolve type
# If we have a type, this type is to be used in document/literal
# as global type. However this is forbidden, at least by WS-I.
# We should store the style/encoding somewhere, and regard it.
# TODO: auto-generate element for RPC bindings
if ( my $type_name = $part->get_type ) {
# FIXME support RPC-style calls
die "unsupported global type <$type_name> found in part ". $part->get_name();
}
# TODO factor out iterator or replace by lookup (probably better)
if ( my $element_name = $part->get_element() ) {
my $element = $types_ref->find_element(
$part->expand($element_name) )
|| die "no element $element_name found for part " . $part->get_name();
$element->_accept($self);
return;
}
warn 'neither type nor element - do not know what to do for part '
. $part->get_name();
return;
}
sub process_referenced_type {
my ( $self, $ns, $localname ) = @_;
return if not $localname;
my $ident = ident $self;
# get type's class name
# Caveat: visits type if it's a referenced type from the
# a ? b : c operation.
my ($type, $typeclass);
if ( $ns eq 'http://www.w3.org/2001/XMLSchema' ) {
$typeclass = "SOAP::WSDL::XSD::Typelib::Builtin::$localname";
}
else {
$type = $self->get_definitions()->first_types()->find_type( $ns, $localname );
$typeclass = join( q{::}, $type_prefix_of{$ident}, $type->get_name() );
}
$type = $self->get_definitions()->first_types()->find_type( $ns, $localname );
$typeclass = $self->get_resolver()->create_xsd_name($type);
# set before to allow it to be used from inside _accept
$self->set_typemap_entry($typeclass);
$type->_accept($self) if ($type);
$type->_accept($self) if ($ns ne 'http://www.w3.org/2001/XMLSchema');
# set afterwards again (just to be sure...)
$self->set_typemap_entry($typeclass);
@@ -171,8 +65,7 @@ sub process_atomic_type {
my ( $self, $type, $callback ) = @_;
return if not $type;
my $ident = ident $self;
$callback->( $self, $type ) if $callback;
$callback->( $self, $type );
return $self;
}
@@ -202,22 +95,20 @@ sub visit_XSD_Element {
if ($element->get_simpleType()) {
# warn "simpleType " . $element->get_name();
my @path = @{ $path_of{ ${ $self } } };
my $typeclass = defined ($parent)
? join '::_', $parent , $element->get_name()
: join q{::}, $element_prefix_of{$ident}, $element->get_name();
my $typeclass = $self->get_resolver()->create_subpackage_name($element);
$self->set_typemap_entry($typeclass);
$typeclass =~s{\.}{::}g;
$typeclass =~s{\-}{_}g;
last SWITCH;
}
# for atomic and complex types , and ref elements
my $typeclass = join q{::}, $element_prefix_of{$ident}, $element->get_name();
$typeclass =~s{\.}{::}g;
$typeclass =~s{\-}{_}g;
my $typeclass = $self->get_resolver()->create_subpackage_name($element);
$self->set_typemap_entry($typeclass);
$self->process_atomic_type( $element->first_complexType()
, sub { $_[1]->_accept($_[0]) } )
&& last;
&& last SWITCH;
# TODO: add element ref handling
};
@@ -226,9 +117,7 @@ sub visit_XSD_Element {
# a normal (not atomic) type, we just override it here
if (not defined($parent)) {
# for atomic and complex types , and ref elements
my $typeclass = join q{::}, $element_prefix_of{$ident}, $element->get_name();
$typeclass =~s{\.}{::}g;
$typeclass =~s{\-}{_}g;
my $typeclass = $self->get_resolver()->create_xsd_name($element);
$self->set_typemap_entry($typeclass);
}
@@ -238,11 +127,12 @@ sub visit_XSD_Element {
sub visit_XSD_ComplexType {
my ($self, $ident, $type) = ($_[0], ident $_[0], $_[1] );
my $content_model = $type->get_flavor();
# TODO is this allowed ? or should we better die ?
return if not $content_model; # empty complexType
my $variety = $type->get_variety();
my $content_model = $type->get_contentModel;
return if not $variety; # empty complexType
return if ($content_model eq 'simpleContent');
if ( grep { $_ eq $content_model} qw(all sequence choice) )
if ( grep { $_ eq $variety} qw(all sequence choice) )
{
# visit child elements
for (@{ $type->get_element() || [] }) {
@@ -251,7 +141,21 @@ sub visit_XSD_ComplexType {
return;
}
warn "unsupported content model $content_model found in "
if (grep { $_ eq $variety } qw(restriction extension) ) {
# resolve base / get atomic type and run on elements
if (my $type_name = $type->get_base()) {
my $subtype = $self->get_definitions()
->first_types()->find_type( $type->expand($type_name) );
# visit child elements
for (@{ $subtype->get_element() || [] }) {
$_->_accept( $self );
}
# that's all for restriction
return if ($variety eq 'restriction');
}
}
warn "unsupported content model $variety found in "
. "complex type " . $type->get_name()
. " - typemap may be incomplete";
}

View File

@@ -22,15 +22,15 @@ service).
=item * Write script
use MyInterface::SERVICE_NAME::PORT_NAME;
my $service = MyInterface::SERVICE_NAME::PORT_NAME->new();
use MyInterfaces::SERVICE_NAME::PORT_NAME;
my $service = MyInterfaces::SERVICE_NAME::PORT_NAME->new();
my $result = $service->SERVICE_METHOD();
die $result if not $result;
print $result;
C<perldoc MyInterface::SERVICE_NAME::PORT_NAME> should give you some overview
C<perldoc MyInterfaces::SERVICE_NAME::PORT_NAME> should give you some overview
about the service's interface structure.
The results of all calls to your service object's methods (except new) are
@@ -103,9 +103,9 @@ included perldoc will be, too - if not, blame the web service author.
=item * Write a perl script (or module) accessing the web service.
use MyInterface::SERVICE_NAME;
my $service = MyInterface::SERVICE_NAME->new();
use MyInterfaces::SERVICE_NAME::PORT_NAME;
my $service = MyInterfaces::SERVICE_NAME::PORT_NAME->new();
my $result = $service->SERVICE_METHOD();
die $result if not $result;
print $result;
@@ -237,62 +237,14 @@ C<--server> or C<-s> option to the call to C<wsdl2perl.pl>.
perl wsdl2perl.pl -s -b BASE_DIR URL
Note that SOAP::WSDL only includes a basic CGI based SOAP servers by now -
while more advanced servers (like standalone or mod_perl based) are no big
deal, no base implementation is included yet.
=head1 Troubleshooting
=head2 Accessing HTTPS webservices
You need Crypt::SSLeay installed to access HTTPS webservices.
=head2 Accessing protected web services
Passing a userndame and password, or a client certificate and key, to the
transport layer is highly dependent on the transport backend.
=head3 Accessing HTTP(S) webservices with basic/digest authentication
When using SOAP::WSDL::Transport::HTTP (SOAP::Lite not installed), add a
method called "get_basic_credentials" to SOAP::WSDL::Transport::HTTP:
*SOAP::WSDL::Transport::HTTP::get_basic_credentials = sub {
return ($user, $password);
};
When using SOAP::Transport::HTTP (SOAP::Lite is installed), do the same to
this backend:
*SOAP::Transport::HTTP::get_basic_credentials = sub {
return ($user, $password);
};
=head3 Accessing HTTP(S) webservices protected by NTLM authentication
Besides passing user credentials as when accessing a web service protected
by basic or digest authentication, you also need to enforce connection
keep_alive on the transport backens.
To do so, pass a I<proxy> argument to the new() method of the generated
class. This unfortunately means that you have to set the endpoint URL, too:
my $interface = MyInterfaces::SERVICE_NAME::PORT_NAME->new({
proxy => [ $url, keep_alive => 1 ]
});
You may, of course, decide to just hack the generated class. Be advised that
subclassing might be a more appropriate solution - re-generating overwrites
changes in interface classes.
=head3 Accessing HTTPS webservices protected by certificate authentication
You need Crypt::SSLeay installed to access HTTPS webservices.
See L<Crypt::SSLeay> on how to configure client certificate authentication.
SOAP::WSDL currently includes classes for building a basic CGI and a
mod_perl 2 based SOAP server.
=head1 SEE ALSO
L<SOAP::WSDL::Manual::Cookbook> cooking recipes for accessing web services,
altering the XML Serializer and others.
L<SOAP::WSDL::Manual::XSD> SOAP::WSDL's XML Schema implementation
L<SOAP::WSDL::Manual::Glossary> The meaning of all these words

View File

@@ -430,7 +430,7 @@ TODO support rpc-literal bindings.
The wsdl:import element imports the referenced WSDL definition.
This is rather hard-wired and does not allow to specify a wsdl:import without
a resolvable location.
a resolvable location in SOAP::WSDL.
=head2 R4002
@@ -681,7 +681,7 @@ is Schema valid.
WSDL description.
SOAP::WSDL (partially) supports the wsdl:import statement. The wsdl:include
statement is not supported (yet).
statement is not supported.
It's the responsibility of the WSDL author to use only the wsdl:import
statement for importing WSDL descriptions.
@@ -1252,9 +1252,9 @@ Martin Kutter E<lt>martin.kutter fen-net.deE<gt>
=head1 REPOSITORY INFORMATION
$Rev: 514 $
$Rev: 562 $
$LastChangedBy: kutterma $
$Id: WS_I.pod 514 2008-01-31 19:57:52Z kutterma $
$Id: WS_I.pod 562 2008-02-22 20:32:17Z kutterma $
$HeadURL: http://soap-wsdl.svn.sourceforge.net/svnroot/soap-wsdl/SOAP-WSDL/trunk/lib/SOAP/WSDL/Manual/WS_I.pod $
=cut

View File

@@ -305,18 +305,17 @@ XML Schema facets are not implemented yet.
They will probably implemented some day by putting constant methods into
the correspondent classes.
=head1 ATTRIBUTES
XML attributes are not implemented yet. The documentation below sketches
how XML attributes will be implemented in the future.
All XML attributes are derived from SOAP::WSDL::XSD::Typelib::Attribute.
=head2 Attributes
The attribute set for a XML element (derived from anySimpleType or
complexType) is implemented as a sub-package of the element derived from
SOAP::WSDL::XSD::Typelib::AttributeSet.
The sub-package is named as the top package, suffixed with C<_ATTR>.
The sub-package is named as the corresponding type or element package,
suffixed with C<XmlAttr>. The suffix "XmlAttr" has carefully been chosen to
avoid potential naming clashes: The name XmlAttr cannot be included as
element or type name in XML schemas - the XML standard bans the use of names
starting with "xml" (case-insensitive).
All XML attributes for a XML element are set- and retrievable via the method
C<attr>. The name is chosen to allow mimicing SOAP::Lite's behaviour, which
@@ -336,6 +335,28 @@ get_FOO methods.
The C<attr> method provides auto-vivification: An xml object's attribute set
is instantiated when accessed.
Auto-vivification is only triggered if there actually B<is> a set of
attributes for the class/object in question, so you may want to test
whether the result of ->attr is defined:
my $attr = $unknownObject->attr();
if (defined($attr)) {
$unknownObject->attr({
some => 'value',
});
}
=head2 group
CAVEAT: Group resolution is not implemented yet.
XML Schema Group definitions are just treated as aliases that can be
inserted in complexType definitions by referencing them. That is, there's
no difference between a complexType with simpleContent and a sequence of
three elements, and a complexType with simpleContent referencing a group
containing the same sequence of elements.
=head1 CAVEATS
=over
@@ -364,70 +385,153 @@ The constructors of all SOAP::WSDL::XSD::Typelib:: classes don't !
The following XML Schema declaration elements are not supported yet:
=head2 XML Schema elements partially supported
=head3 Type definition elements
=over
=item * Declaration elements
=item * simpleContent
attribute
notation
=item * Type definition elements
simpleContent
union
=item * Content model definition elements
any
anyAttribute
attributeGroup
group
=item * Identity definition elements
field
key
keyref
selector
unique
=item * Inclusion elements
import
include
redefine
simpleContent is only supported with a restriction or extension with a C<base>
attribute. simpleContent declarations deriving from a atomic type are not
supported (yet).
=back
The following XML Schema declaration elements are supported, but have no
effect yet:
=head3 Inclusion elements
=over
=item * Factes
=item * import
enumeration
fractionDigits
lenght
maxExclusive
maxInclusiove
maxLength
minExclusive
minInclusive
minLength
pattern
totalDigits
whitespace
The import includion element requires the schemaLocation attribute for
resolving the XML schema to import. Support for the import element is
implemented in L<SOAP::WSDL::Expat::WSDLParser|SOAP::WSDL::Expat::WSDLParser>,
so alternative parsers may or may not support the import element.
=item * Documentation elements
L<SOAP::WSDL::Expat::WSDLParser|SOAP::WSDL::Expat::WSDLParser> keeps track of
included schemas and prevents import loops.
appinfo
=back
=head3 Facets
The following XML Schema declaration elements are supported, but have no
effect yet.
=over
=item * enumeration
=item * fractionDigits
=item * lenght
=item * maxExclusive
=item * maxInclusiove
=item * maxLength
=item * minExclusive
=item * minInclusive
=item * minLength
=item * pattern
=item * totalDigits
=item * whitespace
=back
=head2 XML Schema elements not implemented
=head3 Declaration elements
=over
=item * notation
=back
=head3 Content model definition elements
=over
=item * any
The horror of each XML schema implementation: Just anything...
C<any> declarations are not supported yet.
=item * anyAttribute
=item * attributeGroup
C<attributeGroup> declarations actually just are macros for XML Schema
writers: Including an attributeGroup in a declaration has the same effect
as including all attributes in the group.
Just not implemented yet.
=item * group
The group definition element is not supported yet.
=back
=head3 Identity definition elements
These declaration elements don't declare XML elements, but apply identity
constraints. They have no effect yet.
=over
=item * field
=item * key
=item * keyref
=item * selector
=item * unique
=back
=head3 Inclusion elements
=over
=item * include
Use of the include inclusion element is forbidden by the WS-I basic profile.
It is not supported (yet).
=item * redefine
Not supported (yet).
=back
=head3 * Documentation elements
=over
=item * appinfo
The appinfo documentation element is ignored.
=back
=head1 LICENSE
Copyright 2007 Martin Kutter.
Copyright 2007,2008 Martin Kutter.
This file is part of SOAP-WSDL. You may distribute/modify it under
the same terms as perl itself

View File

@@ -4,6 +4,8 @@ use warnings;
use Class::Std::Fast::Storable;
use base qw(SOAP::WSDL::Base);
use version; our $VERSION = qv('2.00.01');
my %part_of :ATTR(:name<part> :default<[]>);
1;

View File

@@ -4,9 +4,11 @@ use warnings;
use Class::Std::Fast::Storable;
use base qw(SOAP::WSDL::Base);
my %body_of :ATTR(:name<body> :default<[]>);
my %header_of :ATTR(:name<header> :default<[]>);
my %headerfault_of :ATTR(:name<headerfault> :default<[]>);
my %message_of :ATTR(:name<message> :default<()>);
use version; our $VERSION = qv('2.00.01');
my %body_of :ATTR(:name<body> :default<[]>);
my %header_of :ATTR(:name<header> :default<[]>);
my %headerfault_of :ATTR(:name<headerfault> :default<[]>);
my %message_of :ATTR(:name<message> :default<()>);
1;

View File

@@ -4,6 +4,8 @@ use warnings;
use Class::Std::Fast::Storable;
use base qw(SOAP::WSDL::Base);
use version; our $VERSION = qv('2.00.01');
my %operation_of :ATTR(:name<operation> :default<()>);
my %input_of :ATTR(:name<input> :default<[]>);
my %output_of :ATTR(:name<output> :default<[]>);

View File

@@ -6,6 +6,8 @@ use Class::Std::Fast::Storable;
use base qw(SOAP::WSDL::Base);
use version; our $VERSION = qv('2.00.01');
my %element_of :ATTR(:name<element> :default<()>);
my %type_of :ATTR(:name<type> :default<()>);

Some files were not shown because too many files have changed in this diff Show More