Exemple #1
0
 def test_actual_case(self):
     ' Test getting the actual case for files from names on case insensitive filesystems '
     from calibre.ebooks.oeb.polish.utils import actual_case_for_name, corrected_case_for_name
     book = get_simple_book()
     c = get_container(book)
     name = 'f1/f2/added file.html'
     c.add_file(name, b'xxx')
     self.assertTrue(c.exists(name))
     variations = (name, name.upper(), name.replace('f1', 'F1'), name.replace('f2', 'F2'))
     if c.exists(name.upper()):
         for n in variations:
             self.assertEqual(name, actual_case_for_name(c, n))
     else:
         for n in variations:
             self.assertEqual(name, corrected_case_for_name(c, n))
         self.assertIsNone(corrected_case_for_name(c, name+'/xx'))
Exemple #2
0
    def test_actual_case(self):
        " Test getting the actual case for files from names on case insensitive filesystems "
        from calibre.ebooks.oeb.polish.utils import actual_case_for_name, corrected_case_for_name

        book = get_simple_book()
        c = get_container(book)
        name = "f1/f2/added file.html"
        c.add_file(name, b"xxx")
        self.assertTrue(c.exists(name))
        variations = (name, name.upper(), name.replace("f1", "F1"), name.replace("f2", "F2"))
        if c.exists(name.upper()):
            for n in variations:
                self.assertEqual(name, actual_case_for_name(c, n))
        else:
            for n in variations:
                self.assertEqual(name, corrected_case_for_name(c, n))
            self.assertIsNone(corrected_case_for_name(c, name + "/xx"))
Exemple #3
0
def check_links(container):
    links_map = defaultdict(set)
    xml_types = {guess_type('a.opf'), guess_type('a.ncx')}
    errors = []
    a = errors.append

    def fl(x):
        x = repr(x)
        if x.startswith('u'):
            x = x[1:]
        return x

    for name, mt in container.mime_map.iteritems():
        if mt in OEB_DOCS or mt in OEB_STYLES or mt in xml_types:
            for href, lnum, col in container.iterlinks(name):
                try:
                    tname = container.href_to_name(href, name)
                except ValueError:
                    tname = None  # Absolute paths to files on another drive in windows cause this
                if tname is not None:
                    if container.exists(tname):
                        if tname in container.mime_map:
                            links_map[name].add(tname)
                        else:
                            # Filesystem says the file exists, but it is not in
                            # the mime_map, so either there is a case mismatch
                            # or the link is a directory
                            apath = container.name_to_abspath(tname)
                            if os.path.isdir(apath):
                                a(
                                    BadLink(
                                        _('The linked resource %s is a directory'
                                          ) % fl(href), name, lnum, col))
                            else:
                                a(
                                    CaseMismatch(
                                        href,
                                        actual_case_for_name(container, tname),
                                        name, lnum, col))
                    else:
                        cname = corrected_case_for_name(container, tname)
                        if cname is not None:
                            a(CaseMismatch(href, cname, name, lnum, col))
                        else:
                            a(
                                BadLink(
                                    _('The linked resource %s does not exist')
                                    % fl(href), name, lnum, col))
                else:
                    purl = urlparse(href)
                    if purl.scheme == 'file':
                        a(
                            FileLink(
                                _('The link %s is a file:// URL') % fl(href),
                                name, lnum, col))
                    elif purl.path and purl.path.startswith(
                            '/') and purl.scheme in {'', 'file'}:
                        a(
                            LocalLink(
                                _('The link %s points to a file outside the book'
                                  ) % fl(href), name, lnum, col))

    spine_docs = {name for name, linear in container.spine_names}
    spine_styles = {
        tname
        for name in spine_docs for tname in links_map[name]
        if container.mime_map.get(tname, None) in OEB_STYLES
    }
    num = -1
    while len(spine_styles) > num:
        # Handle import rules in stylesheets
        num = len(spine_styles)
        spine_styles |= {
            tname
            for name in spine_styles for tname in links_map[name]
            if container.mime_map.get(tname, None) in OEB_STYLES
        }
    seen = set(OEB_DOCS) | set(OEB_STYLES)
    spine_resources = {
        tname
        for name in spine_docs | spine_styles for tname in links_map[name]
        if container.mime_map[tname] not in seen
    }
    unreferenced = set()

    cover_name = container.guide_type_map.get('cover', None)

    for name, mt in container.mime_map.iteritems():
        if mt in OEB_STYLES and name not in spine_styles:
            a(UnreferencedResource(name))
        elif mt in OEB_DOCS and name not in spine_docs:
            a(UnreferencedDoc(name))
        elif (mt in OEB_FONTS or mt.partition('/')[0] in {
                'image', 'audio', 'video'
        }) and name not in spine_resources and name != cover_name:
            a(UnreferencedResource(name))
        else:
            continue
        unreferenced.add(name)

    manifest_names = set(container.manifest_id_map.itervalues())
    for name in container.mime_map:
        if name not in manifest_names and not container.ok_to_be_unmanifested(
                name):
            a(Unmanifested(name, unreferenced=name in unreferenced))
        if name == 'META-INF/calibre_bookmarks.txt':
            a(Bookmarks(name))

    return errors
Exemple #4
0
def check_links(container):
    links_map = defaultdict(set)
    xml_types = {guess_type('a.opf'), guess_type('a.ncx')}
    errors = []
    a = errors.append

    def fl(x):
        x = repr(x)
        if x.startswith('u'):
            x = x[1:]
        return x

    for name, mt in container.mime_map.iteritems():
        if mt in OEB_DOCS or mt in OEB_STYLES or mt in xml_types:
            for href, lnum, col in container.iterlinks(name):
                try:
                    tname = container.href_to_name(href, name)
                except ValueError:
                    tname = None  # Absolute paths to files on another drive in windows cause this
                if tname is not None:
                    if container.exists(tname):
                        if tname in container.mime_map:
                            links_map[name].add(tname)
                        else:
                            # Filesystem says the file exists, but it is not in
                            # the mime_map, so either there is a case mismatch
                            # or the link is a directory
                            apath = container.name_to_abspath(tname)
                            if os.path.isdir(apath):
                                a(BadLink(_('The linked resource %s is a directory') % fl(href), name, lnum, col))
                            else:
                                a(CaseMismatch(href, actual_case_for_name(container, tname), name, lnum, col))
                    else:
                        cname = corrected_case_for_name(container, tname)
                        if cname is not None:
                            a(CaseMismatch(href, cname, name, lnum, col))
                        else:
                            a(BadLink(_('The linked resource %s does not exist') % fl(href), name, lnum, col))
                else:
                    purl = urlparse(href)
                    if purl.scheme == 'file':
                        a(FileLink(_('The link %s is a file:// URL') % fl(href), name, lnum, col))
                    elif purl.path and purl.path.startswith('/') and purl.scheme in {'', 'file'}:
                        a(LocalLink(_('The link %s points to a file outside the book') % fl(href), name, lnum, col))

    spine_docs = {name for name, linear in container.spine_names}
    spine_styles = {tname for name in spine_docs for tname in links_map[name] if container.mime_map.get(tname, None) in OEB_STYLES}
    num = -1
    while len(spine_styles) > num:
        # Handle import rules in stylesheets
        num = len(spine_styles)
        spine_styles |= {tname for name in spine_styles for tname in links_map[name] if container.mime_map.get(tname, None) in OEB_STYLES}
    seen = set(OEB_DOCS) | set(OEB_STYLES)
    spine_resources = {tname for name in spine_docs | spine_styles for tname in links_map[name] if container.mime_map[tname] not in seen}
    unreferenced = set()

    cover_name = container.guide_type_map.get('cover', None)

    for name, mt in container.mime_map.iteritems():
        if mt in OEB_STYLES and name not in spine_styles:
            a(UnreferencedResource(name))
        elif mt in OEB_DOCS and name not in spine_docs:
            a(UnreferencedDoc(name))
        elif (mt in OEB_FONTS or mt.partition('/')[0] in {'image', 'audio', 'video'}) and name not in spine_resources and name != cover_name:
            a(UnreferencedResource(name))
        else:
            continue
        unreferenced.add(name)

    manifest_names = set(container.manifest_id_map.itervalues())
    for name in container.mime_map:
        if name not in manifest_names and not container.ok_to_be_unmanifested(name):
            a(Unmanifested(name, unreferenced=name in unreferenced))
        if name == 'META-INF/calibre_bookmarks.txt':
            a(Bookmarks(name))

    return errors