home *** CD-ROM | disk | FTP | other *** search
/ Maximum CD 2010 November / maximum-cd-2010-11.iso / DiscContents / calibre-0.7.13.msi / file_2038 (.txt) < prev    next >
Encoding:
Python Compiled Bytecode  |  2010-08-06  |  11.3 KB  |  303 lines

  1. # Source Generated with Decompyle++
  2. # File: in.pyc (Python 2.6)
  3.  
  4. import re
  5. import htmlentitydefs
  6. import sgmllib
  7. import HTMLParser
  8. from xml.sax import saxutils
  9. from _html import unescape, unescape_charref
  10.  
  11. class NoMoreTokensError(Exception):
  12.     pass
  13.  
  14.  
  15. class Token:
  16.     
  17.     def __init__(self, type, data, attrs = None):
  18.         self.type = type
  19.         self.data = data
  20.         self.attrs = attrs
  21.  
  22.     
  23.     def __iter__(self):
  24.         return iter((self.type, self.data, self.attrs))
  25.  
  26.     
  27.     def __eq__(self, other):
  28.         (type, data, attrs) = other
  29.         if self.type == type and self.data == data and self.attrs == attrs:
  30.             return True
  31.         return False
  32.  
  33.     
  34.     def __ne__(self, other):
  35.         return not self.__eq__(other)
  36.  
  37.     
  38.     def __repr__(self):
  39.         args = ', '.join(map(repr, [
  40.             self.type,
  41.             self.data,
  42.             self.attrs]))
  43.         return self.__class__.__name__ + '(%s)' % args
  44.  
  45.     
  46.     def __str__(self):
  47.         if self.type == 'starttag':
  48.             return '<%s%s>' % (self.data, attrs)
  49.         if self.type == 'startendtag':
  50.             return '<%s%s />' % (self.data, attrs)
  51.         if self.type == 'endtag':
  52.             return '</%s>' % self.data
  53.         if self.type == 'charref':
  54.             return '&#%s;' % self.data
  55.         if self.type == 'entityref':
  56.             return '&%s;' % self.data
  57.         if self.type == 'data':
  58.             return self.data
  59.         if self.type == 'comment':
  60.             return '<!--%s-->' % self.data
  61.         if self.type == 'decl':
  62.             return '<!%s>' % self.data
  63.         if self.type == 'pi':
  64.             return '<?%s>' % self.data
  65.  
  66.  
  67.  
  68. def iter_until_exception(fn, exception, *args, **kwds):
  69.     while None:
  70.         
  71.         try:
  72.             yield fn(*args, **kwds)
  73.         continue
  74.         except exception:
  75.             raise StopIteration
  76.             continue
  77.         
  78.  
  79.         return None
  80.  
  81.  
  82. class _AbstractParser:
  83.     chunk = 1024
  84.     compress_re = re.compile('\\s+')
  85.     
  86.     def __init__(self, fh, textify = {
  87.         'img': 'alt',
  88.         'applet': 'alt' }, encoding = 'ascii', entitydefs = None):
  89.         self._fh = fh
  90.         self._tokenstack = []
  91.         self.textify = textify
  92.         self.encoding = encoding
  93.         if entitydefs is None:
  94.             entitydefs = htmlentitydefs.name2codepoint
  95.         
  96.         self._entitydefs = entitydefs
  97.  
  98.     
  99.     def __iter__(self):
  100.         return self
  101.  
  102.     
  103.     def tags(self, *names):
  104.         return iter_until_exception(self.get_tag, NoMoreTokensError, *names)
  105.  
  106.     
  107.     def tokens(self, *tokentypes):
  108.         return iter_until_exception(self.get_token, NoMoreTokensError, *tokentypes)
  109.  
  110.     
  111.     def next(self):
  112.         
  113.         try:
  114.             return self.get_token()
  115.         except NoMoreTokensError:
  116.             raise StopIteration()
  117.  
  118.  
  119.     
  120.     def get_token(self, *tokentypes):
  121.         while None:
  122.             while self._tokenstack:
  123.                 token = self._tokenstack.pop(0)
  124.                 if tokentypes:
  125.                     if token.type in tokentypes:
  126.                         return token
  127.                     continue
  128.                 token.type in tokentypes
  129.                 return token
  130.             data = self._fh.read(self.chunk)
  131.             if not data:
  132.                 raise NoMoreTokensError()
  133.             self.feed(data)
  134.             continue
  135.             return None
  136.  
  137.     
  138.     def unget_token(self, token):
  139.         self._tokenstack.insert(0, token)
  140.  
  141.     
  142.     def get_tag(self, *names):
  143.         while None:
  144.             tok = self.get_token()
  145.             if tok.type not in ('starttag', 'endtag', 'startendtag'):
  146.                 continue
  147.             
  148.             if names:
  149.                 if tok.data in names:
  150.                     return tok
  151.                 continue
  152.             return tok
  153.             continue
  154.             return None
  155.  
  156.     
  157.     def get_text(self, endat = None):
  158.         text = []
  159.         tok = None
  160.         while None:
  161.             
  162.             try:
  163.                 tok = self.get_token()
  164.             except NoMoreTokensError:
  165.                 if tok:
  166.                     self.unget_token(tok)
  167.                 
  168.                 break
  169.  
  170.             if tok.type == 'data':
  171.                 text.append(tok.data)
  172.                 continue
  173.             if tok.type == 'entityref':
  174.                 t = unescape('&%s;' % tok.data, self._entitydefs, self.encoding)
  175.                 text.append(t)
  176.                 continue
  177.             if tok.type == 'charref':
  178.                 t = unescape_charref(tok.data, self.encoding)
  179.                 text.append(t)
  180.                 continue
  181.             if tok.type in ('starttag', 'endtag', 'startendtag'):
  182.                 tag_name = tok.data
  183.                 if tok.type in ('starttag', 'startendtag'):
  184.                     alt = self.textify.get(tag_name)
  185.                     if alt is not None:
  186.                         if callable(alt):
  187.                             text.append(alt(tok))
  188.                         elif tok.attrs is not None:
  189.                             for k, v in tok.attrs:
  190.                                 if k == alt:
  191.                                     text.append(v)
  192.                                     continue
  193.                             
  194.                             text.append('[%s]' % tag_name.upper())
  195.                         
  196.                     
  197.                 
  198.                 if endat is None or endat == (tok.type, tag_name):
  199.                     self.unget_token(tok)
  200.                     break
  201.                 
  202.             endat == (tok.type, tag_name)
  203.             continue
  204.             return ''.join(text)
  205.  
  206.     
  207.     def get_compressed_text(self, *args, **kwds):
  208.         text = self.get_text(*args, **kwds)
  209.         text = text.strip()
  210.         return self.compress_re.sub(' ', text)
  211.  
  212.     
  213.     def handle_startendtag(self, tag, attrs):
  214.         self._tokenstack.append(Token('startendtag', tag, attrs))
  215.  
  216.     
  217.     def handle_starttag(self, tag, attrs):
  218.         self._tokenstack.append(Token('starttag', tag, attrs))
  219.  
  220.     
  221.     def handle_endtag(self, tag):
  222.         self._tokenstack.append(Token('endtag', tag))
  223.  
  224.     
  225.     def handle_charref(self, name):
  226.         self._tokenstack.append(Token('charref', name))
  227.  
  228.     
  229.     def handle_entityref(self, name):
  230.         self._tokenstack.append(Token('entityref', name))
  231.  
  232.     
  233.     def handle_data(self, data):
  234.         self._tokenstack.append(Token('data', data))
  235.  
  236.     
  237.     def handle_comment(self, data):
  238.         self._tokenstack.append(Token('comment', data))
  239.  
  240.     
  241.     def handle_decl(self, decl):
  242.         self._tokenstack.append(Token('decl', decl))
  243.  
  244.     
  245.     def unknown_decl(self, data):
  246.         self._tokenstack.append(Token('decl', data))
  247.  
  248.     
  249.     def handle_pi(self, data):
  250.         self._tokenstack.append(Token('pi', data))
  251.  
  252.     
  253.     def unescape_attr(self, name):
  254.         return unescape(name, self._entitydefs, self.encoding)
  255.  
  256.     
  257.     def unescape_attrs(self, attrs):
  258.         escaped_attrs = []
  259.         for key, val in attrs:
  260.             escaped_attrs.append((key, self.unescape_attr(val)))
  261.         
  262.         return escaped_attrs
  263.  
  264.  
  265.  
  266. class PullParser(_AbstractParser, HTMLParser.HTMLParser):
  267.     
  268.     def __init__(self, *args, **kwds):
  269.         HTMLParser.HTMLParser.__init__(self)
  270.         _AbstractParser.__init__(self, *args, **kwds)
  271.  
  272.     
  273.     def unescape(self, name):
  274.         return self.unescape_attr(name)
  275.  
  276.  
  277.  
  278. class TolerantPullParser(_AbstractParser, sgmllib.SGMLParser):
  279.     
  280.     def __init__(self, *args, **kwds):
  281.         sgmllib.SGMLParser.__init__(self)
  282.         _AbstractParser.__init__(self, *args, **kwds)
  283.  
  284.     
  285.     def unknown_starttag(self, tag, attrs):
  286.         attrs = self.unescape_attrs(attrs)
  287.         self._tokenstack.append(Token('starttag', tag, attrs))
  288.  
  289.     
  290.     def unknown_endtag(self, tag):
  291.         self._tokenstack.append(Token('endtag', tag))
  292.  
  293.  
  294.  
  295. def _test():
  296.     import doctest
  297.     import _pullparser
  298.     return doctest.testmod(_pullparser)
  299.  
  300. if __name__ == '__main__':
  301.     _test()
  302.  
  303.