Setting of application_id

Also when deleting elements, remove all refines that refer to them
This commit is contained in:
Kovid Goyal 2016-06-17 21:04:08 +05:30
parent 1d7eaaafac
commit 9e6ee404b9
2 changed files with 37 additions and 4 deletions

View File

@ -43,6 +43,12 @@ def regex(r, flags=0):
except KeyError:
_re_cache[(r, flags)] = ans = re.compile(r, flags)
return ans
def remove_element(e, refines):
e.getparent().remove(e)
for x in refines[e.get('id')]:
x.getparent().remove(x)
refines.pop(e.get('id'), None)
# }}}
# Prefixes {{{
@ -133,7 +139,7 @@ def set_identifiers(root, prefixes, refines, new_identifiers, force_identifiers=
continue
scheme, val = parse_identifier(ident, val, refines)
if not scheme or not val or force_identifiers or scheme in new_identifiers:
ident.getparent().remove(ident)
remove_element(ident, refines)
continue
metadata = XPath('./opf:metadata')(root)[0]
for scheme, val in new_identifiers.iteritems():
@ -145,6 +151,26 @@ def set_identifiers(root, prefixes, refines, new_identifiers, force_identifiers=
p = package_identifier.getparent()
p.insert(p.index(package_identifier), ident)
def set_application_id(root, refines, new_application_id=None):
uid = root.get('unique-identifier')
package_identifier = None
for ident in XPath('./opf:metadata/dc:identifier')(root):
is_package_id = uid is not None and uid == ident.get('id')
if is_package_id:
package_identifier = ident
val = (ident.text or '').strip()
if val.startswith('calibre:') and not is_package_id:
remove_element(ident, refines)
metadata = XPath('./opf:metadata')(root)[0]
if new_application_id:
ident = metadata.makeelement(DC('identifier'))
ident.text = 'calibre:%s' % new_application_id
if package_identifier is None:
metadata.append(ident)
else:
p = package_identifier.getparent()
p.insert(p.index(package_identifier), ident)
# }}}
def read_metadata(root):

View File

@ -11,7 +11,7 @@ from lxml import etree
from calibre.ebooks.metadata.opf3 import (
parse_prefixes, reserved_prefixes, expand_prefix, read_identifiers,
read_metadata, set_identifiers, XPath
read_metadata, set_identifiers, XPath, set_application_id
)
TEMPLATE = '''<package xmlns="http://www.idpf.org/2007/opf" version="3.0" unique-identifier="uid"><metadata xmlns:dc="http://purl.org/dc/elements/1.1/" xmlns:opf="http://www.idpf.org/2007/opf">{metadata}</metadata></package>''' # noqa
@ -51,9 +51,12 @@ class TestOPF3(unittest.TestCase):
(idt('a:1')+idt('a:2'), {'a':['1', '2']}),
):
self.ae(result, ri(self.get_opf(m)))
mi = read_metadata(self.get_opf(
metadata=idt('a:1')+idt('a:2')+idt('calibre:x')+idt('uuid:y')))
root = self.get_opf(metadata=idt('a:1')+idt('a:2')+idt('calibre:x')+idt('uuid:y'))
mi = read_metadata(root)
self.ae(mi.application_id, 'x')
set_application_id(root, default_refines, 'y')
mi = read_metadata(root)
self.ae(mi.application_id, 'y')
root = self.get_opf(metadata=idt('i:1', iid='uid') + idt('r:1') + idt('o:1'))
set_identifiers(root, reserved_prefixes, default_refines, {'i':'2', 'o':'2'})
@ -62,6 +65,10 @@ class TestOPF3(unittest.TestCase):
root = self.get_opf(metadata=idt('i:1', iid='uid') + idt('r:1') + idt('o:1'))
set_identifiers(root, reserved_prefixes, default_refines, {'i':'2', 'o':'2'}, force_identifiers=True)
self.ae({'i':['2', '1'], 'o':['2']}, ri(root))
root = self.get_opf(metadata=idt('i:1', iid='uid') + idt('r:1') + idt('o:1'))
set_application_id(root, default_refines, 'y')
mi = read_metadata(root)
self.ae(mi.application_id, 'y')
class TestRunner(unittest.main):