web-dev-qa-db-fra.com

Comment puis-je obtenir des liens href à partir de HTML en utilisant Python?

import urllib2

website = "WEBSITE"
openwebsite = urllib2.urlopen(website)
html = getwebsite.read()

print html

Jusqu'ici tout va bien. 

Mais je ne veux que des liens href à partir du texte brut HTML. Comment puis-je résoudre ce problème? 

35
user371012

Essayez avec Beautifulsoup :

from BeautifulSoup import BeautifulSoup
import urllib2
import re

html_page = urllib2.urlopen("http://www.yourwebsite.com")
soup = BeautifulSoup(html_page)
for link in soup.findAll('a'):
    print link.get('href')

Si vous voulez juste des liens commençant par http://, vous devriez utiliser:

soup.findAll('a', attrs={'href': re.compile("^http://")})
78
systempuntoout

Vous pouvez utiliser le module HTMLParser .

Le code ressemblerait probablement à quelque chose comme ça:

from HTMLParser import HTMLParser

class MyHTMLParser(HTMLParser):

    def handle_starttag(self, tag, attrs):
        # Only parse the 'anchor' tag.
        if tag == "a":
           # Check the list of defined attributes.
           for name, value in attrs:
               # If href is defined, print it.
               if name == "href":
                   print name, "=", value


parser = MyHTMLParser()
parser.feed(your_html_string)

Remarque: Le module HTMLParser a été renommé html.parser dans Python 3.0. L'outil 2to3 adaptera automatiquement les importations lors de la conversion de vos sources vers la version 3.0.

28
Stephen

Regardez à l'aide de la belle bibliothèque d'analyse HTML soupe.

http://www.crummy.com/software/BeautifulSoup/

Vous ferez quelque chose comme ça:

import BeautifulSoup
soup = BeautifulSoup.BeautifulSoup(html)
for link in soup.findAll("a"):
    print link.get("href")
12
Peter Lyons

Utiliser BS4 pour cette tâche spécifique semble excessif.

Essayez plutôt:

website = urllib2.urlopen('http://10.123.123.5/foo_images/Repo/')
html = website.read()
files = re.findall('href="(.*tgz|.*tar.gz)"', html)
print sorted(x for x in (files))

J'ai trouvé ce morceau de code astucieux sur http://www.pythonforbeginners.com/code/regular-expression-re-findall et fonctionne assez bien pour moi.

Je l'ai testé uniquement sur mon scénario d'extraction d'une liste de fichiers d'un dossier Web exposant le fichier files\folder, par exemple:

 enter image description here

et j'ai une liste triée des fichiers\dossiers sous l'URL

7
RaamEE

Ma réponse est probablement nulle par rapport aux vrais gourous, mais en utilisant quelques calculs simples, le découpage en chaîne, la recherche et urllib, ce petit script créera une liste contenant des éléments de lien. Je teste google et ma sortie semble juste. J'espère que ça aide!

import urllib
test = urllib.urlopen("http://www.google.com").read()
sane = 0
needlestack = []
while sane == 0:
  curpos = test.find("href")
  if curpos >= 0:
    testlen = len(test)
    test = test[curpos:testlen]
    curpos = test.find('"')
    testlen = len(test)
    test = test[curpos+1:testlen]
    curpos = test.find('"')
    needle = test[0:curpos]
    if needle.startswith("http" or "www"):
        needlestack.append(needle)
  else:
    sane = 1
for item in needlestack:
  print item
5
0xhughes

Voici une version paresseuse de la réponse de @ stephen

from urllib.request import urlopen
from itertools import chain
from html.parser import HTMLParser

class LinkParser(HTMLParser):
    def reset(self):
        HTMLParser.reset(self)
        self.links = iter([])

    def handle_starttag(self, tag, attrs):
        if tag == 'a':
            for name, value in attrs:
                if name == 'href':
                    self.links = chain(self.links, [value])


def gen_links(f, parser):
    encoding = f.headers.get_content_charset() or 'UTF-8'

    for line in f:
        parser.feed(line.decode(encoding))
        yield from parser.links

Utilisez-le comme suit:

>>> parser = LinkParser()
>>> f = urlopen('http://stackoverflow.com/questions/3075550')
>>> links = gen_links(f, parser)
>>> next(links)
'//stackoverflow.com'
2
reubano

Utilisation de requêtes avec BeautifulSoup et Python 3: 

import requests 
from bs4 import BeautifulSoup


page = requests.get('http://www.website.com')
bs = BeautifulSoup(page.content, features='lxml')
for link in bs.findAll('a'):
    print(link.get('href'))
1
Spas

C’est bien tard pour répondre, mais cela fonctionnera pour les derniers utilisateurs de python:

from bs4 import BeautifulSoup
import requests 


html_page = requests.get('http://www.example.com').text

soup = BeautifulSoup(html_page, "lxml")
for link in soup.findAll('a'):
    print(link.get('href'))

N'oubliez pas d'installer les paquets " request " et " BeautifulSoup " ainsi que " lxml ". Utilisez .text avec get sinon cela lève une exception.

" lxml " est utilisé pour supprimer cet avertissement indiquant quel analyseur utiliser. Vous pouvez également utiliser " html.parser " selon votre cas.

0
sak