diff --git a/QtClient/JoplinQtClient/FolderList.qml b/QtClient/JoplinQtClient/FolderList.qml index 176029012..6b88931d7 100755 --- a/QtClient/JoplinQtClient/FolderList.qml +++ b/QtClient/JoplinQtClient/FolderList.qml @@ -46,7 +46,7 @@ Item { } onCurrentItemChanged: { - currentItemId = model.idAtIndex(currentIndex); + currentItemId = model.indexToId(currentIndex); } id: listView diff --git a/QtClient/JoplinQtClient/JoplinQtClient.pro b/QtClient/JoplinQtClient/JoplinQtClient.pro index d87c365de..306f34ab8 100755 --- a/QtClient/JoplinQtClient/JoplinQtClient.pro +++ b/QtClient/JoplinQtClient/JoplinQtClient.pro @@ -18,7 +18,8 @@ SOURCES += \ settings.cpp \ uuid.cpp \ dispatcher.cpp \ - models/change.cpp + models/change.cpp \ + models/basemodel.cpp RESOURCES += qml.qrc \ database.qrc @@ -49,7 +50,9 @@ HEADERS += \ simpletypes.h \ uuid.h \ dispatcher.h \ - models/change.h + models/change.h \ + models/basemodel.h \ + enum.h DISTFILES += diff --git a/QtClient/JoplinQtClient/application.cpp b/QtClient/JoplinQtClient/application.cpp index f64033e85..c33ec464b 100755 --- a/QtClient/JoplinQtClient/application.cpp +++ b/QtClient/JoplinQtClient/application.cpp @@ -105,15 +105,15 @@ void Application::afterSessionInitialization() { } void Application::view_currentFolderChanged() { - QString folderId = selectedFolderId(); - noteCollection_ = NoteCollection(db_, folderId, "title ASC"); - noteModel_.setCollection(noteCollection_); +// QString folderId = selectedFolderId(); +// noteCollection_ = NoteCollection(db_, folderId, "title ASC"); +// noteModel_.setCollection(noteCollection_); } void Application::view_currentNoteChanged() { - QString noteId = selectedNoteId(); - Note note = noteCollection_.byId(noteId); - selectedQmlNote_.setNote(note); +// QString noteId = selectedNoteId(); +// Note note = noteCollection_.byId(noteId); +// selectedQmlNote_.setNote(note); } void Application::view_addNoteButtonClicked() { diff --git a/QtClient/JoplinQtClient/database.cpp b/QtClient/JoplinQtClient/database.cpp index 205e4940c..b6b1450c5 100755 --- a/QtClient/JoplinQtClient/database.cpp +++ b/QtClient/JoplinQtClient/database.cpp @@ -2,23 +2,6 @@ using namespace jop; -Database::Database(const QString &path) { -// version_ = -1; - -// // QFile::remove(path); - -// db_ = QSqlDatabase::addDatabase("QSQLITE"); -// db_.setDatabaseName(path); - -// if (!db_.open()) { -// qDebug() << "Error: connection with database fail"; -// } else { -// qDebug() << "Database: connection ok"; -// } - -// upgrade(); -} - Database::Database() {} void Database::initialize(const QString &path) { @@ -26,6 +9,8 @@ void Database::initialize(const QString &path) { // QFile::remove(path); + //qDebug() << Select << Text; + db_ = QSqlDatabase::addDatabase("QSQLITE"); db_.setDatabaseName(path); @@ -41,6 +26,7 @@ void Database::initialize(const QString &path) { QSqlQuery Database::query(const QString &sql) const { QSqlQuery output(db_); output.prepare(sql); + log(sql); return output; } @@ -101,6 +87,8 @@ QSqlQuery Database::buildSqlQuery(Database::QueryType type, const QString &table } } + log(sql, query); + // qDebug() <<"SQL:"< i(query.boundValues()); @@ -112,6 +100,16 @@ QSqlQuery Database::buildSqlQuery(Database::QueryType type, const QString &table return query; } +QSqlQuery Database::buildSqlQuery(Database::QueryType type, const QString &tableName, const QMap &values, const QString &whereCondition) { + QStringList fields; + VariantVector fieldValues; + for (QMap::const_iterator it = values.begin(); it != values.end(); ++it) { + fields.push_back(it.key()); + fieldValues.push_back(it.value()); + } + return buildSqlQuery(type, tableName, fields, fieldValues, whereCondition); +} + bool Database::errorCheck(const QSqlQuery& query) { if (query.lastError().isValid()) { qCritical().noquote() << "SQL query error: " << query.lastError().text().trimmed() << ". Query was: " << query.lastQuery(); @@ -125,10 +123,15 @@ bool Database::errorCheck(const QSqlQuery& query) { return true; } -//Change Database::newChange() const { -// return Change(*this); -//} +void Database::log(const QString &sql, const QSqlQuery &query) const { + qDebug() <<"SQL:"< i(query.boundValues()); + while (i.hasNext()) { + i.next(); + qDebug() << i.key() << ":" << i.value().toString(); + } +} int Database::version() const { if (version_ >= 0) return version_; diff --git a/QtClient/JoplinQtClient/database.h b/QtClient/JoplinQtClient/database.h index 8a4cde0fe..d46e8a646 100755 --- a/QtClient/JoplinQtClient/database.h +++ b/QtClient/JoplinQtClient/database.h @@ -2,6 +2,7 @@ #define DATABASE_H #include +#include "enum.h" #include "simpletypes.h" namespace jop { @@ -12,18 +13,18 @@ public: enum QueryType { Select, Insert, Update, Delete }; - Database(const QString& path); Database(); void initialize(const QString& path); QSqlQuery query(const QString& sql) const; QSqlDatabase& database(); QSqlQuery buildSqlQuery(Database::QueryType type, const QString& tableName, const QStringList& fields, const VariantVector& values, const QString& whereCondition = ""); + QSqlQuery buildSqlQuery(Database::QueryType type, const QString& tableName, const QMap& values, const QString& whereCondition = ""); bool errorCheck(const QSqlQuery& query); - //Change newChange() const; - private: + void log(const QString& sql, const QSqlQuery& query = QSqlQuery()) const; + QSqlDatabase db_; void upgrade(); int version() const; diff --git a/QtClient/JoplinQtClient/enum.cpp b/QtClient/JoplinQtClient/enum.cpp new file mode 100755 index 000000000..6ecac7120 --- /dev/null +++ b/QtClient/JoplinQtClient/enum.cpp @@ -0,0 +1,6 @@ +#include "enum.h" + +enum::enum() +{ + +} diff --git a/QtClient/JoplinQtClient/enum.h b/QtClient/JoplinQtClient/enum.h new file mode 100755 index 000000000..b707ed651 --- /dev/null +++ b/QtClient/JoplinQtClient/enum.h @@ -0,0 +1,14 @@ +#ifndef ENUM_H +#define ENUM_H + +#include + +namespace jop { + +enum ColType { UndefinedType, TextColType, IntColType }; + +enum Table { UndefinedTable, FoldersTable, NotesTable }; + +} + +#endif // ENUM_H diff --git a/QtClient/JoplinQtClient/models/basemodel.cpp b/QtClient/JoplinQtClient/models/basemodel.cpp new file mode 100755 index 000000000..b65955e33 --- /dev/null +++ b/QtClient/JoplinQtClient/models/basemodel.cpp @@ -0,0 +1,283 @@ +#include "basemodel.h" + +#include "database.h" +#include "uuid.h" + +using namespace jop; + +QMap> BaseModel::tableFields_; +QHash BaseModel::cache_; + +BaseModel::BaseModel() { + +} + +QStringList BaseModel::changedFields() const { + QStringList output; + for (QHash::const_iterator it = changedFields_.begin(); it != changedFields_.end(); ++it) { + output.push_back(it.key()); + } + return output; +} + +int BaseModel::count(Table table) { + QString t = BaseModel::tableName(table); + QString k = QString("%1:count").arg(t); + QVariant r = BaseModel::cacheGet(k); + if (r.isValid()) return r.toInt(); + + QSqlQuery q = jop::db().query("SELECT count(*) as row_count FROM " + t); + q.exec(); + q.next(); + int output = q.value(0).toInt(); + BaseModel::cacheSet(k, QVariant(output)); + return output; +} + +bool BaseModel::save() { + bool isNew = this->isNew(); + + if (!changedFields_.size() && !isNew) return true; + + QStringList fields = changedFields(); + + QMap values; + + foreach (QString field, fields) { + values[field] = value(field).toQVariant(); + } + + if (isNew && primaryKeyIsUuid()) { + values[primaryKey()] = uuid::createUuid(); + } + + changedFields_.clear(); + + const QString& tableName = BaseModel::tableName(table()); + + if (isNew) { + cacheDelete(QString("%1:count").arg(tableName)); + } + + if (isNew) { + QSqlQuery q = jop::db().buildSqlQuery(Database::Insert, tableName, values); + q.exec(); + return jop::db().errorCheck(q); + } else { + QSqlQuery q = jop::db().buildSqlQuery(Database::Update, tableName, values, QString("%1 = '%2'").arg(primaryKey()).arg(value("id").toString())); + q.exec(); + return jop::db().errorCheck(q); + } + + return false; // Unreachable +} + +bool BaseModel::dispose() { + const QString& tableName = BaseModel::tableName(table()); + QSqlQuery q(jop::db().database()); + q.prepare("DELETE FROM " + tableName + " WHERE " + primaryKey() + " = :id"); + q.bindValue(":id", id().toString()); + q.exec(); + cacheDelete(QString("%1:count").arg(tableName)); + return jop::db().errorCheck(q); +} + +Table BaseModel::table() const { + qCritical() << "BaseModel::table() must be overriden"; + return jop::UndefinedTable; +} + +QString BaseModel::primaryKey() const { + return "id"; +} + +bool BaseModel::primaryKeyIsUuid() const { + return false; +} + +bool BaseModel::isNew() const { + return !valueIsSet(primaryKey()); +} + +BaseModel::Field createField(const QString& name, QMetaType::Type type) { + BaseModel::Field c; + c.name = name; + c.type = type; + return c; +} + +QVector BaseModel::tableFields(jop::Table table) { + if (BaseModel::tableFields_.contains(table)) return BaseModel::tableFields_[table]; + + QVector output; + if (table == jop::FoldersTable) { + output.push_back(createField("id", QMetaType::QString )); + output.push_back(createField("title", QMetaType::QString )); + output.push_back(createField("created_time", QMetaType::Int )); + output.push_back(createField("updated_time", QMetaType::Int )); + } + + BaseModel::tableFields_[table] = output; + return output; +} + +QStringList BaseModel::tableFieldNames(Table table) { + QVector fields = BaseModel::tableFields(table); + QStringList output; + foreach (BaseModel::Field field, fields) { + output.push_back(field.name); + } + return output; +} + +bool BaseModel::isValidFieldName(Table table, const QString &name) { + QVector fields = BaseModel::tableFields(table); + foreach (BaseModel::Field col, fields) { + if (col.name == name) return true; + } + return false; +} + +void BaseModel::loadSqlQuery(const QSqlQuery &query) { + values_.clear(); + QSqlRecord record = query.record(); + QVector fields = BaseModel::tableFields(table()); + + foreach (BaseModel::Field field, fields) { + int idx = record.indexOf(field.name); + if (idx < 0) { + qCritical() << "Cannot find field" << field.name; + continue; + } + + if (field.type == QMetaType::QString) { + values_.insert(field.name, Value(query.value(idx).toString())); + } else if (field.type == QMetaType::Int) { + values_.insert(field.name, Value(query.value(idx).toInt())); + } else { + qCritical() << "Unsupported value type" << field.name; + } + } + + changedFields_.clear(); +} + +QHash BaseModel::values() const { + return values_; +} + +BaseModel::Value BaseModel::value(const QString &name) const { + if (!valueIsSet(name)) { + qCritical() << "Value does not exist" << name; + return Value(); + } + return values_[name]; +} + +bool BaseModel::valueIsSet(const QString &name) const { + return values_.contains(name); +} + +void BaseModel::setValue(const QString &name, const BaseModel::Value &value) { + if (!values_.contains(name)) { + values_.insert(name, value); + changedFields_.insert(name, true); + } else { + Value& v = values_[name]; + if (v.isEqual(value)) return; + values_.insert(name, value); + changedFields_.insert(name, true); + } +} + +void BaseModel::setValue(const QString &name, int value) { + setValue(name, Value(value)); +} + +BaseModel::Value BaseModel::id() const { + if (!valueIsSet(primaryKey())) return QVariant(); + return value(primaryKey()); +} + +QString BaseModel::tableName(Table t) { + if (t == jop::FoldersTable) return "folders"; + if (t == jop::NotesTable) return "notes"; + return "UNDEFINED"; +} + +QVariant BaseModel::cacheGet(const QString &key) { + if (!BaseModel::cache_.contains(key)) return QVariant(); + return cache_[key]; +} + +void BaseModel::cacheSet(const QString &key, const QVariant &value) { + BaseModel::cache_[key] = value; +} + +void BaseModel::cacheDelete(const QString &key) { + BaseModel::cache_.remove(key); +} + +void BaseModel::setValue(const QString &name, const QString &value) { + setValue(name, Value(value)); +} + +void BaseModel::setValue(const QString& name, const QVariant& value) { + setValue(name, Value(value)); +} + +BaseModel::Value::Value() {} + +BaseModel::Value::Value(const QString &v) { + type_ = QMetaType::QString; + stringValue_ = v; +} + +BaseModel::Value::Value(int v) { + type_ = QMetaType::Int; + intValue_ = v; +} + +BaseModel::Value::Value(const QVariant &v) { + type_ = (QMetaType::Type)v.type(); + if (type_ == QMetaType::QString) { + stringValue_ = v.toString(); + } else if (type_ == QMetaType::Int) { + intValue_ = v.toInt(); + } else { + // Creates an invalid Value + } +} + +int BaseModel::Value::toInt() const { + return intValue_; +} + +QString BaseModel::Value::toString() const { + return stringValue_; +} + +QVariant BaseModel::Value::toQVariant() const { + QMetaType::Type t = type(); + if (t == QMetaType::QString) return QVariant(toString()); + if (t == QMetaType::Int) return QVariant(toInt()); + return QVariant(); +} + +QMetaType::Type BaseModel::Value::type() const { + return type_; +} + +bool BaseModel::Value::isValid() const { + return type_ > 0; +} + +bool BaseModel::Value::isEqual(const BaseModel::Value &v) const { + QMetaType::Type type = v.type(); + if (this->type() != type) return false; + if (type == QMetaType::QString) return toString() == v.toString(); + if (type == QMetaType::Int) return toInt() == v.toInt(); + + qCritical() << "Unreachable"; + return false; +} diff --git a/QtClient/JoplinQtClient/models/basemodel.h b/QtClient/JoplinQtClient/models/basemodel.h new file mode 100755 index 000000000..2033b2df6 --- /dev/null +++ b/QtClient/JoplinQtClient/models/basemodel.h @@ -0,0 +1,88 @@ +#ifndef BASEMODEL_H +#define BASEMODEL_H + +#include + +#include "database.h" +#include "enum.h" + +namespace jop { + +class BaseModel { + +public: + + struct Field { + QString name; + QMetaType::Type type; + }; + + class Value { + + public: + + Value(); + Value(const QString& v); + Value(int v); + Value(const QVariant& v); + int toInt() const; + QString toString() const; + QVariant toQVariant() const; + QMetaType::Type type() const; + bool isValid() const; + bool isEqual(const Value& v) const; + + private: + + QMetaType::Type type_; + QString stringValue_; + int intValue_; + + }; + + BaseModel(); + QStringList changedFields() const; + static int count(jop::Table table); + bool save(); + bool dispose(); + + virtual Table table() const; + virtual QString primaryKey() const; + virtual bool primaryKeyIsUuid() const; + + bool isNew() const; + + static QVector tableFields(Table table); + static QStringList tableFieldNames(Table table); + static bool isValidFieldName(Table table, const QString& name); + + void loadSqlQuery(const QSqlQuery& query); + QHash values() const; + Value value(const QString& name) const; + bool valueIsSet(const QString& name) const; + void setValue(const QString& name, const Value& value); + void setValue(const QString& name, const QVariant& value); + void setValue(const QString& name, const QString& value); + void setValue(const QString& name, int value); + Value id() const; + + static QString tableName(Table t); + +protected: + + QHash changedFields_; + Table table_; + QHash values_; + + static QVariant cacheGet(const QString& key); + static void cacheSet(const QString& key, const QVariant& value); + static void cacheDelete(const QString& key); + + static QMap> tableFields_; + static QHash cache_; + +}; + +} + +#endif // BASEMODEL_H diff --git a/QtClient/JoplinQtClient/models/folder.cpp b/QtClient/JoplinQtClient/models/folder.cpp index de40cbc22..a73e32d4e 100755 --- a/QtClient/JoplinQtClient/models/folder.cpp +++ b/QtClient/JoplinQtClient/models/folder.cpp @@ -5,64 +5,79 @@ using namespace jop; -Folder::Folder() { +Folder::Folder() : Item() { } -bool Folder::isNew() const { - return id().isEmpty(); -} +//bool Folder::isNew() const { +// return id().isEmpty(); +//} -bool Folder::save() { - bool isNew = this->isNew(); +//bool Folder::save() { +// bool isNew = this->isNew(); - QStringList fields; - VariantVector values; - if (isNew) { - setId(uuid::createUuid()); - fields << "id"; - values << id(); - } - fields << "title" << "synced"; - values << title() << QVariant(0); +// QStringList fields; +// VariantVector values; +// if (isNew) { +// setId(uuid::createUuid()); +// fields << "id"; +// values << id(); +// } +// fields << "title" << "synced"; +// values << title() << QVariant(0); - if (isNew) { - QSqlQuery q = jop::db().buildSqlQuery(Database::Insert, "folders", fields, values); - q.exec(); - return jop::db().errorCheck(q); - } else { - QSqlQuery q = jop::db().buildSqlQuery(Database::Update, "folders", fields, values, "id = \"" + id() + "\""); - q.exec(); - return jop::db().errorCheck(q); - } -} +// if (isNew) { +// QSqlQuery q = jop::db().buildSqlQuery(Database::Insert, "folders", fields, values); +// q.exec(); +// return jop::db().errorCheck(q); +// } else { +// QSqlQuery q = jop::db().buildSqlQuery(Database::Update, "folders", fields, values, "id = \"" + id() + "\""); +// q.exec(); +// return jop::db().errorCheck(q); +// } +//} -bool Folder::dispose() { - QSqlQuery q(jop::db().database()); - q.prepare("DELETE FROM folders WHERE id = :id"); - q.bindValue(":id", id()); - q.exec(); - return jop::db().errorCheck(q); -} +//bool Folder::dispose() { +// return false; +//// QSqlQuery q(jop::db().database()); +//// q.prepare("DELETE FROM folders WHERE id = :id"); +//// q.bindValue(":id", id()); +//// q.exec(); +//// return jop::db().errorCheck(q); +//} int Folder::count() { - QSqlQuery q = jop::db().query("SELECT count(*) as row_count FROM folders"); - q.exec(); - q.next(); - return q.value(0).toInt(); + return BaseModel::count(jop::FoldersTable); } QVector Folder::all(const QString &orderBy) { - QSqlQuery q = jop::db().query("SELECT " + Folder::dbFields().join(",") + " FROM folders ORDER BY " + orderBy); + //QSqlQuery q = jop::db().query("SELECT " + Folder::dbFields().join(",") + " FROM folders ORDER BY " + orderBy); + QSqlQuery q = jop::db().query("SELECT " + BaseModel::tableFieldNames(jop::FoldersTable).join(",") + " FROM folders ORDER BY " + orderBy); q.exec(); QVector output; while (q.next()) { Folder folder; - folder.fromSqlQuery(q); + folder.loadSqlQuery(q); output.push_back(folder); + +// Folder folder; +// folder.fromSqlQuery(q); +// output.push_back(folder); + +// Folder f2; +// f2.loadSqlQuery(q); +// qDebug() << "xxx" << f2.value("title").toString(); } return output; } + +Table Folder::table() const { + return jop::FoldersTable; +} + +bool Folder::primaryKeyIsUuid() const { + return true; +} diff --git a/QtClient/JoplinQtClient/models/folder.h b/QtClient/JoplinQtClient/models/folder.h index 2b65eb198..50e6d2b1b 100755 --- a/QtClient/JoplinQtClient/models/folder.h +++ b/QtClient/JoplinQtClient/models/folder.h @@ -11,13 +11,13 @@ class Folder : public Item { public: Folder(); - bool isNew() const; - bool save(); - bool dispose(); static int count(); static QVector all(const QString& orderBy); + Table table() const; + bool primaryKeyIsUuid() const; + private: }; diff --git a/QtClient/JoplinQtClient/models/foldermodel.cpp b/QtClient/JoplinQtClient/models/foldermodel.cpp index 35ff75075..a0ea59e5a 100755 --- a/QtClient/JoplinQtClient/models/foldermodel.cpp +++ b/QtClient/JoplinQtClient/models/foldermodel.cpp @@ -7,7 +7,7 @@ FolderModel::FolderModel(Database &database) : QAbstractListModel(), db_(databas virtualItemShown_ = false; } -int FolderModel::rowCount(const QModelIndex & parent) const { +int FolderModel::rowCount(const QModelIndex & parent) const { Q_UNUSED(parent); return Folder::count() + (virtualItemShown_ ? 1 : 0); } @@ -18,17 +18,17 @@ QVariant FolderModel::data(const QModelIndex & index, int role) const { Folder folder; if (virtualItemShown_ && index.row() == rowCount() - 1) { - folder.setTitle("Untitled"); + folder.setValue("title", BaseModel::Value(QString("Untitled"))); } else { folder = atIndex(index.row()); } if (role == Qt::DisplayRole) { - return QVariant(folder.title()); + return folder.value("title").toQVariant(); } if (role == IdRole) { - return QVariant(folder.id()); + return folder.id().toQVariant(); } return QVariant(); @@ -38,7 +38,7 @@ bool FolderModel::setData(const QModelIndex &index, const QVariant &value, int r Folder folder = atIndex(index.row()); if (role == Qt::EditRole) { - folder.setTitle(value.toString()); + folder.setValue("title", value); if (!folder.save()) return false; cache_.clear(); @@ -90,7 +90,7 @@ void FolderModel::hideVirtualItem() { endRemoveRows(); } -QString FolderModel::idAtIndex(int index) const { +QString FolderModel::indexToId(int index) const { return data(this->index(index), IdRole).toString(); } @@ -98,7 +98,7 @@ int FolderModel::idToIndex(const QString &id) const { int count = this->rowCount(); for (int i = 0; i < count; i++) { Folder folder = atIndex(i); - if (folder.id() == id) return i; + if (folder.value("id").toString() == id) return i; } return -1; } @@ -125,12 +125,12 @@ QHash FolderModel::roleNames() const { void FolderModel::addData(const QString &title) { Folder folder; - folder.setTitle(title); + folder.setValue("title", title); if (!folder.save()) return; cache_.clear(); - lastInsertId_ = folder.id(); + lastInsertId_ = folder.id().toString(); QVector roles; roles << Qt::DisplayRole; diff --git a/QtClient/JoplinQtClient/models/foldermodel.h b/QtClient/JoplinQtClient/models/foldermodel.h index b253c53e7..989a9469c 100755 --- a/QtClient/JoplinQtClient/models/foldermodel.h +++ b/QtClient/JoplinQtClient/models/foldermodel.h @@ -50,14 +50,10 @@ public slots: void showVirtualItem(); bool virtualItemShown() const; void hideVirtualItem(); - QString idAtIndex(int index) const; + QString indexToId(int index) const; int idToIndex(const QString& id) const; QString lastInsertId() const; -signals: - - void dataChanging(); - }; } diff --git a/QtClient/JoplinQtClient/models/item.cpp b/QtClient/JoplinQtClient/models/item.cpp index 326d160f2..32e6ad74a 100755 --- a/QtClient/JoplinQtClient/models/item.cpp +++ b/QtClient/JoplinQtClient/models/item.cpp @@ -3,56 +3,62 @@ using namespace jop; -Item::Item() { - synced_ = false; -} +Item::Item() {} -QString Item::id() const { - return id_; -} +//Item::Item() { +// synced_ = false; +//} -QString Item::title() const { - return title_; -} +////QString Item::id() const { +//// return id_; +////} -int Item::createdTime() const { - return createdTime_; -} +//QString Item::title() const { +// return title_; +//} -int Item::updatedTime() const { - return updatedTime_; -} +//int Item::createdTime() const { +// return createdTime_; +//} -bool Item::synced() const { - return synced_; -} +//int Item::updatedTime() const { +// return updatedTime_; +//} -void Item::setId(const QString& v) { - id_ = v; -} +//bool Item::synced() const { +// return synced_; +//} -void Item::setTitle(const QString &v) { - title_ = v; -} +//void Item::setId(const QString& v) { +//// if (id_ == v) return; +// id_ = v; +//// changedFields_.push_back("id"); +//} -void Item::setCreatedTime(int v) { - createdTime_ = v; -} +//void Item::setTitle(const QString &v) { +//// if (title_ == v) return; +// title_ = v; +//// changedFields_.push_back("title"); +//} -void Item::setSynced(bool v) { - synced_ = v; -} +//void Item::setCreatedTime(int v) { +// createdTime_ = v; +//} -QStringList Item::dbFields() { - QStringList output; - output << "id" << "title" << "created_time" << "updated_time" << "synced"; - return output; -} +//void Item::setSynced(bool v) { +// synced_ = v; +//} -void Item::fromSqlQuery(const QSqlQuery &q) { - id_ = q.value(0).toString(); - title_ = q.value(1).toString(); - createdTime_ = q.value(2).toInt(); - updatedTime_ = q.value(3).toInt(); - synced_ = q.value(4).toBool(); -} +//QStringList Item::dbFields() { +// QStringList output; +// output << "id" << "title" << "created_time" << "updated_time" << "synced"; +// return output; +//} + +//void Item::fromSqlQuery(const QSqlQuery &q) { +// id_ = q.value(0).toString(); +// title_ = q.value(1).toString(); +// createdTime_ = q.value(2).toInt(); +// updatedTime_ = q.value(3).toInt(); +// synced_ = q.value(4).toBool(); +//} diff --git a/QtClient/JoplinQtClient/models/item.h b/QtClient/JoplinQtClient/models/item.h index 7891b0ba3..2f62d6afe 100755 --- a/QtClient/JoplinQtClient/models/item.h +++ b/QtClient/JoplinQtClient/models/item.h @@ -3,35 +3,36 @@ #include +#include "models/basemodel.h" + namespace jop { -class Item { +class Item : public BaseModel { public: Item(); - QString id() const; - QString title() const; - int createdTime() const; - int updatedTime() const; - bool synced() const; - static QStringList dbFields(); +// QString title() const; +// int createdTime() const; +// int updatedTime() const; +// bool synced() const; +// static QStringList dbFields(); - void setId(const QString &v); - void setTitle(const QString& v); - void setCreatedTime(int v); - void setSynced(bool v); +// void setId(const QString &v); +// void setTitle(const QString& v); +// void setCreatedTime(int v); +// void setSynced(bool v); - void fromSqlQuery(const QSqlQuery& query); +// void fromSqlQuery(const QSqlQuery& query); private: - QString id_; - QString title_; - time_t createdTime_; - time_t updatedTime_; - bool synced_; +// QString id_; +// QString title_; +// time_t createdTime_; +// time_t updatedTime_; +// bool synced_; }; diff --git a/QtClient/JoplinQtClient/models/note.cpp b/QtClient/JoplinQtClient/models/note.cpp index d94d91c21..865df377a 100755 --- a/QtClient/JoplinQtClient/models/note.cpp +++ b/QtClient/JoplinQtClient/models/note.cpp @@ -7,22 +7,22 @@ Note::Note() } -QString Note::body() const { - return body_; -} +//QString Note::body() const { +// return body_; +//} -void Note::setBody(const QString &v) { - body_ = v; -} +//void Note::setBody(const QString &v) { +// body_ = v; +//} -QStringList Note::dbFields() { - QStringList output = Item::dbFields(); - output << "body"; - return output; -} +//QStringList Note::dbFields() { +// QStringList output = Item::dbFields(); +// output << "body"; +// return output; +//} -void Note::fromSqlQuery(const QSqlQuery &q) { - Item::fromSqlQuery(q); - int idx = Item::dbFields().size(); - body_ = q.value(idx).toString(); -} +//void Note::fromSqlQuery(const QSqlQuery &q) { +// Item::fromSqlQuery(q); +// int idx = Item::dbFields().size(); +// body_ = q.value(idx).toString(); +//} diff --git a/QtClient/JoplinQtClient/models/note.h b/QtClient/JoplinQtClient/models/note.h index 9e692900d..abe94a4b8 100755 --- a/QtClient/JoplinQtClient/models/note.h +++ b/QtClient/JoplinQtClient/models/note.h @@ -11,14 +11,14 @@ class Note : public Item { public: Note(); - QString body() const; - void setBody(const QString& v); - static QStringList dbFields(); - void fromSqlQuery(const QSqlQuery &q); +// QString body() const; +// void setBody(const QString& v); +// static QStringList dbFields(); +// void fromSqlQuery(const QSqlQuery &q); -private: +//private: - QString body_; +// QString body_; }; diff --git a/QtClient/JoplinQtClient/models/notecollection.cpp b/QtClient/JoplinQtClient/models/notecollection.cpp index 8c2e4a510..32b2a0698 100755 --- a/QtClient/JoplinQtClient/models/notecollection.cpp +++ b/QtClient/JoplinQtClient/models/notecollection.cpp @@ -11,36 +11,37 @@ NoteCollection::NoteCollection(Database& db, const QString& parentId, const QStr } Note NoteCollection::at(int index) const { - if (parentId_ == "") return Note(); + return Note(); +// if (parentId_ == "") return Note(); - if (cache_.isset(index)) return cache_.get(index); +// if (cache_.isset(index)) return cache_.get(index); - std::vector indexes = cache_.availableBufferAround(index, 32); - if (!indexes.size()) { - qWarning() << "Couldn't acquire buffer"; // "Cannot happen" - return Note(); - } +// std::vector indexes = cache_.availableBufferAround(index, 32); +// if (!indexes.size()) { +// qWarning() << "Couldn't acquire buffer"; // "Cannot happen" +// return Note(); +// } - int from = indexes[0]; - int to = indexes[indexes.size() - 1]; +// int from = indexes[0]; +// int to = indexes[indexes.size() - 1]; - QSqlQuery q = db_.query("SELECT id, title, body FROM notes WHERE parent_id = :parent_id ORDER BY " + orderBy_ + " LIMIT " + QString::number(to - from + 1) + " OFFSET " + QString::number(from)); - q.bindValue(":parent_id", parentId_); - q.exec(); +// QSqlQuery q = db_.query("SELECT id, title, body FROM notes WHERE parent_id = :parent_id ORDER BY " + orderBy_ + " LIMIT " + QString::number(to - from + 1) + " OFFSET " + QString::number(from)); +// q.bindValue(":parent_id", parentId_); +// q.exec(); - int noteIndex = from; - while (q.next()) { - Note note; - note.setId(q.value(0).toString()); - note.setTitle(q.value(1).toString()); - note.setBody(q.value(2).toString()); +// int noteIndex = from; +// while (q.next()) { +// Note note; +// note.setId(q.value(0).toString()); +// note.setTitle(q.value(1).toString()); +// note.setBody(q.value(2).toString()); - cache_.set(noteIndex, note); +// cache_.set(noteIndex, note); - noteIndex++; - } +// noteIndex++; +// } - return cache_.get(index); +// return cache_.get(index); } // TODO: cache result @@ -55,25 +56,26 @@ int NoteCollection::count() const { } Note NoteCollection::byId(const QString& id) const { - std::vector indexes = cache_.indexes(); - for (size_t i = 0; i < indexes.size(); i++) { - Note note = cache_.get(indexes[i]); - if (note.id() == id) return note; - } + return Note(); +// std::vector indexes = cache_.indexes(); +// for (size_t i = 0; i < indexes.size(); i++) { +// Note note = cache_.get(indexes[i]); +// if (note.id() == id) return note; +// } - QSqlQuery q = db_.query("SELECT id, title, body FROM notes WHERE id = :id"); - q.bindValue(":id", id); - q.exec(); - q.next(); - if (!q.isValid()) { - qWarning() << "Invalid note ID:" << id; - return Note(); - } +// QSqlQuery q = db_.query("SELECT id, title, body FROM notes WHERE id = :id"); +// q.bindValue(":id", id); +// q.exec(); +// q.next(); +// if (!q.isValid()) { +// qWarning() << "Invalid note ID:" << id; +// return Note(); +// } - // TODO: refactor creation of note from SQL query object - Note note; - note.setId(q.value(0).toString()); - note.setTitle(q.value(1).toString()); - note.setBody(q.value(2).toString()); - return note; +// // TODO: refactor creation of note from SQL query object +// Note note; +// note.setId(q.value(0).toString()); +// note.setTitle(q.value(1).toString()); +// note.setBody(q.value(2).toString()); +// return note; } diff --git a/QtClient/JoplinQtClient/models/notemodel.cpp b/QtClient/JoplinQtClient/models/notemodel.cpp index 9cf80180c..79f0a787c 100755 --- a/QtClient/JoplinQtClient/models/notemodel.cpp +++ b/QtClient/JoplinQtClient/models/notemodel.cpp @@ -13,13 +13,13 @@ int jop::NoteModel::rowCount(const QModelIndex &parent) const { QVariant jop::NoteModel::data(const QModelIndex &index, int role) const { if (index.row() < 0 || index.row() >= rowCount()) return QVariant(); - Note note = collection_.at(index.row()); +// Note note = collection_.at(index.row()); - if (role == IdRole) { - return QVariant(note.id()); - } +// if (role == IdRole) { +// return QVariant(note.id()); +// } - return QVariant(note.title()); +// return QVariant(note.title()); } void jop::NoteModel::setFolderId(const QString &v) { diff --git a/QtClient/JoplinQtClient/models/qmlnote.cpp b/QtClient/JoplinQtClient/models/qmlnote.cpp index 476e03d6d..b1be8aa56 100755 --- a/QtClient/JoplinQtClient/models/qmlnote.cpp +++ b/QtClient/JoplinQtClient/models/qmlnote.cpp @@ -5,11 +5,11 @@ using namespace jop; QmlNote::QmlNote() {} QString QmlNote::title() const { - return note_.title(); + return note_.value("title").toString(); } QString QmlNote::body() const { - return note_.body(); + return note_.value("body").toString(); } void QmlNote::setNote(const Note ¬e) { diff --git a/QtClient/JoplinQtClient/synchronizer.cpp b/QtClient/JoplinQtClient/synchronizer.cpp index 10e5e2b03..3996d1422 100755 --- a/QtClient/JoplinQtClient/synchronizer.cpp +++ b/QtClient/JoplinQtClient/synchronizer.cpp @@ -14,48 +14,48 @@ void Synchronizer::start() { QSqlQuery query; - std::vector folders; - query = db_.query("SELECT " + Folder::dbFields().join(',') + " FROM folders WHERE synced = 0"); - query.exec(); +// std::vector folders; +// query = db_.query("SELECT " + Folder::dbFields().join(',') + " FROM folders WHERE synced = 0"); +// query.exec(); - while (query.next()) { - Folder folder; - folder.fromSqlQuery(query); - folders.push_back(folder); - } +// while (query.next()) { +// Folder folder; +// folder.fromSqlQuery(query); +// folders.push_back(folder); +// } - QList notes; - query = db_.query("SELECT " + Note::dbFields().join(',') + " FROM notes WHERE synced = 0"); - query.exec(); +// QList notes; +// query = db_.query("SELECT " + Note::dbFields().join(',') + " FROM notes WHERE synced = 0"); +// query.exec(); - while (query.next()) { - Note note; - note.fromSqlQuery(query); - notes << note; - } +// while (query.next()) { +// Note note; +// note.fromSqlQuery(query); +// notes << note; +// } - for (size_t i = 0; i < folders.size(); i++) { - Folder folder = folders[i]; - QUrlQuery data; - data.addQueryItem("id", folder.id()); - data.addQueryItem("title", folder.title()); - data.addQueryItem("created_time", QString::number(folder.createdTime())); - data.addQueryItem("updated_time", QString::number(folder.updatedTime())); - api_.put("folders/" + folder.id(), QUrlQuery(), data, "putFolder:" + folder.id()); - } +// for (size_t i = 0; i < folders.size(); i++) { +// Folder folder = folders[i]; +// QUrlQuery data; +// data.addQueryItem("id", folder.id()); +// data.addQueryItem("title", folder.title()); +// data.addQueryItem("created_time", QString::number(folder.createdTime())); +// data.addQueryItem("updated_time", QString::number(folder.updatedTime())); +// api_.put("folders/" + folder.id(), QUrlQuery(), data, "putFolder:" + folder.id()); +// } - return; +// return; - for (int i = 0; i < notes.size(); i++) { - Note note = notes[i]; - QUrlQuery data; - data.addQueryItem("id", note.id()); - data.addQueryItem("title", note.title()); - data.addQueryItem("body", note.body()); - data.addQueryItem("created_time", QString::number(note.createdTime())); - data.addQueryItem("updated_time", QString::number(note.updatedTime())); - api_.put("notes/" + note.id(), QUrlQuery(), data, "putNote:" + note.id()); - } +// for (int i = 0; i < notes.size(); i++) { +// Note note = notes[i]; +// QUrlQuery data; +// data.addQueryItem("id", note.id()); +// data.addQueryItem("title", note.title()); +// data.addQueryItem("body", note.body()); +// data.addQueryItem("created_time", QString::number(note.createdTime())); +// data.addQueryItem("updated_time", QString::number(note.updatedTime())); +// api_.put("notes/" + note.id(), QUrlQuery(), data, "putNote:" + note.id()); +// } } void Synchronizer::api_requestDone(const QJsonObject& response, const QString& tag) { diff --git a/QtClient/dependencies/dll-debug/libeay32.dll b/QtClient/dependencies/dll-debug/libeay32.dll new file mode 100755 index 000000000..8d31f8668 Binary files /dev/null and b/QtClient/dependencies/dll-debug/libeay32.dll differ diff --git a/QtClient/dependencies/dll-debug/libssl32.dll b/QtClient/dependencies/dll-debug/libssl32.dll new file mode 100755 index 000000000..a30ff0e9e Binary files /dev/null and b/QtClient/dependencies/dll-debug/libssl32.dll differ