2013-03-08 44 views
10

Tôi đang sử dụng Ruby với SQLite3 và nỗ lực sử dụng khóa ngoại của tôi trong Sqlite3 rất tiếc là không thành công. Theo sqlite3 --version, phiên bản 3.7.13 được cài đặt. Theo như tôi biết, Sqlite3 hỗ trợ các khóa ngoại từ phiên bản 3.6.x.SQLite3 "quên" để sử dụng khóa ngoài

Tôi biết rằng khóa ngoài bị tắt theo mặc định và phải được kích hoạt với PRAGMA foreign_keys = ON;. Trong Ruby db-tạo-kịch bản của tôi, tôi đang làm một cái gì đó như thế này:

sql = <<-SQL 
    PRAGMA foreign_keys = ON; 
    CREATE TABLE apps (
    id .... 
); 
    CREATE TABLE requests (
    ... 
    app_id INTEGER NOT NULL, 
    FOREIGN KEY(app_id) REFERENCES apps(id), 
); 
    ... 
SQL 
db.execute_batch(sql) 

Thật không may, tôi hạnh phúc có thể chèn hàng vào requests với biết app-id, nó hoạt động, nhưng tất nhiên nó không nên.

Thú vị: sử dụng vỏ sqlite3 trực tiếp, tôi có thể quan sát các hành vi sau đây:

$ sqlite3 database.db 
sqlite> PRAGMA foreign_keys = ON; 
sqlite> PRAGMA foreign_keys; 
1 // as expected 
sqlite> .quit 
$ sqlite3 database.db 
sqlite> PRAGMA foreign_keys; 
0 // off ?! 

Nếu không bỏ vỏ sqlite3, phím nước ngoài đang làm việc sau khi kích hoạt chúng (và không bỏ vỏ) và Tôi không được phép để chèn các hàng có app_ids không xác định.

+2

tôi Tôi nghĩ rằng tôi có thể trả lời câu hỏi của riêng tôi (trong một bình luận thay vì câu trả lời do đại diện thấp): Tài liệu nói: Các ràng buộc khóa ngoài bị tắt theo mặc định (cho tương thích ngược), vì vậy phải được kích hoạt ** cho mỗi cơ sở dữ liệu kết nối riêng **. Gây phiền nhiễu, nhưng cuối cùng nó đã hoạt động. – cara

+0

Câu hỏi liên quan: nếu dữ liệu vi phạm ràng buộc khoá ngoại được thêm vào và sau đó cờ cờ nước ngoài được đặt thành bật: điều đó có gây ra lỗi không? – gvrocha

Trả lời

19

Tôi nghĩ rằng tôi có thể trả lời câu hỏi của riêng mình: Tài liệu cho biết: Ràng buộc khóa ngoài bị tắt theo mặc định (cho tương thích ngược), vì vậy phải được bật cho mỗi kết nối cơ sở dữ liệu riêng biệt. Gây phiền nhiễu, nhưng cuối cùng nó đã hoạt động.

9

Đặt điều này ở đầu tệp thực thi các lệnh SQL và nó sẽ cho phép các khóa ngoại trong thời gian chạy.

db = SQLite3::Database.new("database.db") 
db.execute("PRAGMA foreign_keys = ON") 
2

Một cách vĩnh viễn bật foreign_keys theo mặc định là để bơm dòng sau vào ~/.sqliterc:

PRAGMA foreign_keys = ON; 

Xin lưu ý rằng nó sẽ ảnh hưởng đến tất cả các cơ sở dữ liệu của bạn ...

Các vấn đề liên quan