【问题标题】:Iterating dependent dropdowns with Python使用 Python 迭代依赖下拉列表
【发布时间】:2017-02-03 08:37:28
【问题描述】:

作为一名 Python 新手,我正在尝试从 This Site 中抓取一些数据

主要目标是使用 pandas 为 excel 文件中的每个选项获取数据。

作为第一步,我们尝试使用以下代码从下拉列表中获取所有选项。 (Python 3.6.0)

import sys
import signal
from selenium import webdriver
from selenium.webdriver.support.ui import Select
from selenium.webdriver.support.ui import WebDriverWait
from selenium.common.exceptions import NoSuchElementException, StaleElementReferenceException

def sigint(signal, frame):
    sys.exit(0)

def make_waitfor_elem_updated_predicate(driver, waitfor_elem_id):
    elem = driver.find_element_by_id(waitfor_elem_id)

    def elem_updated(driver):
        try:
            elem.text
        except StaleElementReferenceException:
            return True
        except:
            pass

        return False

    return lambda driver: elem_updated(driver)

class Scraper(object):
    def __init__(self):
        self.url = 'https://seffaflik.epias.com.tr/transparency/uretim/planlama/kgup.xhtml'
        self.driver = webdriver.Chrome()
        self.driver.maximize_window()

    def get_select(self, id):
        select_elem = self.driver.find_element_by_id(id)
        select = Select(select_elem)
        return select

    def select_option(self, id, value, waitfor_elem_id=None):
        if waitfor_elem_id:
            func = make_waitfor_elem_updated_predicate(
                self.driver, 
                waitfor_elem_id
            )

        select = self.get_select(id)
        select.select_by_value(value)

        if waitfor_elem_id:
            wait = WebDriverWait(self.driver, 10)
            wait.until(func)

        return self.get_select(id)

    def make_select_option_iterator(self, id, waitfor_elem_id):
        def next_option(id, waitfor_elem_id):
            select = self.get_select(id)
            select_option_values = [ 
                '%s' % o.get_attribute('value') 
                for o 
                in select.options 
                if o.text != 'TÜMÜ'
            ]

            for v in select_option_values:
                select = self.select_option(id, v, waitfor_elem_id)
                yield select.first_selected_option.text

        return lambda: next_option(id, waitfor_elem_id)

    def load_page(self):
        self.driver.get(self.url)

        def page_loaded(driver):
            id = 'j_idt102:distributionId_input'
            return driver.find_element_by_id(id)

        wait = WebDriverWait(self.driver, 10)
        wait.until(page_loaded)            

    def scrape(self):
        organisations = self.make_select_option_iterator(
            'j_idt102:distributionId_input',
            'j_idt102:uevcb_input'
        )

        units = self.make_select_option_iterator(
            'j_idt102:uevcb_input',
            'j_idt102:uevcb_input'
        )


        self.load_page()

        for organisation in organisations():
            print (organisation)
            for unit in units():
                print (2*' ', unit)

if __name__ == '__main__':
    signal.signal(signal.SIGINT, sigint)
    scraper = Scraper()
    scraper.scrape()

我们从选择元素中获取 id,但错误代码显示:

selenium.common.exceptions.UnexpectedTagNameException: Message: Select only works on elements, not on 

对此有什么想法吗?

谢谢。

【问题讨论】:

    标签: python python-3.x selenium drop-down-menu web-scraping


    【解决方案1】:

    这是因为您尝试将Select 类应用于<div> 元素,而您只能将Select<select> 元素一起使用!

    尝试通过点击下拉按钮然后点击所需选项来处理下拉菜单,例如:

    driver.find_element_by_id('j_idt102:distributionId_label').click() # opens drop-down
    driver.find_element_by_id('j_idt102:distributionId_1').click() # select option
    

    【讨论】:

    • 那么我应该如何为每个选项迭代它?谢谢。
    • 每个下拉列表中的选项只是无序列表 (<ul>) 中的列表项 (<li>)。您可以从下拉列表中获取选项列表drop_down = driver.find_element_by_xpath('//div[@class="ui-selectonemenu-panel ui-widget ui-widget-content ui-corner-all ui-helper-hidden ui-shadow"][contains(@style, "display: block")]')drop_down.find_elements_by_xpath('.//li[@class="ui-selectonemenu-item ui-selectonemenu-list-item ui-corner-all ui-state-highlight"]')
    • 非常感谢(再次!)
    猜你喜欢
    • 2021-06-11
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    相关资源
    最近更新 更多