mirror of
https://github.com/hkalexling/Mango.git
synced 2025-08-02 19:05:32 -04:00
Set up foreign keys
This commit is contained in:
parent
959560c7a7
commit
7a09c9006a
85
migration/foreign_keys.6.cr
Normal file
85
migration/foreign_keys.6.cr
Normal file
@ -0,0 +1,85 @@
|
|||||||
|
class ForeignKeys < MG::Base
|
||||||
|
def up : String
|
||||||
|
<<-SQL
|
||||||
|
-- add foreign key to tags
|
||||||
|
ALTER TABLE tags RENAME TO tmp;
|
||||||
|
|
||||||
|
CREATE TABLE tags (
|
||||||
|
id TEXT NOT NULL,
|
||||||
|
tag TEXT NOT NULL,
|
||||||
|
UNIQUE (id, tag),
|
||||||
|
FOREIGN KEY (id) REFERENCES titles (id)
|
||||||
|
ON UPDATE CASCADE
|
||||||
|
ON DELETE CASCADE
|
||||||
|
);
|
||||||
|
|
||||||
|
INSERT INTO tags
|
||||||
|
SELECT * FROM tmp;
|
||||||
|
|
||||||
|
DROP TABLE tmp;
|
||||||
|
|
||||||
|
CREATE INDEX tags_id_idx ON tags (id);
|
||||||
|
CREATE INDEX tags_tag_idx ON tags (tag);
|
||||||
|
|
||||||
|
-- add foreign key to thumbnails
|
||||||
|
ALTER TABLE thumbnails RENAME TO tmp;
|
||||||
|
|
||||||
|
CREATE TABLE thumbnails (
|
||||||
|
id TEXT NOT NULL,
|
||||||
|
data BLOB NOT NULL,
|
||||||
|
filename TEXT NOT NULL,
|
||||||
|
mime TEXT NOT NULL,
|
||||||
|
size INTEGER NOT NULL,
|
||||||
|
FOREIGN KEY (id) REFERENCES ids (id)
|
||||||
|
ON UPDATE CASCADE
|
||||||
|
ON DELETE CASCADE
|
||||||
|
);
|
||||||
|
|
||||||
|
INSERT INTO thumbnails
|
||||||
|
SELECT * FROM tmp;
|
||||||
|
|
||||||
|
DROP TABLE tmp;
|
||||||
|
|
||||||
|
CREATE UNIQUE INDEX tn_index ON thumbnails (id);
|
||||||
|
SQL
|
||||||
|
end
|
||||||
|
|
||||||
|
def down : String
|
||||||
|
<<-SQL
|
||||||
|
-- remove foreign key from thumbnails
|
||||||
|
ALTER TABLE thumbnails RENAME TO tmp;
|
||||||
|
|
||||||
|
CREATE TABLE thumbnails (
|
||||||
|
id TEXT NOT NULL,
|
||||||
|
data BLOB NOT NULL,
|
||||||
|
filename TEXT NOT NULL,
|
||||||
|
mime TEXT NOT NULL,
|
||||||
|
size INTEGER NOT NULL
|
||||||
|
);
|
||||||
|
|
||||||
|
INSERT INTO thumbnails
|
||||||
|
SELECT * FROM tmp;
|
||||||
|
|
||||||
|
DROP TABLE tmp;
|
||||||
|
|
||||||
|
CREATE UNIQUE INDEX tn_index ON thumbnails (id);
|
||||||
|
|
||||||
|
-- remove foreign key from tags
|
||||||
|
ALTER TABLE tags RENAME TO tmp;
|
||||||
|
|
||||||
|
CREATE TABLE tags (
|
||||||
|
id TEXT NOT NULL,
|
||||||
|
tag TEXT NOT NULL,
|
||||||
|
UNIQUE (id, tag)
|
||||||
|
);
|
||||||
|
|
||||||
|
INSERT INTO tags
|
||||||
|
SELECT * FROM tmp;
|
||||||
|
|
||||||
|
DROP TABLE tmp;
|
||||||
|
|
||||||
|
CREATE INDEX tags_id_idx ON tags (id);
|
||||||
|
CREATE INDEX tags_tag_idx ON tags (tag);
|
||||||
|
SQL
|
||||||
|
end
|
||||||
|
end
|
@ -78,9 +78,11 @@ class Storage
|
|||||||
private def get_db(&block : DB::Database ->)
|
private def get_db(&block : DB::Database ->)
|
||||||
if @db.nil?
|
if @db.nil?
|
||||||
DB.open "sqlite3://#{@path}" do |db|
|
DB.open "sqlite3://#{@path}" do |db|
|
||||||
|
db.exec "PRAGMA foreign_keys = 1"
|
||||||
yield db
|
yield db
|
||||||
end
|
end
|
||||||
else
|
else
|
||||||
|
@db.not_nil!.exec "PRAGMA foreign_keys = 1"
|
||||||
yield @db.not_nil!
|
yield @db.not_nil!
|
||||||
end
|
end
|
||||||
end
|
end
|
||||||
@ -361,6 +363,7 @@ class Storage
|
|||||||
MainFiber.run do
|
MainFiber.run do
|
||||||
Logger.info "Starting DB optimization"
|
Logger.info "Starting DB optimization"
|
||||||
get_db do |db|
|
get_db do |db|
|
||||||
|
# Delete dangling entry IDs
|
||||||
trash_ids = [] of String
|
trash_ids = [] of String
|
||||||
db.query "select path, id from ids" do |rs|
|
db.query "select path, id from ids" do |rs|
|
||||||
rs.each do
|
rs.each do
|
||||||
@ -369,29 +372,24 @@ class Storage
|
|||||||
end
|
end
|
||||||
end
|
end
|
||||||
|
|
||||||
# Delete dangling IDs
|
|
||||||
db.exec "delete from ids where id in " \
|
db.exec "delete from ids where id in " \
|
||||||
"(#{trash_ids.map { |i| "'#{i}'" }.join ","})"
|
"(#{trash_ids.map { |i| "'#{i}'" }.join ","})"
|
||||||
Logger.debug "#{trash_ids.size} dangling IDs deleted" \
|
Logger.debug "#{trash_ids.size} dangling entry IDs deleted" \
|
||||||
if trash_ids.size > 0
|
if trash_ids.size > 0
|
||||||
|
|
||||||
# Delete dangling thumbnails
|
# Delete dangling title IDs
|
||||||
trash_thumbnails_count = db.query_one "select count(*) from " \
|
trash_titles = [] of String
|
||||||
"thumbnails where id not in " \
|
db.query "select path, id from titles" do |rs|
|
||||||
"(select id from ids)", as: Int32
|
rs.each do
|
||||||
if trash_thumbnails_count > 0
|
path = rs.read String
|
||||||
db.exec "delete from thumbnails where id not in (select id from ids)"
|
trash_titles << rs.read String unless Dir.exists? path
|
||||||
Logger.info "#{trash_thumbnails_count} dangling thumbnails deleted"
|
end
|
||||||
end
|
end
|
||||||
|
|
||||||
# Delete dangling tags
|
db.exec "delete from titles where id in " \
|
||||||
trash_tags_count = db.query_one "select count(*) from tags " \
|
"(#{trash_titles.map { |i| "'#{i}'" }.join ","})"
|
||||||
"where id not in " \
|
Logger.debug "#{trash_titles.size} dangling title IDs deleted" \
|
||||||
"(select id from ids)", as: Int32
|
if trash_titles.size > 0
|
||||||
if trash_tags_count > 0
|
|
||||||
db.exec "delete from tags where id not in (select id from ids)"
|
|
||||||
Logger.info "#{trash_tags_count} dangling tags deleted"
|
|
||||||
end
|
|
||||||
end
|
end
|
||||||
Logger.info "DB optimization finished"
|
Logger.info "DB optimization finished"
|
||||||
end
|
end
|
||||||
|
Loading…
x
Reference in New Issue
Block a user