Added database version field to config db table. Added db
[emufront] / src / db / dbcreator.cpp
1 // EmuFront
2 // Copyright 2010 Mikko Keinänen
3 //
4 // This file is part of EmuFront.
5 //
6 //
7 // EmuFront is free software: you can redistribute it and/or modify
8 // it under the terms of the GNU General Public License version 2 as published by
9 // the Free Software Foundation and appearing in the file gpl.txt included in the
10 // packaging of this file.
11 //
12 // EmuFront is distributed in the hope that it will be useful,
13 // but WITHOUT ANY WARRANTY; without even the implied warranty of
14 // MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
15 // GNU General Public License for more details.
16 //
17 // You should have received a copy of the GNU General Public License
18 // along with EmuFront.  If not, see <http://www.gnu.org/licenses/>.
19
20 #include <QObject>
21 #include <QDir>
22 #include <QSqlDatabase>
23 #include <QSqlQuery>
24 #include <QSqlRecord>
25 #include <QSqlTableModel>
26 #include <QSqlError>
27 #include <QDebug>
28 #include <exception>
29 #include "dbcreator.h"
30
31
32 using namespace std;
33
34 const int DbCreator::DB_VERSION = 1;
35 //const int DbCreator::TABLES_COUNT = 3;
36 //const QString DbCreator::TABLES[] = {"platform", "mediatype", "filepath", "mediaimagecontainer_filepath", "mediaimage", "mediaimagecontainer_mediaimage"};
37
38 DbCreator::DbCreator(QObject *parent) : QObject(parent)
39 {
40 }
41
42
43 bool DbCreator::createDB()
44 {
45     bool ret = false;
46     QSqlQuery query;
47
48     try
49     {
50         query.exec("DROP TABLE IF EXISTS mediaimagecontainer_mediaimage");
51         query.exec("DROP TABLE IF EXISTS mediaimagecontainer_filepath");
52         query.exec("DROP TABLE IF EXISTS filepath");
53         query.exec("DROP TABLE IF EXISTS setup");
54         query.exec("DROP TABLE IF EXISTS mediatype");
55         query.exec("DROP TABLE IF EXISTS platform");
56         query.exec("DROP TABLE IF EXISTS file") ;
57         query.exec("DROP TABLE IF EXISTS executable");
58         query.exec("DROP TABLE IF EXISTS config");
59
60         qDebug() << "Creating TABLE file";
61
62         ret = query.exec("CREATE TABLE IF NOT EXISTS config"
63                 "(tmpdirpath TEXT, "
64                 "dbversion INTEGER)"
65             );
66
67         if (ret) {
68             query.prepare("INSERT INTO config "
69                 "(tmpdirpath, dbversion) "
70                 "VALUES (:tmpdir, :dbversion)");
71             query.bindValue(":tmpdir", QDir::homePath());
72             query.bindValue(":dbversion", DbCreator::DB_VERSION);
73             ret = query.exec();
74         }
75
76         if (!ret) throw QString("tbl config");
77
78         ret = query.exec("CREATE TABLE IF NOT EXISTS file"
79                         "(id INTEGER PRIMARY KEY, "
80                         "name TEXT, "
81                         "type INTEGER, "
82                         "checksum TEXT, "
83                         "size INTEGER, "
84                         "updatetime NUMERIC, "
85                         "extname TEXT)");
86
87         if (!ret) throw QString("tbl file");
88
89         qDebug() << "Creating TABLE platform";
90
91         ret = query.exec("CREATE TABLE IF NOT EXISTS platform "
92                          "(id INTEGER PRIMARY KEY, "
93                          "name TEXT, "
94                          "fileid INTEGER REFERENCES file(id))");
95
96         if (!ret) throw QString("tbl platform");
97
98         qDebug() << "Creating TABLE mediatype ";
99
100         ret = query.exec("CREATE TABLE IF NOT EXISTS mediatype "
101                          "(id INTEGER PRIMARY KEY, "
102                          "name TEXT, "
103                          "fileid INTEGER REFERENCES file(id))");
104
105         if (!ret) throw QString("tbl mediatype");
106
107         qDebug() << "Creating TABLE setup";
108
109         ret = query.exec("CREATE TABLE IF NOT EXISTS setup "
110                         "(id INTEGER PRIMARY KEY, "
111                         "platformid INTEGER REFERENCES platform(id) ON DELETE CASCADE, "
112                         "mediatypeid INTEGER REFERENCES mediatype(id) ON DELETE CASCADE, "
113                         "filetypeextensions TEXT)");
114
115         if (!ret) throw QString("tbl setup");
116
117         qDebug() << "Creating table executable";
118
119         ret = query.exec("CREATE TABLE IF NOT EXISTS executable "
120                         "(id INTEGER PRIMARY KEY, "
121                         "name TEXT, "
122                         "executable TEXT, "
123                         "options TEXT, "
124                         "type INTEGER, "
125                         "setupid INTEGER REFERENCES setup(id))");
126
127         if (!ret) throw QString("tbl executable");
128
129         qDebug() << "Creating TABLE filepath";
130
131         ret = query.exec("CREATE TABLE IF NOT EXISTS filepath "
132                          "(id INTEGER PRIMARY KEY, "
133                          "name TEXT, "
134                          "filetypeid INTEGER, "
135                          "setupid INTEGER, "
136                          "lastscanned NUMERIC, "
137                          "FOREIGN KEY (setupid) REFERENCES setup(id))");
138
139         if (!ret) throw QString("tbl filepath");
140
141         qDebug() << "Creating TABLE mediaimagecontainer_filepath";
142
143         ret = query.exec("CREATE TABLE IF NOT EXISTS mediaimagecontainer_filepath "
144                         "(fileid INTEGER REFERENCES file(id), "
145                         "filepathid INTEGER REFERENCES filepath(id), "
146                         "updatetime NUMERIC)");
147
148         if (!ret) throw QString("tbl mediaimagecontainer_filepath");
149
150
151         qDebug() << "Creating TABLE mediaimagecontainer_mediaimage";
152
153         ret = query.exec("CREATE TABLE IF NOT EXISTS mediaimagecontainer_mediaimage "
154                         "(mediaimagecontainerid INTEGER REFERENCES file(id), "
155                         "mediaimageid INTEGER REFERENCES file(id))");
156
157         if (!ret) throw QString("tbl mediaimagecontainer_mediaimage");
158
159         query.exec(
160             "CREATE TRIGGER IF NOT EXISTS trg_onplatformdelete "
161             "AFTER DELETE ON platform "
162             "BEGIN "
163             "   DELETE FROM setup WHERE setup.platformid = old.id;"
164             "END;"
165             );
166
167         if (!ret) throw QString("trg_onplatformdelete");
168
169         query.exec(
170             "CREATE TRIGGER IF NOT EXISTS trg_onmediatypedelete "
171             "AFTER DELETE ON mediatype "
172             "BEGIN "
173             "   DELETE FROM setup WHERE setup.mediatypeid = old.id;"
174             "END;"
175             );
176
177         if (!ret) throw QString("trg_onmediatypedelete");
178
179         query.exec(
180             "CREATE TRIGGER IF NOT EXISTS trg_onsetupdelete "
181             "AFTER DELETE ON setup "
182             "BEGIN "
183             "   DELETE FROM filepath WHERE filepath.setupid = old.id; "
184             "   DELETE FROM executable WHERE executable.setupid = old.id; "
185             "END;"
186             );
187
188         if (!ret) throw QString("trg_onsetupdelete");
189
190         query.exec(
191             "CREATE TRIGGER IF NOT EXISTS trg_onfilepathdelete "
192             "AFTER DELETE ON filepath "
193             "BEGIN "
194             "   DELETE FROM mediaimagecontainer_filepath WHERE mediaimagecontainer_filepath.filepathid=old.id; "
195             "END;"
196         );
197
198         if (!ret) throw QString("trg_onfilepathdelete");
199
200         query.exec(
201             "CREATE TRIGGER IF NOT EXISTS trg_onmediaimagecontainerdelete "
202             "AFTER DELETE ON mediaimagecontainer_filepath "
203             "BEGIN "
204             "   DELETE FROM mediaimagecontainer_mediaimage WHERE mediaimagecontainer_mediaimage.mediaimagecontainerid=old.fileid;"
205             "END;"
206         );
207
208         if (!ret) throw QString("trg_onmediaimagecontainerdelete");
209
210         query.exec(
211             "CREATE TRIGGER IF NOT EXISTS trg_onmediaimagecontainer_mediaimagedelete "
212             "AFTER DELETE ON mediaimagecontainer_mediaimage "
213             "BEGIN "
214             "    DELETE FROM file WHERE file.id=old.mediaimageid; "
215             "    DELETE FROM file WHERE file.id=old.mediaimagecontainerid; "
216             "END;"
217         );
218         if (!ret) throw QString("trg_onmediaimagecontainer_mediaimagedelete");
219
220     }
221     catch (QString tbl)
222     {
223         QString err = query.lastError().text();
224         throw QString("Couldn't CREATE '%1'!").arg(tbl).append(err);
225     }
226     return ret;
227 }
228
229 /**
230  * Check if database already exists.
231  *
232  * Returns  0 if database doesn't exist
233  *          or database version number 1 if database exists
234  *
235 */
236 int DbCreator::dbExists()
237 {
238     int ret = 0;
239     QString sql("SELECT dbversion FROM config");
240     QSqlQuery q;
241     q.exec(sql);
242     if (q.next()) {
243         ret = q.value(0).toInt();
244         qDebug() << "Database version is " << ret
245             << " the application requires " << DB_VERSION;
246     }
247     return ret;
248     /*for (int i = 0; i < TABLES_COUNT; ++i)
249     {
250         if (!tableExists(TABLES[i]))
251         {
252             qDebug() << "Table " << TABLES[i] << " missing.";
253             return false;
254         }
255        qDebug() << "Table " << TABLES[i] << " exists.";
256     }
257     return true;*/
258 }
259
260 bool DbCreator::tableExists(QString TABLE)
261 {
262     QSqlQuery query;
263     query.exec(QString("SELECT name FROM sqlite_master WHERE name='%1'").arg(TABLE));
264     return query.next();
265 }
266
267 bool DbCreator::deleteDB()
268 {
269     // return QFile::remove(getDbPath());
270     return false;
271 }