Minor fixes

This commit is contained in:
Kovid Goyal 2009-02-05 17:00:04 -08:00
parent a4aaa82564
commit a9f4ab2346
5 changed files with 56 additions and 14 deletions

View File

@ -229,6 +229,9 @@ def get_metadata(stream):
mi.author = lrf.author.strip() mi.author = lrf.author.strip()
mi.comments = lrf.free_text.strip() mi.comments = lrf.free_text.strip()
mi.category = lrf.category.strip()+', '+lrf.classification.strip() mi.category = lrf.category.strip()+', '+lrf.classification.strip()
tags = [x.strip() for x in mi.category.split(',') if x.strip()]
if tags:
mi.tags = tags
mi.publisher = lrf.publisher.strip() mi.publisher = lrf.publisher.strip()
mi.cover_data = lrf.get_cover() mi.cover_data = lrf.get_cover()
try: try:
@ -624,7 +627,9 @@ def set_metadata(stream, mi):
lrf.title = mi.title lrf.title = mi.title
if mi.authors: if mi.authors:
lrf.author = ', '.join(mi.authors) lrf.author = ', '.join(mi.authors)
if mi.category: if mi.tags:
lrf.category = mi.tags[0]
if getattr(mi, 'category', False):
lrf.category = mi.category lrf.category = mi.category
if mi.comments: if mi.comments:
lrf.free_text = mi.comments lrf.free_text = mi.comments

View File

@ -185,7 +185,7 @@ class MetaInformation(object):
@staticmethod @staticmethod
def copy(mi): def copy(mi):
ans = MetaInformation(mi.title, mi.authors) ans = MetaInformation(mi.title, mi.authors)
for attr in ('author_sort', 'title_sort', 'comments', for attr in ('author_sort', 'title_sort', 'comments', 'category',
'publisher', 'series', 'series_index', 'rating', 'publisher', 'series', 'series_index', 'rating',
'isbn', 'tags', 'cover_data', 'application_id', 'guide', 'isbn', 'tags', 'cover_data', 'application_id', 'guide',
'manifest', 'spine', 'toc', 'cover', 'language', 'book_producer'): 'manifest', 'spine', 'toc', 'cover', 'language', 'book_producer'):
@ -210,7 +210,7 @@ class MetaInformation(object):
#: mi.cover_data = (ext, data) #: mi.cover_data = (ext, data)
self.cover_data = getattr(mi, 'cover_data', (None, None)) self.cover_data = getattr(mi, 'cover_data', (None, None))
for x in ('author_sort', 'title_sort', 'comments', 'publisher', for x in ('author_sort', 'title_sort', 'comments', 'category', 'publisher',
'series', 'series_index', 'rating', 'isbn', 'language', 'series', 'series_index', 'rating', 'isbn', 'language',
'application_id', 'manifest', 'toc', 'spine', 'guide', 'cover', 'application_id', 'manifest', 'toc', 'spine', 'guide', 'cover',
'book_producer', 'book_producer',
@ -228,7 +228,7 @@ class MetaInformation(object):
if mi.authors and mi.authors[0] != _('Unknown'): if mi.authors and mi.authors[0] != _('Unknown'):
self.authors = mi.authors self.authors = mi.authors
for attr in ('author_sort', 'title_sort', 'comments', for attr in ('author_sort', 'title_sort', 'comments', 'category',
'publisher', 'series', 'series_index', 'rating', 'publisher', 'series', 'series_index', 'rating',
'isbn', 'application_id', 'manifest', 'spine', 'toc', 'isbn', 'application_id', 'manifest', 'spine', 'toc',
'cover', 'language', 'guide', 'book_producer'): 'cover', 'language', 'guide', 'book_producer'):
@ -251,10 +251,11 @@ class MetaInformation(object):
return '%d'%x if int(x) == x else '%.2f'%x return '%d'%x if int(x) == x else '%.2f'%x
def __unicode__(self): def __unicode__(self):
ans = [ fmt('Title', self.title) ] ans = []
def fmt(x, y): def fmt(x, y):
ans.append(u'%-20s: %s'%(unicode(x), unicode(y))) ans.append(u'%-20s: %s'%(unicode(x), unicode(y)))
fmt('Title', self.title)
if self.title_sort: if self.title_sort:
fmt('Title sort', self.title_sort) fmt('Title sort', self.title_sort)
if self.authors: if self.authors:
@ -264,6 +265,8 @@ class MetaInformation(object):
fmt('Publisher', self.publisher) fmt('Publisher', self.publisher)
if getattr(self, 'book_producer', False): if getattr(self, 'book_producer', False):
fmt('Book Producer', self.book_producer) fmt('Book Producer', self.book_producer)
if self.category:
ans += u'Category : ' + unicode(self.category) + u'\n'
if self.comments: if self.comments:
fmt('Comments', self.comments) fmt('Comments', self.comments)
if self.isbn: if self.isbn:

View File

@ -26,6 +26,7 @@ from calibre.customize.ui import metadata_readers, metadata_writers
from calibre.ebooks.metadata.meta import get_metadata, set_metadata from calibre.ebooks.metadata.meta import get_metadata, set_metadata
from calibre.ebooks.metadata import string_to_authors, authors_to_sort_string, \ from calibre.ebooks.metadata import string_to_authors, authors_to_sort_string, \
title_sort, MetaInformation title_sort, MetaInformation
from calibre.ebooks.lrf.meta import LRFMetaFile
from calibre import prints from calibre import prints
def config(): def config():
@ -50,6 +51,8 @@ def config():
help=_('Set the ebook description.')) help=_('Set the ebook description.'))
c.add_opt('publisher', ['-p', '--publisher'], c.add_opt('publisher', ['-p', '--publisher'],
help=_('Set the ebook publisher.')) help=_('Set the ebook publisher.'))
c.add_opt('category', ['--category'],
help=_('Set the book category.'))
c.add_opt('series', ['-s', '--series'], c.add_opt('series', ['-s', '--series'],
help=_('Set the series this ebook belongs to.')) help=_('Set the series this ebook belongs to.'))
c.add_opt('series_index', ['-i', '--index'], c.add_opt('series_index', ['-i', '--index'],
@ -75,6 +78,9 @@ def config():
help=_('Read metadata from the specified OPF file and use it to ' help=_('Read metadata from the specified OPF file and use it to '
'set metadata in the ebook. Metadata specified on the' 'set metadata in the ebook. Metadata specified on the'
'command line will override metadata read from the OPF file')) 'command line will override metadata read from the OPF file'))
c.add_opt('lrf_bookid', ['--lrf-bookid'],
help=_('Set the BookID in LRF files'))
return c return c
def filetypes(): def filetypes():
@ -102,12 +108,12 @@ def do_set_metadata(opts, mi, stream, stream_type):
for pref in config().option_set.preferences: for pref in config().option_set.preferences:
if pref.name in ('to_opf', 'from_opf', 'authors', 'title_sort', if pref.name in ('to_opf', 'from_opf', 'authors', 'title_sort',
'author_sort', 'get_cover', 'cover', 'tags'): 'author_sort', 'get_cover', 'cover', 'tags',
'lrf_bookid'):
continue continue
val = getattr(opts, pref.name, None) val = getattr(opts, pref.name, None)
if val is not None: if val is not None:
setattr(mi, pref.name, getattr()) setattr(mi, pref.name, val)
if getattr(opts, 'authors', None) is not None: if getattr(opts, 'authors', None) is not None:
mi.authors = string_to_authors(opts.authors) mi.authors = string_to_authors(opts.authors)
mi.author_sort = authors_to_sort_string(mi.authors) mi.author_sort = authors_to_sort_string(mi.authors)
@ -158,11 +164,18 @@ def main(args=sys.argv):
do_set_metadata(opts, mi, stream, stream_type) do_set_metadata(opts, mi, stream, stream_type)
stream.seek(0) stream.seek(0)
stream.flush() stream.flush()
lrf = None
if stream_type == 'lrf':
if opts.lrf_bookid is not None:
lrf = LRFMetaFile(stream)
lrf.book_id = opts.lrf_bookid
mi = get_metadata(stream, stream_type) mi = get_metadata(stream, stream_type)
prints(_('Changed metadata')+'::') prints('\n' + _('Changed metadata') + '::')
metadata = unicode(mi) metadata = unicode(mi)
metadata = '\t'+'\n\t'.join(metadata.split('\n')) metadata = '\t'+'\n\t'.join(metadata.split('\n'))
prints(metadata) prints(metadata)
if lrf is not None:
prints('\tBookID:', lrf.book_id)
if opts.to_opf is not None: if opts.to_opf is not None:
from calibre.ebooks.metadata.opf2 import OPFCreator from calibre.ebooks.metadata.opf2 import OPFCreator

View File

@ -6,13 +6,13 @@
> >
<metadata xmlns:dc="http://purl.org/dc/elements/1.1/" xmlns:opf="http://www.idpf.org/2007/opf" xmlns:calibre="http://calibre.kovidgoyal.net/2009/metadata"> <metadata xmlns:dc="http://purl.org/dc/elements/1.1/" xmlns:opf="http://www.idpf.org/2007/opf" xmlns:calibre="http://calibre.kovidgoyal.net/2009/metadata">
<dc:title py:with="attrs={'opf:files-as':mi.title_sort}" py:attrs="attrs">${mi.title}</dc:title> <dc:title py:with="attrs={'opf:file-as':mi.title_sort}" py:attrs="attrs">${mi.title}</dc:title>
<dc:creator opf:role="aut" py:for="i, author in enumerate(mi.authors)" py:attrs="{'opf:file-as':mi.author_sort} if mi.author_sort and i == 0 else {}">${author}</dc:creator> <dc:creator opf:role="aut" py:for="i, author in enumerate(mi.authors)" py:attrs="{'opf:file-as':mi.author_sort} if mi.author_sort and i == 0 else {}">${author}</dc:creator>
<dc:contributor opf:role="bkp" py:with="attrs={'opf:files-as':__appname__}" py:attrs="attrs">${'%s (%s)'%(__appname__, __version__)} [http://${__appname__}.kovidgoyal.net]</dc:contributor> <dc:contributor opf:role="bkp" py:with="attrs={'opf:file-as':__appname__}" py:attrs="attrs">${'%s (%s)'%(__appname__, __version__)} [http://${__appname__}.kovidgoyal.net]</dc:contributor>
<dc:identifier opf:scheme="${__appname__}" id="${__appname__}_id">${mi.application_id}</dc:identifier> <dc:identifier opf:scheme="${__appname__}" id="${__appname__}_id">${mi.application_id}</dc:identifier>
<dc:language>${mi.language if mi.language else 'UND'}</dc:language> <dc:language>${mi.language if mi.language else 'UND'}</dc:language>
<dc:type py:if="mi.category">${mi.category}</dc:type> <dc:type py:if="getattr(mi, 'category', False)">${mi.category}</dc:type>
<dc:description py:if="mi.comments">${mi.comments}</dc:description> <dc:description py:if="mi.comments">${mi.comments}</dc:description>
<dc:publisher py:if="mi.publisher">${mi.publisher}</dc:publisher> <dc:publisher py:if="mi.publisher">${mi.publisher}</dc:publisher>
<dc:identifier opf:scheme="ISBN" py:if="mi.isbn">${mi.isbn}</dc:identifier> <dc:identifier opf:scheme="ISBN" py:if="mi.isbn">${mi.isbn}</dc:identifier>

View File

@ -414,6 +414,7 @@ class OPF(object):
metadata_path = XPath('descendant::*[re:match(name(), "metadata", "i")]') metadata_path = XPath('descendant::*[re:match(name(), "metadata", "i")]')
metadata_elem_path = XPath('descendant::*[re:match(name(), concat($name, "$"), "i") or (re:match(name(), "meta$", "i") and re:match(@name, concat("^calibre:", $name, "$"), "i"))]') metadata_elem_path = XPath('descendant::*[re:match(name(), concat($name, "$"), "i") or (re:match(name(), "meta$", "i") and re:match(@name, concat("^calibre:", $name, "$"), "i"))]')
title_path = XPath('descendant::*[re:match(name(), "title", "i")]')
authors_path = XPath('descendant::*[re:match(name(), "creator", "i") and (@role="aut" or @opf:role="aut" or (not(@role) and not(@opf:role)))]') authors_path = XPath('descendant::*[re:match(name(), "creator", "i") and (@role="aut" or @opf:role="aut" or (not(@role) and not(@opf:role)))]')
bkp_path = XPath('descendant::*[re:match(name(), "contributor", "i") and (@role="bkp" or @opf:role="bkp")]') bkp_path = XPath('descendant::*[re:match(name(), "contributor", "i") and (@role="bkp" or @opf:role="bkp")]')
tags_path = XPath('descendant::*[re:match(name(), "subject", "i")]') tags_path = XPath('descendant::*[re:match(name(), "subject", "i")]')
@ -503,7 +504,7 @@ class OPF(object):
def set_text(self, elem, content): def set_text(self, elem, content):
if elem.tag == self.META: if elem.tag == self.META:
elem.attib['content'] = content elem.attrib['content'] = content
else: else:
elem.text = content elem.text = content
@ -645,6 +646,26 @@ class OPF(object):
return property(fget=fget, fset=fset) return property(fget=fget, fset=fset)
@apply
def title_sort():
def fget(self):
matches = self.title_path(self.metadata)
if matches:
for match in matches:
ans = match.get('{%s}file-as'%self.NAMESPACES['opf'], None)
if not ans:
ans = match.get('file-as', None)
if ans:
return ans
def fset(self, val):
matches = self.title_path(self.metadata)
if matches:
matches[0].set('file-as', unicode(val))
return property(fget=fget, fset=fset)
@apply @apply
def tags(): def tags():