[niepce: 4/14] Don't crash if the library is gone.



commit edd3f95ea31250a476bca1a1cb6eb3e469485a69
Author: Hubert Figuière <hub figuiere net>
Date:   Fri Jun 7 21:42:16 2013 -0400

    Don't crash if the library is gone.

 src/engine/db/library.cpp                |   16 +++++--
 src/engine/db/library.hpp                |    2 +-
 src/libraryclient/clientimpl.cpp         |    5 ++
 src/libraryclient/clientimpl.hpp         |    3 +-
 src/libraryclient/libraryclient.cpp      |    5 ++
 src/libraryclient/libraryclient.hpp      |    4 +-
 src/libraryclient/locallibraryserver.cpp |    1 -
 src/libraryclient/locallibraryserver.hpp |    6 ++-
 src/niepce/ui/niepcewindow.cpp           |   64 ++++++++++++++++++-----------
 src/niepce/ui/niepcewindow.hpp           |    8 +++-
 10 files changed, 77 insertions(+), 37 deletions(-)
---
diff --git a/src/engine/db/library.cpp b/src/engine/db/library.cpp
index 76f2eac..2ab46f0 100644
--- a/src/engine/db/library.cpp
+++ b/src/engine/db/library.cpp
@@ -60,12 +60,18 @@ Library::Library(const std::string & dir, const NotificationCenter::Ptr & nc)
 {
     DBG_OUT("dir = %s", dir.c_str());
     db::DBDesc desc("", 0, m_dbname);
-    m_dbdrv = m_dbmgr->connect_to_db(desc, "", "");
-    m_inited = init();
+    try {
+        m_dbdrv = m_dbmgr->connect_to_db(desc, "", "");
+        m_inited = init();
 
-    m_dbdrv->create_function0("rewrite_xmp",
-                              std::bind(&Library::triggerRewriteXmp,
-                                          this));
+        m_dbdrv->create_function0("rewrite_xmp",
+                                  std::bind(&Library::triggerRewriteXmp,
+                                            this));
+    }
+    catch(const std::exception &e)
+    {
+        ERR_OUT("Exception: %s", e.what());
+    }
 }
 
 Library::~Library()
diff --git a/src/engine/db/library.hpp b/src/engine/db/library.hpp
index dc63aa0..e4de6ad 100644
--- a/src/engine/db/library.hpp
+++ b/src/engine/db/library.hpp
@@ -76,7 +76,7 @@ public:
     Library(const std::string & dir, const fwk::NotificationCenter::Ptr & nc);
     virtual ~Library();
 
-    bool ok()
+    bool ok() const
         { return m_inited; }
     /** set the main library directory */
 //             void setMainDir(const std::string & dir)
diff --git a/src/libraryclient/clientimpl.cpp b/src/libraryclient/clientimpl.cpp
index f808f8d..203ca1b 100644
--- a/src/libraryclient/clientimpl.cpp
+++ b/src/libraryclient/clientimpl.cpp
@@ -55,6 +55,11 @@ ClientImpl::~ClientImpl()
     delete m_localLibrary;
 }
 
+bool ClientImpl::ok() const
+{
+    return m_localLibrary && m_localLibrary->ok();
+}
+
 tid_t ClientImpl::getAllKeywords()
 {
     tid_t id = LibraryClient::newTid();
diff --git a/src/libraryclient/clientimpl.hpp b/src/libraryclient/clientimpl.hpp
index 28d63c3..860a244 100644
--- a/src/libraryclient/clientimpl.hpp
+++ b/src/libraryclient/clientimpl.hpp
@@ -1,7 +1,7 @@
 /*
  * niepce - libraryclient/clientimpl.hpp
  *
- * Copyright (C) 2007-2008 Hubert Figuiere
+ * Copyright (C) 2007-2013 Hubert Figuiere
  *
  * 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
@@ -39,6 +39,7 @@ public:
                
                ClientImpl(const fwk::Moniker & moniker, const fwk::NotificationCenter::Ptr & nc);
                virtual ~ClientImpl();
+    bool ok() const;
 
                eng::tid_t getAllKeywords();
                eng::tid_t queryKeywordContent(eng::library_id_t id);
diff --git a/src/libraryclient/libraryclient.cpp b/src/libraryclient/libraryclient.cpp
index f09d9c5..178592f 100644
--- a/src/libraryclient/libraryclient.cpp
+++ b/src/libraryclient/libraryclient.cpp
@@ -46,6 +46,11 @@ LibraryClient::~LibraryClient()
     delete m_uidataprovider;
 }
 
+bool LibraryClient::ok() const
+{
+    return m_pImpl && m_pImpl->ok();
+}
+
 tid_t LibraryClient::newTid()
 {
     static tid_t id = 0;
diff --git a/src/libraryclient/libraryclient.hpp b/src/libraryclient/libraryclient.hpp
index 35f8dca..2811273 100644
--- a/src/libraryclient/libraryclient.hpp
+++ b/src/libraryclient/libraryclient.hpp
@@ -48,7 +48,9 @@ public:
     
     LibraryClient(const fwk::Moniker & moniker, const fwk::NotificationCenter::Ptr & nc);
     virtual ~LibraryClient();
-    
+    // @return false in case of error.
+    bool ok() const;
+
     static eng::tid_t newTid();
     /** get all the keywords 
      * @return transaction ID
diff --git a/src/libraryclient/locallibraryserver.cpp b/src/libraryclient/locallibraryserver.cpp
index 0ee9933..656d740 100644
--- a/src/libraryclient/locallibraryserver.cpp
+++ b/src/libraryclient/locallibraryserver.cpp
@@ -25,7 +25,6 @@ using eng::Op;
 
 namespace libraryclient {
 
-
        void LocalLibraryServer::execute(const Op::Ptr & _op)
        {
                (*_op)(m_library);
diff --git a/src/libraryclient/locallibraryserver.hpp b/src/libraryclient/locallibraryserver.hpp
index a9e8e19..08c4627 100644
--- a/src/libraryclient/locallibraryserver.hpp
+++ b/src/libraryclient/locallibraryserver.hpp
@@ -27,7 +27,6 @@
 #include "fwk/utils/worker.hpp"
 #include "engine/library/op.hpp"
 #include "engine/db/library.hpp"
-
 namespace libraryclient {
 
        class LocalLibraryServer
@@ -41,7 +40,10 @@ namespace libraryclient {
                        , m_library(eng::Library::Ptr(new eng::Library(dir, nc)))
                        {
                        }
-
+               bool ok() const
+                       {
+                               return m_library && m_library->ok();
+                       }
        protected:
                virtual void execute(const eng::Op::Ptr & _op);
 
diff --git a/src/niepce/ui/niepcewindow.cpp b/src/niepce/ui/niepcewindow.cpp
index 0a3da5d..948930d 100644
--- a/src/niepce/ui/niepcewindow.cpp
+++ b/src/niepce/ui/niepcewindow.cpp
@@ -340,34 +340,18 @@ void NiepceWindow::on_open_library()
         libMoniker = cfg.getValue("lastOpenLibrary", "");
     }
     if(libMoniker.empty()) {
-        Gtk::FileChooserDialog dialog(gtkWindow(), _("Create library"),
-                                      Gtk::FILE_CHOOSER_ACTION_CREATE_FOLDER);
-                       
-        dialog.add_button(Gtk::Stock::CANCEL, Gtk::RESPONSE_CANCEL);
-        dialog.add_button(_("Create"), Gtk::RESPONSE_OK);
-
-        int result = dialog.run();
-        Glib::ustring libraryToCreate;
-        switch(result)
-        {
-        case Gtk::RESPONSE_OK:
-            libraryToCreate = dialog.get_filename();
-            // pass it to the library
-            libMoniker = "local:";
-            libMoniker += libraryToCreate.c_str();
-            cfg.setValue("lastOpenLibrary", libMoniker);
-            DBG_OUT("created library %s", libMoniker.c_str());
-            break;
-        default:
-            break;
-        }
-                       
+        libMoniker = prompt_open_library();
     }
     else {
         DBG_OUT("last library is %s", libMoniker.c_str());
     }
     if(!libMoniker.empty()) {
-        open_library(libMoniker);
+        if(!open_library(libMoniker)) {
+            ERR_OUT("library %s cannot be open. Prompting.",
+                    libMoniker.c_str());
+            libMoniker = prompt_open_library();
+            open_library(libMoniker);
+        }
     }
 }
 
@@ -428,16 +412,48 @@ void NiepceWindow::on_lib_notification(const eng::LibNotification & ln)
     }
 }
 
+std::string NiepceWindow::prompt_open_library()
+{
+    std::string libMoniker;
+    Gtk::FileChooserDialog dialog(gtkWindow(), _("Create library"),
+                                  Gtk::FILE_CHOOSER_ACTION_CREATE_FOLDER);
+    dialog.add_button(Gtk::Stock::CANCEL, Gtk::RESPONSE_CANCEL);
+    dialog.add_button(_("Create"), Gtk::RESPONSE_OK);
+
+    int result = dialog.run();
+    Glib::ustring libraryToCreate;
+    switch(result)
+    {
+    case Gtk::RESPONSE_OK: {
+        Configuration & cfg = Application::app()->config();
+        libraryToCreate = dialog.get_filename();
+        // pass it to the library
+        libMoniker = "local:";
+        libMoniker += libraryToCreate.c_str();
+        cfg.setValue("lastOpenLibrary", libMoniker);
+        DBG_OUT("created library %s", libMoniker.c_str());
+        break;
+    }
+    default:
+        break;
+    }
+    return libMoniker;
+}
 
-void NiepceWindow::open_library(const std::string & libMoniker)
+bool NiepceWindow::open_library(const std::string & libMoniker)
 {
     m_libClient = LibraryClient::Ptr(new LibraryClient(fwk::Moniker(libMoniker),
                                                        m_notifcenter));
+    if(!m_libClient->ok()) {
+        m_libClient = nullptr;
+        return false;
+    }
     set_title(libMoniker);
     m_libClient->getAllLabels();
     if(!m_moduleshell) {
         _createModuleShell();
     }
+    return true;
 }
 
 void NiepceWindow::on_action_edit_labels()
diff --git a/src/niepce/ui/niepcewindow.hpp b/src/niepce/ui/niepcewindow.hpp
index f2025d6..247a72f 100644
--- a/src/niepce/ui/niepcewindow.hpp
+++ b/src/niepce/ui/niepcewindow.hpp
@@ -1,7 +1,7 @@
 /*
  * niepce - ui/niepcewindow.hpp
  *
- * Copyright (C) 2007-2009 Hubert Figuiere
+ * Copyright (C) 2007-2013 Hubert Figuiere
  *
  * 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
@@ -74,7 +74,11 @@ private:
     void init_ui(const Glib::RefPtr<Gtk::UIManager> & manager);
     void init_actions(const Glib::RefPtr<Gtk::UIManager> & manager);
 
-    void open_library(const std::string & libMoniker);
+    // UI to open library
+    std::string prompt_open_library();
+    // open the library
+    // @return false if error.
+    bool open_library(const std::string & libMoniker);
 
     void _createModuleShell();
                


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