J'essaie de rassembler des informations sur les prix pour chaque variante de produit à partir de cette page Web : https ://www.safetysign.com/products/7337/ez-pipe-marker

J'utilise Selenium et FireFox avec Python 3 et Windows 10.

Voici mon code actuel:

driver = webdriver.Firefox()
driver.get('https://www.safetysign.com/products/7337/ez-pipe-marker')
#frame = driver.find_element_by_class_name('product-dual-holder')
# driver.switch_to.frame('skuer5c866ddb91611')
# driver.implicitly_wait(5)
driver.find_element_by_id('skuer5c866ddb91611-size-label-324').click()   
price = driver.find_element_by_class_name("product-pricingnodecontent product-price-content").text.replace('$', '')
products.at[counter, 'safetysign.com Price'] = price
print(price)
print(products['safetysign.com URL'].count()-counter)

Donc, j'essaie de commencer par sélectionner simplement la première variation de produit par id (j'ai également essayé le nom de la classe). Mais, j'obtiens une erreur d'élément impossible à localiser. Comme suggéré dans de nombreux articles SO, j'ai essayé de changer les cadres (même si je ne trouve pas de balise de cadre dans le html qui contient cet élément). J'ai essayé de passer à différents cadres en utilisant l'index, le nom de classe et l'id de différents éléments div que je pensais être un cadre, mais rien de tout cela n'a fonctionné. J'ai également essayé d'utiliser des temps d'attente, mais cela renvoie la même erreur.

Une idée de ce qui me manque ou que je fais mal?

1
Jarod Jacobs 11 mars 2019 à 17:59

2 réponses

Meilleure réponse

Ils peuvent bien être dynamiques. Sélectionnez plutôt par label sélecteur de type et indexez pour cliquer sur l'élément requis, par ex. 0 pour l'élément que vous mentionnez (premier dans la liste). Ajoutez également une condition d'attente pour que label soit présent.

Si vous souhaitez vous limiter à ces 5 size choix, utilisez le sélecteur css suivant au lieu de label:

.sku-contents ul:nth-child(3) label

C'est à dire.

sizes = WebDriverWait(driver,10).until(EC.presence_of_all_elements_located((By.CSS_SELECTOR, ".sku-contents ul:nth-child(3) label")))
sizes[0].click()

Après avoir sélectionné la taille, vous pouvez récupérer le prix à partir du nœud de prix selon que vous souhaitez le prix pour une taille d'échantillon donnée, par exemple 0-99.

Pour obtenir le prix final, utilisez:

.product-under-sku-total-label

Code:

from selenium import webdriver
from selenium.webdriver.common.by import By
from selenium.webdriver.support.ui import WebDriverWait
from selenium.webdriver.support import expected_conditions as EC
url = 'https://www.safetysign.com/products/7337/ez-pipe-marker'
driver = webdriver.Chrome()
driver.get(url)
labels = WebDriverWait(driver,10).until(EC.presence_of_all_elements_located((By.CSS_SELECTOR, "label")))
labels[0].click()
price0to99 = driver.find_element_by_css_selector('.product-pricingnodecontent').text
priceTotal = driver.find_element_by_css_selector('.product-under-sku-total-label').text
print(priceTotal, price0To99)
# driver.quit()
0
QHarr 11 mars 2019 à 16:52

Pour localiser les éléments, vous devez induire WebDriverWait pour le visibility_of_all_elements_located() et vous pouvez créer une Liste et la parcourir jusqu'à click() chaque élément et vous peut utiliser la solution suivante :

  • Bloc de code:

    from selenium import webdriver
    from selenium.webdriver.common.by import By
    from selenium.webdriver.support.ui import WebDriverWait
    from selenium.webdriver.support import expected_conditions as EC
    
    
    driver=webdriver.Firefox(executable_path=r'C:\Utility\BrowserDrivers\geckodriver.exe')
    driver.get("https://www.safetysign.com/products/7337/ez-pipe-marker")
    for product in WebDriverWait(driver, 20).until(EC.visibility_of_all_elements_located((By.XPATH, "//form[@class='product-page-form']//div[@class='sku-contents']//following::ul[1]/li//label[starts-with(@for, 'skuer') and contains(., 'Pipe')]"))):
        WebDriverWait(driver, 20).until(EC.visibility_of(product)).click()
    driver.quit()
    
1
DebanjanB 11 mars 2019 à 16:46