Mercurial > pub > Impl
comparison Lib/IMPL/SQL/Schema/Table.pm @ 167:1f7a6d762394
SQL schema in progress
| author | sourcer |
|---|---|
| date | Thu, 12 May 2011 08:57:19 +0400 |
| parents | 76515373dac0 |
| children | 6148f89bb7bf |
comparison
equal
deleted
inserted
replaced
| 166:4267a2ac3d46 | 167:1f7a6d762394 |
|---|---|
| 1 use strict; | 1 use strict; |
| 2 package IMPL::SQL::Schema::Table; | 2 package IMPL::SQL::Schema::Table; |
| 3 | 3 |
| 4 use IMPL::lang; | 4 use IMPL::lang qw(:declare :constants is); |
| 5 | 5 |
| 6 use parent qw( | 6 use parent qw( |
| 7 IMPL::Object | 7 IMPL::Object |
| 8 IMPL::Object::Disposable | 8 IMPL::Object::Disposable |
| 9 ); | 9 ); |
| 10 | 10 |
| 11 use IMPL::SQL::Schema::Column(); | 11 require IMPL::SQL::Schema::Column; |
| 12 use IMPL::SQL::Schema::Constraint(); | 12 require IMPL::SQL::Schema::Constraint; |
| 13 use IMPL::SQL::Schema::Constraint::PrimaryKey(); | 13 require IMPL::SQL::Schema::Constraint::PrimaryKey; |
| 14 use IMPL::SQL::Schema::Constraint::ForeignKey(); | 14 require IMPL::SQL::Schema::Constraint::ForeignKey; |
| 15 | 15 |
| 16 use IMPL::Class::Property; | |
| 17 use IMPL::Class::Property::Direct; | 16 use IMPL::Class::Property::Direct; |
| 18 | 17 |
| 19 BEGIN { | 18 BEGIN { |
| 20 public _direct property name => prop_get; | 19 public _direct property name => PROP_GET; |
| 21 public _direct property schema => prop_get; | 20 public _direct property schema => PROP_GET; |
| 22 public _direct property columns => prop_get; | 21 public _direct property columns => PROP_GET; |
| 23 public _direct property constraints => prop_get; | 22 public _direct property constraints => PROP_GET; |
| 24 public _direct property columnsByName => prop_none; | 23 public _direct property columnsByName => 0; |
| 25 public _direct property primaryKey => prop_get; | 24 public _direct property primaryKey => PROP_GET; |
| 26 public _direct property tag => prop_all; | 25 public _direct property tag => PROP_ALL; |
| 27 } | 26 } |
| 28 | 27 |
| 29 sub CTOR { | 28 sub CTOR { |
| 30 my ($this,%args) = @_; | 29 my ($this,%args) = @_; |
| 31 | 30 |
| 99 } else { | 98 } else { |
| 100 die new IMPL::InvalidOperationException("The column not found",$NameOrColumn->name); | 99 die new IMPL::InvalidOperationException("The column not found",$NameOrColumn->name); |
| 101 } | 100 } |
| 102 } | 101 } |
| 103 | 102 |
| 104 sub Column { | 103 sub GetColumn { |
| 105 my ($this,$name) = @_; | 104 my ($this,$name) = @_; |
| 106 | 105 |
| 107 return $this->{$columnsByName}->{$name}; | 106 return $this->{$columnsByName}->{$name}; |
| 108 } | 107 } |
| 109 | 108 |
| 110 sub ColumnAt { | 109 sub GetColumnAt { |
| 111 my ($this,$index) = @_; | 110 my ($this,$index) = @_; |
| 112 | 111 |
| 113 die new IMPL::InvalidArgumentException("The index is out of range") | 112 die new IMPL::InvalidArgumentException("The index is out of range") |
| 114 if $index < 0 || $index >= ($this->{$columns} ? scalar(@{$this->{$columns}}) : 0); | 113 if $index < 0 || $index >= ($this->{$columns} ? scalar(@{$this->{$columns}}) : 0); |
| 115 | 114 |
| 165 my ($this,$name) = @_; | 164 my ($this,$name) = @_; |
| 166 | 165 |
| 167 return $this->{$constraints}{$name}; | 166 return $this->{$constraints}{$name}; |
| 168 } | 167 } |
| 169 | 168 |
| 169 sub GetConstraints { | |
| 170 my ($this) = @_; | |
| 171 | |
| 172 return wantarray ? values %{$this->{$constraints}} : [values %{$this->{$constraints}}]; | |
| 173 } | |
| 174 | |
| 170 sub GetColumnConstraints { | 175 sub GetColumnConstraints { |
| 171 my ($this,@Columns) = @_; | 176 my ($this,@Columns) = @_; |
| 172 | 177 |
| 173 my @cn = map { UNIVERSAL::isa($_ ,'IMPL::SQL::Schema::Column') ? $_ ->name : $_ } @Columns; | 178 my @cn = map { UNIVERSAL::isa($_ ,'IMPL::SQL::Schema::Column') ? $_ ->name : $_ } @Columns; |
| 174 exists $this->{$columnsByName}->{$_} or die new IMPL::InvalidOperationException('The specified column isn\'t found',$_) foreach @cn; | 179 exists $this->{$columnsByName}->{$_} or die new IMPL::InvalidOperationException('The specified column isn\'t found',$_) foreach @cn; |
| 184 | 189 |
| 185 sub LinkTo { | 190 sub LinkTo { |
| 186 my ($this,$table,@ColumnList) = @_; | 191 my ($this,$table,@ColumnList) = @_; |
| 187 $table->primaryKey or die new IMPL::InvalidOperationException('The referenced table must have a primary key'); | 192 $table->primaryKey or die new IMPL::InvalidOperationException('The referenced table must have a primary key'); |
| 188 my $constraintName = $this->{$name}.'_'.$table->name.'_FK_'.join('_',map {ref $_ ? $_->name : $_} @ColumnList); | 193 my $constraintName = $this->{$name}.'_'.$table->name.'_FK_'.join('_',map {ref $_ ? $_->name : $_} @ColumnList); |
| 189 $this->AddConstraint(new IMPL::SQL::Schema::Constraint::ForeignKey(name => $constraintName, table => $this, columns => \@ColumnList, referencedTable => $table, referencedColumns => $table->primaryKey->columns)); | 194 $this->AddConstraint(new IMPL::SQL::Schema::Constraint::ForeignKey(name => $constraintName, table => $this, columns => \@ColumnList, referencedTable => $table, referencedColumns => scalar $table->primaryKey->columns)); |
| 190 } | 195 } |
| 191 | 196 |
| 192 sub Dispose { | 197 sub Dispose { |
| 193 my ($this) = @_; | 198 my ($this) = @_; |
| 194 | 199 |
| 196 | 201 |
| 197 undef %{$this}; | 202 undef %{$this}; |
| 198 $this->SUPER::Dispose(); | 203 $this->SUPER::Dispose(); |
| 199 } | 204 } |
| 200 | 205 |
| 206 sub SameValue { | |
| 207 my ($this,$other) = @_; | |
| 208 | |
| 209 return 0 unless is $other, typeof $this; | |
| 210 | |
| 211 return 0 unless $this->name eq $other->name; | |
| 212 return 0 unless $this->ColumnsCount eq $other->ColumnsCount; | |
| 213 | |
| 214 for (my $i = 0; $i < $this->ColumsCount; $i ++) { | |
| 215 return 0 unless $this->($i)->SameValue($other->GetColumnAt($i)); | |
| 216 } | |
| 217 | |
| 218 my %thisConstraints = map { $_->name, $_ } $this->GetConstraints(); | |
| 219 my %otherConstraints = map { $_->name, $_ } $other->GetConstraints(); | |
| 220 | |
| 221 foreach my $name ( keys %thisConstraints ) { | |
| 222 return 0 unless $otherConstraints{$name}; | |
| 223 return 0 unless $thisConstraints{$name}->SameValue(delete $otherConstraints{$name}); | |
| 224 } | |
| 225 | |
| 226 return 0 if %otherConstraints; | |
| 227 | |
| 228 return 1; | |
| 229 } | |
| 230 | |
| 201 1; | 231 1; |
| 202 | 232 |
| 203 | 233 |
