我用python编写了一个脚本,以到达目标页面,该页面的每个类别在网站中都有其可用的项目名称。我的下面的脚本可以从大多数链接(通过流动类别链接,然后通过子类别链接生成)中获取产品名称。
该脚本可以解析在单击每个图片旁边的+
符号后显示的子类别链接,这些符号在下图中可见,然后从目标页面解析所有产品名称。 This is one of such个目标页面。
无论深度如何,如何从所有链接中获得所有产品名称?
这是我到目前为止尝试过的:
import requests
from urllib.parse import urljoin
from bs4 import BeautifulSoup
link = "https://www.courts.com.sg/"
res = requests.get(link)
soup = BeautifulSoup(res.text,"lxml")
for item in soup.select(".nav-dropdown li a"):
if "#" in item.get("href"):continue #kick out invalid links
newlink = urljoin(link,item.get("href"))
req = requests.get(newlink)
sauce = BeautifulSoup(req.text,"lxml")
for elem in sauce.select(".product-item-info .product-item-link"):
print(elem.get_text(strip=True))
如何找到trget链接:
答案 0 :(得分:6)
该网站有六个主要产品类别。也可以在主类别中找到属于子类别的产品(例如,在/furniture/furniture/tables
中也可以找到/furniture
中的产品),因此您只需要从主要类别中收集产品。您可以从主页上获得类别链接,但是使用站点地图会更容易。
url = 'https://www.courts.com.sg/sitemap/'
r = requests.get(url)
soup = BeautifulSoup(r.text, 'html.parser')
cats = soup.select('li.level-0.category > a')[:6]
links = [i['href'] for i in cats]
您已经提到,有些链接具有不同的结构,例如/televisions
。但是,如果单击该页面上的View All Products
链接,您将被重定向到/tv-entertainment/vision/television
。因此,您可以从/televisions
获取所有/tv-entertainment
个产品。同样,可以在主要类别中找到与品牌链接的产品。例如,可以在/asus
和其他类别中找到/computing-mobile
产品。
下面的代码收集所有主要类别的产品,因此它应收集该站点上的所有产品。
from bs4 import BeautifulSoup
import requests
url = 'https://www.courts.com.sg/sitemap/'
r = requests.get(url)
soup = BeautifulSoup(r.text, 'html.parser')
cats = soup.select('li.level-0.category > a')[:6]
links = [i['href'] for i in cats]
products = []
for link in links:
link += '?product_list_limit=24'
while link:
r = requests.get(link)
soup = BeautifulSoup(r.text, 'html.parser')
link = (soup.select_one('a.action.next') or {}).get('href')
for elem in soup.select(".product-item-info .product-item-link"):
product = elem.get_text(strip=True)
products += [product]
print(product)
我已经将每页的产品数量增加到24,但是由于收集所有主要类别及其分页链接的产品,此代码仍需要花费大量时间。但是,使用threads可以使速度更快。
from bs4 import BeautifulSoup
import requests
from threading import Thread, Lock
from urllib.parse import urlparse, parse_qs
lock = Lock()
threads = 10
products = []
def get_products(link, products):
soup = BeautifulSoup(requests.get(link).text, 'html.parser')
tags = soup.select(".product-item-info .product-item-link")
with lock:
products += [tag.get_text(strip=True) for tag in tags]
print('page:', link, 'items:', len(tags))
url = 'https://www.courts.com.sg/sitemap/'
soup = BeautifulSoup(requests.get(url).text, 'html.parser')
cats = soup.select('li.level-0.category > a')[:6]
links = [i['href'] for i in cats]
for link in links:
link += '?product_list_limit=24'
soup = BeautifulSoup(requests.get(link).text, 'html.parser')
last_page = soup.select_one('a.page.last')['href']
last_page = int(parse_qs(urlparse(last_page).query)['p'][0])
threads_list = []
for i in range(1, last_page + 1):
page = '{}&p={}'.format(link, i)
thread = Thread(target=get_products, args=(page, products))
thread.start()
threads_list += [thread]
if i % threads == 0 or i == last_page:
for t in threads_list:
t.join()
print(len(products))
print('\n'.join(products))
此代码在大约5分钟内从773页中收集了18466种产品。我使用10个线程是因为我不想给服务器施加过多压力,但是您可以使用更多线程(大多数服务器可以轻松处理20个线程)。
答案 1 :(得分:2)
答案 2 :(得分:1)
由于您的主要问题是查找链接,因此以下是一个生成器,该生成器将使用其解决方案中指出的站点地图krflol查找所有类别和子类别链接:
connectToStore
要找到产品名称,只需刮掉每个产生的from bs4 import BeautifulSoup
import requests
def category_urls():
response = requests.get('https://www.courts.com.sg/sitemap')
html_soup = BeautifulSoup(response.text, features='html.parser')
categories_sitemap = html_soup.find(attrs={'class': 'xsitemap-categories'})
for category_a_tag in categories_sitemap.find_all('a'):
yield category_a_tag.attrs['href']
。
答案 3 :(得分:1)
我看到了要解析的网站,发现所有产品都位于https://www.courts.com.sg/主页的左下角。单击其中的一个后,我们转到特定类别的广告首页。我们必须去的地方,单击所有产品以获取它。
以下是整个代码:
static func setCurrent(_ user: User, writeToUserDefaults: Bool = false) {
if writeToUserDefaults {
if let data = try? FirestoreEncoder().encode(user) {
print("Encoded Data")
UserDefaults.standard.set(data, forKey: Constants.UserDefaults.currentUser)
}
}
_current = user
}
此函数将返回您的代码未从中抓取的所有类别的所有产品的列表。