Внешний ключ SQLite в Kotlin
Ограничение FOREIGN KEY привязывает колонку
зависимой таблицы к первичному ключу родителя.
В SQLite проверка срабатывает только после
PRAGMA foreign_keys = ON на соединении.
Таблица складов и ячеек с явной ссылкой на родителя создаётся так:
import java.sql.DriverManager
fun main() {
DriverManager.getConnection("jdbc:sqlite:fk_bins.db")
.use { connection ->
connection.createStatement().execute(
"PRAGMA foreign_keys = ON"
)
connection.createStatement().use { statement ->
statement.execute(
"""
CREATE TABLE IF NOT EXISTS warehouses (
id INTEGER PRIMARY KEY,
code TEXT NOT NULL
)
"""
)
statement.execute(
"""
CREATE TABLE IF NOT EXISTS bins (
id INTEGER PRIMARY KEY,
warehouse_id INTEGER NOT NULL,
label TEXT NOT NULL,
FOREIGN KEY (warehouse_id)
REFERENCES warehouses (id)
)
"""
)
}
val parent = connection.prepareStatement(
"INSERT INTO warehouses (code) VALUES (?)"
)
parent.setString(1, "W1")
parent.executeUpdate()
val child = connection.prepareStatement(
"""
INSERT INTO bins (warehouse_id, label)
VALUES (?, ?)
"""
)
child.setInt(1, 1)
child.setString(2, "A-01")
println(child.executeUpdate())
}
}
Число в warehouse_id должно совпадать с
существующим id склада. Иначе вставка
завершится SQLException:
import java.sql.DriverManager
import java.sql.SQLException
fun main() {
DriverManager.getConnection("jdbc:sqlite:fk_bins.db")
.use { connection ->
connection.createStatement().execute(
"PRAGMA foreign_keys = ON"
)
connection.createStatement().use { statement ->
statement.execute(
"""
CREATE TABLE IF NOT EXISTS warehouses (
id INTEGER PRIMARY KEY,
code TEXT NOT NULL
)
"""
)
statement.execute(
"""
CREATE TABLE IF NOT EXISTS bins (
id INTEGER PRIMARY KEY,
warehouse_id INTEGER NOT NULL,
label TEXT NOT NULL,
FOREIGN KEY (warehouse_id)
REFERENCES warehouses (id)
)
"""
)
}
val bad = connection.prepareStatement(
"""
INSERT INTO bins (warehouse_id, label)
VALUES (?, ?)
"""
)
bad.setInt(1, 99)
bad.setString(2, "ghost")
try {
bad.executeUpdate()
} catch (ex: SQLException) {
println("rejected")
}
}
}
В fk_bins.db добавьте склад "W2"
и ячейку "B-02" с корректным
warehouse_id. Выведите число затронутых
строк при вставке ячейки.
Попробуйте вставить ячейку с warehouse_id
500 в try. При ошибке выведите
"bad link".
Создайте в новом файле fk_rooms.db
таблицы buildings и rooms со
ссылкой на здание. Добавьте здание и комнату с
валидным ключом.