mirror of
https://github.com/gryf/ebook-converter.git
synced 2025-12-18 13:10:17 +01:00
1143 lines
38 KiB
Python
1143 lines
38 KiB
Python
import glob
|
|
import mimetypes
|
|
import os
|
|
import re
|
|
|
|
from ebook_converter.constants_old import numeric_version
|
|
from ebook_converter.customize import FileTypePlugin
|
|
from ebook_converter.customize import InterfaceActionBase
|
|
from ebook_converter.customize import MetadataReaderPlugin
|
|
from ebook_converter.customize import MetadataWriterPlugin
|
|
from ebook_converter.ebooks.html.to_zip import HTML2ZIP
|
|
from ebook_converter.ebooks.metadata.archive import ArchiveExtract
|
|
from ebook_converter.ebooks.metadata.archive import KPFExtract
|
|
from ebook_converter.ebooks.metadata.archive import get_comic_metadata
|
|
|
|
|
|
plugins = []
|
|
|
|
# To archive plugins {{{
|
|
|
|
|
|
class PML2PMLZ(FileTypePlugin):
|
|
name = 'PML to PMLZ'
|
|
author = 'John Schember'
|
|
description = ('Create a PMLZ archive containing the PML file '
|
|
'and all images in the directory pmlname_img or images. '
|
|
'This plugin is run every time you add '
|
|
'a PML file to the library.')
|
|
version = numeric_version
|
|
file_types = {'pml'}
|
|
supported_platforms = ['osx', 'linux']
|
|
on_import = True
|
|
|
|
def run(self, pmlfile):
|
|
import zipfile
|
|
|
|
of = self.temporary_file('_plugin_pml2pmlz.pmlz')
|
|
pmlz = zipfile.ZipFile(of.name, 'w')
|
|
pmlz.write(pmlfile, os.path.basename(pmlfile), zipfile.ZIP_DEFLATED)
|
|
|
|
pml_img = os.path.splitext(pmlfile)[0] + '_img'
|
|
i_img = os.path.join(os.path.dirname(pmlfile), 'images')
|
|
img_dir = pml_img if os.path.isdir(pml_img) else i_img if \
|
|
os.path.isdir(i_img) else ''
|
|
if img_dir:
|
|
for image in glob.glob(os.path.join(img_dir, '*.png')):
|
|
pmlz.write(image, os.path.join('images',
|
|
(os.path.basename(image))))
|
|
pmlz.close()
|
|
|
|
return of.name
|
|
|
|
|
|
class TXT2TXTZ(FileTypePlugin):
|
|
name = 'TXT to TXTZ'
|
|
author = 'John Schember'
|
|
description = ('Create a TXTZ archive when a TXT file is imported '
|
|
'containing Markdown or Textile references to images. The '
|
|
'referenced images as well as the TXT file are added to '
|
|
'the archive.')
|
|
version = numeric_version
|
|
file_types = {'txt', 'text'}
|
|
supported_platforms = ['osx', 'linux']
|
|
on_import = True
|
|
|
|
def _get_image_references(self, txt, base_dir):
|
|
from ebook_converter.ebooks.oeb.base import OEB_IMAGES
|
|
|
|
images = []
|
|
|
|
# Textile
|
|
for m in re.finditer(r'(?mu)(?:[\[{])?\!(?:\. )?(?P<path>[^\s(!]+)\s?(?:\(([^\)]+)\))?\!(?::(\S+))?(?:[\]}]|(?=\s|$))', txt):
|
|
path = m.group('path')
|
|
if path and not os.path.isabs(path) and mimetypes.guess_type(path)[0] in OEB_IMAGES and os.path.exists(os.path.join(base_dir, path)):
|
|
images.append(path)
|
|
|
|
# Markdown inline
|
|
for m in re.finditer(r'(?mu)\!\[([^\]\[]*(\[[^\]\[]*(\[[^\]\[]*(\[[^\]\[]*(\[[^\]\[]*(\[[^\]\[]*(\[[^\]\[]*\])*[^\]\[]*\])*[^\]\[]*\])*[^\]\[]*\])*[^\]\[]*\])*[^\]\[]*\])*[^\]\[]*)\]\s*\((?P<path>[^\)]*)\)', txt): # noqa
|
|
path = m.group('path')
|
|
if path and not os.path.isabs(path) and mimetypes.guess_type(path)[0] in OEB_IMAGES and os.path.exists(os.path.join(base_dir, path)):
|
|
images.append(path)
|
|
|
|
# Markdown reference
|
|
refs = {}
|
|
for m in re.finditer(r'(?mu)^(\ ?\ ?\ ?)\[(?P<id>[^\]]*)\]:\s*(?P<path>[^\s]*)$', txt):
|
|
if m.group('id') and m.group('path'):
|
|
refs[m.group('id')] = m.group('path')
|
|
for m in re.finditer(r'(?mu)\!\[([^\]\[]*(\[[^\]\[]*(\[[^\]\[]*(\[[^\]\[]*(\[[^\]\[]*(\[[^\]\[]*(\[[^\]\[]*\])*[^\]\[]*\])*[^\]\[]*\])*[^\]\[]*\])*[^\]\[]*\])*[^\]\[]*\])*[^\]\[]*)\]\s*\[(?P<id>[^\]]*)\]', txt): # noqa
|
|
path = refs.get(m.group('id'), None)
|
|
if path and not os.path.isabs(path) and mimetypes.guess_type(path)[0] in OEB_IMAGES and os.path.exists(os.path.join(base_dir, path)):
|
|
images.append(path)
|
|
|
|
# Remove duplicates
|
|
return list(set(images))
|
|
|
|
def run(self, path_to_ebook):
|
|
from ebook_converter.ebooks.metadata.opf2 import metadata_to_opf
|
|
|
|
with open(path_to_ebook, 'rb') as ebf:
|
|
txt = ebf.read().decode('utf-8', 'replace')
|
|
base_dir = os.path.dirname(path_to_ebook)
|
|
images = self._get_image_references(txt, base_dir)
|
|
|
|
if images:
|
|
# Create TXTZ and put file plus images inside of it.
|
|
import zipfile
|
|
of = self.temporary_file('_plugin_txt2txtz.txtz')
|
|
txtz = zipfile.ZipFile(of.name, 'w')
|
|
# Add selected TXT file to archive.
|
|
txtz.write(path_to_ebook, os.path.basename(path_to_ebook), zipfile.ZIP_DEFLATED)
|
|
# metadata.opf
|
|
if os.path.exists(os.path.join(base_dir, 'metadata.opf')):
|
|
txtz.write(os.path.join(base_dir, 'metadata.opf'), 'metadata.opf', zipfile.ZIP_DEFLATED)
|
|
else:
|
|
from ebook_converter.ebooks.metadata.txt import get_metadata
|
|
with open(path_to_ebook, 'rb') as ebf:
|
|
mi = get_metadata(ebf)
|
|
opf = metadata_to_opf(mi)
|
|
txtz.writestr('metadata.opf', opf, zipfile.ZIP_DEFLATED)
|
|
# images
|
|
for image in images:
|
|
txtz.write(os.path.join(base_dir, image), image)
|
|
txtz.close()
|
|
|
|
return of.name
|
|
else:
|
|
# No images so just import the TXT file.
|
|
return path_to_ebook
|
|
|
|
|
|
plugins += [HTML2ZIP, PML2PMLZ, TXT2TXTZ, ArchiveExtract, KPFExtract]
|
|
# }}}
|
|
|
|
# Metadata reader plugins {{{
|
|
|
|
|
|
class ComicMetadataReader(MetadataReaderPlugin):
|
|
|
|
name = 'Read comic metadata'
|
|
file_types = {'cbr', 'cbz'}
|
|
description = 'Extract cover from comic files'
|
|
|
|
def customization_help(self, gui=False):
|
|
return 'Read series number from volume or issue number. Default is volume, set this to issue to use issue number instead.'
|
|
|
|
def get_metadata(self, stream, ftype):
|
|
if hasattr(stream, 'seek') and hasattr(stream, 'tell'):
|
|
pos = stream.tell()
|
|
id_ = stream.read(3)
|
|
stream.seek(pos)
|
|
if id_ == b'Rar':
|
|
ftype = 'cbr'
|
|
elif id_.startswith(b'PK'):
|
|
ftype = 'cbz'
|
|
if ftype == 'cbr':
|
|
from ebook_converter.utils.unrar import extract_cover_image
|
|
else:
|
|
from ebook_converter.libunzip import extract_cover_image
|
|
from ebook_converter.ebooks.metadata import MetaInformation
|
|
ret = extract_cover_image(stream)
|
|
mi = MetaInformation(None, None)
|
|
stream.seek(0)
|
|
if ftype in {'cbr', 'cbz'}:
|
|
series_index = self.site_customization
|
|
if series_index not in {'volume', 'issue'}:
|
|
series_index = 'volume'
|
|
try:
|
|
mi.smart_update(get_comic_metadata(stream, ftype, series_index=series_index))
|
|
except:
|
|
pass
|
|
if ret is not None:
|
|
path, data = ret
|
|
ext = os.path.splitext(path)[1][1:]
|
|
mi.cover_data = (ext.lower(), data)
|
|
return mi
|
|
|
|
|
|
class CHMMetadataReader(MetadataReaderPlugin):
|
|
|
|
name = 'Read CHM metadata'
|
|
file_types = {'chm'}
|
|
description = 'Read metadata from CHM files'
|
|
|
|
def get_metadata(self, stream, ftype):
|
|
from ebook_converter.ebooks.chm.metadata import get_metadata
|
|
return get_metadata(stream)
|
|
|
|
|
|
class EPUBMetadataReader(MetadataReaderPlugin):
|
|
|
|
name = 'Read EPUB metadata'
|
|
file_types = {'epub'}
|
|
description = 'Read metadata from EPUB files'
|
|
|
|
def get_metadata(self, stream, ftype):
|
|
from ebook_converter.ebooks.metadata.epub import get_metadata, get_quick_metadata
|
|
if self.quick:
|
|
return get_quick_metadata(stream)
|
|
return get_metadata(stream)
|
|
|
|
|
|
class FB2MetadataReader(MetadataReaderPlugin):
|
|
|
|
name = 'Read FB2 metadata'
|
|
file_types = {'fb2', 'fbz'}
|
|
description = 'Read metadata from FB2 files'
|
|
|
|
def get_metadata(self, stream, ftype):
|
|
from ebook_converter.ebooks.metadata.fb2 import get_metadata
|
|
return get_metadata(stream)
|
|
|
|
|
|
class HTMLMetadataReader(MetadataReaderPlugin):
|
|
|
|
name = 'Read HTML metadata'
|
|
file_types = {'html'}
|
|
description = 'Read metadata from HTML files'
|
|
|
|
def get_metadata(self, stream, ftype):
|
|
from ebook_converter.ebooks.metadata.html import get_metadata
|
|
return get_metadata(stream)
|
|
|
|
|
|
class HTMLZMetadataReader(MetadataReaderPlugin):
|
|
|
|
name = 'Read HTMLZ metadata'
|
|
file_types = {'htmlz'}
|
|
description = 'Read metadata from HTMLZ files'
|
|
author = 'John Schember'
|
|
|
|
def get_metadata(self, stream, ftype):
|
|
from ebook_converter.ebooks.metadata.extz import get_metadata
|
|
return get_metadata(stream)
|
|
|
|
|
|
class IMPMetadataReader(MetadataReaderPlugin):
|
|
|
|
name = 'Read IMP metadata'
|
|
file_types = {'imp'}
|
|
description = 'Read metadata from IMP files'
|
|
author = 'Ashish Kulkarni'
|
|
|
|
def get_metadata(self, stream, ftype):
|
|
from ebook_converter.ebooks.metadata.imp import get_metadata
|
|
return get_metadata(stream)
|
|
|
|
|
|
class LITMetadataReader(MetadataReaderPlugin):
|
|
|
|
name = 'Read LIT metadata'
|
|
file_types = {'lit'}
|
|
description = 'Read metadata from LIT files'
|
|
|
|
def get_metadata(self, stream, ftype):
|
|
from ebook_converter.ebooks.metadata.lit import get_metadata
|
|
return get_metadata(stream)
|
|
|
|
|
|
class LRFMetadataReader(MetadataReaderPlugin):
|
|
|
|
name = 'Read LRF metadata'
|
|
file_types = {'lrf'}
|
|
description = 'Read metadata from LRF files'
|
|
|
|
def get_metadata(self, stream, ftype):
|
|
from ebook_converter.ebooks.lrf.meta import get_metadata
|
|
return get_metadata(stream)
|
|
|
|
|
|
class LRXMetadataReader(MetadataReaderPlugin):
|
|
|
|
name = 'Read LRX metadata'
|
|
file_types = {'lrx'}
|
|
description = 'Read metadata from LRX files'
|
|
|
|
def get_metadata(self, stream, ftype):
|
|
from ebook_converter.ebooks.metadata.lrx import get_metadata
|
|
return get_metadata(stream)
|
|
|
|
|
|
class MOBIMetadataReader(MetadataReaderPlugin):
|
|
|
|
name = 'Read MOBI metadata'
|
|
file_types = {'mobi', 'prc', 'azw', 'azw3', 'azw4', 'pobi'}
|
|
description = 'Read metadata from MOBI files'
|
|
|
|
def get_metadata(self, stream, ftype):
|
|
from ebook_converter.ebooks.metadata.mobi import get_metadata
|
|
return get_metadata(stream)
|
|
|
|
|
|
class ODTMetadataReader(MetadataReaderPlugin):
|
|
|
|
name = 'Read ODT metadata'
|
|
file_types = {'odt'}
|
|
description = 'Read metadata from ODT files'
|
|
|
|
def get_metadata(self, stream, ftype):
|
|
from ebook_converter.ebooks.metadata.odt import get_metadata
|
|
return get_metadata(stream)
|
|
|
|
|
|
class DocXMetadataReader(MetadataReaderPlugin):
|
|
|
|
name = 'Read DOCX metadata'
|
|
file_types = {'docx'}
|
|
description = 'Read metadata from DOCX files'
|
|
|
|
def get_metadata(self, stream, ftype):
|
|
from ebook_converter.ebooks.metadata.docx import get_metadata
|
|
return get_metadata(stream)
|
|
|
|
|
|
class OPFMetadataReader(MetadataReaderPlugin):
|
|
|
|
name = 'Read OPF metadata'
|
|
file_types = {'opf'}
|
|
description = 'Read metadata from OPF files'
|
|
|
|
def get_metadata(self, stream, ftype):
|
|
from ebook_converter.ebooks.metadata.opf import get_metadata
|
|
return get_metadata(stream)[0]
|
|
|
|
|
|
class PDBMetadataReader(MetadataReaderPlugin):
|
|
|
|
name = 'Read PDB metadata'
|
|
file_types = {'pdb', 'updb'}
|
|
description = 'Read metadata from PDB files'
|
|
author = 'John Schember'
|
|
|
|
def get_metadata(self, stream, ftype):
|
|
from ebook_converter.ebooks.metadata.pdb import get_metadata
|
|
return get_metadata(stream)
|
|
|
|
|
|
class PDFMetadataReader(MetadataReaderPlugin):
|
|
|
|
name = 'Read PDF metadata'
|
|
file_types = {'pdf'}
|
|
description = 'Read metadata from PDF files'
|
|
|
|
def get_metadata(self, stream, ftype):
|
|
from ebook_converter.ebooks.metadata.pdf import get_metadata, get_quick_metadata
|
|
if self.quick:
|
|
return get_quick_metadata(stream)
|
|
return get_metadata(stream)
|
|
|
|
|
|
class PMLMetadataReader(MetadataReaderPlugin):
|
|
|
|
name = 'Read PML metadata'
|
|
file_types = {'pml', 'pmlz'}
|
|
description = 'Read metadata from PML files'
|
|
author = 'John Schember'
|
|
|
|
def get_metadata(self, stream, ftype):
|
|
from ebook_converter.ebooks.metadata.pml import get_metadata
|
|
return get_metadata(stream)
|
|
|
|
|
|
class RARMetadataReader(MetadataReaderPlugin):
|
|
|
|
name = 'Read RAR metadata'
|
|
file_types = {'rar'}
|
|
description = 'Read metadata from e-books in RAR archives'
|
|
|
|
def get_metadata(self, stream, ftype):
|
|
from ebook_converter.ebooks.metadata.rar import get_metadata
|
|
return get_metadata(stream)
|
|
|
|
|
|
class RBMetadataReader(MetadataReaderPlugin):
|
|
|
|
name = 'Read RB metadata'
|
|
file_types = {'rb'}
|
|
description = 'Read metadata from RB files'
|
|
author = 'Ashish Kulkarni'
|
|
|
|
def get_metadata(self, stream, ftype):
|
|
from ebook_converter.ebooks.metadata.rb import get_metadata
|
|
return get_metadata(stream)
|
|
|
|
|
|
class RTFMetadataReader(MetadataReaderPlugin):
|
|
|
|
name = 'Read RTF metadata'
|
|
file_types = {'rtf'}
|
|
description = 'Read metadata from RTF files'
|
|
|
|
def get_metadata(self, stream, ftype):
|
|
from ebook_converter.ebooks.metadata.rtf import get_metadata
|
|
return get_metadata(stream)
|
|
|
|
|
|
class SNBMetadataReader(MetadataReaderPlugin):
|
|
|
|
name = 'Read SNB metadata'
|
|
file_types = {'snb'}
|
|
description = 'Read metadata from SNB files'
|
|
author = 'Li Fanxi'
|
|
|
|
def get_metadata(self, stream, ftype):
|
|
from ebook_converter.ebooks.metadata.snb import get_metadata
|
|
return get_metadata(stream)
|
|
|
|
|
|
class TOPAZMetadataReader(MetadataReaderPlugin):
|
|
|
|
name = 'Read Topaz metadata'
|
|
file_types = {'tpz', 'azw1'}
|
|
description = 'Read metadata from MOBI files'
|
|
|
|
def get_metadata(self, stream, ftype):
|
|
from ebook_converter.ebooks.metadata.topaz import get_metadata
|
|
return get_metadata(stream)
|
|
|
|
|
|
class TXTMetadataReader(MetadataReaderPlugin):
|
|
|
|
name = 'Read TXT metadata'
|
|
file_types = {'txt'}
|
|
description = 'Read metadata from TXT files'
|
|
author = 'John Schember'
|
|
|
|
def get_metadata(self, stream, ftype):
|
|
from ebook_converter.ebooks.metadata.txt import get_metadata
|
|
return get_metadata(stream)
|
|
|
|
|
|
class TXTZMetadataReader(MetadataReaderPlugin):
|
|
|
|
name = 'Read TXTZ metadata'
|
|
file_types = {'txtz'}
|
|
description = 'Read metadata from TXTZ files'
|
|
author = 'John Schember'
|
|
|
|
def get_metadata(self, stream, ftype):
|
|
from ebook_converter.ebooks.metadata.extz import get_metadata
|
|
return get_metadata(stream)
|
|
|
|
|
|
class ZipMetadataReader(MetadataReaderPlugin):
|
|
|
|
name = 'Read ZIP metadata'
|
|
file_types = {'zip', 'oebzip'}
|
|
description = 'Read metadata from e-books in ZIP archives'
|
|
|
|
def get_metadata(self, stream, ftype):
|
|
from ebook_converter.ebooks.metadata.zip import get_metadata
|
|
return get_metadata(stream)
|
|
|
|
|
|
plugins += [x for x in list(locals().values()) if isinstance(x, type) and
|
|
x.__name__.endswith('MetadataReader')]
|
|
|
|
# }}}
|
|
|
|
# Metadata writer plugins {{{
|
|
|
|
|
|
class EPUBMetadataWriter(MetadataWriterPlugin):
|
|
|
|
name = 'Set EPUB metadata'
|
|
file_types = {'epub'}
|
|
description = 'Set metadata in EPUB files'
|
|
|
|
def set_metadata(self, stream, mi, type):
|
|
from ebook_converter.ebooks.metadata.epub import set_metadata
|
|
q = self.site_customization or ''
|
|
set_metadata(stream, mi, apply_null=self.apply_null, force_identifiers=self.force_identifiers, add_missing_cover='disable-add-missing-cover' != q)
|
|
|
|
def customization_help(self, gui=False):
|
|
h = 'disable-add-missing-cover'
|
|
if gui:
|
|
h = '<i>' + h + '</i>'
|
|
return ('Enter {0} below to have the EPUB metadata writer plugin not '
|
|
'add cover images to EPUB files that have no existing cover '
|
|
'image.'.format(h))
|
|
|
|
|
|
class FB2MetadataWriter(MetadataWriterPlugin):
|
|
|
|
name = 'Set FB2 metadata'
|
|
file_types = {'fb2', 'fbz'}
|
|
description = 'Set metadata in FB2 files'
|
|
|
|
def set_metadata(self, stream, mi, type):
|
|
from ebook_converter.ebooks.metadata.fb2 import set_metadata
|
|
set_metadata(stream, mi, apply_null=self.apply_null)
|
|
|
|
|
|
class HTMLZMetadataWriter(MetadataWriterPlugin):
|
|
|
|
name = 'Set HTMLZ metadata'
|
|
file_types = {'htmlz'}
|
|
description = 'Set metadata from HTMLZ files'
|
|
author = 'John Schember'
|
|
|
|
def set_metadata(self, stream, mi, type):
|
|
from ebook_converter.ebooks.metadata.extz import set_metadata
|
|
set_metadata(stream, mi)
|
|
|
|
|
|
class LRFMetadataWriter(MetadataWriterPlugin):
|
|
|
|
name = 'Set LRF metadata'
|
|
file_types = {'lrf'}
|
|
description = 'Set metadata in LRF files'
|
|
|
|
def set_metadata(self, stream, mi, type):
|
|
from ebook_converter.ebooks.lrf.meta import set_metadata
|
|
set_metadata(stream, mi)
|
|
|
|
|
|
class MOBIMetadataWriter(MetadataWriterPlugin):
|
|
|
|
name = 'Set MOBI metadata'
|
|
file_types = {'mobi', 'prc', 'azw', 'azw3', 'azw4'}
|
|
description = 'Set metadata in MOBI files'
|
|
author = 'Marshall T. Vandegrift'
|
|
|
|
def set_metadata(self, stream, mi, type):
|
|
from ebook_converter.ebooks.metadata.mobi import set_metadata
|
|
set_metadata(stream, mi)
|
|
|
|
|
|
class PDBMetadataWriter(MetadataWriterPlugin):
|
|
|
|
name = 'Set PDB metadata'
|
|
file_types = {'pdb'}
|
|
description = 'Set metadata from PDB files'
|
|
author = 'John Schember'
|
|
|
|
def set_metadata(self, stream, mi, type):
|
|
from ebook_converter.ebooks.metadata.pdb import set_metadata
|
|
set_metadata(stream, mi)
|
|
|
|
|
|
class PDFMetadataWriter(MetadataWriterPlugin):
|
|
|
|
name = 'Set PDF metadata'
|
|
file_types = {'pdf'}
|
|
description = 'Set metadata in PDF files'
|
|
author = 'Kovid Goyal'
|
|
|
|
def set_metadata(self, stream, mi, type):
|
|
from ebook_converter.ebooks.metadata.pdf import set_metadata
|
|
set_metadata(stream, mi)
|
|
|
|
|
|
class RTFMetadataWriter(MetadataWriterPlugin):
|
|
|
|
name = 'Set RTF metadata'
|
|
file_types = {'rtf'}
|
|
description = 'Set metadata in RTF files'
|
|
|
|
def set_metadata(self, stream, mi, type):
|
|
from ebook_converter.ebooks.metadata.rtf import set_metadata
|
|
set_metadata(stream, mi)
|
|
|
|
|
|
class TOPAZMetadataWriter(MetadataWriterPlugin):
|
|
|
|
name = 'Set TOPAZ metadata'
|
|
file_types = {'tpz', 'azw1'}
|
|
description = 'Set metadata in TOPAZ files'
|
|
author = 'Greg Riker'
|
|
|
|
def set_metadata(self, stream, mi, type):
|
|
from ebook_converter.ebooks.metadata.topaz import set_metadata
|
|
set_metadata(stream, mi)
|
|
|
|
|
|
class TXTZMetadataWriter(MetadataWriterPlugin):
|
|
|
|
name = 'Set TXTZ metadata'
|
|
file_types = {'txtz'}
|
|
description = 'Set metadata from TXTZ files'
|
|
author = 'John Schember'
|
|
|
|
def set_metadata(self, stream, mi, type):
|
|
from ebook_converter.ebooks.metadata.extz import set_metadata
|
|
set_metadata(stream, mi)
|
|
|
|
|
|
class ODTMetadataWriter(MetadataWriterPlugin):
|
|
|
|
name = 'Set ODT metadata'
|
|
file_types = {'odt'}
|
|
description = 'Set metadata from ODT files'
|
|
|
|
def set_metadata(self, stream, mi, type):
|
|
from ebook_converter.ebooks.metadata.odt import set_metadata
|
|
return set_metadata(stream, mi)
|
|
|
|
|
|
class DocXMetadataWriter(MetadataWriterPlugin):
|
|
|
|
name = 'Set DOCX metadata'
|
|
file_types = {'docx'}
|
|
description = 'Set metadata from DOCX files'
|
|
|
|
def set_metadata(self, stream, mi, type):
|
|
from ebook_converter.ebooks.metadata.docx import set_metadata
|
|
return set_metadata(stream, mi)
|
|
|
|
|
|
plugins += [x for x in list(locals().values()) if isinstance(x, type) and
|
|
x.__name__.endswith('MetadataWriter')]
|
|
|
|
# }}}
|
|
|
|
# Conversion plugins {{{
|
|
from ebook_converter.ebooks.conversion.plugins.comic_input import ComicInput
|
|
from ebook_converter.ebooks.conversion.plugins.djvu_input import DJVUInput
|
|
from ebook_converter.ebooks.conversion.plugins.epub_input import EPUBInput
|
|
from ebook_converter.ebooks.conversion.plugins.fb2_input import FB2Input
|
|
from ebook_converter.ebooks.conversion.plugins.html_input import HTMLInput
|
|
from ebook_converter.ebooks.conversion.plugins.htmlz_input import HTMLZInput
|
|
from ebook_converter.ebooks.conversion.plugins.lit_input import LITInput
|
|
from ebook_converter.ebooks.conversion.plugins.mobi_input import MOBIInput
|
|
from ebook_converter.ebooks.conversion.plugins.odt_input import ODTInput
|
|
from ebook_converter.ebooks.conversion.plugins.pdb_input import PDBInput
|
|
from ebook_converter.ebooks.conversion.plugins.azw4_input import AZW4Input
|
|
from ebook_converter.ebooks.conversion.plugins.pdf_input import PDFInput
|
|
from ebook_converter.ebooks.conversion.plugins.pml_input import PMLInput
|
|
from ebook_converter.ebooks.conversion.plugins.rb_input import RBInput
|
|
from ebook_converter.ebooks.conversion.plugins.recipe_input import RecipeInput
|
|
from ebook_converter.ebooks.conversion.plugins.rtf_input import RTFInput
|
|
from ebook_converter.ebooks.conversion.plugins.tcr_input import TCRInput
|
|
from ebook_converter.ebooks.conversion.plugins.txt_input import TXTInput
|
|
from ebook_converter.ebooks.conversion.plugins.lrf_input import LRFInput
|
|
from ebook_converter.ebooks.conversion.plugins.chm_input import CHMInput
|
|
from ebook_converter.ebooks.conversion.plugins.snb_input import SNBInput
|
|
from ebook_converter.ebooks.conversion.plugins.docx_input import DOCXInput
|
|
|
|
from ebook_converter.ebooks.conversion.plugins.epub_output import EPUBOutput
|
|
from ebook_converter.ebooks.conversion.plugins.fb2_output import FB2Output
|
|
from ebook_converter.ebooks.conversion.plugins.lit_output import LITOutput
|
|
from ebook_converter.ebooks.conversion.plugins.lrf_output import LRFOutput
|
|
from ebook_converter.ebooks.conversion.plugins.mobi_output import (MOBIOutput,
|
|
AZW3Output)
|
|
from ebook_converter.ebooks.conversion.plugins.oeb_output import OEBOutput
|
|
from ebook_converter.ebooks.conversion.plugins.pdb_output import PDBOutput
|
|
from ebook_converter.ebooks.conversion.plugins.pdf_output import PDFOutput
|
|
from ebook_converter.ebooks.conversion.plugins.pml_output import PMLOutput
|
|
from ebook_converter.ebooks.conversion.plugins.rb_output import RBOutput
|
|
from ebook_converter.ebooks.conversion.plugins.rtf_output import RTFOutput
|
|
from ebook_converter.ebooks.conversion.plugins.tcr_output import TCROutput
|
|
from ebook_converter.ebooks.conversion.plugins.txt_output import TXTOutput, TXTZOutput
|
|
from ebook_converter.ebooks.conversion.plugins.html_output import HTMLOutput
|
|
from ebook_converter.ebooks.conversion.plugins.htmlz_output import HTMLZOutput
|
|
from ebook_converter.ebooks.conversion.plugins.snb_output import SNBOutput
|
|
from ebook_converter.ebooks.conversion.plugins.docx_output import DOCXOutput
|
|
|
|
plugins += [
|
|
ComicInput,
|
|
DJVUInput,
|
|
EPUBInput,
|
|
FB2Input,
|
|
HTMLInput,
|
|
HTMLZInput,
|
|
LITInput,
|
|
MOBIInput,
|
|
ODTInput,
|
|
PDBInput,
|
|
AZW4Input,
|
|
PDFInput,
|
|
PMLInput,
|
|
RBInput,
|
|
RecipeInput,
|
|
RTFInput,
|
|
TCRInput,
|
|
TXTInput,
|
|
LRFInput,
|
|
CHMInput,
|
|
SNBInput,
|
|
DOCXInput,
|
|
]
|
|
plugins += [
|
|
EPUBOutput,
|
|
DOCXOutput,
|
|
FB2Output,
|
|
LITOutput,
|
|
LRFOutput,
|
|
MOBIOutput, AZW3Output,
|
|
OEBOutput,
|
|
PDBOutput,
|
|
PDFOutput,
|
|
PMLOutput,
|
|
RBOutput,
|
|
RTFOutput,
|
|
TCROutput,
|
|
TXTOutput,
|
|
TXTZOutput,
|
|
HTMLOutput,
|
|
HTMLZOutput,
|
|
SNBOutput,
|
|
]
|
|
# }}}
|
|
|
|
# Profiles {{{
|
|
from ebook_converter.customize.profiles import input_profiles, output_profiles
|
|
plugins += input_profiles + output_profiles
|
|
# }}}
|
|
|
|
# Device driver plugins {{{
|
|
#from ebook_converter.devices.hanlin.driver import HANLINV3, HANLINV5, BOOX, SPECTRA
|
|
#from ebook_converter.devices.blackberry.driver import BLACKBERRY, PLAYBOOK
|
|
#from ebook_converter.devices.cybook.driver import CYBOOK, ORIZON, MUSE, DIVA
|
|
#from ebook_converter.devices.eb600.driver import (EB600, COOL_ER, SHINEBOOK, TOLINO,
|
|
# POCKETBOOK360, GER2, ITALICA, ECLICTO, DBOOK, INVESBOOK,
|
|
# BOOQ, ELONEX, POCKETBOOK301, MENTOR, POCKETBOOK602,
|
|
# POCKETBOOK701, POCKETBOOK740, POCKETBOOK360P, PI2, POCKETBOOK622,
|
|
# POCKETBOOKHD)
|
|
#from ebook_converter.devices.iliad.driver import ILIAD
|
|
#from ebook_converter.devices.irexdr.driver import IREXDR1000, IREXDR800
|
|
#from ebook_converter.devices.jetbook.driver import (JETBOOK, MIBUK, JETBOOK_MINI,
|
|
# JETBOOK_COLOR)
|
|
#from ebook_converter.devices.kindle.driver import (KINDLE, KINDLE2, KINDLE_DX,
|
|
# KINDLE_FIRE)
|
|
#from ebook_converter.devices.nook.driver import NOOK, NOOK_COLOR
|
|
#from ebook_converter.devices.prs505.driver import PRS505
|
|
#from ebook_converter.devices.prst1.driver import PRST1
|
|
#from ebook_converter.devices.user_defined.driver import USER_DEFINED
|
|
#from ebook_converter.devices.android.driver import ANDROID, S60, WEBOS
|
|
#from ebook_converter.devices.nokia.driver import N770, N810, E71X, E52
|
|
#from ebook_converter.devices.eslick.driver import ESLICK, EBK52
|
|
#from ebook_converter.devices.nuut2.driver import NUUT2
|
|
#from ebook_converter.devices.iriver.driver import IRIVER_STORY
|
|
#from ebook_converter.devices.binatone.driver import README
|
|
#from ebook_converter.devices.hanvon.driver import (N516, EB511, ALEX, AZBOOKA, THEBOOK,
|
|
# LIBREAIR, ODYSSEY, KIBANO)
|
|
#from ebook_converter.devices.edge.driver import EDGE
|
|
#from ebook_converter.devices.teclast.driver import (TECLAST_K3, NEWSMY, IPAPYRUS,
|
|
# SOVOS, PICO, SUNSTECH_EB700, ARCHOS7O, STASH, WEXLER)
|
|
#from ebook_converter.devices.sne.driver import SNE
|
|
#from ebook_converter.devices.misc import (
|
|
# PALMPRE, AVANT, SWEEX, PDNOVEL, GEMEI, VELOCITYMICRO, PDNOVEL_KOBO,
|
|
# LUMIREAD, ALURATEK_COLOR, TREKSTOR, EEEREADER, NEXTBOOK, ADAM, MOOVYBOOK,
|
|
# COBY, EX124G, WAYTEQ, WOXTER, POCKETBOOK626, SONYDPTS1, CERVANTES)
|
|
#from ebook_converter.devices.folder_device.driver import FOLDER_DEVICE_FOR_CONFIG
|
|
#from ebook_converter.devices.kobo.driver import KOBO, KOBOTOUCH
|
|
#from ebook_converter.devices.boeye.driver import BOEYE_BEX, BOEYE_BDX
|
|
#from ebook_converter.devices.smart_device_app.driver import SMART_DEVICE_APP
|
|
#from ebook_converter.devices.mtp.driver import MTP_DEVICE
|
|
|
|
# Order here matters. The first matched device is the one used.
|
|
#plugins += [
|
|
# HANLINV3,
|
|
# HANLINV5,
|
|
# BLACKBERRY, PLAYBOOK,
|
|
# CYBOOK, ORIZON, MUSE, DIVA,
|
|
# ILIAD,
|
|
# IREXDR1000,
|
|
# IREXDR800,
|
|
# JETBOOK, JETBOOK_MINI, MIBUK, JETBOOK_COLOR,
|
|
# SHINEBOOK,
|
|
# POCKETBOOK360, POCKETBOOK301, POCKETBOOK602, POCKETBOOK701, POCKETBOOK360P,
|
|
# POCKETBOOK622, PI2, POCKETBOOKHD, POCKETBOOK740,
|
|
# KINDLE, KINDLE2, KINDLE_DX, KINDLE_FIRE,
|
|
# NOOK, NOOK_COLOR,
|
|
# PRS505, PRST1,
|
|
# ANDROID, S60, WEBOS,
|
|
# N770,
|
|
# E71X,
|
|
# E52,
|
|
# N810,
|
|
# COOL_ER,
|
|
# ESLICK,
|
|
# EBK52,
|
|
# NUUT2,
|
|
# IRIVER_STORY,
|
|
# GER2,
|
|
# ITALICA,
|
|
# ECLICTO,
|
|
# DBOOK,
|
|
# INVESBOOK,
|
|
# BOOX,
|
|
# BOOQ,
|
|
# EB600, TOLINO,
|
|
# README,
|
|
# N516, KIBANO,
|
|
# THEBOOK, LIBREAIR,
|
|
# EB511,
|
|
# ELONEX,
|
|
# TECLAST_K3,
|
|
# NEWSMY,
|
|
# PICO, SUNSTECH_EB700, ARCHOS7O, SOVOS, STASH, WEXLER,
|
|
# IPAPYRUS,
|
|
# EDGE,
|
|
# SNE,
|
|
# ALEX, ODYSSEY,
|
|
# PALMPRE,
|
|
# KOBO, KOBOTOUCH,
|
|
# AZBOOKA,
|
|
# FOLDER_DEVICE_FOR_CONFIG,
|
|
# AVANT, CERVANTES,
|
|
# MENTOR,
|
|
# SWEEX,
|
|
# PDNOVEL,
|
|
# SPECTRA,
|
|
# GEMEI,
|
|
# VELOCITYMICRO,
|
|
# PDNOVEL_KOBO,
|
|
# LUMIREAD,
|
|
# ALURATEK_COLOR,
|
|
# TREKSTOR,
|
|
# EEEREADER,
|
|
# NEXTBOOK,
|
|
# ADAM,
|
|
# MOOVYBOOK, COBY, EX124G, WAYTEQ, WOXTER, POCKETBOOK626, SONYDPTS1,
|
|
# BOEYE_BEX,
|
|
# BOEYE_BDX,
|
|
# MTP_DEVICE,
|
|
# SMART_DEVICE_APP,
|
|
# USER_DEFINED,
|
|
#]
|
|
|
|
|
|
# }}}
|
|
|
|
# Interface Actions {{{
|
|
|
|
|
|
class ActionAdd(InterfaceActionBase):
|
|
name = 'Add Books'
|
|
actual_plugin = 'ebook_converter.gui2.actions.add:AddAction'
|
|
description = 'Add books to calibre or the connected device'
|
|
|
|
|
|
class ActionFetchAnnotations(InterfaceActionBase):
|
|
name = 'Fetch Annotations'
|
|
actual_plugin = 'ebook_converter.gui2.actions.annotate:FetchAnnotationsAction'
|
|
description = 'Fetch annotations from a connected Kindle (experimental)'
|
|
|
|
|
|
class ActionGenerateCatalog(InterfaceActionBase):
|
|
name = 'Generate Catalog'
|
|
actual_plugin = 'ebook_converter.gui2.actions.catalog:GenerateCatalogAction'
|
|
description = 'Generate a catalog of the books in your calibre library'
|
|
|
|
|
|
class ActionConvert(InterfaceActionBase):
|
|
name = 'Convert Books'
|
|
actual_plugin = 'ebook_converter.gui2.actions.convert:ConvertAction'
|
|
description = 'Convert books to various e-book formats'
|
|
|
|
|
|
class ActionPolish(InterfaceActionBase):
|
|
name = 'Polish Books'
|
|
actual_plugin = 'ebook_converter.gui2.actions.polish:PolishAction'
|
|
description = 'Fine tune your e-books'
|
|
|
|
|
|
class ActionEditToC(InterfaceActionBase):
|
|
name = 'Edit ToC'
|
|
actual_plugin = 'ebook_converter.gui2.actions.toc_edit:ToCEditAction'
|
|
description = 'Edit the Table of Contents in your books'
|
|
|
|
|
|
class ActionDelete(InterfaceActionBase):
|
|
name = 'Remove Books'
|
|
actual_plugin = 'ebook_converter.gui2.actions.delete:DeleteAction'
|
|
description = 'Delete books from your calibre library or connected device'
|
|
|
|
|
|
class ActionEmbed(InterfaceActionBase):
|
|
name = 'Embed Metadata'
|
|
actual_plugin = 'ebook_converter.gui2.actions.embed:EmbedAction'
|
|
description = ('Embed updated metadata into the actual book files in '
|
|
'your calibre library')
|
|
|
|
|
|
class ActionEditMetadata(InterfaceActionBase):
|
|
name = 'Edit Metadata'
|
|
actual_plugin = 'ebook_converter.gui2.actions.edit_metadata:EditMetadataAction'
|
|
description = 'Edit the metadata of books in your calibre library'
|
|
|
|
|
|
class ActionView(InterfaceActionBase):
|
|
name = 'View'
|
|
actual_plugin = 'ebook_converter.gui2.actions.view:ViewAction'
|
|
description = 'Read books in your calibre library'
|
|
|
|
|
|
class ActionFetchNews(InterfaceActionBase):
|
|
name = 'Fetch News'
|
|
actual_plugin = 'ebook_converter.gui2.actions.fetch_news:FetchNewsAction'
|
|
description = 'Download news from the internet in e-book form'
|
|
|
|
|
|
class ActionQuickview(InterfaceActionBase):
|
|
name = 'Quickview'
|
|
actual_plugin = 'ebook_converter.gui2.actions.show_quickview:ShowQuickviewAction'
|
|
description = 'Show a list of related books quickly'
|
|
|
|
|
|
class ActionTagMapper(InterfaceActionBase):
|
|
name = 'Tag Mapper'
|
|
actual_plugin = 'ebook_converter.gui2.actions.tag_mapper:TagMapAction'
|
|
description = 'Filter/transform the tags for books in the library'
|
|
|
|
|
|
class ActionAuthorMapper(InterfaceActionBase):
|
|
name = 'Author Mapper'
|
|
actual_plugin = 'ebook_converter.gui2.actions.author_mapper:AuthorMapAction'
|
|
description = 'Transform the authors for books in the library'
|
|
|
|
|
|
class ActionTemplateTester(InterfaceActionBase):
|
|
name = 'Template Tester'
|
|
actual_plugin = 'ebook_converter.gui2.actions.show_template_tester:ShowTemplateTesterAction'
|
|
description = 'Show an editor for testing templates'
|
|
|
|
|
|
class ActionSaveToDisk(InterfaceActionBase):
|
|
name = 'Save To Disk'
|
|
actual_plugin = 'ebook_converter.gui2.actions.save_to_disk:SaveToDiskAction'
|
|
description = 'Export books from your calibre library to the hard disk'
|
|
|
|
|
|
class ActionShowBookDetails(InterfaceActionBase):
|
|
name = 'Show Book Details'
|
|
actual_plugin = 'ebook_converter.gui2.actions.show_book_details:ShowBookDetailsAction'
|
|
description = 'Show Book details in a separate popup'
|
|
|
|
|
|
class ActionRestart(InterfaceActionBase):
|
|
name = 'Restart'
|
|
actual_plugin = 'ebook_converter.gui2.actions.restart:RestartAction'
|
|
description = 'Restart calibre'
|
|
|
|
|
|
class ActionOpenFolder(InterfaceActionBase):
|
|
name = 'Open Folder'
|
|
actual_plugin = 'ebook_converter.gui2.actions.open:OpenFolderAction'
|
|
description = ('Open the folder that contains the book files in your'
|
|
' calibre library')
|
|
|
|
|
|
class ActionSendToDevice(InterfaceActionBase):
|
|
name = 'Send To Device'
|
|
actual_plugin = 'ebook_converter.gui2.actions.device:SendToDeviceAction'
|
|
description = 'Send books to the connected device'
|
|
|
|
|
|
class ActionConnectShare(InterfaceActionBase):
|
|
name = 'Connect Share'
|
|
actual_plugin = 'ebook_converter.gui2.actions.device:ConnectShareAction'
|
|
description = ('Send books via email or the web. Also connect to'
|
|
' folders on your computer as if they are devices')
|
|
|
|
|
|
class ActionHelp(InterfaceActionBase):
|
|
name = 'Help'
|
|
actual_plugin = 'ebook_converter.gui2.actions.help:HelpAction'
|
|
description = 'Browse the calibre User Manual'
|
|
|
|
|
|
class ActionPreferences(InterfaceActionBase):
|
|
name = 'Preferences'
|
|
actual_plugin = 'ebook_converter.gui2.actions.preferences:PreferencesAction'
|
|
description = 'Customize calibre'
|
|
|
|
|
|
class ActionSimilarBooks(InterfaceActionBase):
|
|
name = 'Similar Books'
|
|
actual_plugin = 'ebook_converter.gui2.actions.similar_books:SimilarBooksAction'
|
|
description = 'Easily find books similar to the currently selected one'
|
|
|
|
|
|
class ActionChooseLibrary(InterfaceActionBase):
|
|
name = 'Choose Library'
|
|
actual_plugin = 'ebook_converter.gui2.actions.choose_library:ChooseLibraryAction'
|
|
description = ('Switch between different calibre libraries and perform '
|
|
'maintenance on them')
|
|
|
|
|
|
class ActionAddToLibrary(InterfaceActionBase):
|
|
name = 'Add To Library'
|
|
actual_plugin = 'ebook_converter.gui2.actions.add_to_library:AddToLibraryAction'
|
|
description = 'Copy books from the device to your calibre library'
|
|
|
|
|
|
class ActionEditCollections(InterfaceActionBase):
|
|
name = 'Edit Collections'
|
|
actual_plugin = 'ebook_converter.gui2.actions.edit_collections:EditCollectionsAction'
|
|
description = ('Edit the collections in which books are placed on your '
|
|
'device')
|
|
|
|
|
|
class ActionMatchBooks(InterfaceActionBase):
|
|
name = 'Match Books'
|
|
actual_plugin = 'ebook_converter.gui2.actions.match_books:MatchBookAction'
|
|
description = 'Match book on the devices to books in the library'
|
|
|
|
|
|
class ActionCopyToLibrary(InterfaceActionBase):
|
|
name = 'Copy To Library'
|
|
actual_plugin = 'ebook_converter.gui2.actions.copy_to_library:CopyToLibraryAction'
|
|
description = 'Copy a book from one calibre library to another'
|
|
|
|
|
|
class ActionTweakEpub(InterfaceActionBase):
|
|
name = 'Tweak ePub'
|
|
actual_plugin = 'ebook_converter.gui2.actions.tweak_epub:TweakEpubAction'
|
|
description = 'Edit e-books in the EPUB or AZW3 formats'
|
|
|
|
|
|
class ActionUnpackBook(InterfaceActionBase):
|
|
name = 'Unpack Book'
|
|
actual_plugin = 'ebook_converter.gui2.actions.unpack_book:UnpackBookAction'
|
|
description = ('Make small changes to EPUB or HTMLZ files in your '
|
|
'calibre library')
|
|
|
|
|
|
class ActionNextMatch(InterfaceActionBase):
|
|
name = 'Next Match'
|
|
actual_plugin = 'ebook_converter.gui2.actions.next_match:NextMatchAction'
|
|
description = ('Find the next or previous match when searching in '
|
|
'your calibre library in highlight mode')
|
|
|
|
|
|
class ActionPickRandom(InterfaceActionBase):
|
|
name = 'Pick Random Book'
|
|
actual_plugin = 'ebook_converter.gui2.actions.random:PickRandomAction'
|
|
description = 'Choose a random book from your calibre library'
|
|
|
|
|
|
class ActionSortBy(InterfaceActionBase):
|
|
name = 'Sort By'
|
|
actual_plugin = 'ebook_converter.gui2.actions.sort:SortByAction'
|
|
description = 'Sort the list of books'
|
|
|
|
|
|
class ActionMarkBooks(InterfaceActionBase):
|
|
name = 'Mark Books'
|
|
actual_plugin = 'ebook_converter.gui2.actions.mark_books:MarkBooksAction'
|
|
description = 'Temporarily mark books'
|
|
|
|
|
|
class ActionVirtualLibrary(InterfaceActionBase):
|
|
name = 'Virtual Library'
|
|
actual_plugin = 'ebook_converter.gui2.actions.virtual_library:VirtualLibraryAction'
|
|
description = 'Change the current Virtual library'
|
|
|
|
|
|
class ActionStore(InterfaceActionBase):
|
|
name = 'Store'
|
|
author = 'John Schember'
|
|
actual_plugin = 'ebook_converter.gui2.actions.store:StoreAction'
|
|
description = 'Search for books from different book sellers'
|
|
|
|
def customization_help(self, gui=False):
|
|
return 'Customize the behavior of the store search.'
|
|
|
|
def config_widget(self):
|
|
from ebook_converter.gui2.store.config.store import config_widget as get_cw
|
|
return get_cw()
|
|
|
|
def save_settings(self, config_widget):
|
|
from ebook_converter.gui2.store.config.store import save_settings as save
|
|
save(config_widget)
|
|
|
|
|
|
class ActionPluginUpdater(InterfaceActionBase):
|
|
name = 'Plugin Updater'
|
|
author = 'Grant Drake'
|
|
description = ('Get new ebook_converter plugins or update your existing '
|
|
'ones')
|
|
actual_plugin = 'calibre.gui2.actions.plugin_updates:PluginUpdaterAction'
|
|
|
|
|
|
plugins += [ActionAdd, ActionFetchAnnotations, ActionGenerateCatalog,
|
|
ActionConvert, ActionDelete, ActionEditMetadata, ActionView,
|
|
ActionFetchNews, ActionSaveToDisk, ActionQuickview, ActionPolish,
|
|
ActionShowBookDetails,ActionRestart, ActionOpenFolder, ActionConnectShare,
|
|
ActionSendToDevice, ActionHelp, ActionPreferences, ActionSimilarBooks,
|
|
ActionAddToLibrary, ActionEditCollections, ActionMatchBooks, ActionChooseLibrary,
|
|
ActionCopyToLibrary, ActionTweakEpub, ActionUnpackBook, ActionNextMatch, ActionStore,
|
|
ActionPluginUpdater, ActionPickRandom, ActionEditToC, ActionSortBy,
|
|
ActionMarkBooks, ActionEmbed, ActionTemplateTester, ActionTagMapper, ActionAuthorMapper,
|
|
ActionVirtualLibrary]
|
|
|
|
# }}}
|
|
|
|
|
|
if __name__ == '__main__':
|
|
# Test load speed
|
|
import subprocess, textwrap
|
|
try:
|
|
subprocess.check_call(['python', '-c', textwrap.dedent(
|
|
'''
|
|
import init_calibre # noqa
|
|
|
|
def doit():
|
|
import ebook_converter.customize.builtins as b # noqa
|
|
|
|
def show_stats():
|
|
from pstats import Stats
|
|
s = Stats('/tmp/calibre_stats')
|
|
s.sort_stats('cumulative')
|
|
s.print_stats(30)
|
|
|
|
import cProfile
|
|
cProfile.run('doit()', '/tmp/calibre_stats')
|
|
show_stats()
|
|
|
|
'''
|
|
)])
|
|
except subprocess.CalledProcessError:
|
|
raise SystemExit(1)
|
|
try:
|
|
subprocess.check_call(['python', '-c', textwrap.dedent(
|
|
'''
|
|
import time, sys, init_calibre
|
|
st = time.time()
|
|
import ebook_converter.customize.builtins
|
|
t = time.time() - st
|
|
ret = 0
|
|
|
|
for x in ('lxml', 'ebook_converter.ebooks.BeautifulSoup', 'uuid',
|
|
'ebook_converter.utils.terminal', 'ebook_converter.utils.img', 'PIL', 'Image',
|
|
'sqlite3', 'mechanize', 'httplib', 'xml', 'inspect', 'urllib',
|
|
'ebook_converter.utils.date', 'ebook_converter.utils.config', 'platform',
|
|
'ebook_converter.utils.zipfile', 'ebook_converter.utils.formatter',
|
|
):
|
|
if x in sys.modules:
|
|
ret = 1
|
|
print (x, 'has been loaded by a plugin')
|
|
if ret:
|
|
print ('\\nA good way to track down what is loading something is to run'
|
|
' python -c "import init_calibre; import ebook_converter.customize.builtins"')
|
|
print()
|
|
print ('Time taken to import all plugins: %.2f'%t)
|
|
sys.exit(ret)
|
|
|
|
''')])
|
|
except subprocess.CalledProcessError:
|
|
raise SystemExit(1)
|