2620: GEPS 031: Python 3 support - 3.2

round 2 for python 3 support:
* no more cmp, also not in sort and sorted
* bsddb needs bytestring keys
* gtk does not need utf-8 encoded anymore...


svn: r20658
This commit is contained in:
Benny Malengier 2012-11-15 08:08:31 +00:00
parent b9aafe5b49
commit 8b39b80dc8
45 changed files with 596 additions and 419 deletions

View File

@ -190,7 +190,10 @@ class CLIDbManager(object):
else:
retval["Locked?"] = "no"
retval["DB version"] = version
retval["Family tree"] = name.encode(sys.getfilesystemencoding())
if sys.version_info[0] < 3:
retval["Family tree"] = name.encode(sys.getfilesystemencoding())
else:
retval["Family tree"] = name
retval["Path"] = dirpath
retval["Last accessed"] = time.strftime('%x %X',
time.localtime(tval))
@ -202,7 +205,8 @@ class CLIDbManager(object):
"""
# make the default directory if it does not exist
dbdir = os.path.expanduser(config.get('behavior.database-path'))
dbdir = dbdir.encode(sys.getfilesystemencoding())
if sys.version_info[0] < 3:
dbdir = dbdir.encode(sys.getfilesystemencoding())
db_ok = make_dbdir(dbdir)
self.current_names = []
@ -211,7 +215,8 @@ class CLIDbManager(object):
dirpath = os.path.join(dbdir, dpath)
path_name = os.path.join(dirpath, NAME_FILE)
if os.path.isfile(path_name):
name = file(path_name).readline().strip()
file = open(path_name)
name = file.readline().strip()
(tval, last) = time_val(dirpath)
(enable, stock_id) = self.icon_values(dirpath, self.active,
@ -436,7 +441,8 @@ def find_next_db_dir():
while True:
base = "%x" % int(time.time())
dbdir = os.path.expanduser(config.get('behavior.database-path'))
dbdir = dbdir.encode(sys.getfilesystemencoding())
if sys.version_info[0] < 3:
dbdir = dbdir.encode(sys.getfilesystemencoding())
new_path = os.path.join(dbdir, base)
if not os.path.isdir(new_path):
break

View File

@ -105,12 +105,14 @@ DBERRS = (db.DBRunRecoveryError, db.DBAccessError,
def find_surname(key, data):
"""
Creating a surname from raw data of a person, to use for sort and index
returns a byte string
"""
return __index_surname(data[3][5])
def find_surname_name(key, data):
"""
Creating a surname from raw name, to use for sort and index
returns a byte string
"""
return __index_surname(data[5])
@ -118,6 +120,7 @@ def __index_surname(surn_list):
"""
All non pa/matronymic surnames are used in indexing.
pa/matronymic not as they change for every generation!
returns a byte string
"""
if surn_list:
surn = " ".join([x[0] for x in surn_list if not (x[3][0] in [
@ -532,9 +535,12 @@ class DbBsddbRead(DbReadBase, Callback):
Helper function for find_next_<object>_gramps_id methods
"""
index = prefix % map_index
while trans.get(str(index), txn=self.txn) is not None:
#in bytes
bindex = index.encode('utf-8')
while trans.get(bindex, txn=self.txn) is not None:
map_index += 1
index = prefix % map_index
bindex = index.encode('utf-8')
map_index += 1
return (map_index, index)
@ -620,7 +626,9 @@ class DbBsddbRead(DbReadBase, Callback):
return gid
def get_from_handle(self, handle, class_type, data_map):
data = data_map.get(str(handle))
if isinstance(handle, UNITYPE):
handle = handle.encode('utf-8')
data = data_map.get(handle)
if data:
newobj = class_type()
newobj.unserialize(data)
@ -737,8 +745,10 @@ class DbBsddbRead(DbReadBase, Callback):
return self.get_from_handle(handle, Tag, self.tag_map)
def __get_obj_from_gramps_id(self, val, tbl, class_, prim_tbl):
if isinstance(val, UNITYPE):
val = val.encode('utf-8')
try:
data = tbl.get(str(val), txn=self.txn)
data = tbl.get(val, txn=self.txn)
if data is not None:
obj = class_()
### FIXME: this is a dirty hack that works without no
@ -852,12 +862,9 @@ class DbBsddbRead(DbReadBase, Callback):
Return the default grouping name for a surname.
Return type is a unicode object
"""
if isinstance(surname, UNITYPE):
ssurname = surname.encode('utf-8')
return conv_dbstr_to_unicode(self.name_group.get(ssurname, ssurname))
else:
return conv_dbstr_to_unicode(self.name_group.get(surname, surname))
surname = surname.encode('utf-8')
return conv_dbstr_to_unicode(self.name_group.get(surname, surname))
def get_name_group_keys(self):
"""
@ -872,9 +879,8 @@ class DbBsddbRead(DbReadBase, Callback):
# The use of has_key seems allright because there is no write lock
# on the name_group table when this is called.
if isinstance(name, UNITYPE):
return name.encode('utf-8') in self.name_group
else:
return name in self.name_group
name = name.encode('utf-8')
return name in self.name_group
def get_number_of_records(self, table):
if not self.db_is_open:
@ -1148,8 +1154,9 @@ class DbBsddbRead(DbReadBase, Callback):
}
table = key2table[obj_key]
#return str(gramps_id) in table
return table.get(str(gramps_id), txn=self.txn) is not None
if isinstance(gramps_id, UNITYPE):
gramps_id = gramps_id.encode('utf-8')
return table.get(gramps_id, txn=self.txn) is not None
def find_initial_person(self):
person = self.get_default_person()
@ -1189,7 +1196,7 @@ class DbBsddbRead(DbReadBase, Callback):
id_number = gramps_id[len(str_prefix):]
if id_number.isdigit():
id_value = int(id_number, 10)
if len(str(id_value)) > nr_width:
if len(cuni(id_value)) > nr_width:
# The ID to be imported is too large to fit in the
# users format. For now just create a new ID,
# because that is also what happens with IDs that
@ -1383,13 +1390,13 @@ class DbBsddbRead(DbReadBase, Callback):
if person:
return person
elif (self.metadata is not None) and (not self.readonly):
self.metadata['default'] = None
self.metadata[b'default'] = None
return None
def get_default_handle(self):
"""Return the default Person of the database."""
if self.metadata is not None:
return self.metadata.get('default')
return self.metadata.get(b'default')
return None
def get_save_path(self):
@ -1505,8 +1512,10 @@ class DbBsddbRead(DbReadBase, Callback):
"""
Helper method for get_raw_<object>_data methods
"""
if isinstance(handle, UNITYPE):
handle = handle.encode('utf-8')
try:
return table.get(str(handle), txn=self.txn)
return table.get(handle, txn=self.txn)
except DBERRS as msg:
self.__log_error()
raise DbError(msg)
@ -1545,8 +1554,10 @@ class DbBsddbRead(DbReadBase, Callback):
"""
Helper function for has_<object>_handle methods
"""
if isinstance(handle, UNITYPE):
handle = handle.encode('utf-8')
try:
return table.get(str(handle), txn=self.txn) is not None
return table.get(handle, txn=self.txn) is not None
except DBERRS as msg:
self.__log_error()
raise DbError(msg)
@ -1611,62 +1622,94 @@ class DbBsddbRead(DbReadBase, Callback):
"""
return self.__has_handle(self.tag_map, handle)
def __sortbyperson_key(self, person):
return locale.strxfrm(find_surname(str(person),
self.person_map.get(str(person))))
def __sortbyperson_key(self, handle):
if isinstance(handle, UNITYPE):
handle = handle.encode('utf-8')
return locale.strxfrm(find_surname(handle,
self.person_map.get(handle)))
def __sortbyplace(self, first, second):
return locale.strcoll(self.place_map.get(str(first))[2],
self.place_map.get(str(second))[2])
if isinstance(first, UNITYPE):
first = first.encode('utf-8')
if isinstance(second, UNITYPE):
second = second.encode('utf-8')
return locale.strcoll(self.place_map.get(first)[2],
self.place_map.get(second)[2])
def __sortbyplace_key(self, place):
return locale.strxfrm(self.place_map.get(str(place))[2])
if isinstance(place, UNITYPE):
place = place.encode('utf-8')
return locale.strxfrm(self.place_map.get(place)[2])
def __sortbysource(self, first, second):
source1 = cuni(self.source_map[str(first)][2])
source2 = cuni(self.source_map[str(second)][2])
if isinstance(first, UNITYPE):
first = first.encode('utf-8')
if isinstance(second, UNITYPE):
second = second.encode('utf-8')
source1 = cuni(self.source_map[first][2])
source2 = cuni(self.source_map[second][2])
return locale.strcoll(source1, source2)
def __sortbysource_key(self, key):
source = cuni(self.source_map[str(key)][2])
if isinstance(key, UNITYPE):
key = key.encode('utf-8')
source = cuni(self.source_map[key][2])
return locale.strxfrm(source)
def __sortbycitation(self, first, second):
citation1 = cuni(self.citation_map[str(first)][3])
citation2 = cuni(self.citation_map[str(second)][3])
if isinstance(first, UNITYPE):
first = first.encode('utf-8')
if isinstance(second, UNITYPE):
second = second.encode('utf-8')
citation1 = cuni(self.citation_map[first][3])
citation2 = cuni(self.citation_map[second][3])
return locale.strcoll(citation1, citation2)
def __sortbycitation_key(self, key):
citation = cuni(self.citation_map[str(key)][3])
if isinstance(key, UNITYPE):
key = key.encode('utf-8')
citation = cuni(self.citation_map[key][3])
return locale.strxfrm(citation)
def __sortbymedia(self, first, second):
media1 = self.media_map[str(first)][4]
media2 = self.media_map[str(second)][4]
if isinstance(first, UNITYPE):
first = first.encode('utf-8')
if isinstance(second, UNITYPE):
second = second.encode('utf-8')
media1 = self.media_map[first][4]
media2 = self.media_map[second][4]
return locale.strcoll(media1, media2)
def __sortbymedia_key(self, key):
media = self.media_map[str(key)][4]
if isinstance(key, UNITYPE):
key = key.encode('utf-8')
media = self.media_map[key][4]
return locale.strxfrm(media)
def __sortbytag(self, first, second):
tag1 = self.tag_map[str(first)][1]
tag2 = self.tag_map[str(second)][1]
if isinstance(first, UNITYPE):
first = first.encode('utf-8')
if isinstance(second, UNITYPE):
second = second.encode('utf-8')
tag1 = self.tag_map[first][1]
tag2 = self.tag_map[second][1]
return locale.strcoll(tag1, tag2)
def __sortbytag_key(self, key):
tag = self.tag_map[str(key)][1]
if isinstance(key, UNITYPE):
key = key.encode('utf-8')
tag = self.tag_map[key][1]
return locale.strxfrm(tag)
def set_mediapath(self, path):
"""Set the default media path for database, path should be utf-8."""
if (self.metadata is not None) and (not self.readonly):
self.metadata['mediapath'] = path
self.metadata[b'mediapath'] = path
def get_mediapath(self):
"""Return the default media path of the database."""
if self.metadata is not None:
return self.metadata.get('mediapath', None)
return self.metadata.get(b'mediapath', None)
return None
def find_backlink_handles(self, handle, include_classes=None):

View File

@ -80,7 +80,7 @@ from ..utils.callback import Callback
from ..utils.cast import (conv_unicode_tosrtkey, conv_dbstr_to_unicode)
from ..updatecallback import UpdateCallback
from ..errors import DbError
from ..constfunc import win, conv_to_unicode
from ..constfunc import win, conv_to_unicode, cuni, UNITYPE
_LOG = logging.getLogger(DBLOGNAME)
LOG = logging.getLogger(".citation")
@ -165,7 +165,13 @@ KEY_TO_NAME_MAP = {PERSON_KEY: 'person',
#-------------------------------------------------------------------------
def find_idmap(key, data):
return str(data[1])
""" return id for association of secondary index.
returns a byte string
"""
val = data[1]
if isinstance(val, UNITYPE):
val = val.encode('utf-8')
return val
# Secondary database key lookups for reference_map table
# reference_map data values are of the form:
@ -173,10 +179,22 @@ def find_idmap(key, data):
# (referenced_object_class_name, referenced_object_handle))
def find_primary_handle(key, data):
return str((data)[0][1])
""" return handle for association of indexes
returns byte string
"""
val = (data)[0][1]
if isinstance(val, UNITYPE):
val = val.encode('utf-8')
return val
def find_referenced_handle(key, data):
return str((data)[1][1])
""" return handle for association of indexes
returns byte string
"""
val = (data)[1][1]
if isinstance(val, UNITYPE):
val = val.encode('utf-8')
return val
#-------------------------------------------------------------------------
#
@ -351,10 +369,13 @@ class DbBsddb(DbBsddbRead, DbWriteBase, UpdateCallback):
@catch_db_error
def set_default_person_handle(self, handle):
"""Set the default Person to the passed instance."""
#we store a byte string!
if isinstance(handle, UNITYPE):
handle = handle.encode('utf-8')
if not self.readonly:
# Start transaction
with BSDDBTxn(self.env, self.metadata) as txn:
txn.put('default', str(handle))
txn.put(b'default', handle)
self.emit('home-person-changed')
@catch_db_error
@ -366,7 +387,7 @@ class DbBsddb(DbBsddbRead, DbWriteBase, UpdateCallback):
elif (self.metadata) and (not self.readonly):
# Start transaction
with BSDDBTxn(self.env, self.metadata) as txn:
txn.put('default', None)
txn.put(b'default', None)
return None
def set_mediapath(self, path):
@ -374,7 +395,7 @@ class DbBsddb(DbBsddbRead, DbWriteBase, UpdateCallback):
if self.metadata and not self.readonly:
# Start transaction
with BSDDBTxn(self.env, self.metadata) as txn:
txn.put('mediapath', path)
txn.put(b'mediapath', path)
def __check_bdb_version(self, name):
"""Older version of Berkeley DB can't read data created by a newer
@ -399,12 +420,12 @@ class DbBsddb(DbBsddbRead, DbWriteBase, UpdateCallback):
@catch_db_error
def version_supported(self):
dbversion = self.metadata.get('version', default=0)
dbversion = self.metadata.get(b'version', default=0)
return ((dbversion <= _DBVERSION) and (dbversion >= _MINVERSION))
@catch_db_error
def need_upgrade(self):
dbversion = self.metadata.get('version', default=0)
dbversion = self.metadata.get(b'version', default=0)
return not self.readonly and dbversion < _DBVERSION
def __check_readonly(self, name):
@ -505,7 +526,7 @@ class DbBsddb(DbBsddbRead, DbWriteBase, UpdateCallback):
raise DbVersionError()
self.__load_metadata()
gstats = self.metadata.get('gender_stats', default=None)
gstats = self.metadata.get(b'gender_stats', default=None)
# Ensure version info in metadata
if not self.readonly:
@ -515,7 +536,7 @@ class DbBsddb(DbBsddbRead, DbWriteBase, UpdateCallback):
# New database. Set up the current version.
#self.metadata.put('version', _DBVERSION, txn=the_txn)
txn.put('version', _DBVERSION)
elif 'version' not in self.metadata:
elif b'version' not in self.metadata:
# Not new database, but the version is missing.
# Use 0, but it is likely to fail anyway.
txn.put('version', 0)
@ -605,7 +626,7 @@ class DbBsddb(DbBsddbRead, DbWriteBase, UpdateCallback):
def __load_metadata(self):
# name display formats
self.name_formats = self.metadata.get('name_formats', default=[])
self.name_formats = self.metadata.get(b'name_formats', default=[])
# upgrade formats if they were saved in the old way
for format_ix in range(len(self.name_formats)):
format = self.name_formats[format_ix]
@ -615,7 +636,7 @@ class DbBsddb(DbBsddbRead, DbWriteBase, UpdateCallback):
# database owner
try:
owner_data = self.metadata.get('researcher')
owner_data = self.metadata.get(b'researcher')
if owner_data:
if len(owner_data[0]) == 7: # Pre-3.3 format
owner_data = upgrade_researcher(owner_data)
@ -626,35 +647,35 @@ class DbBsddb(DbBsddbRead, DbWriteBase, UpdateCallback):
# bookmarks
meta = lambda meta: self.metadata.get(meta, default=[])
self.bookmarks.set(meta('bookmarks'))
self.family_bookmarks.set(meta('family_bookmarks'))
self.event_bookmarks.set(meta('event_bookmarks'))
self.source_bookmarks.set(meta('source_bookmarks'))
self.citation_bookmarks.set(meta('citation_bookmarks'))
self.repo_bookmarks.set(meta('repo_bookmarks'))
self.media_bookmarks.set(meta('media_bookmarks'))
self.place_bookmarks.set(meta('place_bookmarks'))
self.note_bookmarks.set(meta('note_bookmarks'))
self.bookmarks.set(meta(b'bookmarks'))
self.family_bookmarks.set(meta(b'family_bookmarks'))
self.event_bookmarks.set(meta(b'event_bookmarks'))
self.source_bookmarks.set(meta(b'source_bookmarks'))
self.citation_bookmarks.set(meta(b'citation_bookmarks'))
self.repo_bookmarks.set(meta(b'repo_bookmarks'))
self.media_bookmarks.set(meta(b'media_bookmarks'))
self.place_bookmarks.set(meta(b'place_bookmarks'))
self.note_bookmarks.set(meta(b'note_bookmarks'))
# Custom type values
self.family_event_names = set(meta('fevent_names'))
self.individual_event_names = set(meta('pevent_names'))
self.family_attributes = set(meta('fattr_names'))
self.individual_attributes = set(meta('pattr_names'))
self.marker_names = set(meta('marker_names'))
self.child_ref_types = set(meta('child_refs'))
self.family_rel_types = set(meta('family_rels'))
self.event_role_names = set(meta('event_roles'))
self.name_types = set(meta('name_types'))
self.origin_types = set(meta('origin_types'))
self.repository_types = set(meta('repo_types'))
self.note_types = set(meta('note_types'))
self.source_media_types = set(meta('sm_types'))
self.url_types = set(meta('url_types'))
self.media_attributes = set(meta('mattr_names'))
self.family_event_names = set(meta(b'fevent_names'))
self.individual_event_names = set(meta(b'pevent_names'))
self.family_attributes = set(meta(b'fattr_names'))
self.individual_attributes = set(meta(b'pattr_names'))
self.marker_names = set(meta(b'marker_names'))
self.child_ref_types = set(meta(b'child_refs'))
self.family_rel_types = set(meta(b'family_rels'))
self.event_role_names = set(meta(b'event_roles'))
self.name_types = set(meta(b'name_types'))
self.origin_types = set(meta(b'origin_types'))
self.repository_types = set(meta(b'repo_types'))
self.note_types = set(meta(b'note_types'))
self.source_media_types = set(meta(b'sm_types'))
self.url_types = set(meta(b'url_types'))
self.media_attributes = set(meta(b'mattr_names'))
# surname list
self.surname_list = meta('surname_list')
self.surname_list = meta(b'surname_list')
def __connect_secondary(self):
"""
@ -790,8 +811,8 @@ class DbBsddb(DbBsddbRead, DbWriteBase, UpdateCallback):
result_list = list(find_backlink_handles(handle))
"""
handle = str(handle)
if isinstance(handle, UNITYPE):
handle = handle.encode('utf-8')
# Use the secondary index to locate all the reference_map entries
# that include a reference to the object we are looking for.
referenced_cur = self.get_reference_map_referenced_cursor()
@ -925,25 +946,28 @@ class DbBsddb(DbBsddbRead, DbWriteBase, UpdateCallback):
Remove the reference specified by the key, preserving the change in
the passed transaction.
"""
if isinstance(key, UNITYPE):
key = key.encode('utf-8')
if not self.readonly:
if not transaction.batch:
old_data = self.reference_map.get(str(key), txn=txn)
transaction.add(REFERENCE_KEY, TXNDEL, str(key), old_data, None)
old_data = self.reference_map.get(key, txn=txn)
transaction.add(REFERENCE_KEY, TXNDEL, key, old_data, None)
#transaction.reference_del.append(str(key))
self.reference_map.delete(str(key), txn=txn)
self.reference_map.delete(key, txn=txn)
def __add_reference(self, key, data, transaction, txn):
"""
Add the reference specified by the key and the data, preserving the
change in the passed transaction.
"""
if isinstance(key, UNITYPE):
key = key.encode('utf-8')
if self.readonly or not key:
return
self.reference_map.put(str(key), data, txn=txn)
self.reference_map.put(key, data, txn=txn)
if not transaction.batch:
transaction.add(REFERENCE_KEY, TXNADD, str(key), None, data)
transaction.add(REFERENCE_KEY, TXNADD, key, None, data)
#transaction.reference_add.append((str(key), data))
@catch_db_error
@ -1030,45 +1054,45 @@ class DbBsddb(DbBsddbRead, DbWriteBase, UpdateCallback):
with BSDDBTxn(self.env, self.metadata) as txn:
# name display formats
txn.put('name_formats', self.name_formats)
txn.put(b'name_formats', self.name_formats)
# database owner
owner_data = self.owner.serialize()
txn.put('researcher', owner_data)
txn.put(b'researcher', owner_data)
# bookmarks
txn.put('bookmarks', self.bookmarks.get())
txn.put('family_bookmarks', self.family_bookmarks.get())
txn.put('event_bookmarks', self.event_bookmarks.get())
txn.put('source_bookmarks', self.source_bookmarks.get())
txn.put('citation_bookmarks', self.citation_bookmarks.get())
txn.put('place_bookmarks', self.place_bookmarks.get())
txn.put('repo_bookmarks', self.repo_bookmarks.get())
txn.put('media_bookmarks', self.media_bookmarks.get())
txn.put('note_bookmarks', self.note_bookmarks.get())
txn.put(b'bookmarks', self.bookmarks.get())
txn.put(b'family_bookmarks', self.family_bookmarks.get())
txn.put(b'event_bookmarks', self.event_bookmarks.get())
txn.put(b'source_bookmarks', self.source_bookmarks.get())
txn.put(b'citation_bookmarks', self.citation_bookmarks.get())
txn.put(b'place_bookmarks', self.place_bookmarks.get())
txn.put(b'repo_bookmarks', self.repo_bookmarks.get())
txn.put(b'media_bookmarks', self.media_bookmarks.get())
txn.put(b'note_bookmarks', self.note_bookmarks.get())
# gender stats
txn.put('gender_stats', self.genderStats.save_stats())
txn.put(b'gender_stats', self.genderStats.save_stats())
# Custom type values
txn.put('fevent_names', list(self.family_event_names))
txn.put('pevent_names', list(self.individual_event_names))
txn.put('fattr_names', list(self.family_attributes))
txn.put('pattr_names', list(self.individual_attributes))
txn.put('marker_names', list(self.marker_names))
txn.put('child_refs', list(self.child_ref_types))
txn.put('family_rels', list(self.family_rel_types))
txn.put('event_roles', list(self.event_role_names))
txn.put('name_types', list(self.name_types))
txn.put('origin_types', list(self.origin_types))
txn.put('repo_types', list(self.repository_types))
txn.put('note_types', list(self.note_types))
txn.put('sm_types', list(self.source_media_types))
txn.put('url_types', list(self.url_types))
txn.put('mattr_names', list(self.media_attributes))
txn.put(b'fevent_names', list(self.family_event_names))
txn.put(b'pevent_names', list(self.individual_event_names))
txn.put(b'fattr_names', list(self.family_attributes))
txn.put(b'pattr_names', list(self.individual_attributes))
txn.put(b'marker_names', list(self.marker_names))
txn.put(b'child_refs', list(self.child_ref_types))
txn.put(b'family_rels', list(self.family_rel_types))
txn.put(b'event_roles', list(self.event_role_names))
txn.put(b'name_types', list(self.name_types))
txn.put(b'origin_types', list(self.origin_types))
txn.put(b'repo_types', list(self.repository_types))
txn.put(b'note_types', list(self.note_types))
txn.put(b'sm_types', list(self.source_media_types))
txn.put(b'url_types', list(self.url_types))
txn.put(b'mattr_names', list(self.media_attributes))
# name display formats
txn.put('surname_list', self.surname_list)
txn.put(b'surname_list', self.surname_list)
self.metadata.close()
@ -1169,10 +1193,14 @@ class DbBsddb(DbBsddbRead, DbWriteBase, UpdateCallback):
if self.update_env_version:
versionpath = os.path.join(self.path, BDBVERSFN)
try:
with open(versionpath, "w") as version_file:
version_file.write(str(db.version()))
with open(versionpath, "wb") as version_file:
version = db.version()
if isinstance(version, UNITYPE):
version = version.encode('utf-8')
version_file.write(version)
except:
# Storing the version of Berkeley Db is not really vital.
print ("Error storing berkeley db version")
pass
try:
@ -1322,7 +1350,8 @@ class DbBsddb(DbBsddbRead, DbWriteBase, UpdateCallback):
if self.readonly or not handle:
return
handle = str(handle)
if isinstance(handle, UNITYPE):
handle = handle.encode('utf-8')
if transaction.batch:
with BSDDBTxn(self.env, data_map) as txn:
self.delete_primary_from_reference_map(handle, transaction,
@ -1346,6 +1375,8 @@ class DbBsddb(DbBsddbRead, DbWriteBase, UpdateCallback):
person = self.get_person_from_handle(handle)
self.genderStats.uncount_person (person)
self.remove_from_surname_list(person)
if isinstance(handle, UNITYPE):
handle = handle.encode('utf-8')
if transaction.batch:
with BSDDBTxn(self.env, self.person_map) as txn:
self.delete_primary_from_reference_map(handle, transaction,
@ -1354,7 +1385,7 @@ class DbBsddb(DbBsddbRead, DbWriteBase, UpdateCallback):
else:
self.delete_primary_from_reference_map(handle, transaction,
txn=self.txn)
self.person_map.delete(str(handle), txn=self.txn)
self.person_map.delete(handle, txn=self.txn)
transaction.add(PERSON_KEY, TXNDEL, handle, person.serialize(), None)
def remove_source(self, handle, transaction):
@ -1496,7 +1527,7 @@ class DbBsddb(DbBsddbRead, DbWriteBase, UpdateCallback):
else:
if isinstance(name, str):
uname = name
name = str(name)
name = name.encode('utf-8')
else:
uname = str(name)
try:
@ -1525,7 +1556,9 @@ class DbBsddb(DbBsddbRead, DbWriteBase, UpdateCallback):
return
obj.change = int(change_time or time.time())
handle = str(obj.handle)
handle = obj.handle
if isinstance(handle, UNITYPE):
handle = handle.encode('utf-8')
self.update_reference_map(obj, transaction, self.txn)
@ -1748,8 +1781,10 @@ class DbBsddb(DbBsddbRead, DbWriteBase, UpdateCallback):
transaction, change_time)
def get_from_handle(self, handle, class_type, data_map):
if isinstance(handle, UNITYPE):
handle = handle.encode('utf-8')
try:
data = data_map.get(str(handle), txn=self.txn)
data = data_map.get(handle, txn=self.txn)
except:
data = None
# under certain circumstances during a database reload,
@ -1938,7 +1973,7 @@ class DbBsddb(DbBsddbRead, DbWriteBase, UpdateCallback):
def gramps_upgrade(self, callback=None):
UpdateCallback.__init__(self, callback)
version = self.metadata.get('version', default=_MINVERSION)
version = self.metadata.get(b'version', default=_MINVERSION)
t = time.time()

View File

@ -117,7 +117,8 @@ PAT_AS_SURN = False
# avoid translations of shorter terms which appear in longer ones, eg
# namelast may not be mistaken with name, so namelast must first be
# converted to %k before name is converted.
def _make_cmp(a, b): return -cmp((len(a[1]),a[1]), (len(b[1]), b[1]))
##def _make_cmp(a, b): return -cmp((len(a[1]),a[1]), (len(b[1]), b[1]))
def _make_cmp_key(a): return (len(a[1]),a[1]) # set reverse to True!!
#-------------------------------------------------------------------------
#
@ -458,7 +459,7 @@ class NameDisplay(object):
"""
the_list = []
keys = sorted(self.name_formats, self._sort_name_format)
keys = sorted(self.name_formats, key=self.cmp_to_key(self._sort_name_format))
for num in keys:
if ((also_default or num) and
@ -468,6 +469,29 @@ class NameDisplay(object):
return the_list
def cmp_to_key(self, mycmp):
"""
python 2 to 3 conversion, python recipe http://code.activestate.com/recipes/576653/
Convert a cmp= function into a key= function
We use this in Gramps as understanding the old compare function is
not trivial. This should be replaced by a proper key function
"""
class K(object):
def __init__(self, obj, *args):
self.obj = obj
def __lt__(self, other):
return mycmp(self.obj, other.obj) < 0
def __gt__(self, other):
return mycmp(self.obj, other.obj) > 0
def __eq__(self, other):
return mycmp(self.obj, other.obj) == 0
def __le__(self, other):
return mycmp(self.obj, other.obj) <= 0
def __ge__(self, other):
return mycmp(self.obj, other.obj) >= 0
def __ne__(self, other):
return mycmp(self.obj, other.obj) != 0
return K
def _sort_name_format(self, x, y):
if x < 0:
if y < 0:
@ -942,7 +966,7 @@ class NameDisplay(object):
pass
else:
d_keys = [(code, _tuple[2]) for code, _tuple in d.items()]
d_keys.sort(_make_cmp) # reverse on length and by ikeyword
d_keys.sort(key=_make_cmp_key, reverse=True) # reverse on length and by ikeyword
for (code, ikeyword) in d_keys:
exp, keyword, ikeyword = d[code]
#ikeyword = unicode(ikeyword, "utf8")
@ -958,7 +982,7 @@ class NameDisplay(object):
pass
else:
d_keys = [(code, _tuple[1]) for code, _tuple in d.items()]
d_keys.sort(_make_cmp) # reverse sort on length and by keyword
d_keys.sort(key=_make_cmp_key, reverse=True) # reverse sort on length and by keyword
# if in double quotes, just use % codes
for (code, keyword) in d_keys:
exp, keyword, ikeyword = d[code]
@ -1024,6 +1048,6 @@ def fn(%s):
return cleanup_name("%s" %% (%s))""" % (args, new_fmt, ",".join(param))
exec(s)
return fn
return locals()['fn']
displayer = NameDisplay()

View File

@ -249,17 +249,20 @@ class Span(object):
else:
return (self.sort[0] + self.sort[1])
def __cmp__(self, other):
"""
Comparing two Spans for SORTING purposes.
Use cmp(abs(int(span1)), abs(int(span2))) for comparing
actual spans of times, as spans have directionality
as indicated by negative values.
"""
if other is None:
return cmp(int(self), -9999)
else:
return cmp(int(self), int(other))
## def __cmp__(self, other):
## """
## DEPRECATED - not available in python 3
##
## Comparing two Spans for SORTING purposes.
## Use cmp(abs(int(span1)), abs(int(span2))) for comparing
## actual spans of times, as spans have directionality
## as indicated by negative values.
## """
## raise NotImplementedError
## if other is None:
## return cmp(int(self), -9999)
## else:
## return cmp(int(self), int(other))
def as_age(self):
"""
@ -699,17 +702,64 @@ class Date(object):
self.sortval = source.sortval
self.newyear = source.newyear
def __cmp__(self, other):
## PYTHON 3 no __cmp__
## def __cmp__(self, other):
## """
## Compare two dates.
##
## Comparison function. Allows the usage of equality tests.
## This allows you do run statements like 'date1 <= date2'
## """
## if isinstance(other, Date):
## return cmp(self.sortval, other.sortval)
## else:
## return -1
# Can't use this (as is) as this breaks comparing dates to None
#def __eq__(self, other):
# return self.sortval == other.sortval
def __eq__(self, other):
"""
Compare two dates.
Comparison function. Allows the usage of equality tests.
This allows you do run statements like 'date1 <= date2'
Equality based on sort value, use is_equal/match instead if needed
"""
if isinstance(other, Date):
return cmp(self.sortval, other.sortval)
return self.sortval == other.sortval
else:
return -1
#indicate this is not supported
return False
def __ne__(self, other):
"""
Equality based on sort value, use is_equal/match instead if needed
"""
if isinstance(other, Date):
return self.sortval != other.sortval
else:
#indicate this is not supported
return True
def __le__(self, other):
"""
<= based on sort value, use match instead if needed
So this is different from using < which uses match!
"""
if isinstance(other, Date):
return self.sortval <= other.sortval
else:
#indicate this is not supported
return NotImplemented
def __ge__(self, other):
"""
>= based on sort value, use match instead if needed
So this is different from using > which uses match!
"""
if isinstance(other, Date):
return self.sortval >= other.sortval
else:
#indicate this is not supported
return NotImplemented
def __add__(self, other):
"""
@ -741,10 +791,6 @@ class Date(object):
else:
raise AttributeError("unknown date sub type: %s " % type(other))
# Can't use this (as is) as this breaks comparing dates to None
#def __eq__(self, other):
# return self.sortval == other.sortval
def __contains__(self, string):
"""
For use with "x in Date" syntax.
@ -759,7 +805,7 @@ class Date(object):
def __lt__(self, other):
"""
Comparison for less than.
Comparison for less than using match, use sortval instead if needed.
"""
return self.match(other, comparison="<")
@ -771,7 +817,7 @@ class Date(object):
def __gt__(self, other):
"""
Comparison for greater than.
Comparison for greater than using match, use sortval instead if needed.
"""
return self.match(other, comparison=">")

View File

@ -271,24 +271,50 @@ class GrampsType(GrampsTypeC):
def get_custom(self):
return self._CUSTOM
def __cmp__(self, value):
def __eq__(self, value):
if isinstance(value, int):
return cmp(self.__value, value)
return self.__value == value
elif isinstance(value, STRTYPE):
if self.__value == self._CUSTOM:
return cmp(self.__string, value)
return self.__string == value
else:
return cmp(self._I2SMAP.get(self.__value), value)
return self._I2SMAP.get(self.__value) == value
elif isinstance(value, tuple):
if self.__value == self._CUSTOM:
return cmp((self.__value, self.__string), value)
return (self.__value, self.__string) == value
else:
return cmp(self.__value, value[0])
return self.__value == value[0]
else:
if value.value == self._CUSTOM:
return cmp(self.__string, value.string)
return self.__string == value.string
else:
return cmp(self.__value, value.value)
return self.__value == value.value
def __ne__(self, value):
return not self.__eq__(value)
## Python 3 does not have __cmp__
## def __cmp__(self, value):
## print ('cmp', type(value), STRTYPE)
## if isinstance(value, int):
## return cmp(self.__value, value)
## elif isinstance(value, STRTYPE):
## print('ok!')
## if self.__value == self._CUSTOM:
## return cmp(self.__string, value)
## else:
## print (self._I2SMAP.get(self.__value), value, cmp(self._I2SMAP.get(self.__value), value))
## return cmp(self._I2SMAP.get(self.__value), value)
## elif isinstance(value, tuple):
## if self.__value == self._CUSTOM:
## return cmp((self.__value, self.__string), value)
## else:
## return cmp(self.__value, value[0])
## else:
## if value.value == self._CUSTOM:
## return cmp(self.__string, value.string)
## else:
## return cmp(self.__value, value.value)
value = property(__int__, __set_int, None, "Returns or sets integer value")
string = property(__str__, __set_str, None, "Returns or sets string value")

View File

@ -43,7 +43,7 @@ class SecondaryObject(BaseObject):
"""
def is_equal(self, source):
return cmp(self.serialize(), source.serialize()) == 0
return self.serialize() == source.serialize()
def is_equivalent(self, other):
"""

View File

@ -1089,10 +1089,12 @@ class PluginRegister(object):
continue
lenpd = len(self.__plugindata)
full_filename = os.path.join(dir, filename)
if sys.version_info[0] < 3:
full_filename = full_filename.encode(sys.getfilesystemencoding())
local_gettext = get_addon_translator(full_filename).gettext
try:
#execfile(full_filename,
exec(compile(open(full_filename.encode(sys.getfilesystemencoding())).read(), full_filename.encode(sys.getfilesystemencoding()), 'exec'),
exec(compile(open(full_filename).read(), full_filename, 'exec'),
make_environment(_=local_gettext),
{})
except ValueError as msg:

View File

@ -80,8 +80,27 @@ class RecentItem(object):
def get_time(self):
return self.time
def __cmp__(self, other_item):
return cmp(self.time, other_item.time)
def __eq__(self, other_item):
return self.time == other_item.time
def __ne__(self, other_item):
return self.time != other_item.time
def __lt__(self, other_item):
return self.time < other_item.time
def __gt__(self, other_item):
return self.time > other_item.time
def __le__(self, other_item):
return self.time <= other_item.time
def __ge__(self, other_item):
return self.time >= other_item.time
## Python 3, no __cmp__
## def __cmp__(self, other_item):
## return cmp(self.time, other_item.time)
#-------------------------------------------------------------------------
#

View File

@ -994,6 +994,7 @@ class SimpleAccess(object):
def by_date(event1, event2):
"""
DEPRECATED!
Sort function that will compare two events by their dates.
@param event1: first event

View File

@ -186,9 +186,9 @@ class SimpleTable(object):
idx = self._columns.index(self._sort_col)
# FIXME: move raw_data with this
if self._sort_reverse:
self._rows.sort(lambda a, b: -cmp(a[idx],b[idx]))
self._rows.sort(key=lambda a: a[idx], reverse=True)
else:
self._rows.sort(lambda a, b: cmp(a[idx],b[idx]))
self._rows.sort(key=lambda a: a[idx])
def write(self, document, column_widths=None):
doc = document.doc

View File

@ -54,27 +54,27 @@ class Sort(object):
def __init__(self, database):
self.database = database
def by_last_name(self, first_id, second_id):
"""Sort routine for comparing two last names. If last names are equal,
uses the given name and suffix"""
first = self.database.get_person_from_handle(first_id)
second = self.database.get_person_from_handle(second_id)
name1 = first.get_primary_name()
name2 = second.get_primary_name()
fsn = name1.get_surname()
ssn = name2.get_surname()
if fsn == ssn :
ffn = name1.get_first_name()
sfn = name2.get_first_name()
if ffn == sfn:
return locale.strcoll(name1.get_suffix(), name2.get_suffix())
else:
return locale.strcoll(ffn, sfn)
else:
return locale.strcoll(fsn, ssn)
## def by_last_name(self, first_id, second_id):
## """Sort routine for comparing two last names. If last names are equal,
## uses the given name and suffix"""
## first = self.database.get_person_from_handle(first_id)
## second = self.database.get_person_from_handle(second_id)
##
## name1 = first.get_primary_name()
## name2 = second.get_primary_name()
##
## fsn = name1.get_surname()
## ssn = name2.get_surname()
##
## if fsn == ssn :
## ffn = name1.get_first_name()
## sfn = name2.get_first_name()
## if ffn == sfn:
## return locale.strcoll(name1.get_suffix(), name2.get_suffix())
## else:
## return locale.strcoll(ffn, sfn)
## else:
## return locale.strcoll(fsn, ssn)
def by_last_name_key(self, first_id):
"""Sort routine for comparing two last names. If last names are equal,
@ -88,18 +88,18 @@ class Sort(object):
fsu = name1.get_suffix()
return locale.strxfrm(fsn + ffn + fsu)
def by_sorted_name(self, first_id, second_id):
"""
Sort routine for comparing two displayed names.
"""
first = self.database.get_person_from_handle(first_id)
second = self.database.get_person_from_handle(second_id)
name1 = _nd.sorted(first)
name2 = _nd.sorted(second)
return locale.strcoll(name1, name2)
## def by_sorted_name(self, first_id, second_id):
## """
## Sort routine for comparing two displayed names.
## """
##
## first = self.database.get_person_from_handle(first_id)
## second = self.database.get_person_from_handle(second_id)
##
## name1 = _nd.sorted(first)
## name2 = _nd.sorted(second)
##
## return locale.strcoll(name1, name2)
def by_sorted_name_key(self, first_id):
"""
@ -112,31 +112,31 @@ class Sort(object):
return locale.strxfrm(name1)
def by_birthdate(self, first_id, second_id):
"""Sort routine for comparing two people by birth dates. If the birth dates
are equal, sorts by name"""
first = self.database.get_person_from_handle(first_id)
second = self.database.get_person_from_handle(second_id)
birth1 = get_birth_or_fallback(self.database, first)
if birth1:
date1 = birth1.get_date_object()
else:
date1 = Date()
birth2 = get_birth_or_fallback(self.database, second)
if birth2:
date2 = birth2.get_date_object()
else:
date2 = Date()
dsv1 = date1.get_sort_value()
dsv2 = date2.get_sort_value()
val = cmp(dsv1, dsv2)
if val == 0:
return self.by_last_name(first_id, second_id)
return val
## def by_birthdate(self, first_id, second_id):
## """Sort routine for comparing two people by birth dates. If the birth dates
## are equal, sorts by name"""
## first = self.database.get_person_from_handle(first_id)
## second = self.database.get_person_from_handle(second_id)
##
## birth1 = get_birth_or_fallback(self.database, first)
## if birth1:
## date1 = birth1.get_date_object()
## else:
## date1 = Date()
##
## birth2 = get_birth_or_fallback(self.database, second)
## if birth2:
## date2 = birth2.get_date_object()
## else:
## date2 = Date()
##
## dsv1 = date1.get_sort_value()
## dsv2 = date2.get_sort_value()
##
## val = cmp(dsv1, dsv2)
## if val == 0:
## return self.by_last_name(first_id, second_id)
## return val
def by_birthdate_key(self, first_id):
"""Sort routine for comparing two people by birth dates. If the birth dates
@ -152,15 +152,15 @@ class Sort(object):
dsv1 = date1.get_sort_value()
return "%08d" % dsv1 + self.by_last_name_key(first_id)
def by_date(self, a_id, b_id):
"""Sort routine for comparing two events by their dates. """
if not (a_id and b_id):
return 0
a_obj = self.database.get_event_from_handle(a_id)
b_obj = self.database.get_event_from_handle(b_id)
dsv1 = a_obj.get_date_object().get_sort_value()
dsv2 = b_obj.get_date_object().get_sort_value()
return cmp(dsv1, dsv2)
## def by_date(self, a_id, b_id):
## """Sort routine for comparing two events by their dates. """
## if not (a_id and b_id):
## return 0
## a_obj = self.database.get_event_from_handle(a_id)
## b_obj = self.database.get_event_from_handle(b_id)
## dsv1 = a_obj.get_date_object().get_sort_value()
## dsv2 = b_obj.get_date_object().get_sort_value()
## return cmp(dsv1, dsv2)
def by_date_key(self, a_id):
"""Sort routine for comparing two events by their dates. """
@ -169,13 +169,13 @@ class Sort(object):
a_obj = self.database.get_event_from_handle(a_id)
return a_obj.get_date_object().get_sort_value()
def by_place_title(self, a_id, b_id):
"""Sort routine for comparing two places. """
if not (a_id and b_id):
return 0
a_obj = self.database.get_place_from_handle(a_id)
b_obj = self.database.get_place_from_handle(b_id)
return locale.strcoll(a_obj.title, b_obj.title)
## def by_place_title(self, a_id, b_id):
## """Sort routine for comparing two places. """
## if not (a_id and b_id):
## return 0
## a_obj = self.database.get_place_from_handle(a_id)
## b_obj = self.database.get_place_from_handle(b_id)
## return locale.strcoll(a_obj.title, b_obj.title)
def by_place_title_key(self, a_id):
"""Sort routine for comparing two places. """
@ -184,21 +184,21 @@ class Sort(object):
a_obj = self.database.get_place_from_handle(a_id)
return locale.strxfrm(a_obj.title)
def by_event_place(self, a_id, b_id):
"""Sort routine for comparing two events by their places. """
if not (a_id and b_id):
return 0
evt_a = self.database.get_event_from_handle(a_id)
evt_b = self.database.get_event_from_handle(b_id)
plc_a = self.database.get_place_from_handle(evt_a.get_place_handle())
plc_b = self.database.get_place_from_handle(evt_b.get_place_handle())
plc_a_title = ""
plc_b_title = ""
if plc_a:
plc_a_title = plc_a.title
if plc_b:
plc_b_title = plc_b.title
return locale.strcoll(plc_a_title, plc_b_title)
## def by_event_place(self, a_id, b_id):
## """Sort routine for comparing two events by their places. """
## if not (a_id and b_id):
## return 0
## evt_a = self.database.get_event_from_handle(a_id)
## evt_b = self.database.get_event_from_handle(b_id)
## plc_a = self.database.get_place_from_handle(evt_a.get_place_handle())
## plc_b = self.database.get_place_from_handle(evt_b.get_place_handle())
## plc_a_title = ""
## plc_b_title = ""
## if plc_a:
## plc_a_title = plc_a.title
## if plc_b:
## plc_b_title = plc_b.title
## return locale.strcoll(plc_a_title, plc_b_title)
def by_event_place_key(self, a_id):
"""Sort routine for comparing two events by their places. """
@ -209,13 +209,13 @@ class Sort(object):
plc_a_title = plc_a.title if plc_a else ""
return locale.strxfrm(plc_a_title)
def by_event_description(self, a_id, b_id):
"""Sort routine for comparing two events by their descriptions. """
if not (a_id and b_id):
return 0
evt_a = self.database.get_event_from_handle(a_id)
evt_b = self.database.get_event_from_handle(b_id)
return locale.strcoll(evt_a.get_description(), evt_b.get_description())
## def by_event_description(self, a_id, b_id):
## """Sort routine for comparing two events by their descriptions. """
## if not (a_id and b_id):
## return 0
## evt_a = self.database.get_event_from_handle(a_id)
## evt_b = self.database.get_event_from_handle(b_id)
## return locale.strcoll(evt_a.get_description(), evt_b.get_description())
def by_event_description_key(self, a_id):
"""Sort routine for comparing two events by their descriptions. """
@ -224,13 +224,13 @@ class Sort(object):
evt_a = self.database.get_event_from_handle(a_id)
return locale.strxfrm(evt_a.get_description())
def by_event_id(self, a_id, b_id):
"""Sort routine for comparing two events by their ID. """
if not (a_id and b_id):
return 0
evt_a = self.database.get_event_from_handle(a_id)
evt_b = self.database.get_event_from_handle(b_id)
return locale.strcoll(evt_a.get_gramps_id(), evt_b.get_gramps_id())
## def by_event_id(self, a_id, b_id):
## """Sort routine for comparing two events by their ID. """
## if not (a_id and b_id):
## return 0
## evt_a = self.database.get_event_from_handle(a_id)
## evt_b = self.database.get_event_from_handle(b_id)
## return locale.strcoll(evt_a.get_gramps_id(), evt_b.get_gramps_id())
def by_event_id_key(self, a_id):
"""Sort routine for comparing two events by their ID. """
@ -239,13 +239,13 @@ class Sort(object):
evt_a = self.database.get_event_from_handle(a_id)
return locale.strxfrm(evt_a.get_gramps_id())
def by_event_type(self, a_id, b_id):
"""Sort routine for comparing two events by their type. """
if not (a_id and b_id):
return 0
evt_a = self.database.get_event_from_handle(a_id)
evt_b = self.database.get_event_from_handle(b_id)
return locale.strcoll(str(evt_a.get_type()), str(evt_b.get_type()))
## def by_event_type(self, a_id, b_id):
## """Sort routine for comparing two events by their type. """
## if not (a_id and b_id):
## return 0
## evt_a = self.database.get_event_from_handle(a_id)
## evt_b = self.database.get_event_from_handle(b_id)
## return locale.strcoll(str(evt_a.get_type()), str(evt_b.get_type()))
def by_event_type_key(self, a_id):
"""Sort routine for comparing two events by their type. """
@ -254,13 +254,13 @@ class Sort(object):
evt_a = self.database.get_event_from_handle(a_id)
return locale.strxfrm(str(evt_a.get_type()))
def by_media_title(self,a_id,b_id):
"""Sort routine for comparing two media objects by their title. """
if not (a_id and b_id):
return False
a = self.database.get_object_from_handle(a_id)
b = self.database.get_object_from_handle(b_id)
return locale.strcoll(a.desc, b.desc)
## def by_media_title(self,a_id,b_id):
## """Sort routine for comparing two media objects by their title. """
## if not (a_id and b_id):
## return False
## a = self.database.get_object_from_handle(a_id)
## b = self.database.get_object_from_handle(b_id)
## return locale.strcoll(a.desc, b.desc)
def by_media_title_key(self, a_id):
"""Sort routine for comparing two media objects by their title. """
@ -268,4 +268,3 @@ class Sort(object):
return False
a = self.database.get_object_from_handle(a_id)
return locale.strxfrm(a.desc)

View File

@ -32,6 +32,7 @@ Utility functions to cast types
#
#-------------------------------------------------------------------------
import locale
import sys
#-------------------------------------------------------------------------
#
@ -44,8 +45,10 @@ from ..constfunc import conv_to_unicode, conv_to_unicode_direct, UNITYPE, STRTYP
"""
strxfrm needs it's unicode argument correctly cast before used.
"""
conv_unicode_tosrtkey = lambda x: locale.strxfrm(x.encode(codeset, 'replace'))
if sys.version_info[0] < 3:
conv_unicode_tosrtkey = lambda x: locale.strxfrm(x.encode(codeset, 'replace'))
else:
conv_unicode_tosrtkey = lambda x: locale.strxfrm(x)
if codeset == 'UTF-8':
conv_str_tosrtkey = lambda x: locale.strxfrm(x)
@ -56,6 +59,8 @@ else:
def conv_tosrtkey(value):
if isinstance(value, UNITYPE):
return conv_unicode_tosrtkey(value)
elif not isinstance(value, STRTYPE):
return conv_str_tosrtkey(str(value))
return conv_str_tosrtkey(value)
#strings in database are utf-8

View File

@ -271,6 +271,9 @@ class ConfigManager(object):
if sys.version_info[0] >= 3:
if raw_value[:2] == "u'":
raw_value = raw_value[1:]
elif raw_value.startswith('['):
raw_value = raw_value.replace(", u'", ", '")
raw_value = raw_value.replace("[u'", "['")
setting = opt.lower()
if oldstyle:
####################### Upgrade from oldstyle < 3.2

View File

@ -96,11 +96,11 @@ def get_keyword_from_translation(word):
def get_keywords():
""" Get all keywords, longest to shortest """
keys = list(KEY_TO_TRANS.keys())
keys.sort(lambda a,b: -cmp(len(a), len(b)))
keys.sort(key= lambda a: len(a), reverse=True)
return keys
def get_translations():
""" Get all translations, longest to shortest """
trans = list(TRANS_TO_KEY.keys())
trans.sort(lambda a,b: -cmp(len(a), len(b)))
trans.sort(key= lambda a: len(a), reverse=True)
return trans

View File

@ -26,6 +26,7 @@ Parses the lds.xml file to build the temple/code maps
from ..const import DATA_DIR
import os
import sys
import logging
from xml.parsers.expat import ParserCreate
@ -51,7 +52,10 @@ class LdsTemples(object):
lds_filename = os.path.join(DATA_DIR, "lds.xml")
try:
xml_file = open(os.path.expanduser(lds_filename))
if sys.version_info[0] < 3:
xml_file = open(os.path.expanduser(lds_filename))
else:
xml_file = open(os.path.expanduser(lds_filename), 'rb')
parser = ParserCreate()
parser.StartElementHandler = self.__start_element
parser.EndElementHandler = self.__end_element

View File

@ -167,7 +167,7 @@ class StandardCustomSelector(object):
"""
Fill with data
"""
keys = sorted(self.mapping, self.by_value)
keys = sorted(self.mapping, key=self.by_value)
index = 0
for key in keys:
if key != self.custom_key:
@ -190,13 +190,11 @@ class StandardCustomSelector(object):
self.active_index = index
index += 1
def by_value(self, first, second):
def by_value(self, val):
"""
Method for sorting keys based on the values.
"""
fvalue = self.mapping[first]
svalue = self.mapping[second]
return locale.strcoll(fvalue, svalue)
return locale.strxfrm(self.mapping[val])
def get_values(self):
"""

View File

@ -191,7 +191,10 @@ class ErrorDialog(Gtk.MessageDialog):
class RunDatabaseRepair(ErrorDialog):
def __init__(self, msg, parent=None):
msg = cuni(str(msg).decode(sys.getfilesystemencoding()))
if sys.version_info[0] < 3:
msg = cuni(str(msg).decode(sys.getfilesystemencoding()))
else:
msg = str(msg)
ErrorDialog.__init__(
self,
_('Error detected in database'),
@ -203,7 +206,10 @@ class RunDatabaseRepair(ErrorDialog):
class DBErrorDialog(ErrorDialog):
def __init__(self, msg, parent=None):
msg = cuni(str(msg).decode(sys.getfilesystemencoding()))
if sys.version_info[0] < 3:
msg = cuni(str(msg).decode(sys.getfilesystemencoding()))
else:
msg = str(msg)
ErrorDialog.__init__(
self,
_("Low level database corruption detected"),

View File

@ -21,6 +21,8 @@
# $Id$
import sys
#-------------------------------------------------------------------------
#
# GTK libraries
@ -53,7 +55,10 @@ class BackRefModel(Gtk.ListStore):
self.db = db
self.sref_list = sref_list
self.count = 0
self.idle = GObject.idle_add(self.load_model().next)
if sys.version_info[0] < 3:
self.idle = GObject.idle_add(self.load_model().next)
else:
self.idle = GObject.idle_add(self.load_model().__next__)
def destroy(self):
GObject.source_remove(self.idle)

View File

@ -114,7 +114,8 @@ class SurnameTab(EmbeddedList):
no = NameOriginType()
self.cmborig = Gtk.ListStore(GObject.TYPE_INT, GObject.TYPE_STRING)
self.cmborigmap = no.get_map().copy()
keys = sorted(self.cmborigmap, self.by_value)
#sort the keys based on the value
keys = sorted(self.cmborigmap, key=lambda x: locale.strxfrm(self.cmborigmap[x]))
for key in keys:
if key != no.get_custom():
self.cmborig.append(row=[key, self.cmborigmap[key]])
@ -154,13 +155,13 @@ class SurnameTab(EmbeddedList):
self.columns.append(column)
self.tree.append_column(column)
def by_value(self, first, second):
"""
Method for sorting keys based on the values.
"""
fvalue = self.cmborigmap[first]
svalue = self.cmborigmap[second]
return locale.strcoll(fvalue, svalue)
## def by_value(self, first, second):
## """
## Method for sorting keys based on the values.
## """
## fvalue = self.cmborigmap[first]
## svalue = self.cmborigmap[second]
## return locale.strcoll(fvalue, svalue)
def get_data(self):
return self.obj.get_surname_list()

View File

@ -455,8 +455,7 @@ class EditCitation(EditPrimary):
def source_is_empty(self, obj):
empty_object = Source()
return cmp(obj.serialize()[1:],
empty_object.serialize()[1:]) == 0
return obj.serialize()[1:] == empty_object.serialize()[1:]
def source_uses_duplicate_id(self, obj):
"""
@ -495,12 +494,10 @@ class EditCitation(EditPrimary):
cmp_obj = orig
else:
cmp_obj = self.empty_object()
return cmp(cmp_obj.serialize(True)[1:],
self.obj.serialize(True)[1:]) != 0
return cmp_obj.serialize(True)[1:] != self.obj.serialize(True)[1:]
else:
cmp_obj = self.empty_object()
return cmp(cmp_obj.serialize(True)[1:],
self.obj.serialize()[1:]) != 0
return cmp_obj.serialize(True)[1:] != self.obj.serialize()[1:]
def source_data_has_changed(self):
"""
@ -514,12 +511,10 @@ class EditCitation(EditPrimary):
cmp_obj = orig
else:
cmp_obj = Source()
return cmp(cmp_obj.serialize()[1:],
self.source.serialize()[1:]) != 0
return cmp_obj.serialize()[1:] != self.source.serialize()[1:]
else:
cmp_obj = Source()
return cmp(cmp_obj.serialize()[1:],
self.source.serialize()[1:]) != 0
return cmp_obj.serialize()[1:] != self.source.serialize()[1:]
class DeleteCitationQuery(object):
def __init__(self, dbstate, uistate, citation, the_lists):

View File

@ -261,7 +261,7 @@ class EditEvent(EditPrimary):
self.db.add_event(self.obj, trans)
else:
orig = self.get_from_handle(self.obj.handle)
if cmp(self.obj.serialize(), orig.serialize()):
if self.obj.serialize() != orig.serialize():
with DbTxn(_("Edit Event (%s)") % self.obj.get_gramps_id(),
self.db) as trans:
if not self.obj.get_gramps_id():
@ -288,12 +288,10 @@ class EditEvent(EditPrimary):
cmp_obj = orig
else:
cmp_obj = self.empty_object()
return cmp(cmp_obj.serialize(True)[1:],
self.obj.serialize(True)[1:]) != 0
return cmp_obj.serialize(True)[1:] != self.obj.serialize(True)[1:]
else:
cmp_obj = self.empty_object()
return cmp(cmp_obj.serialize(True)[1:],
self.obj.serialize()[1:]) != 0
return cmp_obj.serialize(True)[1:] != self.obj.serialize()[1:]
class EditPersonEvent(EditEvent):

View File

@ -1070,7 +1070,7 @@ class EditFamily(EditPrimary):
self.db.commit_person(child, trans)
self.db.add_family(self.obj, trans)
elif cmp(original.serialize(),self.obj.serialize()):
elif original.serialize() != self.obj.serialize():
with DbTxn(_("Edit Family"), self.db) as trans:

View File

@ -324,12 +324,10 @@ class EditMedia(EditPrimary):
cmp_obj = orig
else:
cmp_obj = self.empty_object()
return cmp(cmp_obj.serialize(True)[1:],
self.obj.serialize(True)[1:]) != 0
return cmp_obj.serialize(True)[1:] != self.obj.serialize(True)[1:]
else:
cmp_obj = self.empty_object()
return cmp(cmp_obj.serialize(True)[1:],
self.obj.serialize()[1:]) != 0
return cmp_obj.serialize(True)[1:] != self.obj.serialize()[1:]
class DeleteMediaQuery(object):

View File

@ -161,8 +161,7 @@ class EditPrimary(ManagedWindow, DbGUIElement):
self.__tabs = None
def object_is_empty(self):
return cmp(self.obj.serialize()[1:],
self.empty_object().serialize()[1:]) == 0
return self.obj.serialize()[1:] == self.empty_object().serialize()[1:]
def define_ok_button(self, button, function):
self.ok_button = button
@ -258,12 +257,10 @@ class EditPrimary(ManagedWindow, DbGUIElement):
cmp_obj = orig
else:
cmp_obj = self.empty_object()
return cmp(cmp_obj.serialize()[1:],
self.obj.serialize()[1:]) != 0
return cmp_obj.serialize()[1:] != self.obj.serialize()[1:]
else:
cmp_obj = self.empty_object()
return cmp(cmp_obj.serialize()[1:],
self.obj.serialize()[1:]) != 0
return cmp_obj.serialize()[1:] != self.obj.serialize()[1:]
def save(self, *obj):
""" Save changes and close. Inheriting classes must implement this

View File

@ -107,14 +107,6 @@ _name2typeclass = {
_('Surname origin type:'): NameOriginType,
}
#-------------------------------------------------------------------------
#
# Sorting function for the filter rules
#
#-------------------------------------------------------------------------
def by_rule_name(f, s):
return cmp(f.name, s.name)
#-------------------------------------------------------------------------
#
# MyBoolean - check button with standard interface
@ -597,7 +589,7 @@ class EditRule(ManagedWindow):
else:
self.sel_class = None
keys = sorted(the_map, by_rule_name, reverse=True)
keys = sorted(the_map, key=lambda x: x.name, reverse=True)
catlist = sorted(set(class_obj.category for class_obj in keys))
for category in catlist:

View File

@ -292,7 +292,7 @@ class ListModel(object):
"""
val = self.model.get_sort_column_id()
col = val[0]
if col < 0:
if col is None or col < 0:
return
if col > 0:
self.model.set_sort_column_id(col, val[1])

View File

@ -208,7 +208,7 @@ class PluginDialog(ManagedWindow):
node = self.store.insert_after(None, prev)
self.store.set(node, 0, key)
next = None
data.sort(lambda x, y: cmp(x.name, y.name))
data.sort(key=lambda x: x.name)
for item in data:
next = self.store.insert_after(node, next)
ilist.append((next, item))

View File

@ -157,7 +157,7 @@ def create_quickreport_menu(category,dbstate,uistate, handle) :
#add tuple function, translated name, name, status
showlst.append(pdata)
showlst.sort(by_menu_name)
showlst.sort(key=lambda x: x.name)
for pdata in showlst:
new_key = pdata.id.replace(' ', '-')
ofile.write('<menuitem action="%s"/>' % new_key)
@ -168,9 +168,6 @@ def create_quickreport_menu(category,dbstate,uistate, handle) :
return (ofile.getvalue(), actions)
def by_menu_name(first, second):
return cmp(first.name, second.name)
def make_quick_report_callback(pdata, category, dbstate, uistate, handle):
return lambda x: run_report(dbstate, uistate, category, handle, pdata)

View File

@ -24,7 +24,7 @@
Utility functions that depend on GUI components or for GUI components
"""
from __future__ import print_function
from __future__ import print_function, division
#-------------------------------------------------------------------------
#
@ -463,7 +463,7 @@ def hex_to_rgb_float(value):
"""
value = value.lstrip('#')
lenv = len(value)
return tuple(int(value[i:i+lenv/3], 16)/256.0 for i in range(0, lenv, lenv/3))
return tuple(int(value[i:i+lenv//3], 16)/256.0 for i in range(0, lenv, lenv//3))
def hex_to_rgb(value):
"""
@ -471,7 +471,7 @@ def hex_to_rgb(value):
"""
value = value.lstrip('#')
lenv = len(value)
return tuple(int(value[i:i+lenv/3], 16) for i in range(0, lenv, lenv/3))
return tuple(int(value[i:i+lenv//3], 16) for i in range(0, lenv, lenv//3))
def rgb_to_hex(rgb):
"""

View File

@ -1372,7 +1372,8 @@ class ViewManager(CLIManager):
value = dialog.run()
if value:
(filename, title) = value
filename = filename.encode(sys.getfilesystemencoding())
if sys.version_info[0] < 3:
filename = filename.encode(sys.getfilesystemencoding())
self.db_loader.read_file(filename)
self._post_load_newdb(filename, 'x-directory/normal', title)

View File

@ -566,7 +566,7 @@ class EditTag(object):
self.db.add_tag(self.tag, trans)
else:
orig = self.db.get_tag_from_handle(self.tag.get_handle())
if cmp(self.tag.serialize(), orig.serialize()):
if self.tag.serialize() != orig.serialize():
msg = _("Edit Tag (%s)") % self.tag.get_name()
with DbTxn(msg, self.db) as trans:
self.db.commit_tag(self.tag, trans)

View File

@ -768,7 +768,7 @@ class FlatBaseModel(GObject.Object, Gtk.TreeModel):
#print 'do_get_val', iter, iter.user_data, col
handle = self.node_map._index2hndl[iter.user_data][1]
if handle != self.prev_handle:
data = self.map(str(handle))
data = self.map(handle)
if data is None:
#object is no longer present
return ''
@ -780,8 +780,8 @@ class FlatBaseModel(GObject.Object, Gtk.TreeModel):
return val
else:
#GTK 3 should convert unicode objects automatically, but this
# gives wrong column values, so we convert
if isinstance(val, UNITYPE):
# gives wrong column values, so we convert for python 2.7
if not isinstance(val, str):
return val.encode('utf-8')
else:
return val

View File

@ -204,11 +204,12 @@ class PeopleBaseModel(object):
name = self.lru_name[handle]
else:
name = name_displayer.raw_display_name(data[COLUMN_NAME])
# internally we work with utf-8
if isinstance(name, UNITYPE):
# internally we work with utf-8 for python 2.7
if not isinstance(name, str):
name = name.encode('utf-8')
if not self._in_build:
self.lru_name[handle] = name
return name
def column_spouse(self, data):

View File

@ -891,8 +891,8 @@ class TreeBaseModel(GObject.Object, Gtk.TreeModel):
# according to column_defs table
val = self._get_value(node.handle, col, node.secondary)
#GTK 3 should convert unicode objects automatically, but this
# gives wrong column values, so we convert
if isinstance(val, UNITYPE):
# gives wrong column values, so we convert, so we convert for python 2.7
if not isinstance(val, str):
return val.encode('utf-8')
else:
return val

View File

@ -35,6 +35,7 @@ __all__ = ["MonitoredCheckbox", "MonitoredEntry",
import logging
_LOG = logging.getLogger(".widgets.monitoredwidgets")
import locale
import sys
#-------------------------------------------------------------------------
#
@ -140,7 +141,11 @@ class MonitoredEntry(object):
self.obj.connect(signal, callback, *data)
def _on_change(self, obj):
self.set_val(cuni(obj.get_text(), 'utf-8'))
if sys.version_info[0] < 3:
self.set_val(cuni(obj.get_text(), 'utf-8'))
else:
#all is unicode
self.set_val(obj.get_text())
if self.changed:
self.changed(obj)

View File

@ -761,11 +761,6 @@ class StatisticsChart(Report):
#print heading
#print table[1]
def lookup_compare(self, a, b):
"compare given keys according to corresponding lookup values"
return cmp(self.lookup_items[a], self.lookup_items[b])
def index_items(self, data, sort, reverse):
"""creates & stores a sorted index for the items"""
@ -777,8 +772,8 @@ class StatisticsChart(Report):
self.lookup_items = data
# then sort by value
index.sort(self.lookup_compare,
reverse=True if reverse else False)
index.sort(key=lambda x: self.lookup_items[x],
reverse=True if reverse else False)
return index

View File

@ -118,16 +118,6 @@ QUALITY_MAP = {
Citation.CONF_VERY_LOW : "0",
}
#-------------------------------------------------------------------------
#
# sort_by_gramps_id
#
#-------------------------------------------------------------------------
def sort_by_gramps_id(first, second):
"""
Sort objects by their Gramps ID.
"""
return cmp(first.gramps_id, second.gramps_id)
#-------------------------------------------------------------------------
#

View File

@ -310,8 +310,7 @@ class VCardWriter(object):
[self.db.get_event_from_handle(ref.ref) for ref in event_refs]
if event.get_type() == EventType(EventType.OCCUPATION)]
if len(events) > 0:
events.sort(cmp=lambda x, y: cmp(x.get_date_object(),
y.get_date_object()))
events.sort(key=lambda x: x.get_date_object())
occupation = events[-1].get_description()
if occupation:
self.writeln("ROLE:%s" % occupation)

View File

@ -1089,11 +1089,18 @@ class GedcomInfoDB(object):
self.standard = GedcomDescription("GEDCOM 5.5 standard")
self.standard.set_dest("GEDCOM 5.5")
try:
filepath = os.path.join(DATA_DIR,"gedcom.xml")
ged_file = open(filepath.encode('iso8859-1'),"r")
except:
return
if sys.version_info[0] < 3:
try:
filepath = os.path.join(DATA_DIR, "gedcom.xml")
ged_file = open(filepath.encode('iso8859-1'), "r")
except:
return
else:
try:
filepath = os.path.join(DATA_DIR, "gedcom.xml")
ged_file = open(filepath, "rb")
except:
return
parser = GedInfoParser(self)
parser.parse(ged_file)

View File

@ -269,8 +269,9 @@ def find_records(db, filter, top_size, callname):
_record(family_shortest, family_longest,
duration, name, 'Family', family.handle, top_size)
return [(text, varname, locals()[varname])
#python 3 workaround: assign locals to tmp so we work with runtime version
tmp = locals()
return [(text, varname, tmp[varname])
for (text, varname, default) in RECORDS]
def _record(lowest, highest, value, text, handle_type, handle, top_size):
@ -284,7 +285,7 @@ def _record(lowest, highest, value, text, handle_type, handle, top_size):
if lowest is not None:
lowest.append((high_value, value, text, handle_type, handle))
lowest.sort(lambda a, b: cmp(a[0], b[0])) # FIXME: Ist das lambda notwendig?
lowest.sort(key=lambda a: a[0]) # FIXME: Ist das lambda notwendig?
for i in range(top_size, len(lowest)):
if lowest[i-1][0] < lowest[i][0]:
del lowest[i:]

View File

@ -50,7 +50,7 @@ def run(database, document, person):
event_list += sdb.events(family)
# Sort the events by their date
event_list.sort(by_date)
event_list.sort(key=lambda x: x.get_date_object())
# display the results
@ -93,8 +93,8 @@ def run_fam(database, document, family):
event_list_children += [(child, x) for x in sdb.events(child)]
# Sort the events by their date
event_list.sort(fam_sort)
event_list_children.sort(fam_sort)
event_list.sort(key=lambda x: x[1].get_date_object())
event_list_children.sort(key=lambda x: x[1].get_date_object())
# display the results
@ -123,17 +123,3 @@ def run_fam(database, document, family):
sdb.event_place(event))
document.has_data = True
stab.write(sdoc)
def fam_sort(event1, event2):
"""
Sort function that will compare two events by their dates.
@param event1: first event
@type event1: L{Event}
@param event2: second event
@type event2: L{Event}
@return: Returns -1 if event1 < event2, 0 if they are equal, and
1 if they are the same.
@rtype: int
"""
return by_date(event1[1],event2[1])

View File

@ -171,7 +171,7 @@ class PlaceReport(Report):
"""
event_handles = [event_handle for (object_type, event_handle) in
self.database.find_backlink_handles(handle)]
event_handles.sort(self.sort.by_date)
event_handles.sort(key=self.sort.by_date_key)
if event_handles:
self.doc.start_paragraph("PLC-Section")
@ -311,7 +311,7 @@ class PlaceReport(Report):
for entry in keys:
people = entry
person_dict[entry].sort(self.sort.by_date)
person_dict[entry].sort(key=self.sort.by_date_key)
for evt_handle in person_dict[entry]:
event = self.database.get_event_from_handle(evt_handle)
if event:

View File

@ -199,8 +199,8 @@ class EventComparison(tool.Tool,ManagedWindow):
#
#
#-------------------------------------------------------------------------
def by_value(first,second):
return cmp(second[0],first[0])
##def by_value(first,second):
## return cmp(second[0],first[0])
#-------------------------------------------------------------------------
#
@ -244,7 +244,7 @@ class DisplayChart(ManagedWindow):
self.eventlist = self.topDialog.get_object('treeview')
self.sort = Sort(self.db)
self.my_list.sort(self.sort.by_last_name)
self.my_list.sort(key=self.sort.by_last_name_key)
self.event_titles = self.make_event_titles()
@ -371,7 +371,8 @@ class DisplayChart(ManagedWindow):
break
the_map[name] += 1
unsort_list = sorted([(d, k) for k,d in the_map.items()],by_value)
unsort_list = sorted([(d, k) for k,d in the_map.items()],
key=lambda x: x[0], reverse=True)
sort_list = [ item[1] for item in unsort_list ]
## Presently there's no Birth and Death. Instead there's Birth Date and

View File

@ -662,15 +662,6 @@ def get_surnames(name):
"""Construct a full surname of the surnames"""
return ' '.join([surn.get_surname() for surn in name.get_surname_list()])
#-------------------------------------------------------------------------
#
#
#
#-------------------------------------------------------------------------
def by_id(p1,p2):
return cmp(p1.get_handle(),p2.get_handle())
#------------------------------------------------------------------------
#
#