Modules Index

XML Schema Home

# XML::Schema::Type::Complex

This module implements an object class for representing XML Schema complex types. A complex type is one which carries attributes and/or contains other elements.

## Table of Contents

Synopsis |  |  |
Methods | : | attribute() |

## Synopsis

    use XML::Schema::Type::Complex;

    my $complex = XML::Schema::Type::Complex->new(
        name       => 'MyComplexType',
        attributes => {
            attr1  => {
    	    name    => 'attr1',
    	    type    => $type_obj,
    	    default => $value,		  # 'default' or 'fixed' optional
    	},
            attr2  => { type => $type_obj },  # no default, implicit name
            attr3  => $type_obj,		  # short form of above
            attr4  => $attr_obj,		  # XML::Schema::Attribute object
        }
        content    => [ ... ],
        # and more...
    );

    # add new attribute
    my $string = XML::Schema::Type::string->new();
    my $attrib = XML::Schema::Attribute->new( name => 'foo, type => $string );

    # add attribute object
    $complex->attribute($attrib);        # calls $attrib->name() to get 'foo'

    # fetch attribute object
    my $acopy = $complex->attribute('foo');

    # add attribute by values
    $complex->attribute( name => 'bar', type => $string );

## Methods

- attribute( $name )
  attribute( $attr_obj )
  attribute( name => $name, type => $type, ... )

  This method can be used to define and subsequently retrieve attribute definitions for the complex type.

  When called with a single non-reference argument, `$name`, the attribute corresponding to that name is returned. If there is no attribute defined with that name then `undef` is returned and an appropriate error message of the form `"no such attribute: $name"` is set internally for subsequent access via the `error()` method.

      my $attr = $complex->attribute('lang')
          || die $complex->error();

  In all other cases, the arguments passed are used to create and/or define a new attribute for the complex type. If a single argument is passed which is already a reference to an XML::Schema::Attribute object (or appropriate subclass or substitution class - see XML::Schema::Factory) then its `name()` method is called and a reference to the object is stored internally against that name as an attribute for the complex type.

      my $attr = XML::Schema::Attribute->new( name => 'lang', type => 'language' );

      $complex->attribute($attr);

  If a single argument is passed which is a reference to a hash array then the values contained therein will be used to create a new attribute object which will be assigned to the complex type as above. The hash array should contain `name` and `type` elements as a minimum.

      $complex->attribute({ name => 'lang', type => 'language' });

  If a list of arguments are passed then they will be automatically folded into a hash reference and treated as above.

      $complex->attribute( name => 'lang', type => 'language' );

  Attributes may define their `type` value in terms of a reference to a type object or a string indicating the name of a builtin simple type or one previously defined within the scope of the current complex type via the `simpleType()` method. The `attribute()` method calls the `scope()` on each attribute it adopts or adds the `scope` item to the hash reference used to create an attribute, as appropriate. In either case, the effect is to bind the attribute to the scope of the current complex type (`$self`) so that it can resolve type names to real type objects when an instance document is parsed.

  The Good Thing about this is that you can generally define types by their names and leave the objects to worry about resolving them to type objects at the right time. The Bad Thing about this is that you can't define an attribute once and then use it in a dozen different places because it's `scope` item will get overwritten each time you assign it to a complex type. However, all is not lost because W3C XML Schema defines Attribute Groups which are "Write Once, Reuse Many" attributes that Do The Right Thing to bind themselves to a scope as necessary. We'll be supporting something like that Real Soon Now.

Perl XML::Schema Documentation