Seite 1 von 1
Effektiv viele Dateien von Webseite herunterladen
Verfasst: Dienstag 29. November 2022, 20:45
von leex
Hallo zusammen,
ich suche nach einer Möglichkeit, wie ich den Download von sehr vielen + ständig neu hinzukommenden Dateien, effektiv bewerkstelligen kann. Derzeit habe ich es so implementiert, dass eine Linkliste erstellt wird und danach dann beim abarbeiten geprüft wird, ob es den Pfad schon gibt -> wenn nicht, downloaden. Mir wäre es aber lieber, wenn ich nicht immer wieder alle links holen müsste.
Konkret geht es um diese Webseitdaten:
https://gentool.net/data/zh/
Hat jemand einen Lösungsvorschlag/Hinweis/Framework wie ich das angehen könnte?
LG Leex
Re: Effektiv viele Dateien von Webseite herunterladen
Verfasst: Dienstag 29. November 2022, 22:05
von nezzcarth
Ein klassischer Ansatz dafür (unter Unix/Linux) ist
wget mit den richtigen Parametern + cronjob/systemd-timer. Unter Windows kann man sich evtl. mal
https://www.httrack.com/ oder vergleichbare Tools anschauen. Da braucht man kein Python oder sonst irgendeine Programmiersprache für. Geht natürlich schon, ist aber größerer Aufwand. Interessant wird das vor allem dann, wenn man irgendeine spezielle "Nachverarbeitungs-Logik" braucht.
Re: Effektiv viele Dateien von Webseite herunterladen
Verfasst: Freitag 2. Dezember 2022, 20:20
von leex
Danke für deine Antwort. Läuft alles unter Linux und wird auch danach noch mit python-skripten weiter verarbeitet und in elastic indexiert.
wget kenne ich natürlich, mir ist aber nicht klar wie ich hier die Anforderung umsetzten kann, dass er eben nicht alle Seiten nochmal durchgeht, sondern das er sich merkt wo er aufgehört hat. Das ist ja mein Problem, nicht das downloaden allgemein (das hab ich ja bereits).
Hast du evtl. ein Beispiel?
Re: Effektiv viele Dateien von Webseite herunterladen
Verfasst: Freitag 2. Dezember 2022, 22:14
von leex
Hier mal noch mein aktueller Code, der noch eine Einschränkung auf den Monat hat, sodass ich zumindest nur immer den aktuellen Monat neu crawle:
Code: Alles auswählen
import os
import pathlib
import re
import time
import urllib.request
from datetime import datetime
from bs4 import BeautifulSoup
from pysitemap import crawler
start = f'https://www.gentool.net/data/zh/'
download_path = "./downloads"
def getLinks(start_url):
print(f"Start-URL: {start_url}")
path = pathlib.PurePath(start_url)
print(path.parts[(len(path.parts) - 1)])
str_path = path.parts[(len(path.parts) - 1)]
html_page = urllib.request.urlopen(start_url)
soup = BeautifulSoup(html_page, "lxml")
links = []
for link in soup.findAll('a'):
regex = re.compile(r'\?|data')
if not regex.search(link.get('href')):
print(f"Link: {link.get('href')}")
if not str_path in "zh":
create_path = f"{download_path}/{str_path}/{link.get('href')}"
print(f"Create Path: {create_path}")
else:
create_path = f"{download_path}/{link.get('href')}"
print("no path")
links.append(link.get('href'))
if not os.path.exists(create_path):
os.makedirs(create_path)
return links
def cleanup_links(filename):
with open(filename, "r+") as f:
d = f.readlines()
f.seek(0)
for idx, i in enumerate(d):
if "txt" in i:
print(idx, i)
f.write(i)
f.truncate()
if os.stat(filename).st_size == 0:
print(" Removing ", filename)
os.remove(filename)
if __name__ == '__main__':
while True:
months = getLinks(start)
for month in months:
if month == "2022_11_November/":
filename = f'{month.replace("/", "")}.txt'
print(start + month)
# getLinks(start + month)
crawler(start + month, out_file=filename, exclude_urls=[".rep", ".jpg", "?"], out_format="txt")
cleanup_links("2022_11_November.txt")
print(f"Sleeping 30min {datetime.now()}")
time.sleep(900)
Re: Effektiv viele Dateien von Webseite herunterladen
Verfasst: Freitag 2. Dezember 2022, 22:34
von nezzcarth
So ganz ist mir nicht klar, was du dann noch benötigst und was dein Skript (von dem für mich aus dem Eingangspost nicht klar war, dass es existiert; das klang eher manuell) im Detail tut. Wenn es darum geht, HTTP Requests einzusparen und aus der Struktur, wie die heruntergeladenen Dateien lokal abgelegt werden der ursprüngliche Remote-Pfad/Link nicht mehr hervorgeht, kannst du dir diesen doch einfach nach dem erfolgreichen Herunterladen einer Datei in z.B. einem set merken. Das serialisierst du bei Programmende als z.B. JSON, initialisierst damit das set beim nächsten Durchlauf erneut und überspringst die bereits besuchten Links. Zumindest die Indices musst du aber stets neu abfragen. Falls sich auch an bereits heruntergeladenen Dateien etwas ändern kann, wird es etwas komplizierter und geht nicht ohne zumindest einen HEAD-Request.
EDIT: Das zwischenzeitlich gepostete Skript habe ich noch nicht angesehen.
Re: Effektiv viele Dateien von Webseite herunterladen
Verfasst: Freitag 2. Dezember 2022, 22:38
von leex
Danke, werde das mit dem "set" mal versuchen/recherchieren.
Das Skript liest eigentlich nur alle Links aus und speichert sie in einer Textdatei (2022_11_November.txt). Mit einem zweiten Skript gehe ich die Links dann durch und lade alles herunter, wenn es nicht schon auf der Festplatte (Pfad) vorhanden ist.
Bestehende Links ändern sich nicht mehr.
Re: Effektiv viele Dateien von Webseite herunterladen
Verfasst: Freitag 2. Dezember 2022, 22:45
von Sirius3
Du hast eine seltsame Verwendung von pathlib. Für URLs ist es nicht gedacht, aber dort, wo es sinnvoll wäre, benutzt Du Format-Strings um Pfade zusammenzufummeln, und os.path um Verzeichnisse zu erzeugen.
In `cleanup_links` benutzt Du fast ausschließlich einbuchstabige nichtssagende Variablennamen, um das Lesen besonders schwierig zu machen. Der Filemode r+ wird auch fast nie gebraucht, wie hier, wo es viel klarer und einfacher wäre, einfach eine neue Datei zu erzeugen. Der in-Vergleich ist etwas zu optimistisch.
Code: Alles auswählen
def cleanup_links(filename):
with open(filename, encoding="ascii") as links:
cleaned_links = [
link for link in links
if "txt" in link
]
if cleaned_links:
with open(filename, "w", encoding="ascii") as links:
links.writelines(cleaned_links)
else:
os.remove(filename)
Re: Effektiv viele Dateien von Webseite herunterladen
Verfasst: Freitag 2. Dezember 2022, 22:50
von leex
Danke für das Feedback. Ist ein Freizeitprojekt und habe auch lange daran nichts gemacht und bin gerade jetzt dabei das wieder anzugehen und zu optimieren / weiter zu lernen, weshalb ich auch auf das Forum gestoßen bin. Werde versuchen das umsetzten / ändern ). Bin über jeden Tipp/Hinweis/Lösungsvorschläge/Denkanstöße dankbar. Erwarte keine fertigen Lösungen.
Re: Effektiv viele Dateien von Webseite herunterladen
Verfasst: Samstag 3. Dezember 2022, 13:34
von nezzcarth
Ich habe noch nicht verstanden, warum das zwei getrennte Skripte sein müssen. Links suchen, bereits besuchte Links entfernen und den Rest runterladen geht doch in einem Skript, das auch nicht besonders lang ist.
Re: Effektiv viele Dateien von Webseite herunterladen
Verfasst: Donnerstag 8. Dezember 2022, 18:29
von leex
Da hast du recht. Hat keine logischen Grund. Ist einfach so einfacher für mich als Anfänger gewesen das alles zu trennen. Wenn ich mal alles soweit habe, dass es funktioniert wie ich will, kann ich auch zusammenfassen.