]> git.phdru.name Git - bookmarks_db.git/blobdiff - parse_html/bkmk_ph_beautifulsoup.py
Fix(parse_html): Do not parse empty strings
[bookmarks_db.git] / parse_html / bkmk_ph_beautifulsoup.py
index f796744a406812e92cbd208b8b132adf88f47643..0aad3dde72557abdb2f97edeea4d814151f388f6 100644 (file)
@@ -5,7 +5,7 @@ This file is a part of Bookmarks database and Internet robot.
 """
 
 __author__ = "Oleg Broytman <phd@phdru.name>"
-__copyright__ = "Copyright (C) 2007-2017 PhiloSoft Design"
+__copyright__ = "Copyright (C) 2007-2023 PhiloSoft Design"
 __license__ = "GNU GPL"
 
 __all__ = ['parse_html']
@@ -14,11 +14,15 @@ __all__ = ['parse_html']
 import re
 from sgmllib import SGMLParser, SGMLParseError
 from BeautifulSoup import BeautifulSoup, CData
+
 from .bkmk_ph_util import HTMLParser
+from compat import string_type
 
-DEFAULT_CHARSET = "cp1251" # Stupid default for Russian Cyrillic
+DEFAULT_CHARSET = "cp1251"  # Stupid default for Russian Cyrillic
 
 # http://groups.google.com/group/beautifulsoup/browse_thread/thread/69093cb0d3a3cf63
+
+
 class BadDeclParser(BeautifulSoup):
     def parse_declaration(self, i):
         """Treat a bogus SGML declaration as raw data. Treat a CDATA
@@ -37,7 +41,10 @@ class BadDeclParser(BeautifulSoup):
             except SGMLParseError:
                 # Could not parse the DOCTYPE declaration
                 # Try to just skip the actual declaration
-                match = re.search(r'<!DOCTYPE([^>]*?)>', self.rawdata[i:], re.MULTILINE|re.IGNORECASE)
+                match = re.search(
+                    r'<!DOCTYPE([^>]*?)>', self.rawdata[i:],
+                    re.MULTILINE|re.IGNORECASE)  # noqa: E227
+                #           missing whitespace around bitwise or shift operator
                 if match:
                     toHandle = self.rawdata[i:match.end()]
                 else:
@@ -53,13 +60,17 @@ def _parse_html(html_text, charset):
     except TypeError:
         return None
 
+
 def parse_html(html_text, charset=None, log=None):
+    if not html_text:
+        return None
     root = _parse_html(html_text, charset)
     if root is None:
         return None
 
     _charset = root.originalEncoding
-    if _charset in ("ISO-8859-2", "windows-1252", "MacCyrillic"): # Replace default
+    if _charset in ("ISO-8859-2", "windows-1252", "MacCyrillic"):
+        # Replace with default and re-parse
         _charset = DEFAULT_CHARSET
         root = _parse_html(html_text, _charset)
         if root is None:
@@ -71,7 +82,7 @@ def parse_html(html_text, charset=None, log=None):
 
     head = html.head
     if head is None:
-        head = html # Some sites put TITLE in HTML without HEAD
+        head = html  # Some sites put TITLE in HTML without HEAD
 
     title = head.title
     if (title is None) and (html is not head):
@@ -88,8 +99,8 @@ def parse_html(html_text, charset=None, log=None):
         else:
             parts = []
             for part in title:
-                if not isinstance(part, basestring):
-                    part = unicode(part)
+                if not isinstance(part, string_type):
+                    part = part.decode()
                 parts.append(part.strip())
             title = ''.join(parts)
 
@@ -98,10 +109,11 @@ def parse_html(html_text, charset=None, log=None):
         try:
             meta_content = meta.get("content")
             if meta_content:
-                __charset = meta_content.lower().split('charset=')[1].split(';')[0]
+                __charset = meta_content.lower().split('charset=')[1].\
+                    split(';')[0]
             else:
                 __charset = False
-        except IndexError: # No charset in the META Content-Type
+        except IndexError:  # No charset in the META Content-Type
             meta_charset = False
         else:
             meta_charset = _charset == __charset
@@ -115,8 +127,8 @@ def parse_html(html_text, charset=None, log=None):
             if meta_content:
                 meta_charset = _charset = meta_content.lower()
 
-    if title and (_charset or meta_charset):
-        title = title.encode(_charset or meta_charset)
+    #if title and (_charset or meta_charset):
+    #    title = title.encode(_charset or meta_charset)
 
     meta = head.find(_find_refresh, recursive=False)
     if meta:
@@ -134,17 +146,21 @@ def parse_html(html_text, charset=None, log=None):
         return None
     return HTMLParser(_charset, meta_charset, title, refresh, icon)
 
+
 def _find_contenttype(Tag):
     return (Tag.name == "meta") and \
        (Tag.get("http-equiv", '').lower() == "content-type")
 
+
 def _find_charset(Tag):
     return (Tag.name == "meta") and Tag.get("charset", '')
 
+
 def _find_refresh(Tag):
     return (Tag.name == "meta") and \
        (Tag.get("http-equiv", '').lower() == "refresh")
 
+
 def _find_icon(Tag):
     return (Tag.name == "link") and \
        (Tag.get("rel", '').lower() in ('icon', 'shortcut icon'))