2011-07-15 4 views
1

私は、実稼働環境を模倣するテスト環境としてsqlite3データベースを作成しようとしています。プロダクションが設定されているため、テーブルは複数のスキーマにあります。添付されたsqliteデータベースで外部キーをどのように作成しますか?

$schema->storage->dbh_doを使用してデータベースをスキーマにアタッチし、$schema-deploy()を使用してデータベースを作成して、DBIx :: Classでクラスをセットアップしました。それは第二のテーブルに外部キーを作成することになると

は、しかし、私は次のエラーを取得する:

DBIx::Class::Schema::deploy(): DBIx::Class::Schema::deploy(): DBI Exception: DBD::SQLite::db do failed: near ".": syntax error 

は、次のように再現するための最も簡単なテストがあるDBIx::Classを奪います。

sqlite3 initial.db 
SQLite version 3.6.23 
Enter ".help" for instructions 
Enter SQL statements terminated with a ";" 
sqlite> attach database 'other.db' as 'other'; 
sqlite> create table other.a(col1_a, col2_a); 
sqlite> create table other.b(col1_b, col2_b, foreign key(col1_b) references other.a(col1_a)); 
Error: near ".": syntax error 
sqlite> create table other.b(col1_b, col2_b, foreign key(col1_b) references a(col1_a)); 
sqlite> 

スキーマを外部キー句から削除すると、テーブルが正常に作成されます。

DBIx :: Classを使用して外部スキーマでテーブルを作成するにはどうすればよいですか?

編集:コードの完全なサンプル。

package MyApp::Schema; 
use base qw/DBIx::Class::Schema/; 
__PACKAGE__->load_namespaces(); 
1; 


package MyApp::Schema::Result::A; 
use base qw/DBIx::Class::Core/; 
__PACKAGE__->table('other_db.A'); 
__PACKAGE__->add_columns(qw/ a1 a2 /); 
__PACKAGE__->set_primary_key('a1'); 
__PACKAGE__->has_many(bs => 'MyApp::Schema::Result::B', 'b1'); 
1; 

package MyApp::Schema::Result::B; 
use base qw/DBIx::Class::Core/; 
__PACKAGE__->table('other_db.B'); 
__PACKAGE__->add_columns(qw/ b1 b2 /); 
__PACKAGE__->set_primary_key('b1'); 
__PACKAGE__->belongs_to(a => 'MyApp::Schema::Result::A', 'b1'); 
1; 

メインスクリプト:

use MyApp::Schema; 

my $schema = MyApp::Schema->connect('dbi:SQLite:dbname=test.db','','',{}); 

my $res = $schema->storage->dbh_do(
    sub { 
     my ($storage, $dbh) = @_; 
     $dbh->do("attach database 'other.db' as other_db"); 
    } 
); 

$schema->deploy(); 

指定されたエラーは次のとおりです。

DBIx::Class::Schema::deploy(): DBIx::Class::Schema::deploy(): DBI Exception: DBD::SQLite::db do failed: near ".": syntax error [for Statement "CREATE TABLE other_db.B (
    b1 NOT NULL, 
    b2 NOT NULL, 
    PRIMARY KEY (b1), 
    FOREIGN KEY(b1) REFERENCES other_db.A(a1) 
)"] at dbi.pl line 17 
(running "CREATE TABLE other_db.B (
    b1 NOT NULL, 
    b2 NOT NULL, 
    PRIMARY KEY (b1), 
    FOREIGN KEY(b1) REFERENCES other_db.A(a1) 
)") at dbi.pl line 17 
+0

だからあなたが使用することを好むだろう「他を。」あなたのコードをより洗練された/よりシンプルに保つために? –

+0

私は本当に好みがありません。私の好みは、DBIx :: Class :: Schema :: deploy()がSQLite上で動作するcreate table文を生成することです。 –

+0

あなたの問題は、sqliteの構文ではなく、perlであると思われるので、あなたはperlコードを投稿できますか? –

答えて

2

単純な答えではデータベース名を指定(してする必要はありません)することができないということですいつ外来キーの定義でテーブル名と。 sqliteドキュメントはそのように示しています。

このリンクは、あなたが「テーブルdb.tableを作成する」の部分で新しいテーブル名とデータベース名を使用する方法を示しています。このリンクは、あなたが使用することはできません方法を示しに対し

http://www.sqlite.org/lang_createtable.html

外部キー定義でデータベース名:

http://www.sqlite.org/syntaxdiagrams.html#foreign-key-clause

+1

しかし、添付されたデータベースがメインデータベースと同じテーブル名を持つ場合はどうなりますか?そのあいまいさを解決する外部キーの関係をどのように指定しますか? – vargonian