Decrease startup time for large libraries with at least one composite custom column

This commit is contained in:
Kovid Goyal 2012-01-17 23:25:04 +05:30
commit d749690e79

View File

@ -7,8 +7,8 @@ __docformat__ = 'restructuredtext en'
The database used to store ebook metadata The database used to store ebook metadata
''' '''
import os, sys, shutil, cStringIO, glob, time, functools, traceback, re, \ import os, sys, shutil, cStringIO, glob, time, functools, traceback, re, \
json, uuid, hashlib, copy json, uuid, hashlib, copy, weakref
from collections import defaultdict from collections import defaultdict, MutableMapping, MutableSequence
import threading, random import threading, random
from itertools import repeat from itertools import repeat
from math import ceil from math import ceil
@ -81,6 +81,109 @@ class Tag(object):
def __repr__(self): def __repr__(self):
return str(self) return str(self)
class MutablePrintMixin(object): # {{{
def __str__(self):
self._resolve()
return str(self.values)
def __repr__(self):
self._resolve()
return repr(self.values)
def __unicode__(self):
self._resolve()
return unicode(self.values)
# }}}
class FormatMetadata(MutableMapping, MutablePrintMixin): # {{{
def __init__(self, db, id_, formats):
self.dbwref = weakref.ref(db)
self.id_ = id_
self.formats = formats
self._must_do = True
self.values = {}
def _resolve(self):
if self._must_do:
self._must_do = False
db = self.dbwref()
for f in self.formats:
try:
self.values[f] = db.format_metadata(self.id_, f)
except:
pass
def __contains__(self, key):
self._resolve()
return key in self.values
def __getitem__(self, fmt):
self._resolve()
return self.values[fmt]
def __setitem__(self, key, val):
self._resolve()
self.values[key] = val
def __delitem__(self, key):
self._resolve()
self.values.__delitem__(key)
def __len__(self):
self._resolve()
return len(self.values)
def __iter__(self):
self._resolve()
return self.values.__iter__()
class FormatsList(MutableSequence, MutablePrintMixin):
def __init__(self, formats, format_metadata):
self.formats = formats
self.format_metadata = format_metadata
self._must_do = True
self.values = []
def _resolve(self):
if self._must_do:
self._must_do = False
for f in self.formats:
try:
if f in self.format_metadata:
self.values.append(f)
except:
pass
def __getitem__(self, dex):
self._resolve()
return self.values[dex]
def __setitem__(self, key, dex):
self._resolve()
self.values[key] = dex
def __delitem__(self, dex):
self._resolve()
self.values.__delitem__(dex)
def __len__(self):
self._resolve()
return len(self.values)
def __iter__(self):
self._resolve()
return self.values.__iter__()
def insert(self, idx, val):
self._resolve()
self.values.insert(idx, val)
# }}}
class LibraryDatabase2(LibraryDatabase, SchemaUpgrade, CustomColumns): class LibraryDatabase2(LibraryDatabase, SchemaUpgrade, CustomColumns):
''' '''
@ -944,14 +1047,8 @@ class LibraryDatabase2(LibraryDatabase, SchemaUpgrade, CustomColumns):
good_formats = None good_formats = None
else: else:
formats = sorted(formats.split(',')) formats = sorted(formats.split(','))
good_formats = [] mi.format_metadata = FormatMetadata(self, id, formats)
for f in formats: good_formats = FormatsList(formats, mi.format_metadata)
try:
mi.format_metadata[f] = self.format_metadata(id, f)
except:
pass
else:
good_formats.append(f)
mi.formats = good_formats mi.formats = good_formats
tags = row[fm['tags']] tags = row[fm['tags']]
if tags: if tags: