2009-01-19 64 views
3

我在用BeautifulSoup解析一些狡猾的HTML時遇到了麻煩。事實證明,在較新版本中使用的HTMLParser比以前使用的SGMLParser具有更小的容錯性。BeautifulSoup 3.1解析器太容易打破


BeautifulSoup有某種調試模式嗎?我試圖找出如何阻止它borking一些討厭的HTML我從倔網站加載:

<HTML> 
    <HEAD> 
     <TITLE>Title</TITLE> 
     <HTTP-EQUIV="PRAGMA" CONTENT="NO-CACHE"> 
    </HEAD> 
    <BODY> 
     ... 
     ... 
    </BODY> 
</HTML> 

BeautifulSoup的<HTTP-EQUIV...>標籤

In [1]: print BeautifulSoup(c).prettify() 
<html> 
<head> 
    <title> 
    Title 
    </title> 
</head> 
</html> 

的問題顯然是後放棄HTTP-EQUIV標記,它實際上是畸形的<META HTTP-EQUIV="PRAGMA" CONTENT="NO-CACHE">標記。顯然,我需要將其指定爲自閉,但不管如何我指定我不能修復它:

In [2]: print BeautifulSoup(c,selfClosingTags=['http-equiv', 
          'http-equiv="pragma"']).prettify() 
<html> 
<head> 
    <title> 
    Title 
    </title> 
</head> 
</html> 

是否有詳細的調試模式,其中BeautifulSoup會告訴我它在做什麼,所以在這種情況下,我可以弄清楚它作爲標籤名稱是什麼?

回答

2

您的問題必須是別的;它工作正常,我:

In [1]: import BeautifulSoup 

In [2]: c = """<HTML> 
    ...:  <HEAD> 
    ...:   <TITLE>Title</TITLE> 
    ...:   <HTTP-EQUIV="PRAGMA" CONTENT="NO-CACHE"> 
    ...:  </HEAD> 
    ...:  <BODY> 
    ...:   ... 
    ...:   ... 
    ...:  </BODY> 
    ...: </HTML> 
    ...: """ 

In [3]: print BeautifulSoup.BeautifulSoup(c).prettify() 
<html> 
<head> 
    <title> 
    Title 
    </title> 
    <http-equiv> 
    </http-equiv> 
</head> 
<body> 
    ... 
     ... 
</body> 
</html> 


In [4]: 

這是Python的2.5.2與BeautifulSoup 3.0.7a - 也許這是中老年/新版本有什麼不同?這正是BeautifulSoup處理得如此精美的那種湯,所以我懷疑它在某個時候已經發生了變化......在結構中還有別的東西,你沒有在問題中提到過嗎?

+0

我有Python 2.5.1和BeautifulSoup 3.1.0.1。原始的破碎結構是不同的,但問題也出現在問題的簡化結構中。我剛剛在您的示例中運行了代碼,並且遇到了與以前相同的問題,在之後沒有任何問題。現在我真的很困惑! – Mat 2009-01-19 23:49:26

6

Having problems with Beautiful Soup 3.1.0?建議使用html5lib的解析器作爲解決方法之一。

#!/usr/bin/env python 
from html5lib import HTMLParser, treebuilders 

parser = HTMLParser(tree=treebuilders.getTreeBuilder("beautifulsoup")) 

c = """<HTML> 
    <HEAD> 
     <TITLE>Title</TITLE> 
     <HTTP-EQUIV="PRAGMA" CONTENT="NO-CACHE"> 
    </HEAD> 
    <BODY> 
     ... 
     ... 
    </BODY> 
</HTML>""" 

soup = parser.parse(c) 
print soup.prettify() 

輸出:

<html> 
<head> 
    <title> 
    Title 
    </title> 
</head> 
<body> 
    <http-equiv="pragma" content="NO-CACHE"> 
    ... 
     ... 
    </http-equiv="pragma"> 
</body> 
</html> 

的輸出表明html5lib還沒有固定在這種情況下,問題雖然。

3

嘗試lxml(及其html模塊)。儘管它的名字,它也用於解析和刮取HTML。它比BeautifulSoup快得多,甚至比BeautifulSoup處理「破碎」的HTML更好。如果您不想學習lxml API,它也具有用於BeautifulSoup的兼容性API。

Ian Blicking agrees

沒有理由再使用BeautifulSoup,除非您使用的是Google App Engine或其他任何不是純粹Python不允許的東西。