Skip Menu |

This queue is for tickets about the SQL-Statement CPAN distribution.

Report information
The Basics
Id: 42855
Status: resolved
Priority: 0/
Queue: SQL-Statement

People
Owner: Nobody in particular
Requestors: DDICK [...] cpan.org
Cc:
AdminCc:

Bug Information
Severity: Wishlist
Broken in: 1.17
Fixed in: 1.19



Subject: support for table level constraints in CREATE TABLE. patch included.
The patch includes test suite additions to cover the new cases it includes, basically the the PRIMARY KEY ("id") and FOREIGN KEY ("fkey") REFERENCES "ref_table" ("ref_key"). Hope this is useful.
On Wed Jan 28 06:27:37 2009, DDICK wrote: Show quoted text
> The patch includes test suite additions to cover the new cases it > includes, basically the the PRIMARY KEY ("id") and FOREIGN KEY ("fkey") > REFERENCES "ref_table" ("ref_key"). Hope this is useful.
Hi David, at first - the patch is missing. Further I can tell you, that there is no support to prove the referential integrity of a database scheme. Does your patch includes this, too? If so - we should talk in private mail, because I plan larger changes and maybe you could help to integrate this feature directly into the new implementation. Jens
On Fri Jan 30 08:57:48 2009, REHSACK wrote: Show quoted text
> at first - the patch is missing.
whoops, attached now. Show quoted text
> Further I can tell you, that there is no support to prove the > referential integrity of a database scheme. Does your patch includes > this, too? If so - we should talk in private mail, because I plan larger > changes and maybe you could help to integrate this feature directly into > the new implementation.
no it doesn't. sorry.
diff -Naur old/lib/SQL/Parser.pm new/lib/SQL/Parser.pm --- old/lib/SQL/Parser.pm 2009-01-18 04:38:15.000000000 +1100 +++ new/lib/SQL/Parser.pm 2009-01-28 22:04:25.000000000 +1100 @@ -181,6 +181,14 @@ } } +sub replace_quoted_commas +{ + my $self = shift; + my $id = shift; + $id =~ s/\?COMMA\?/,/gs; + return $id; +} + sub replace_quoted_ids { my $self = shift; @@ -1007,8 +1015,74 @@ return undef unless $self->TABLE_NAME($table_name); $table_element_def =~ s/\s+\(/(/g; my $primary_defined; + $table_element_def =~ s/( # start of grouping 1 + \( # match a bracket; vi compatible bracket -> \)( + [^)]+ # everything up to but not including the comma, no nesting of brackets is required + ) # end of grouping 1 + , # the comma to be removed to allow splitting on commas + ( # start of grouping 2; vi compatible bracket -> \( + .*?\) # everything up to and including the end bracket + )/$1?COMMA?$2/sgx; for my $col ( split ',', $table_element_def ) { + if ($col =~ /^\s*(?:CONSTRAINT\s+(\S+)\s*)? # optional name of foreign key + FOREIGN\s+KEY\s*\(\s* # start of list of; vi compatibile bracket -> ( + (\s*[^)]+\s*) # field names in this table + \s*\)\s* # end of field names in this table + REFERENCES # key word + \s*(\S+)\s* # table name being referenced in foreign key + \(\s* # start of list of; vi compatible bracket -> ( + (\s*[^)]+\s*) # field names in foreign table + \s*\)\s* # end of field names in foreign table + $/x) + { + my ($name, $local_cols, $referenced_table, $referenced_cols) = ($1, $2, $3, $4); + my @local_cols = map { $self->replace_quoted_ids($_) } split(',', $self->replace_quoted_commas($local_cols)); + $referenced_table = $self->replace_quoted_ids($referenced_table); + my @referenced_cols = map { $self->replace_quoted_ids($_) } split(',', $self->replace_quoted_commas($referenced_cols)); + if (defined $name) { + $name = $self->replace_quoted_ids($name); + } else { + $name = $self->replace_quoted_ids($table_name); + my ($quote_char) = ''; + if ($name =~ s/(\W)$//) { + $quote_char = ($1); + } + foreach my $local_col (@local_cols) { + my $col_name = $local_col; + $col_name =~ s/^\W//; + $col_name =~ s/\W$//; + $name .= "_" . $col_name; + } + $name .= "_fkey" . $quote_char; + } + $self->{"struct"}->{"table_defs"}->{"$name"}->{"type"} = "FOREIGN"; + $self->{"struct"}->{"table_defs"}->{"$name"}->{"local_cols"} = \@local_cols; + $self->{"struct"}->{"table_defs"}->{"$name"}->{"referenced_table"} = $referenced_table; + $self->{"struct"}->{"table_defs"}->{"$name"}->{"referenced_cols"} = \@referenced_cols; + next; + } elsif ($col =~ /^\s*(?:CONSTRAINT\s+(\S+)\s*)? # optional name of foreign key + PRIMARY\s+KEY\s*\(\s* # start of list of; vi compatibile bracket -> ( + (\s*[^)]+\s*) # field names in this table + \s*\)\s* # end of field names in this table + $/x) + { + my ($name, $local_cols) = ($1, $2); + my @local_cols = map { $self->replace_quoted_ids($_) } split(',', $self->replace_quoted_commas($local_cols)); + if (defined $name) { + $name = $self->replace_quoted_ids($name); + } else { + $name = $table_name; + if ($name =~ s/(\W)$//) { + $name .= "_pkey" . $1; + } else { + $name .= "_pkey"; + } + } + $self->{"struct"}->{"table_defs"}->{"$name"}->{"type"} = "PRIMARY"; + $self->{"struct"}->{"table_defs"}->{"$name"}->{"local_cols"} = \@local_cols; + next; + } my ( $name, $type, $constraints ) = ( $col =~ /\s*(\S+)\s+(\S+)\s*(.*)/ ); if ( !$type ) diff -Naur old/t/01prepare.t new/t/01prepare.t --- old/t/01prepare.t 2009-01-12 19:40:43.000000000 +1100 +++ new/t/01prepare.t 2009-01-28 22:21:46.000000000 +1100 @@ -3,7 +3,7 @@ $|=1; use lib qw' ./ ./t '; use SQLtest; -use Test::More tests => 100; +use Test::More tests => 102; $parser = new_parser(); $parser->{PrintError}=0; @@ -48,6 +48,8 @@ CREATE TABLE foo ( id INTEGER PRIMARY KEY, phrase VARCHAR(40) NOT NULL ) CREATE TABLE foo ( id INTEGER NOT NULL, phrase VARCHAR(40) NOT NULL ) CREATE TABLE foo ( id INTEGER UNIQUE NOT NULL, phrase VARCHAR(40) ) +CREATE TABLE foo ( id INTEGER, phrase VARCHAR(40), CONSTRAINT "foo_pkey" PRIMARY KEY ( "id", "phrase" ), CONSTRAINT "foo_fkey" FOREIGN KEY ( "id" ) REFERENCES "bar" ( "bar_id" )) +CREATE TABLE foo ( id INTEGER, phrase VARCHAR(40), PRIMARY KEY ( "id" ), FOREIGN KEY ("id", "phrase") REFERENCES "bar" ("id2", "phrase2")) /* JOINS */ SELECT Lnum,Llet,Ulet FROM zLower NATURAL INNER JOIN zUpper SELECT Lnum,Llet,Ulet FROM zLower NATURAL LEFT JOIN zUpper
Patch applied in 1.19 - seems to have no impact. Closing here. Thanks for patch submission.