Commits

Iñigo Serna committed f99e887

Store imported folders in lib db. Don't allow to import a folder twice

Comments (0)

Files changed (5)

 ============================================================================
-Last update:	Time-stamp: <2012-05-27 18:04:07 inigo>
+Last update:	Time-stamp: <2012-05-27 21:16:01 inigo>
 ============================================================================
 
 
 . added documentation skeleton
 . fix bug: stop loading covers if library changed 
 . add books: check folder to import must be located inside library base path
+. store imported folders in lib db. Don't allow to import a folder twice
 
 
 v0.6
+. fix bug: stop loading covers if creating new lib
 . before delete, bulkedit => thaw
 . refresh library:
   "Found 13 new books. 7 missing files, do you want to review and delete their entries in library?"
 class PathBooks(object):
     def __init__(self, path):
         self.path = path if path.endswith(os.sep) else path+os.sep
+        if db.check_folder_in_lib(self.path):
+            raise ValueError
         self.files = []
+        self.recursive = None
 
 
     def populate(self, recursive=True):
         """get all the e-books under a path"""
         log.info('Analyzing: %s' % self.path)
+        self.recursive = recursive
         fs = []
         if recursive:
             for root, dirs, files in os.walk(self.path, topdown=False):
             yield -1
         log.info('Analyzing %d files, %s' % (len(self.files),
                                              "with covers" if cover_from_file else "no covers"))
+        db.add_folder_parameters(self.path, self.recursive, pattern)
         for f in self.files:
             count += 1
             if db.check_book_exists(f):
 ##### DB Exceptions
 class DBInvalidException(Exception): pass
 
+class DBFolderNotImportedException(Exception): pass
+
 class DBBookNotExistException(Exception): pass
 
 class DBAuthorNotExistException(Exception): pass
     dbversion  INTEGER
 );
 
+CREATE TABLE folders (
+    path        TEXT       PRIMARY KEY NOT NULL,
+    recursive   BOOLEAN    NOT NULL,
+    pattern     TEXT,
+    added       DATETIME,
+    lastupdate  DATETIME
+);
+
 CREATE TABLE books (
     book_id       INTEGER    PRIMARY KEY NOT NULL,
     path          TEXT       UNIQUE NOT NULL,
 
 
 ########################################################################
+##### Imported folders within a library
+def check_folder_in_lib(path):
+    cur.execute('SELECT COUNT(*) FROM folders WHERE path=?', (path, ))
+    return cur.fetchone()[0] != 0
+
+
+def get_folders_in_lib():
+    cur.execute('SELECT path FROM folders')
+    return [row[0] for row in cur.fetchall()]
+
+
+def get_folder_parameters(path):
+    cur.execute('SELECT * FROM folders WHERE path=?', (path, ))
+    row = cur.fetchone()
+    if row is None:
+        raise DBFolderNotImportedException
+    else:
+        return row[1:2] # recursive, pattern
+
+
+def add_folder_parameters(path, recursive, pattern):
+    cur.execute('INSERT INTO folders VALUES (?, ?, ?, CURRENT_TIMESTAMP, CURRENT_TIMESTAMP)', (path, recursive, pattern))
+    conn.commit()
+
+
+def update_folder_update(path):
+    cur.execute('UPDATE folders SET lastupdate=CURRENT_TIMESTAMP WHERE path=?', (path, ))
+    conn.commit()
+
+
+########################################################################
 ##### Book
 class Book(object):
     VALID_FIELDS = ('id', 'path', 'format', 'size', 'added', 'modified',
 
 
     def on_add_books(self, menuitem, recursive):
-        w = AddBooks(self, self.cfg.patterns, self.cfg.active_lib.path, recursive)
+        imported_folders = db.get_folders_in_lib()
+        w = AddBooks(self, self.cfg.patterns, self.cfg.active_lib.path, recursive, imported_folders)
         while not w.res['finished']:
             process_events()
             time.sleep(.33)
         # add books
         dlg = DialogSplash(self, 'Analyzing "%s"' % path)
         process_events()
-        pb = PathBooks(unicode(path))
+        try:
+            pb = PathBooks(unicode(path))
+        except ValueError:
+            dlg.elliminate()
+            dlg_error(self, 'Error', 'Selected folder is already imported.\nRefresh library to add new books instead.')
+            return
         pb.populate(recursive)
         dlg.elliminate()
         if len(pb.files) == 0:
         name = entry.get_text().strip()
         page = self.get_nth_page(self.get_current_page())
         if len(name) > MAX_LIB_NAME:
-            dlg_error(self, 'ERROR!',
-                      'Library name maximum length is %d characters' % MAX_LIB_NAME)
+            dlg_error(self, 'Error', 'Library name maximum length is %d characters' % MAX_LIB_NAME)
             self.set_page_complete(page, False)
             return
         if name in self.libs_name:
-            dlg_error(self, 'ERROR!',
-                      '<i>"%s"</i> library already exists, please choose a different name.' % name)
+            dlg_error(self, 'Error', '<i>"%s"</i> library already exists, please choose a different name.' % name)
             self.set_page_complete(page, False)
             return
         for c in name:
             if c in punctuation:
-                dlg_error(self, 'ERROR!',
-                          'Library name <i>"%s"</i> contains invalid character <i>%c</i>, please choose a different name.' % (name, c))
+                dlg_error(self, 'Error', 'Library name <i>"%s"</i> contains invalid character <i>%c</i>, please choose a different name.' % (name, c))
                 self.set_page_complete(page, False)
                 break
         else:
 ########################################################################
 ##### Import folder
 class AddBooks(gtk.Assistant):
-    def __init__(self, parent, patterns=[], initialpath='', recursive=True):
+    def __init__(self, parent, patterns=[], initialpath='', recursive=True, imported_folders=[]):
         super(AddBooks, self).__init__()
         self.set_transient_for(parent)
         self.set_position(gtk.WIN_POS_CENTER_ON_PARENT)
         self.connect('apply', self.on_apply)
         self.connect('prepare', self.on_prepare)
         self.base_path = initialpath if initialpath!= '' else os.path.expandvars('$HOME')
+        self.imported_folders = imported_folders
         self.finished = False
         self.res = {'finished': False}
         # 1st. page: Introduction
 
 
     def check_folder(self, *args):
+        if self.get_current_page() != 1:
+            return
+        folder = self.btn_folder.get_filename()
+        if not folder.endswith(os.sep):
+            folder += os.sep
         page = self.get_nth_page(1)
-        if self.btn_folder.get_filename().startswith(self.base_path):
-            self.set_page_complete(page, True)
+        if folder.startswith(self.base_path):
+            if folder in self.imported_folders:
+                dlg_error(self, 'Error', 'Selected folder is already imported.\nRefresh library to add new books instead.')
+                self.set_page_complete(page, False)
+                return False
+            else:
+                self.set_page_complete(page, True)
+                return True
         else:
             self.set_page_complete(page, False)
-            dlg_error(self, 'ERROR!',
-                      'Folder to import must be located under library base path.')
-        return True
+            dlg_error(self, 'Error', 'Folder to import must be located under library base path.')
+            return False
 
 
     def check_pattern(self, *args):
     def on_prepare(self, assistant, *args):
         if self.get_current_page() == 2:
             if not self.check_folder():
-                dlg_error(self, 'ERROR!',
-                          'Folder to import must be located under library base path.')
+                dlg_error(self, 'Error', 'Selected folder is already imported.\nRefresh library to add new books instead.')
                 self.set_current_page(0)
                 return
             pattern = self.combobox_pattern.get_active_text()
             if not check_pattern(pattern):
-                dlg_error(self, 'ERROR!',
-                          '<i>%s</i> is not a valid pattern, please select a valid one.' % txt2pango(pattern))
+                dlg_error(self, 'Error', '<i>%s</i> is not a valid pattern, please select a valid one.' % txt2pango(pattern))
                 self.set_current_page(0)
                 return
         elif self.get_current_page() == 3: