A hash is not an adequate structure for representing XML. XML can be order sensitive and Perl hashes are not. Also, the author of XML::Simple admits in his FAQ that even he doesnt process XML using his module --- it was only intended for XML as config files. It cant handle mixed content for instance.
On the other hand HTML::Element has a new_from_lol method that takes nested arrayrefs to form any type of XML possible.
Along those lines, I've developed code that compiles XML structure to the nested arrayref structure and uses Data::Diver to fill in the XML content with the hash values. Here a small sample of a file representing XML:
sub lol {
my ($self) = @_;
my $root = $self->data;
[
QBXML => DIVE( $root, qw() ),
[
QBXMLMsgsRq => { 'onError' => 'stopOnError' } =>
DIVE( $root, qw() ),
[
CustomerAddRq => DIVE( $root, qw() ),
[
CustomerAdd => DIVE( $root, qw() ),
[ Name => DIVE( $root, qw(Name) ) ],
[ IsActive => DIVE( $root, qw(IsActive) ) ],
[
ParentRef => DIVE( $root, qw(ParentRef) ),
[ ListID => DIVE( $root, qw(ParentRef ListID)
+) ],
[ FullName => DIVE( $root, qw(ParentRef FullNa
+me) ) ]
],
[ CompanyName => DIVE( $root, qw(CompanyName) ) ],
[ Salutation => DIVE( $root, qw(Salutation) ) ],
[ FirstName => DIVE( $root, qw(FirstName) ) ],
[ MiddleName => DIVE( $root, qw(MiddleName) ) ],
[ LastName => DIVE( $root, qw(LastName) ) ],
[
BillAddress => DIVE( $root, qw(BillAddress) ),
[ Addr1 => DIVE( $root, qw(BillAddress Addr1)
+) ],
[ Addr2 => DIVE( $root, qw(BillAddress Addr2)
+) ],
[ Addr3 => DIVE( $root, qw(BillAddress Addr3)
+) ],
[ Addr4 => DIVE( $root, qw(BillAddress Addr4)
+) ],
[ Addr5 => DIVE( $root, qw(BillAddress Addr5)
+) ],
[ City => DIVE( $root, qw(BillAddress City) )
+],
[ State => DIVE( $root, qw(BillAddress State)
+) ],
[
PostalCode =>
DIVE( $root, qw(BillAddress PostalCode)
+)
],
[ Country => DIVE( $root, qw(BillAddress Count
+ry) ) ],
[ Note => DIVE( $root, qw(BillAddress Note) )
+]
],
[
ShipAddress => DIVE( $root, qw(ShipAddress) ),
[ Addr1 => DIVE( $root, qw(ShipAddress Addr1)
+) ],
[ Addr2 => DIVE( $root, qw(ShipAddress Addr2)
+) ],
[ Addr3 => DIVE( $root, qw(ShipAddress Addr3)
+) ],
[ Addr4 => DIVE( $root, qw(ShipAddress Addr4)
+) ],
[ Addr5 => DIVE( $root, qw(ShipAddress Addr5)
+) ],
[ City => DIVE( $root, qw(ShipAddress City) )
+],
[ State => DIVE( $root, qw(ShipAddress State)
+) ],
[
PostalCode =>
DIVE( $root, qw(ShipAddress PostalCode)
+)
],
[ Country => DIVE( $root, qw(ShipAddress Count
+ry) ) ],
[ Note => DIVE( $root, qw(ShipAddress Note) )
+]
],
[ Phone => DIVE( $root, qw(Phone) ) ],
[ AltPhone => DIVE( $root, qw(AltPhone) ) ],
[ Fax => DIVE( $root, qw(Fax) ) ],
[ Email => DIVE( $root, qw(Email) ) ],
[ Contact => DIVE( $root, qw(Contact) ) ],
[ AltContact => DIVE( $root, qw(AltContact) ) ],
...
|