【发布时间】:2021-10-05 12:42:24
【问题描述】:
为了在 facebook 页面中抓取帖子的反应,我可以抓取所有信息(cmets、反应、标签等),但是当我想将它们放入数据框中时,会出现错误(数组必须全部长度相同)这是正常的,因为有时有人只发表评论而另一个人只发表标签,所以我有不同长度的列表。我想我可以提出一个条件如果但可能有另一个优化的解决方案...... 例如 len(tag) =2, len(usr) = 17, len(commentaire)=12。
谢谢:)
#imports here
from selenium import webdriver
from selenium.webdriver.common.keys import Keys
from selenium.webdriver.support import expected_conditions as EC
from selenium.webdriver.common.by import By
from selenium.webdriver.support.wait import WebDriverWait
import requests
from bs4 import BeautifulSoup
import time
from time import sleep
from lxml import html
import logging as log
import pandas as pd
#chemin de chrome et desactivation des adds automatique de FB anti scrape
chrome_options = webdriver.ChromeOptions()
prefs = {"profile.default_content_setting_values.notifications" : 2}
chrome_options.add_experimental_option("prefs",prefs)
driver = webdriver.Chrome('C:/Users/User/Downloads/chromedriver.exe',
chrome_options=chrome_options)
#open FB
driver.get("http://www.facebook.com")
print ("facebook page log ok")
sleep(1)
#reperage de user et pass (css_selector)
username = WebDriverWait(driver, 10).until(EC.element_to_be_clickable((By.CSS_SELECTOR,
"input[name='email']")))
password = WebDriverWait(driver, 10).until(EC.element_to_be_clickable((By.CSS_SELECTOR,
"input[name='pass']")))
##reperage de user et pass et click (xpath)
#username = driver.find_element(By.XPATH,"//input[contains(@id,'email')]")
#password = driver.find_element(By.XPATH,"//input[contains(@id,'pass')]")
usr=input('Enter Email Id:')
pwd=input('Enter Password:')
#enter données
username.clear()
username.send_keys(usr)
print ("Email Id entered")
sleep(1)
password.clear()
password.send_keys(pwd)
print ("Pass entered")
#reperage bouton log in et click
button = WebDriverWait(driver, 2).until(EC.element_to_be_clickable((By.CSS_SELECTOR,
"button[type='submit']"))).click()
print("login Successfully...")
time.sleep(5)
post = 'https://mbasic.facebook.com/AJSTunisie/posts/6452145678144265'
#open the webpage
driver.get(post)
page = requests.get(post)
df_comm = pd.DataFrame(columns = ['post_url', 'user', 'commentaire', 'tag', 'user_url'])
page_count = 0
while (True ):
#scrape les reactions
tree = html.fromstring(driver.page_source)
user = tree.xpath("//div[@class='eb']/div/h3/a/text()")
commentaire = tree.xpath("//div[@class='eb']/div/div[1]/text()")
tag = tree.xpath("//div[@class='eb']/div/div[1]/a/text()")
user_url = tree.xpath("//div[@class='eb']/div/h3/a/@href")
data= {'post_url':[post]*len(user), 'user':user, 'commentaire':commentaire, 'tag':tag,
'user_url':user_url}
df_comm = df_comm.append(pd.DataFrame(columns = df_comm.columns,data=data))
#Check if more reaction exist ("En afficher davantage" existe ou pas)
next_link = tree.xpath("//div[@class='eb eu']/a/@href")
if len(next_link)!= 0:
driver.find_element_by_xpath("//div[@class='eb eu']/a/@href").click()
page_count = page_count+1
else :
next_link = ''
break
df_comm =df_comm.reset_index()
#df_comm.to_csv(path,index=False)
driver.close()
【问题讨论】:
-
总是将完整的错误消息(从单词“Traceback”开始)作为文本(不是截图,不是链接到外部门户)有问题(不是评论)。还有其他有用的信息。
-
首先你应该抓取所有帖子,然后你应该使用 for-loop 来分别处理每个帖子,并且在每个帖子中你应该使用相对 xpath 只抓取这个帖子的信息 - 然后你应该创建包含单个帖子信息的列表,并作为单行添加到 DataFrame。这样您就可以查看 post 是否包含所有元素并为缺失值设置默认值。如果您将抓取所有 post_urls、下一个所有用户等,那么您不知道哪个帖子没有标签,也不知道在哪里放置缺失值 - 您可以从第二个帖子中获取带有标签的第一个帖子。
标签: python dataframe selenium xpath python-requests