Я написал простой сценарий, который должен запрашивать корневую карту сайта по заданному адресу (в файле sitedefs.txt), анализировать xml, а затем загружать все дочерние карты сайта на этой странице и сжимать их в файл gzip. Некоторые из этих файлов Sitemap уже находятся в сжатом файле, что означает, что мне нужно загрузить эти файлы, а затем переместить их в соответствующий каталог. Тем не менее, при загрузке этих файлов селен ведет себя очень странно. Иногда он может успешно загрузить файл, но в большинстве случаев кажется, что он загружается только частично (файл остается как .crdownload и является ненужным - без EOF) или просто не может создать какую-либо загрузку вообще. Это выполняется на удаленном сервере (с большим количеством ресурсов) под управлением Ubuntu.
import time
import gzip
import lxml.etree as ET
import os
from selenium import webdriver
from pyvirtualdisplay import Display
from selenium.webdriver.chrome.options import Options
options = Options()
options.add_experimental_option("prefs", {
"download.default_directory": r"/home/ubuntu/Downloads",
"download.prompt_for_download": False,
"download.directory_upgrade": True,
"safebrowsing.enabled": True
})
display = Display(visible=0, size=(800, 600))
display.start()
GZIP_LOC = "/home/ubuntu/Downloads"
def get_sitemap_list(root, list):
if "loc" in root.tag:
#print(root.text)
list.append(root.text)
for child in root:
get_sitemap_list(child, list)
def get_content_from_webdriver(wbdriver, url):
wbdriver.get(url)
return wbdriver.page_source
def consume_dlfile(name, dest, wbdriver=None, url=None):
file_loc = os.path.join(GZIP_LOC, name)
el_time = 0
while not os.path.exists(file_loc):
time.sleep(1)
el_time+=1
if el_time > 200:
print("DOWNLOAD TIMED OUT @",file_loc)
if wbdriver and url:
print(get_content_from_webdriver(wbdriver, url))
exit()
os.rename(file_loc, dest)
def main(driver):
with open("sitedefs.txt") as sdf:
for line in sdf:
if line[0] == "#":
continue
else:
spl = line.split(",")
url = spl[1]
print(url)
origin = spl[0]
file_name = spl[2].strip()
try:
os.mkdir(file_name) #we make a new folder for our junt
except FileExistsError:
pass
content = get_content_from_webdriver(driver, url)
if url[-3:] == ".gz":
download = url.split("/")[-1]
consume_dlfile(download,os.path.join(file_name, "rootf.xml.gz"))
with gzip.open(os.path.join(file_name, "rootf.xml.gz"),"rb") as gfile:
textl = gfile.read()
else:
textl = content
root = ET.fromstring(textl)
my_list = list()
get_sitemap_list(root, my_list)
i=0
for sitemap in my_list:
print(sitemap)
i+=1
path = os.path.join(file_name, str(i)+".xml.gz")
if (sitemap[-3:] == ".gz"):
download = url.split("/")[-1]
consume_dlfile(download, str(i)+".xml.gz", wbdriver=driver, url=sitemap)
else:
with gzip.open(path, 'wb') as f:
f.write(get_content_from_webdriver(driver, sitemap).encode('utf-8'))
if __name__ == '__main__':
driver = webdriver.Chrome(chrome_options=options)
try:
main(driver)
finally:
driver.close()
Sitedefs - это файл, каждая строка которого отформатирована так:
https://www.shutterstock.com/,https://cdn.shutterstock.com/sitemaps/video/sitemap/sitemap-video-index.xml,shutterstock
По разным причинам, к сожалению, мы вынуждены использовать селен вместо запросов. Некоторые веб-сайты, хотя и явно предоставляют файлы Sitemap, по-видимому, имеют средства защиты, которые защищают запросы - даже если указаны правильные заголовки.