From 99666740e882e1c2eba960cc1d960ccfa565e048 Mon Sep 17 00:00:00 2001 From: Laurent Cozic Date: Fri, 27 Jan 2017 19:48:10 +0000 Subject: [PATCH 1/3] Added support for changing front end client --- QtClient/JoplinQtClient/JoplinQtClient.pro | 29 ++++++++++++++++++++-- QtClient/JoplinQtClient/main.cpp | 20 ++++++++++++++- 2 files changed, 46 insertions(+), 3 deletions(-) diff --git a/QtClient/JoplinQtClient/JoplinQtClient.pro b/QtClient/JoplinQtClient/JoplinQtClient.pro index 327a7be6e..19310b2eb 100755 --- a/QtClient/JoplinQtClient/JoplinQtClient.pro +++ b/QtClient/JoplinQtClient/JoplinQtClient.pro @@ -1,7 +1,29 @@ +# To enable CLI or GUI, add either of these: +# "JOP_FRONT_END_CLI=1" +# "JOP_FRONT_END_GUI=1" +# to the qmake command. So that it looks like this: +# qmake JoplinQtClient.pro -spec linux-g++ CONFIG+=debug CONFIG+=qml_debug "JOP_FRONT_END_CLI=1" && /usr/bin/make qmake_all + QT += qml quick sql quickcontrols2 network CONFIG += c++11 +defined(JOP_FRONT_END_CLI, var) { + message(Building CLI client) + DEFINES += "JOP_FRONT_END_CLI=$$JOP_FRONT_END_CLI" +} + +defined(JOP_FRONT_END_GUI, var) { + message(Building GUI client) + DEFINES += "JOP_FRONT_END_GUI=$$JOP_FRONT_END_GUI" +} + +defined(JOP_FRONT_END_CLI, var) { + QT -= gui + CONFIG += console + CONFIG -= app_bundle +} + SOURCES += \ main.cpp \ models/item.cpp \ @@ -10,7 +32,6 @@ SOURCES += \ models/foldermodel.cpp \ models/notemodel.cpp \ models/note.cpp \ - application.cpp \ models/qmlnote.cpp \ webapi.cpp \ synchronizer.cpp \ @@ -44,7 +65,6 @@ HEADERS += \ models/foldermodel.h \ models/notemodel.h \ models/note.h \ - application.h \ sparsevector.hpp \ models/qmlnote.h \ webapi.h \ @@ -63,6 +83,11 @@ HEADERS += \ filters.h \ models/abstractlistmodel.h +defined(JOP_FRONT_END_GUI, var) { + SOURCES += application.cpp + HEADERS += application.h +} + DISTFILES += \ AndroidManifest.xml diff --git a/QtClient/JoplinQtClient/main.cpp b/QtClient/JoplinQtClient/main.cpp index 32377c468..2e3440fda 100755 --- a/QtClient/JoplinQtClient/main.cpp +++ b/QtClient/JoplinQtClient/main.cpp @@ -9,7 +9,25 @@ using namespace jop; int main(int argc, char *argv[]) { + +#if (!defined(JOP_FRONT_END_GUI) && !defined(JOP_FRONT_END_CLI)) + qFatal("Either JOP_FRONT_END_GUI or JOP_FRONT_END_CLI must be defined!"); + return 1; +#endif + +#if (defined(JOP_FRONT_END_GUI) && defined(JOP_FRONT_END_CLI)) + qFatal("JOP_FRONT_END_GUI and JOP_FRONT_END_CLI cannot both be defined!"); + return 1; +#endif + +#ifdef JOP_FRONT_END_GUI QCoreApplication::setAttribute(Qt::AA_EnableHighDpiScaling); Application app(argc, argv); - return app.exec(); +#endif + +#ifdef JOP_FRONT_END_CLI + QCoreApplication app(argc, argv); +#endif + + return app.exec(); } From 2fbbdbdb348e78a82b6aa6158725c47f0f2bc47e Mon Sep 17 00:00:00 2001 From: Laurent Cozic Date: Fri, 27 Jan 2017 20:26:46 +0000 Subject: [PATCH 2/3] Setup for CLI app --- QtClient/JoplinQtClient/JoplinQtClient.pro | 6 ++-- QtClient/JoplinQtClient/cliapplication.cpp | 41 ++++++++++++++++++++++ QtClient/JoplinQtClient/cliapplication.h | 19 ++++++++++ QtClient/JoplinQtClient/constants.h | 6 ++++ QtClient/JoplinQtClient/main.cpp | 7 +++- QtClient/JoplinQtClient/stable.h | 1 + 6 files changed, 77 insertions(+), 3 deletions(-) create mode 100644 QtClient/JoplinQtClient/cliapplication.cpp create mode 100644 QtClient/JoplinQtClient/cliapplication.h diff --git a/QtClient/JoplinQtClient/JoplinQtClient.pro b/QtClient/JoplinQtClient/JoplinQtClient.pro index 19310b2eb..57ed8034b 100755 --- a/QtClient/JoplinQtClient/JoplinQtClient.pro +++ b/QtClient/JoplinQtClient/JoplinQtClient.pro @@ -44,7 +44,8 @@ SOURCES += \ paths.cpp \ window.cpp \ filters.cpp \ - models/abstractlistmodel.cpp + models/abstractlistmodel.cpp \ + cliapplication.cpp RESOURCES += qml.qrc \ database.qrc @@ -81,7 +82,8 @@ HEADERS += \ constants.h \ window.h \ filters.h \ - models/abstractlistmodel.h + models/abstractlistmodel.h \ + cliapplication.h defined(JOP_FRONT_END_GUI, var) { SOURCES += application.cpp diff --git a/QtClient/JoplinQtClient/cliapplication.cpp b/QtClient/JoplinQtClient/cliapplication.cpp new file mode 100644 index 000000000..f2cde0684 --- /dev/null +++ b/QtClient/JoplinQtClient/cliapplication.cpp @@ -0,0 +1,41 @@ +#include + +#include "cliapplication.h" +#include "constants.h" +#include "database.h" +#include "paths.h" +#include "uuid.h" +#include "settings.h" + +namespace jop { + +CliApplication::CliApplication(int &argc, char **argv) : QCoreApplication(argc, argv) { + // This is linked to where the QSettings will be saved. In other words, + // if these values are changed, the settings will be reset and saved + // somewhere else. + QCoreApplication::setOrganizationName(jop::ORG_NAME); + QCoreApplication::setOrganizationDomain(jop::ORG_DOMAIN); + QCoreApplication::setApplicationName(jop::APP_NAME); + + qInfo() << "Config dir:" << paths::configDir(); + qInfo() << "Database file:" << paths::databaseFile(); + qInfo() << "SSL:" << QSslSocket::sslLibraryBuildVersionString() << QSslSocket::sslLibraryVersionNumber(); + + jop::db().initialize(paths::databaseFile()); + + Settings::initialize(); + + Settings settings; + + if (!settings.contains("clientId")) { + // Client ID should be unique per instance of a program + settings.setValue("clientId", uuid::createUuid()); + } +} + +int CliApplication::exec() { + qDebug() << "exec"; + return 0; +} + +} diff --git a/QtClient/JoplinQtClient/cliapplication.h b/QtClient/JoplinQtClient/cliapplication.h new file mode 100644 index 000000000..b275af1f2 --- /dev/null +++ b/QtClient/JoplinQtClient/cliapplication.h @@ -0,0 +1,19 @@ +#ifndef CLIAPPLICATION_H +#define CLIAPPLICATION_H + +#include + +namespace jop { + +class CliApplication : public QCoreApplication { + +public: + + CliApplication(int &argc, char **argv); + int exec(); + +}; + +} + +#endif // CLIAPPLICATION_H diff --git a/QtClient/JoplinQtClient/constants.h b/QtClient/JoplinQtClient/constants.h index 4cb9a485a..4a222dc04 100755 --- a/QtClient/JoplinQtClient/constants.h +++ b/QtClient/JoplinQtClient/constants.h @@ -9,6 +9,12 @@ const QString ORG_NAME = "Cozic"; const QString ORG_DOMAIN = "cozic.net"; const QString APP_NAME = "Joplin"; +#if defined(JOP_FRONT_END_CLI) +const QString FRONT_END = "cli"; +#elif defined(JOP_FRONT_END_GUI) +const QString FRONT_END = "gui"; +#endif + } #endif // CONSTANTS_H diff --git a/QtClient/JoplinQtClient/main.cpp b/QtClient/JoplinQtClient/main.cpp index 2e3440fda..8b1518e4c 100755 --- a/QtClient/JoplinQtClient/main.cpp +++ b/QtClient/JoplinQtClient/main.cpp @@ -1,6 +1,11 @@ #include +#if defined(JOP_FRONT_END_CLI) +#include "cliapplication.h" +#elif defined(JOP_FRONT_END_GUI) #include "application.h" +#endif + #include "models/folder.h" #include "database.h" #include "models/foldermodel.h" @@ -26,7 +31,7 @@ int main(int argc, char *argv[]) { #endif #ifdef JOP_FRONT_END_CLI - QCoreApplication app(argc, argv); + CliApplication app(argc, argv); #endif return app.exec(); diff --git a/QtClient/JoplinQtClient/stable.h b/QtClient/JoplinQtClient/stable.h index 0bb43aa44..c0886ad2e 100755 --- a/QtClient/JoplinQtClient/stable.h +++ b/QtClient/JoplinQtClient/stable.h @@ -6,6 +6,7 @@ #include #include +#include #include #include #include From 51c154bd2414136f60dbb785fbc4d44168335fc6 Mon Sep 17 00:00:00 2001 From: Laurent Cozic Date: Tue, 31 Jan 2017 20:19:03 +0000 Subject: [PATCH 3/3] CLI changes --- QtClient/JoplinQtClient/JoplinQtClient.pro | 6 +- .../JoplinQtClient.pro.user.13661a9 | 336 ++++++++++++++++++ QtClient/JoplinQtClient/build.sh | 8 + QtClient/JoplinQtClient/cliapplication.cpp | 112 +++++- QtClient/JoplinQtClient/cliapplication.h | 16 + QtClient/JoplinQtClient/command.cpp | 24 ++ QtClient/JoplinQtClient/command.h | 27 ++ QtClient/JoplinQtClient/database.cpp | 6 + QtClient/JoplinQtClient/database.h | 1 + QtClient/JoplinQtClient/main.cpp | 12 +- QtClient/JoplinQtClient/models/basemodel.cpp | 18 + QtClient/JoplinQtClient/models/basemodel.h | 1 + QtClient/JoplinQtClient/models/folder.h | 2 +- QtClient/JoplinQtClient/schema.sql | 41 +-- QtClient/JoplinQtClient/stable.h | 2 + joplin.sublime-project | 4 + 16 files changed, 586 insertions(+), 30 deletions(-) create mode 100644 QtClient/JoplinQtClient/JoplinQtClient.pro.user.13661a9 create mode 100755 QtClient/JoplinQtClient/build.sh create mode 100644 QtClient/JoplinQtClient/command.cpp create mode 100644 QtClient/JoplinQtClient/command.h diff --git a/QtClient/JoplinQtClient/JoplinQtClient.pro b/QtClient/JoplinQtClient/JoplinQtClient.pro index 57ed8034b..882d9e70f 100755 --- a/QtClient/JoplinQtClient/JoplinQtClient.pro +++ b/QtClient/JoplinQtClient/JoplinQtClient.pro @@ -45,7 +45,8 @@ SOURCES += \ window.cpp \ filters.cpp \ models/abstractlistmodel.cpp \ - cliapplication.cpp + cliapplication.cpp \ + command.cpp RESOURCES += qml.qrc \ database.qrc @@ -83,7 +84,8 @@ HEADERS += \ window.h \ filters.h \ models/abstractlistmodel.h \ - cliapplication.h + cliapplication.h \ + command.h defined(JOP_FRONT_END_GUI, var) { SOURCES += application.cpp diff --git a/QtClient/JoplinQtClient/JoplinQtClient.pro.user.13661a9 b/QtClient/JoplinQtClient/JoplinQtClient.pro.user.13661a9 new file mode 100644 index 000000000..0cc2f29be --- /dev/null +++ b/QtClient/JoplinQtClient/JoplinQtClient.pro.user.13661a9 @@ -0,0 +1,336 @@ + + + + + + EnvironmentId + {13661a96-7123-4040-a8b0-364538c1219d} + + + ProjectExplorer.Project.ActiveTarget + 0 + + + ProjectExplorer.Project.EditorSettings + + true + false + true + + Cpp + + CppGlobal + + + + QmlJS + + QmlJSGlobal + + + 2 + UTF-8 + false + 4 + false + 80 + true + true + 1 + true + false + 0 + true + true + 0 + 8 + true + 1 + true + true + true + false + + + + ProjectExplorer.Project.PluginSettings + + + + ProjectExplorer.Project.Target.0 + + Desktop Qt 5.7.1 GCC 64bit + Desktop Qt 5.7.1 GCC 64bit + qt.57.gcc_64_kit + 0 + 0 + 0 + + /home/laurent/src/notes/QtClient/build-JoplinQtClient-Desktop_Qt_5_7_1_GCC_64bit-Debug + + + true + qmake + + QtProjectManager.QMakeBuildStep + true + "JOP_FRONT_END_CLI=1" + false + false + false + + + true + Make + + Qt4ProjectManager.MakeStep + + -w + -r + + false + + + + 2 + Build + + ProjectExplorer.BuildSteps.Build + + + + true + Make + + Qt4ProjectManager.MakeStep + + -w + -r + + true + clean + + + 1 + Clean + + ProjectExplorer.BuildSteps.Clean + + 2 + false + + Debug + + Qt4ProjectManager.Qt4BuildConfiguration + 2 + true + + + /home/laurent/src/notes/QtClient/build-JoplinQtClient-Desktop_Qt_5_7_1_GCC_64bit-Release + + + true + qmake + + QtProjectManager.QMakeBuildStep + false + + false + false + false + + + true + Make + + Qt4ProjectManager.MakeStep + + -w + -r + + false + + + + 2 + Build + + ProjectExplorer.BuildSteps.Build + + + + true + Make + + Qt4ProjectManager.MakeStep + + -w + -r + + true + clean + + + 1 + Clean + + ProjectExplorer.BuildSteps.Clean + + 2 + false + + Release + + Qt4ProjectManager.Qt4BuildConfiguration + 0 + true + + + /home/laurent/src/notes/QtClient/build-JoplinQtClient-Desktop_Qt_5_7_1_GCC_64bit-Profile + + + true + qmake + + QtProjectManager.QMakeBuildStep + true + + false + true + false + + + true + Make + + Qt4ProjectManager.MakeStep + + -w + -r + + false + + + + 2 + Build + + ProjectExplorer.BuildSteps.Build + + + + true + Make + + Qt4ProjectManager.MakeStep + + -w + -r + + true + clean + + + 1 + Clean + + ProjectExplorer.BuildSteps.Clean + + 2 + false + + Profile + + Qt4ProjectManager.Qt4BuildConfiguration + 0 + true + + 3 + + + 0 + Deploy + + ProjectExplorer.BuildSteps.Deploy + + 1 + Deploy locally + + ProjectExplorer.DefaultDeployConfiguration + + 1 + + + false + false + 1000 + + true + + false + false + false + false + true + 0.01 + 10 + true + 1 + 25 + + 1 + true + false + true + valgrind + + 0 + 1 + 2 + 3 + 4 + 5 + 6 + 7 + 8 + 9 + 10 + 11 + 12 + 13 + 14 + + 2 + + JoplinQtClient + + Qt4ProjectManager.Qt4RunConfiguration:/home/laurent/src/notes/QtClient/JoplinQtClient/JoplinQtClient.pro + true + + JoplinQtClient.pro + false + + + 3768 + false + true + false + false + true + + 1 + + + + ProjectExplorer.Project.TargetCount + 1 + + + ProjectExplorer.Project.Updater.FileVersion + 18 + + + Version + 18 + + diff --git a/QtClient/JoplinQtClient/build.sh b/QtClient/JoplinQtClient/build.sh new file mode 100755 index 000000000..71a286bee --- /dev/null +++ b/QtClient/JoplinQtClient/build.sh @@ -0,0 +1,8 @@ +#!/bin/bash + +BUILD_DIR=/home/laurent/src/notes/QtClient/build-JoplinQtClient-Desktop_Qt_5_7_1_GCC_64bit-Debug +mkdir -p "$BUILD_DIR" +cd "$BUILD_DIR" +/opt/Qt/5.7/gcc_64/bin/qmake /home/laurent/src/notes/QtClient/JoplinQtClient/JoplinQtClient.pro -spec linux-g++ CONFIG+=debug CONFIG+=qml_debug JOP_FRONT_END_CLI=1 +/usr/bin/make qmake_all +/usr/bin/make \ No newline at end of file diff --git a/QtClient/JoplinQtClient/cliapplication.cpp b/QtClient/JoplinQtClient/cliapplication.cpp index f2cde0684..3a906076f 100644 --- a/QtClient/JoplinQtClient/cliapplication.cpp +++ b/QtClient/JoplinQtClient/cliapplication.cpp @@ -6,9 +6,24 @@ #include "paths.h" #include "uuid.h" #include "settings.h" +#include "models/folder.h" + + + + + + + + + +#include + + namespace jop { +StdoutHandler::StdoutHandler() : QTextStream(stdout) {} + CliApplication::CliApplication(int &argc, char **argv) : QCoreApplication(argc, argv) { // This is linked to where the QSettings will be saved. In other words, // if these values are changed, the settings will be reset and saved @@ -33,8 +48,103 @@ CliApplication::CliApplication(int &argc, char **argv) : QCoreApplication(argc, } } +// void CliApplication::processCommand(const Command& command) { +// qDebug() << "Command" << command.name(); +// qDebug() << "Flags" << command.flags(); +// qDebug() << "Args" << command.args(); + +// // if (command == "mkdir") { + +// // //Folder folder; +// // //folder.setValue("title", args[ + +// // } +// } + int CliApplication::exec() { - qDebug() << "exec"; + qDebug() << "==========================================="; + + + + + // QProcess* process = new QProcess(); + // qint64* processId = new qint64(); + // process->startDetached("/usr/bin/vim", QStringList(), QString(), processId); + // while (kill(*processId, 0) == 0) {} + // delete processId; + + + QString command = "help"; + QStringList args = arguments(); + + if (args.size() >= 2) { + command = args[1]; + args.erase(args.begin() + 1); + } + + QCommandLineParser parser; + parser.addHelpOption(); + parser.addVersionOption(); + + // mkdir "new_folder" + // ls + // ls new_folder + // touch new_folder/new_note + + if (command == "mkdir") { + parser.addPositionalArgument("path", "Folder path."); + } else if (command == "ls") { + parser.addPositionalArgument("path", "Folder path."); + } else if (command == "touch") { + parser.addPositionalArgument("path", "Note path."); + } else { + qDebug().noquote() << parser.helpText(); + return 1; + } + + parser.process(args); + + args = parser.positionalArguments(); + + if (command == "mkdir") { + QString title = args.size() ? args[0] : QString(); + Folder folder; + folder.setValue("title", title); + folder.save(); + } + + if (command == "ls") { + QString path = args.size() ? args[0] : QString(); + if (path == "") { + std::vector> folders = Folder::all(); + for (size_t i = 0; i < folders.size(); i++) { + qDebug().noquote() << folders[i].get()->value("title").toString(); + } + } else { + Folder folder; + bool found = folder.loadByField("", "title", path); + if (found) { + qStdout() << "Found" << path << endl; + } else { + qWarning() << "Not found:" << path; + } + } + } + + if (command == "touch") { + // QString path = args.size() ? args[0] : QString(); + // if (path == "") { + // std::vector> folders = Folder::all(); + // for (size_t i = 0; i < folders.size(); i++) { + // qDebug().noquote() << folders[i].get()->value("title").toString(); + // } + // } else { + // // TODO: Get folder by name + // } + } + + qDebug() << "==========================================="; + return 0; } diff --git a/QtClient/JoplinQtClient/cliapplication.h b/QtClient/JoplinQtClient/cliapplication.h index b275af1f2..27ca61582 100644 --- a/QtClient/JoplinQtClient/cliapplication.h +++ b/QtClient/JoplinQtClient/cliapplication.h @@ -3,13 +3,29 @@ #include +#include "command.h" + namespace jop { +class StdoutHandler : public QTextStream { + +public: + + StdoutHandler(); + +}; + +inline StdoutHandler& qStdout() { + static StdoutHandler r; + return r; +} + class CliApplication : public QCoreApplication { public: CliApplication(int &argc, char **argv); + void processCommand(const Command &command); int exec(); }; diff --git a/QtClient/JoplinQtClient/command.cpp b/QtClient/JoplinQtClient/command.cpp new file mode 100644 index 000000000..372dd1d6d --- /dev/null +++ b/QtClient/JoplinQtClient/command.cpp @@ -0,0 +1,24 @@ +#include "command.h" + +namespace jop { + +Command::Command(const QStringList &arguments) : name_("help"), args_(arguments) { + args_.removeFirst(); + if (args_.size() >= 1) { + name_ = args_.takeFirst(); + } +} + +QString Command::name() const { + return name_; +} + +std::map Command::flags() const { + return flags_; +} + +QStringList Command::args() const { + return args_; +} + +} diff --git a/QtClient/JoplinQtClient/command.h b/QtClient/JoplinQtClient/command.h new file mode 100644 index 000000000..378a7340e --- /dev/null +++ b/QtClient/JoplinQtClient/command.h @@ -0,0 +1,27 @@ +#ifndef COMMAND_H +#define COMMAND_H + +#include + +namespace jop { + +class Command { + +public: + + Command(const QStringList& arguments); + QString name() const; + std::map flags() const; + QStringList args() const; + +private: + + QString name_; + std::map flags_; + QStringList args_; + +}; + +} + +#endif // COMMAND_H diff --git a/QtClient/JoplinQtClient/database.cpp b/QtClient/JoplinQtClient/database.cpp index 54b581fa7..3fccb30b2 100755 --- a/QtClient/JoplinQtClient/database.cpp +++ b/QtClient/JoplinQtClient/database.cpp @@ -4,6 +4,12 @@ using namespace jop; Database::Database() {} +Database::~Database() { + if (db_.open()) { + db_.close(); + } +} + void Database::initialize(const QString &path) { version_ = -1; transactionCount_ = 0; diff --git a/QtClient/JoplinQtClient/database.h b/QtClient/JoplinQtClient/database.h index 6cd6b2ab1..148a14aed 100755 --- a/QtClient/JoplinQtClient/database.h +++ b/QtClient/JoplinQtClient/database.h @@ -14,6 +14,7 @@ public: enum QueryType { Select, Insert, Update, Delete }; Database(); + ~Database(); void initialize(const QString& path); QSqlDatabase& database(); QSqlQuery buildSqlQuery(Database::QueryType type, const QString& tableName, const QStringList& fields, const VariantVector& values, const QString& whereCondition = ""); diff --git a/QtClient/JoplinQtClient/main.cpp b/QtClient/JoplinQtClient/main.cpp index 8b1518e4c..b47c974cb 100755 --- a/QtClient/JoplinQtClient/main.cpp +++ b/QtClient/JoplinQtClient/main.cpp @@ -11,9 +11,7 @@ #include "models/foldermodel.h" #include "services/folderservice.h" -using namespace jop; - -int main(int argc, char *argv[]) { +int main(int argc, char *argv[]) { #if (!defined(JOP_FRONT_END_GUI) && !defined(JOP_FRONT_END_CLI)) qFatal("Either JOP_FRONT_END_GUI or JOP_FRONT_END_CLI must be defined!"); @@ -26,13 +24,15 @@ int main(int argc, char *argv[]) { #endif #ifdef JOP_FRONT_END_GUI + qDebug() << "Front end: GUI"; QCoreApplication::setAttribute(Qt::AA_EnableHighDpiScaling); - Application app(argc, argv); + jop::Application app(argc, argv); #endif #ifdef JOP_FRONT_END_CLI - CliApplication app(argc, argv); + qDebug() << "Front end: CLI"; + jop::CliApplication app(argc, argv); #endif return app.exec(); -} +} \ No newline at end of file diff --git a/QtClient/JoplinQtClient/models/basemodel.cpp b/QtClient/JoplinQtClient/models/basemodel.cpp index f3372bca8..6ce97b835 100755 --- a/QtClient/JoplinQtClient/models/basemodel.cpp +++ b/QtClient/JoplinQtClient/models/basemodel.cpp @@ -47,6 +47,24 @@ bool BaseModel::load(const QString &id) { return true; } +bool BaseModel::loadByField(const QString& parentId, const QString& field, const QString& fieldValue) { + QSqlQuery q(jop::db().database()); + QString sql = QString("SELECT %1 FROM %2 WHERE %3 = :field_value AND parent_id = :parent_id LIMIT 1") + .arg(BaseModel::tableFieldNames(table()).join(",")) + .arg(BaseModel::tableName(table())) + .arg(field); + q.prepare(sql); + q.bindValue(":parent_id", parentId); + q.bindValue(":field_value", fieldValue); + jop::db().execQuery(q); + q.next(); + if (!jop::db().errorCheck(q)) return false; + if (!q.isValid()) return false; + + loadSqlQuery(q); + return true; +} + bool BaseModel::save(bool trackChanges) { bool isNew = this->isNew(); diff --git a/QtClient/JoplinQtClient/models/basemodel.h b/QtClient/JoplinQtClient/models/basemodel.h index d4b4a0dc1..401f31526 100755 --- a/QtClient/JoplinQtClient/models/basemodel.h +++ b/QtClient/JoplinQtClient/models/basemodel.h @@ -43,6 +43,7 @@ public: QStringList changedFields() const; static int count(jop::Table table); bool load(const QString& id); + bool loadByField(const QString& parentId, const QString& field, const QString& fieldValue); virtual bool save(bool trackChanges = true); virtual bool dispose(); diff --git a/QtClient/JoplinQtClient/models/folder.h b/QtClient/JoplinQtClient/models/folder.h index 611ccf6dc..be6883cb6 100755 --- a/QtClient/JoplinQtClient/models/folder.h +++ b/QtClient/JoplinQtClient/models/folder.h @@ -14,7 +14,7 @@ public: Folder(); static int count(); - static std::vector> all(const QString& orderBy); + static std::vector> all(const QString& orderBy = "title"); //Table table() const; bool primaryKeyIsUuid() const; diff --git a/QtClient/JoplinQtClient/schema.sql b/QtClient/JoplinQtClient/schema.sql index 995d46277..95a548930 100755 --- a/QtClient/JoplinQtClient/schema.sql +++ b/QtClient/JoplinQtClient/schema.sql @@ -1,29 +1,30 @@ CREATE TABLE folders ( id TEXT PRIMARY KEY, - title TEXT, - created_time INT, - updated_time INT + parent_id TEXT NOT NULL DEFAULT "", + title TEXT NOT NULL DEFAULT "", + created_time INT NOT NULL DEFAULT 0, + updated_time INT NOT NULL DEFAULT 0 ); CREATE TABLE notes ( id TEXT PRIMARY KEY, - title TEXT, - body TEXT, - parent_id TEXT, - created_time INT, - updated_time INT, - latitude NUMERIC, - longitude NUMERIC, - altitude NUMERIC, - source TEXT, - author TEXT, - source_url TEXT, - is_todo BOOLEAN, - todo_due INT, - todo_completed INT, - source_application TEXT, - application_data TEXT, - `order` INT + parent_id TEXT NOT NULL DEFAULT "", + title TEXT NOT NULL DEFAULT "", + body TEXT NOT NULL DEFAULT "", + created_time INT NOT NULL DEFAULT 0, + updated_time INT NOT NULL DEFAULT 0, + latitude NUMERIC NOT NULL DEFAULT 0, + longitude NUMERIC NOT NULL DEFAULT 0, + altitude NUMERIC NOT NULL DEFAULT 0, + source TEXT NOT NULL DEFAULT "", + author TEXT NOT NULL DEFAULT "", + source_url TEXT NOT NULL DEFAULT "", + is_todo BOOLEAN NOT NULL DEFAULT 0, + todo_due INT NOT NULL DEFAULT 0, + todo_completed INT NOT NULL DEFAULT 0, + source_application TEXT NOT NULL DEFAULT "", + application_data TEXT NOT NULL DEFAULT "", + `order` INT NOT NULL DEFAULT 0 ); CREATE TABLE tags ( diff --git a/QtClient/JoplinQtClient/stable.h b/QtClient/JoplinQtClient/stable.h index c0886ad2e..c9cf9e04a 100755 --- a/QtClient/JoplinQtClient/stable.h +++ b/QtClient/JoplinQtClient/stable.h @@ -33,6 +33,8 @@ #include #include #include +#include +#include #endif // __cplusplus diff --git a/joplin.sublime-project b/joplin.sublime-project index 2bc6fcdb5..eb3efb241 100755 --- a/joplin.sublime-project +++ b/joplin.sublime-project @@ -13,6 +13,10 @@ { "name": "Build evernote-import", "shell_cmd": "D:\\Programmes\\cygwin\\bin\\bash.exe --login D:\\Web\\www\\joplin\\QtClient\\evernote-import\\build.sh" + }, + { + "name": "Build QtClient CLI - Linux", + "shell_cmd": "/home/laurent/src/notes/QtClient/JoplinQtClient/build.sh" } ] }