move these to ::Producer::SQL::
[dbsrgits/SQL-Translator-2.0-ish.git] / lib / SQL / Translator / Producer / SQL / PostgreSQL.pm
1 package SQL::Translator::Producer::SQL::PostgreSQL;
2 use namespace::autoclean;
3 use Moose::Role;
4 use SQL::Translator::Constants qw(:sqlt_types);
5
6 my %data_type_mapping = (
7     SQL_LONGVARCHAR() => 'text',
8     SQL_TIMESTAMP()   => 'timestamp',
9     SQL_TYPE_TIMESTAMP() => 'timestamp without time zone',
10     SQL_TYPE_TIMESTAMP_WITH_TIMEZONE() => 'timestamp',
11     SQL_INTEGER()     => 'integer',
12     SQL_CHAR()        => 'character',
13     SQL_VARCHAR()     => 'varchar',
14     SQL_BIGINT()      => 'bigint',
15 );
16
17 sub _create_table {
18     my $self = shift;
19     my $table = shift;
20
21     my $pg_version = 0;
22
23     my $create_table;
24     my (@create, @column_defs, @index_defs, @constraint_defs);
25
26     $create_table .= 'DROP TABLE '   . $table->name . ";\n" if $self->drop_table;
27     $create_table .= 'CREATE TABLE ' . $table->name . " (\n";
28
29     push @column_defs, $self->_create_column($_) for values %{$table->columns};
30     $create_table .= join(",\n", map { '  ' . $_ } @column_defs ) . "\n)";
31
32     #use Data::Dumper; print Dumper($table->indexes);
33     foreach my $index (values %{$table->indexes}) {
34         if ($index->type eq 'NORMAL') {
35             push @index_defs, $self->_create_index($index, $table);
36         } else {
37             push @constraint_defs, $self->_create_index($index);
38         }
39     }
40
41     print $create_table . ";\n";
42 #    use Data::Dumper; print Dumper(@index_defs); print Dumper(@constraint_defs);
43     return (@create, $create_table, @index_defs, @constraint_defs);
44 }
45
46 sub _create_column {
47     my $self = shift;
48     my $column = shift;
49
50     my $size = $column->size;
51     my $default_value = $column->default_value;
52
53     my $column_def;
54     $column_def  = $column->name . ' ';
55     $column_def .= defined $data_type_mapping{$column->data_type}
56                    ? $data_type_mapping{$column->data_type}
57                    : $column->data_type;
58     $column_def .= '(' . $column->size . ')' if $size;
59     $column_def .= ' NOT NULL' unless $column->is_nullable;
60     $column_def .= ' PRIMARY KEY' if $column->is_auto_increment;
61     $column_def .= ' DEFAULT ' . $default_value if $column->default_value && !$column->is_auto_increment;
62     $column_def;
63 }
64
65 sub _create_index {
66     my $self = shift;
67     my $index = shift;
68     my $table = shift;
69
70     my $index_def;
71     if ($index->type eq 'PRIMARY_KEY') {
72         $index_def = 'CONSTRAINT ' . $index->name .  ' PRIMARY KEY ' .  '(' . (join ', ', map { $_->name } values %{$index->columns}) . ')';
73     }
74     elsif ($index->type eq 'UNIQUE') {
75         $index_def = 'CONSTRAINT ' . $index->name .  ' UNIQUE ' .  '(' . (join ', ', map { $_->name } values %{$index->columns}) . ')';
76     }
77     elsif ($index->type eq 'NORMAL') {
78         $index_def = 'CREATE INDEX ' . $index->name . ' ON ' . $table->name . '('.  (join ', ', map { $_->name } values %{$index->columns}) . ')';
79     }
80
81     $index_def;
82 }
83
84 1;