[gnote] Add new base class for GVFS based sync



commit 2d22ac89e628d3ebe2189365d6c777dc15f3b2e6
Author: Aurimas Černius <aurisc4 gmail com>
Date:   Sat Feb 6 13:49:16 2021 +0200

    Add new base class for GVFS based sync

 src/Makefile.am                         |   1 +
 src/synchronization/gvfssyncservice.cpp | 221 ++++++++++++++++++++++++++++++++
 src/synchronization/gvfssyncservice.hpp |  59 +++++++++
 3 files changed, 281 insertions(+)
---
diff --git a/src/Makefile.am b/src/Makefile.am
index 53189385..1706d277 100644
--- a/src/Makefile.am
+++ b/src/Makefile.am
@@ -146,6 +146,7 @@ libgnote_la_SOURCES = \
        notebooks/specialnotebooks.hpp notebooks/specialnotebooks.cpp \
        synchronization/filesystemsyncserver.hpp synchronization/filesystemsyncserver.cpp \
        synchronization/fusesyncserviceaddin.hpp synchronization/fusesyncserviceaddin.cpp \
+       synchronization/gvfssyncservice.hpp synchronization/gvfssyncservice.cpp \
        synchronization/isyncmanager.hpp synchronization/isyncmanager.cpp \
        synchronization/syncui.hpp synchronization/syncui.cpp \
         synchronization/syncutils.hpp synchronization/syncutils.cpp \
diff --git a/src/synchronization/gvfssyncservice.cpp b/src/synchronization/gvfssyncservice.cpp
new file mode 100644
index 00000000..7dad12c2
--- /dev/null
+++ b/src/synchronization/gvfssyncservice.cpp
@@ -0,0 +1,221 @@
+/*
+ * gnote
+ *
+ * Copyright (C) 2019-2021 Aurimas Cernius
+ *
+ * This program is free software: you can redistribute it and/or modify
+ * it under the terms of the GNU General Public License as published by
+ * the Free Software Foundation, either version 3 of the License, or
+ * (at your option) any later version.
+ *
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with this program.  If not, see <http://www.gnu.org/licenses/>.
+ */
+
+
+#include <glibmm/i18n.h>
+#include <glibmm/miscutils.h>
+#include <glibmm/thread.h>
+
+#include "debug.hpp"
+#include "gvfssyncservice.hpp"
+#include "sharp/directory.hpp"
+#include "sharp/files.hpp"
+
+
+namespace gnote
+{
+namespace sync
+{
+
+
+GvfsSyncService::GvfsSyncService()
+  : m_initialized(false)
+  , m_enabled(false)
+{
+}
+
+void GvfsSyncService::initialize()
+{
+  m_initialized = true;
+  m_enabled = true;
+}
+
+void GvfsSyncService::shutdown()
+{
+  m_enabled = false;
+}
+
+void GvfsSyncService::post_sync_cleanup()
+{
+  unmount_sync();
+}
+
+bool GvfsSyncService::is_supported()
+{
+  return true;
+}
+
+bool GvfsSyncService::initialized()
+{
+  return m_initialized && m_enabled;
+}
+
+bool GvfsSyncService::test_sync_directory(const Glib::RefPtr<Gio::File> & path, const Glib::ustring & 
sync_uri, Glib::ustring & error)
+{
+  try {
+    if(sharp::directory_exists(path) == false) {
+      if(!sharp::directory_create(path)) {
+        DBG_OUT("Could not create \"%s\"", sync_uri.c_str());
+        error = _("Specified folder path does not exist, and Gnote was unable to create it.");
+        return false;
+      }
+    }
+    else {
+      // Test creating/writing/deleting a file
+      Glib::ustring test_path_base = Glib::build_filename(sync_uri, "test");
+      Glib::RefPtr<Gio::File> test_path = Gio::File::create_for_uri(test_path_base);
+      int count = 0;
+
+      // Get unique new file name
+      while(test_path->query_exists()) {
+        test_path = Gio::File::create_for_uri(test_path_base + TO_STRING(++count));
+      }
+
+      // Test ability to create and write
+      Glib::ustring test_line = "Testing write capabilities.";
+      auto stream = test_path->create_file();
+      stream->write(test_line);
+      stream->close();
+
+      if(!test_path->query_exists()) {
+        error = _("Failure writing test file");
+        return false;
+      }
+      Glib::ustring line = sharp::file_read_all_text(test_path);
+      if(line != test_line) {
+        error = _("Failure when checking test file contents");
+        return false;
+      }
+
+      // Test ability to delete
+      if(!test_path->remove()) {
+        error = _("Failure when trying to remove test file");
+        return false;
+      }
+    }
+
+    return true;
+  }
+  catch(Glib::Exception & e) {
+    error = e.what();
+    return false;
+  }
+  catch(std::exception & e) {
+    error = e.what();
+    return false;
+  }
+  catch(...) {
+    error = _("Unknown error");
+    return false;
+  }
+}
+
+bool GvfsSyncService::mount_async(const Glib::RefPtr<Gio::File> & path, const std::function<void(bool, const 
Glib::ustring &)> & completed, const Glib::RefPtr<Gio::MountOperation> & op)
+{
+  try {
+    path->find_enclosing_mount();
+    return true;
+  }
+  catch(Gio::Error & e) {
+  }
+
+  path->mount_enclosing_volume(op, [this, path, completed](Glib::RefPtr<Gio::AsyncResult> & result) {
+    Glib::ustring error;
+    try {
+      if(path->mount_enclosing_volume_finish(result)) {
+        m_mount = path->find_enclosing_mount();
+      }
+    }
+    catch(Glib::Error & e) {
+      error = e.what();
+    }
+    catch(...) {
+    }
+
+    completed(bool(m_mount), error);
+  });
+
+  return false;
+}
+
+bool GvfsSyncService::mount_sync(const Glib::RefPtr<Gio::File> & path, const 
Glib::RefPtr<Gio::MountOperation> & op)
+{
+  bool ret = true, done = false;
+  Glib::Mutex mutex;
+  Glib::Cond cond;
+  mutex.lock();
+  if(mount_async(path, [&ret, &mutex, &cond, &done](bool result, const Glib::ustring&) {
+       mutex.lock();
+       ret = result;
+       done = true;
+       cond.signal();
+       mutex.unlock();
+     }, op)) {
+    mutex.unlock();
+    return true;
+  }
+
+  while(!done) {
+    cond.wait(mutex);
+  }
+  mutex.unlock();
+  return ret;
+}
+
+void GvfsSyncService::unmount_async(const std::function<void()> & completed)
+{
+  if(!m_mount) {
+    completed();
+    return;
+  }
+
+  m_mount->unmount([this, completed](Glib::RefPtr<Gio::AsyncResult> & result) {
+    try {
+      m_mount->unmount_finish(result);
+    }
+    catch(...) {
+    }
+
+    m_mount.reset();
+    completed();
+  });
+}
+
+void GvfsSyncService::unmount_sync()
+{
+  if(!m_mount) {
+    return;
+  }
+
+  Glib::Mutex mutex;
+  Glib::Cond cond;
+  mutex.lock();
+  unmount_async([&mutex, &cond]{
+    mutex.lock();
+    cond.signal();
+    mutex.unlock();
+  });
+  cond.wait(mutex);
+  mutex.unlock();
+}
+
+
+}
+}
+
diff --git a/src/synchronization/gvfssyncservice.hpp b/src/synchronization/gvfssyncservice.hpp
new file mode 100644
index 00000000..1f92042e
--- /dev/null
+++ b/src/synchronization/gvfssyncservice.hpp
@@ -0,0 +1,59 @@
+/*
+ * gnote
+ *
+ * Copyright (C) 2019-2021 Aurimas Cernius
+ *
+ * This program is free software: you can redistribute it and/or modify
+ * it under the terms of the GNU General Public License as published by
+ * the Free Software Foundation, either version 3 of the License, or
+ * (at your option) any later version.
+ *
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with this program.  If not, see <http://www.gnu.org/licenses/>.
+ */
+
+
+#include <functional>
+#include "synchronization/syncserviceaddin.hpp"
+
+
+namespace gnote
+{
+namespace sync
+{
+
+class GvfsSyncService
+  : public SyncServiceAddin
+{
+public:
+  GvfsSyncService();
+
+  virtual void initialize() override;
+  virtual void shutdown() override;
+
+  virtual void post_sync_cleanup() override;
+  virtual bool is_supported() override;
+  virtual bool initialized() override;
+protected:
+  static bool test_sync_directory(const Glib::RefPtr<Gio::File> & path, const Glib::ustring & sync_uri, 
Glib::ustring & error);
+
+  bool mount_async(const Glib::RefPtr<Gio::File> & path, const std::function<void(bool, const Glib::ustring 
&)> & completed,
+    const Glib::RefPtr<Gio::MountOperation> & op = Glib::RefPtr<Gio::MountOperation>());
+  bool mount_sync(const Glib::RefPtr<Gio::File> & path, const Glib::RefPtr<Gio::MountOperation> & op = 
Glib::RefPtr<Gio::MountOperation>());
+  void unmount_async(const std::function<void()> & completed);
+  void unmount_sync();
+
+  bool m_initialized;
+  bool m_enabled;
+  Glib::ustring m_uri;
+  Glib::RefPtr<Gio::Mount> m_mount;
+};
+
+}
+}
+


[Date Prev][Date Next]   [Thread Prev][Thread Next]   [Thread Index] [Date Index] [Author Index]