Commit c66efeba authored by camilo higuita's avatar camilo higuita

reqoek the whole syncing part with new syncer worker

parent b42bb400
...@@ -32,6 +32,9 @@ include_directories( ...@@ -32,6 +32,9 @@ include_directories(
${CMAKE_CURRENT_SOURCE_DIR}/src/syncing ${CMAKE_CURRENT_SOURCE_DIR}/src/syncing
${CMAKE_CURRENT_BINARY_DIR}/src/syncing ${CMAKE_CURRENT_BINARY_DIR}/src/syncing
${CMAKE_CURRENT_SOURCE_DIR}/src/providers
${CMAKE_CURRENT_BINARY_DIR}/src/providers
) )
set(buho_SRCS set(buho_SRCS
...@@ -42,7 +45,7 @@ set(buho_SRCS ...@@ -42,7 +45,7 @@ set(buho_SRCS
src/utils/htmlparser.cpp src/utils/htmlparser.cpp
src/models/notes/notes.cpp src/models/notes/notes.cpp
src/models/links/links.cpp src/models/links/links.cpp
src/syncing/nextnote.cpp src/providers/nextnote.cpp
src/syncing/syncer.cpp src/syncing/syncer.cpp
) )
...@@ -54,8 +57,8 @@ set(buho_HDRS ...@@ -54,8 +57,8 @@ set(buho_HDRS
src/utils/htmlparser.h src/utils/htmlparser.h
src/models/notes/notes.h src/models/notes/notes.h
src/models/links/links.h src/models/links/links.h
src/syncing/nextnote.h src/providers/nextnote.h
src/syncing/abstractnotessyncer.h src/providers/abstractnotesprovider.h
src/syncing/syncer.h src/syncing/syncer.h
) )
......
...@@ -23,18 +23,9 @@ along with this program. If not, see <http://www.gnu.org/licenses/>. ...@@ -23,18 +23,9 @@ along with this program. If not, see <http://www.gnu.org/licenses/>.
#include <QString> #include <QString>
#include <QStringList> #include <QStringList>
#include <QSqlQuery> #include <QSqlQuery>
#include <QCoreApplication>
DB::DB(QObject *parent) : QObject(parent) DB::DB(QObject *parent) : QObject(parent)
{
init();
}
DB::~DB()
{
this->m_db.close();
}
void DB::init()
{ {
QDir collectionDBPath_dir(OWL::CollectionDBPath); QDir collectionDBPath_dir(OWL::CollectionDBPath);
if (!collectionDBPath_dir.exists()) if (!collectionDBPath_dir.exists())
...@@ -47,6 +38,14 @@ void DB::init() ...@@ -47,6 +38,14 @@ void DB::init()
qDebug()<<"Collection doesn't exists, trying to create it" << OWL::CollectionDBPath + OWL::DBName; qDebug()<<"Collection doesn't exists, trying to create it" << OWL::CollectionDBPath + OWL::DBName;
this->prepareCollectionDB(); this->prepareCollectionDB();
}else this->openDB(this->name); }else this->openDB(this->name);
//make sure the instances are deleted when the app exists
connect(qApp, &QCoreApplication::aboutToQuit, instance, &DB::deleteLater);
}
DB::~DB()
{
this->m_db.close();
} }
DB *DB::instance = nullptr; DB *DB::instance = nullptr;
...@@ -56,7 +55,6 @@ DB *DB::getInstance() ...@@ -56,7 +55,6 @@ DB *DB::getInstance()
{ {
instance = new DB(); instance = new DB();
qDebug() << "getInstance(): First DB instance\n"; qDebug() << "getInstance(): First DB instance\n";
instance->init();
return instance; return instance;
} else } else
{ {
...@@ -184,6 +182,8 @@ QSqlQuery DB::getQuery(const QString &queryTxt) ...@@ -184,6 +182,8 @@ QSqlQuery DB::getQuery(const QString &queryTxt)
bool DB::insert(const QString &tableName, const QVariantMap &insertData) bool DB::insert(const QString &tableName, const QVariantMap &insertData)
{ {
qDebug() << "TRY TO ISNERT NOTE TO DB" << insertData;
if (tableName.isEmpty()) if (tableName.isEmpty())
{ {
qDebug()<<QStringLiteral("Fatal error on insert! The table name is empty!"); qDebug()<<QStringLiteral("Fatal error on insert! The table name is empty!");
......
...@@ -68,7 +68,6 @@ public: ...@@ -68,7 +68,6 @@ public:
bool remove(const QString &tableName, const QVariantMap &removeData); bool remove(const QString &tableName, const QVariantMap &removeData);
protected: protected:
void init();
void openDB(const QString &name); void openDB(const QString &name);
void prepareCollectionDB() const; void prepareCollectionDB() const;
......
#include "notes.h" #include "notes.h"
#include <QUuid> #include "syncer.h"
#include "db/db.h"
#include "nextnote.h"
#ifdef STATIC_MAUIKIT #ifdef STATIC_MAUIKIT
#include "tagging.h" #include "tagging.h"
...@@ -12,29 +10,21 @@ ...@@ -12,29 +10,21 @@
#endif #endif
Notes::Notes(QObject *parent) : MauiList(parent), Notes::Notes(QObject *parent) : MauiList(parent),
db(DB::getInstance()), syncer(new Syncer(this))
tag(Tagging::getInstance()),
syncer(new NextNote(this))
{ {
qDebug()<< "CREATING NOTES LIST"; qDebug()<< "CREATING NOTES LIST";
this->sortList(); this->sortList();
connect(this, &Notes::sortByChanged, this, &Notes::sortList); connect(this, &Notes::sortByChanged, this, &Notes::sortList);
connect(this, &Notes::orderChanged, this, &Notes::sortList); connect(this, &Notes::orderChanged, this, &Notes::sortList);
connect(syncer, &NextNote::notesReady, [&](FMH::MODEL_LIST notes)
{
emit this->preListChanged();
this->notes << notes;
emit this->postListChanged();
});
} }
void Notes::sortList() void Notes::sortList()
{ {
emit this->preListChanged(); emit this->preListChanged();
this->notes = this->db->getDBData(QString("select * from notes ORDER BY %1 %2").arg( // this->notes = this->db->getDBData(QString("select * from notes ORDER BY %1 %2").arg(
FMH::MODEL_NAME[static_cast<FMH::MODEL_KEY>(this->sort)], // FMH::MODEL_NAME[static_cast<FMH::MODEL_KEY>(this->sort)],
this->order == ORDER::ASC ? "asc" : "desc")); // this->order == ORDER::ASC ? "asc" : "desc"));
emit this->postListChanged(); emit this->postListChanged();
} }
...@@ -73,57 +63,18 @@ Notes::ORDER Notes::getOrder() const ...@@ -73,57 +63,18 @@ Notes::ORDER Notes::getOrder() const
bool Notes::insert(const QVariantMap &note) bool Notes::insert(const QVariantMap &note)
{ {
qDebug()<<"TAGS"<< note[FMH::MODEL_NAME[FMH::MODEL_KEY::TAG]].toStringList();
emit this->preItemAppended(); emit this->preItemAppended();
auto title = note[FMH::MODEL_NAME[FMH::MODEL_KEY::TITLE]].toString(); auto __note = FM::toModel(note);
auto content = note[FMH::MODEL_NAME[FMH::MODEL_KEY::CONTENT]].toString(); __note[FMH::MODEL_KEY::MODIFIED] = QDateTime::currentDateTime().toString(Qt::TextDate);
auto color = note[FMH::MODEL_NAME[FMH::MODEL_KEY::COLOR]].toString(); __note[FMH::MODEL_KEY::ADDDATE] = QDateTime::currentDateTime().toString(Qt::TextDate);
auto pin = note[FMH::MODEL_NAME[FMH::MODEL_KEY::PIN]].toInt();
auto fav = note[FMH::MODEL_NAME[FMH::MODEL_KEY::FAVORITE]].toInt();
auto tags = note[FMH::MODEL_NAME[FMH::MODEL_KEY::TAG]].toStringList();
auto id = QUuid::createUuid().toString();
QVariantMap note_map =
{
{FMH::MODEL_NAME[FMH::MODEL_KEY::ID], id},
{FMH::MODEL_NAME[FMH::MODEL_KEY::TITLE], title},
{FMH::MODEL_NAME[FMH::MODEL_KEY::CONTENT], content},
{FMH::MODEL_NAME[FMH::MODEL_KEY::COLOR], color},
{FMH::MODEL_NAME[FMH::MODEL_KEY::PIN], pin},
{FMH::MODEL_NAME[FMH::MODEL_KEY::FAVORITE], fav},
{FMH::MODEL_NAME[FMH::MODEL_KEY::MODIFIED], QDateTime::currentDateTime().toString()},
{FMH::MODEL_NAME[FMH::MODEL_KEY::ADDDATE], QDateTime::currentDateTime().toString()}
};
if(this->db->insert(OWL::TABLEMAP[OWL::TABLE::NOTES], note_map))
{
for(auto tg : tags)
this->tag->tagAbstract(tg, OWL::TABLEMAP[OWL::TABLE::NOTES], id, color);
this->notes << FMH::MODEL this->syncer->insertNote(__note);
({
{FMH::MODEL_KEY::ID, id},
{FMH::MODEL_KEY::TITLE, title},
{FMH::MODEL_KEY::CONTENT, content},
{FMH::MODEL_KEY::COLOR, color},
{FMH::MODEL_KEY::PIN, QString::number(pin)},
{FMH::MODEL_KEY::FAVORITE, QString::number(fav)},
{FMH::MODEL_KEY::MODIFIED, QDateTime::currentDateTime().toString()},
{FMH::MODEL_KEY::ADDDATE, QDateTime::currentDateTime().toString()}
}); this->notes << __note;
emit postItemAppended(); emit this->postItemAppended();
return true;
this->syncer->insertNote(FM::toModel(note_map));
return true;
} else qDebug()<< "NOTE COULD NOT BE INSTED";
return false;
} }
bool Notes::update(const int &index, const QVariant &value, const int &role) bool Notes::update(const int &index, const QVariant &value, const int &role)
...@@ -190,10 +141,11 @@ bool Notes::update(const FMH::MODEL &note) ...@@ -190,10 +141,11 @@ bool Notes::update(const FMH::MODEL &note)
{FMH::MODEL_NAME[FMH::MODEL_KEY::MODIFIED], modified} {FMH::MODEL_NAME[FMH::MODEL_KEY::MODIFIED], modified}
}; };
for(auto tg : tags) // for(auto tg : tags)
this->tag->tagAbstract(tg, OWL::TABLEMAP[OWL::TABLE::NOTES], id, color); // this->tag->tagAbstract(tg, OWL::TABLEMAP[OWL::TABLE::NOTES], id, color);
return this->db->update(OWL::TABLEMAP[OWL::TABLE::NOTES], note_map, {{FMH::MODEL_NAME[FMH::MODEL_KEY::ID], id}} ); // return this->db->update(OWL::TABLEMAP[OWL::TABLE::NOTES], note_map, {{FMH::MODEL_NAME[FMH::MODEL_KEY::ID], id}} );
return false;
} }
bool Notes::remove(const int &index) bool Notes::remove(const int &index)
...@@ -202,23 +154,23 @@ bool Notes::remove(const int &index) ...@@ -202,23 +154,23 @@ bool Notes::remove(const int &index)
auto id = this->notes.at(index)[FMH::MODEL_KEY::ID]; auto id = this->notes.at(index)[FMH::MODEL_KEY::ID];
QVariantMap note = {{FMH::MODEL_NAME[FMH::MODEL_KEY::ID], id}}; QVariantMap note = {{FMH::MODEL_NAME[FMH::MODEL_KEY::ID], id}};
if(this->db->remove(OWL::TABLEMAP[OWL::TABLE::NOTES], note)) // if(this->db->remove(OWL::TABLEMAP[OWL::TABLE::NOTES], note))
{ // {
this->notes.removeAt(index); // this->notes.removeAt(index);
emit this->postItemRemoved(); // emit this->postItemRemoved();
return true; // return true;
} // }
return false; return false;
} }
void Notes::setAccount(const QVariantMap &account) void Notes::setAccount(const QVariantMap &account)
{ {
this->m_account = account; // this->m_account = account;
const auto data = FM::toModel(this->m_account); // const auto data = FM::toModel(this->m_account);
syncer->setCredentials(data[FMH::MODEL_KEY::USER], data[FMH::MODEL_KEY::PASSWORD], QUrl(data[FMH::MODEL_KEY::SERVER]).host()); // syncer->setCredentials(data[FMH::MODEL_KEY::USER], data[FMH::MODEL_KEY::PASSWORD], QUrl(data[FMH::MODEL_KEY::SERVER]).host());
syncer->getNotes(); // syncer->getNotes();
emit accountChanged(); // emit accountChanged();
} }
QVariantMap Notes::getAccount() const QVariantMap Notes::getAccount() const
...@@ -228,11 +180,12 @@ QVariantMap Notes::getAccount() const ...@@ -228,11 +180,12 @@ QVariantMap Notes::getAccount() const
QVariantList Notes::getTags(const int &index) QVariantList Notes::getTags(const int &index)
{ {
if(index < 0 || index >= this->notes.size()) // if(index < 0 || index >= this->notes.size())
return QVariantList(); // return QVariantList();
auto id = this->notes.at(index)[FMH::MODEL_KEY::ID]; // auto id = this->notes.at(index)[FMH::MODEL_KEY::ID];
return this->tag->getAbstractTags(OWL::TABLEMAP[OWL::TABLE::NOTES], id); // return this->tag->getAbstractTags(OWL::TABLEMAP[OWL::TABLE::NOTES], id);
return QVariantList();
} }
QVariantMap Notes::get(const int &index) const QVariantMap Notes::get(const int &index) const
......
...@@ -13,9 +13,7 @@ ...@@ -13,9 +13,7 @@
#endif #endif
class DB; class Syncer;
class Tagging;
class AbstractNotesSyncer;
class Notes : public MauiList class Notes : public MauiList
{ {
Q_OBJECT Q_OBJECT
...@@ -54,9 +52,8 @@ public: ...@@ -54,9 +52,8 @@ public:
QVariantMap getAccount() const; QVariantMap getAccount() const;
private: private:
DB *db;
Tagging *tag; Syncer *syncer;
AbstractNotesSyncer *syncer;
FMH::MODEL_LIST notes; FMH::MODEL_LIST notes;
void sortList(); void sortList();
......
#ifndef ABSTRACTNOTESYNCER_H #ifndef ABSTRACTNOTESPROVIDER_H
#define ABSTRACTNOTESYNCER_H #define ABSTRACTNOTESPROVIDER_H
#include <QObject> #include <QObject>
#include <functional> #include <functional>
...@@ -14,13 +14,13 @@ ...@@ -14,13 +14,13 @@
* Different services to be added to Buho are expected to derived from this. * Different services to be added to Buho are expected to derived from this.
*/ */
class AbstractNotesSyncer : public QObject class AbstractNotesProvider : public QObject
{ {
Q_OBJECT Q_OBJECT
public: public:
AbstractNotesSyncer(QObject *parent) : QObject(parent) {}; AbstractNotesProvider(QObject *parent) : QObject(parent) {}
virtual ~AbstractNotesSyncer() {}; virtual ~AbstractNotesProvider() {}
virtual void setCredentials(const QString &user, const QString &password, const QString &provider) final virtual void setCredentials(const QString &user, const QString &password, const QString &provider) final
{ {
...@@ -124,6 +124,6 @@ signals: ...@@ -124,6 +124,6 @@ signals:
}; };
#endif // ABSTRACTNOTESYNCER_H #endif // ABSTRACTNOTESPROVIDER_H
...@@ -13,7 +13,7 @@ ...@@ -13,7 +13,7 @@
const QString NextNote::API = "https://PROVIDER/index.php/apps/notes/api/v0.2/"; const QString NextNote::API = "https://PROVIDER/index.php/apps/notes/api/v0.2/";
NextNote::NextNote(QObject *parent) : AbstractNotesSyncer(parent) NextNote::NextNote(QObject *parent) : AbstractNotesProvider(parent)
{ {
} }
...@@ -74,7 +74,7 @@ void NextNote::insertNote(const FMH::MODEL &note) ...@@ -74,7 +74,7 @@ void NextNote::insertNote(const FMH::MODEL &note)
QByteArray payload=QJsonDocument::fromVariant(FM::toMap(note)).toJson(); QByteArray payload=QJsonDocument::fromVariant(FM::toMap(note)).toJson();
qDebug() << "UPLOADING NEW NOT" << QVariant(payload).toString(); qDebug() << "UPLOADING NEW NOT" << QVariant(payload).toString();
auto url = QString(NextNote::API+"%1").replace("PROVIDER", this->m_provider).arg("notes"); const auto url = QString(NextNote::API+"%1").replace("PROVIDER", this->m_provider).arg("notes");
QString concatenated = this->m_user + ":" + this->m_password; QString concatenated = this->m_user + ":" + this->m_password;
QByteArray data = concatenated.toLocal8Bit().toBase64(); QByteArray data = concatenated.toLocal8Bit().toBase64();
......
...@@ -3,19 +3,19 @@ ...@@ -3,19 +3,19 @@
#include <QObject> #include <QObject>
#include <QString> #include <QString>
#include "abstractnotessyncer.h" #include "abstractnotesprovider.h"
#include<functional> #include<functional>
/** /**
* @brief The NextNote class follows the NextCloud API specification * @brief The NextNote class follows the NextCloud API specification
* for syncing notes. * for syncing notes.
*/ */
class NextNote : public AbstractNotesSyncer class NextNote : public AbstractNotesProvider
{ {
Q_OBJECT Q_OBJECT
public: public:
explicit NextNote(QObject *parent = nullptr); explicit NextNote(QObject *parent = nullptr);
~NextNote(); ~NextNote() override final;
void getNote(const QString &id) override final; void getNote(const QString &id) override final;
void getNotes() override final; void getNotes() override final;
void insertNote(const FMH::MODEL &note) override final; void insertNote(const FMH::MODEL &note) override final;
......
#include "syncer.h" #include "syncer.h"
#include "db/db.h"
#include "nextnote.h"
Syncer::Syncer(QObject *parent) : QObject(parent) #include <QUuid>
#ifdef STATIC_MAUIKIT
#include "tagging.h"
#include "fm.h"
#else
#include <MauiKit/tagging.h>
#include <MauiKit/fm.h>
#endif
Syncer::Syncer(QObject *parent) : QObject(parent),
tag(Tagging::getInstance()),
db(DB::getInstance()),
provider(new NextNote(this))
{}
void Syncer::insertNote(FMH::MODEL &note)
{
qDebug()<<"TAGS"<< note[FMH::MODEL_KEY::TAG];
Syncer::stampNote(note);
const auto __noteMap = FM::toMap(Syncer::packNote(note));
if(this->db->insert(OWL::TABLEMAP[OWL::TABLE::NOTES], __noteMap))
{
for(const auto &tg : note[FMH::MODEL_KEY::TAG].split(",", QString::SplitBehavior::SkipEmptyParts))
this->tag->tagAbstract(tg, OWL::TABLEMAP[OWL::TABLE::NOTES], note[FMH::MODEL_KEY::ID], note[FMH::MODEL_KEY::COLOR]);
// this->provider->insertNote(note);
}
}
void Syncer::stampNote(FMH::MODEL &note)
{ {
const auto id = QUuid::createUuid().toString();
note[FMH::MODEL_KEY::ID] = id;
}
FMH::MODEL Syncer::packNote(const FMH::MODEL &note)
{
return FMH::MODEL {
{FMH::MODEL_KEY::ID, note[FMH::MODEL_KEY::ID]},
{FMH::MODEL_KEY::TITLE, note[FMH::MODEL_KEY::TITLE]},
{FMH::MODEL_KEY::CONTENT, note[FMH::MODEL_KEY::CONTENT]},
{FMH::MODEL_KEY::COLOR, note[FMH::MODEL_KEY::COLOR]},
{FMH::MODEL_KEY::PIN, note[FMH::MODEL_KEY::PIN]},
{FMH::MODEL_KEY::FAVORITE, note[FMH::MODEL_KEY::FAVORITE]},
{FMH::MODEL_KEY::MODIFIED, note[FMH::MODEL_KEY::MODIFIED]},
{FMH::MODEL_KEY::ADDDATE, note[FMH::MODEL_KEY::ADDDATE]}
};
} }
...@@ -2,7 +2,11 @@ ...@@ -2,7 +2,11 @@
#define SYNCER_H #define SYNCER_H
#include <QObject> #include <QObject>
#ifdef STATIC_MAUIKIT
#include "fmh.h"
#else
#include <MauiKit/fmh.h>
#endif
/** /**
* @brief The Syncer class * @brief The Syncer class
* This interfaces between local storage and cloud * This interfaces between local storage and cloud
...@@ -12,13 +16,142 @@ ...@@ -12,13 +16,142 @@
* instead of manually inserting to the db or the cloud providers * instead of manually inserting to the db or the cloud providers
*/ */
class Syncer : public QObject struct STATE
{
enum TYPE : uint
{
OK,
ERROR
};
TYPE type;
QString msg;
};
class DB;
class AbstractNotesProvider;
class Tagging;
class Syncer: public QObject
{ {
Q_OBJECT Q_OBJECT
public: public:
explicit Syncer(QObject *parent = nullptr); explicit Syncer(QObject *parent = nullptr);
/**
* @brief insertNote
* saves a new note online and offline
* The signal noteInserted(FMH::MODEL, STATE) is emitted,
* indicating the created note and the transaction resulting state
* @param note
* the note to be stored represented by FMH::MODEL
*/
void insertNote(FMH::MODEL &note);
/**
* @brief updateNote
* Update online and offline an existing note.
* The signal noteUpdated(FMH::MODEL, STATE) is emitted,
* indicating the updated note and the transaction resulting state
* @param id
* ID of the existing note
* @param note
* the new note contents represented by FMH::MODEL
*/
void updateNote(const QString &id, const FMH::MODEL &note);
/**
* @brief removeNote
* remove a note from online and offline storage
* The signal noteRemoved(FMH::MODEL, STATE) is emitted,
* indicating the removed note and the transaction resulting state
* @param id
* ID of the exisiting note
*/
void removeNote(const QString &id);
/**
* @brief getNote
* Retrieves an existing note, whether the note is located offline or online.
* When the note is ready the signal noteReady(FMH::MODEL) is emitted
* @param id
* ID of the exisiting note
*/
void getNote(const QString &id);
/**
* @brief getNotes
* Retrieves all the notes, online and offline notes.
* When the notes are ready the signal notesReady(FMH::MODEL_LIST) is emitted.
*/
void getNotes();
private:
/**
* @brief currentAccount
* The current account to store the notes online.
* The account data is represented by FMH::MODEL, using the keys:
* FMH::MODEL_KEY::USER representing the username
* FMH::MODEL_KEY::PASSWORD representing the user password
* FMH::MODEL_KEY::PROVIDER representing the address to the provider server
*/
FMH::MODEL currentAccount;
/**
* @brief tag
* Instance of the Maui project tag-ger. It adds tags to the abtract notes
* For online tagging one could use the categories ?
*/
Tagging *tag;
/**
* @brief db
* Instance to the data base storing the notes information and location,
* offline and online.
*/
DB *db;
/**
* @brief server
* Abstract instance to the online server to perfom CRUD actions
*/
AbstractNotesProvider *provider;
/**
* @brief syncNote
* Has the job to sync a note between the offline and online versions
* @param id
* ID of the note to be synced
*/
void syncNote(const QString &id);
/**
* @brief stampNote
* Adds an stamp id to identify the note offline and online
* @param note
* the note model is passed by ref and a STAMP key value is inserted
*/
static void stampNote(FMH::MODEL &note);
/**
* @brief packNote
* packs the note to what is expected by the internal database,
* by only using the needed fields
* @param note
* @return
*/
static FMH::MODEL packNote(const FMH::MODEL &note);
signals: signals:
void noteInserted(FMH::MODEL note, STATE state);
void noteUpdated(FMH::MODEL note, STATE state);
void noteRemoved(FMH::MODEL note, STATE state);
void noteReady(FMH::MODEL note);
void notesReady(FMH::MODEL_LIST notes);
void accountChanged(FMH::MODEL account);
public slots: public slots:
}; };
......
Markdown is supported
0% or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment