2315b201fbc8c432ea81a1482f69ca397a1e0c86
[dbsrgits/SQL-Translator.git] / lib / SQL / Translator / Producer / XML.pm
1 package SQL::Translator::Producer::XML;
2
3 # -------------------------------------------------------------------
4 # $Id: XML.pm,v 1.11 2003-07-31 20:48:23 dlc Exp $
5 # -------------------------------------------------------------------
6 # Copyright (C) 2003 Ken Y. Clark <kclark@cpan.org>,
7 #                    darren chamberlain <darren@cpan.org>,
8 #                    Chris Mungall <cjm@fruitfly.org>
9 #
10 # This program is free software; you can redistribute it and/or
11 # modify it under the terms of the GNU General Public License as
12 # published by the Free Software Foundation; version 2.
13 #
14 # This program is distributed in the hope that it will be useful, but
15 # WITHOUT ANY WARRANTY; without even the implied warranty of
16 # MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
17 # General Public License for more details.
18 #
19 # You should have received a copy of the GNU General Public License
20 # along with this program; if not, write to the Free Software
21 # Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA
22 # 02111-1307  USA
23 # -------------------------------------------------------------------
24
25 use strict;
26 use vars qw[ $VERSION ];
27 $VERSION = sprintf "%d.%02d", q$Revision: 1.11 $ =~ /(\d+)\.(\d+)/;
28
29 use IO::Scalar;
30 use SQL::Translator::Utils qw(header_comment);
31 use XML::Writer;
32
33 my $namespace = 'http://sqlfairy.sourceforge.net/sqlfairy.xml';
34 my $name = 'sqlt';
35
36 # -------------------------------------------------------------------
37 sub produce {
38     my $translator = shift;
39     my $schema     = $translator->schema;
40     my $args       = $translator->producer_args;
41
42     my $io          = IO::Scalar->new;
43     my $xml         = XML::Writer->new(
44         OUTPUT      => $io,
45         NAMESPACES  => 1,
46         PREFIX_MAP  => { $namespace => $name },
47         DATA_MODE   => 1,
48         DATA_INDENT => 2,
49     );
50
51     $xml->xmlDecl('UTF-8');
52     $xml->comment(header_comment('', ''));
53     $xml->startTag([ $namespace => 'schema' ]);
54
55     for my $table ( $schema->get_tables ) {
56         my $table_name = $table->name or next;
57         $xml->startTag   ( [ $namespace => 'table' ] );
58         $xml->dataElement( [ $namespace => 'name'  ], $table_name );
59         $xml->dataElement( [ $namespace => 'order' ], $table->order );
60
61         #
62         # Fields
63         #
64         $xml->startTag( [ $namespace => 'fields' ] );
65         for my $field ( $table->get_fields ) {
66             $xml->startTag( [ $namespace => 'field' ] );
67
68             for my $method ( 
69                 qw[ 
70                     name data_type default_value is_auto_increment 
71                     is_primary_key is_nullable is_foreign_key order size
72                 ]
73             ) {
74                 my $val = $field->$method || '';
75                 $xml->dataElement( [ $namespace => $method ], $val )
76                     if ( defined $val || 
77                         ( !defined $val && $args->{'emit_empty_tags'} ) );
78             }
79
80             $xml->endTag( [ $namespace => 'field' ] );
81         }
82
83         $xml->endTag( [ $namespace => 'fields' ] );
84
85         #
86         # Indices
87         #
88         $xml->startTag( [ $namespace => 'indices' ] );
89         for my $index ( $table->get_indices ) {
90             $xml->startTag( [ $namespace => 'index' ] );
91
92             for my $method ( qw[ fields name options type ] ) {
93                 my $val = $index->$method || '';
94                    $val = ref $val eq 'ARRAY' ? join(',', @$val) : $val;
95                 $xml->dataElement( [ $namespace => $method ], $val )
96                     if ( defined $val || 
97                         ( !defined $val && $args->{'emit_empty_tags'} ) );
98             }
99
100             $xml->endTag( [ $namespace => 'index' ] );
101         }
102         $xml->endTag( [ $namespace => 'indices' ] );
103
104         #
105         # Constraints
106         #
107         $xml->startTag( [ $namespace => 'constraints' ] );
108         for my $index ( $table->get_constraints ) {
109             $xml->startTag( [ $namespace => 'constraint' ] );
110
111             for my $method ( 
112                 qw[ 
113                     deferrable expression fields match_type name 
114                     options on_delete on_update reference_fields
115                     reference_table type 
116                 ] 
117             ) {
118                 my $val = $index->$method || '';
119                    $val = ref $val eq 'ARRAY' ? join(',', @$val) : $val;
120                 $xml->dataElement( [ $namespace => $method ], $val )
121                     if ( defined $val || 
122                         ( !defined $val && $args->{'emit_empty_tags'} ) );
123             }
124
125             $xml->endTag( [ $namespace => 'constraint' ] );
126         }
127         $xml->endTag( [ $namespace => 'constraints' ] );
128
129         $xml->endTag( [ $namespace => 'table' ] );
130     }
131
132     $xml->endTag([ $namespace => 'schema' ]);
133     $xml->end;
134
135     return $io;
136 }
137
138 1;
139
140 # -------------------------------------------------------------------
141 # The eyes of fire, the nostrils of air,
142 # The mouth of water, the beard of earth.
143 # William Blake
144 # -------------------------------------------------------------------
145
146 =head1 NAME
147
148 SQL::Translator::Producer::XML - XML output
149
150 =head1 SYNOPSIS
151
152   use SQL::Translator::Producer::XML;
153
154 =head1 DESCRIPTION
155
156 Creates XML output of a schema.
157
158 =head1 AUTHOR
159
160 Ken Y. Clark E<lt>kclark@cpan.orgE<gt>, darren chamberlain E<lt>darren@cpan.orgE<gt>
161
162 =head1 SEE ALSO
163
164 L<XML::Writer>