簡體   English   中英

無法使用 Selenium Python 將日期輸入到帶有 shadow-root(用戶代理)的字段

[英]Cannot input date to field with shadow-root (user-agent) with Selenium Python

我正在嘗試編寫一個穩定的代碼來將日期輸入到日歷輸入字段中。 本機 Selenium 輸入僅在本地工作,但是當我在 CICD 中運行此代碼時,我發現有時將數字輸入到錯誤的位置。

例如,時間戳為2022-07-22 00:56:42. 用戶的預期輸入是220720220056 通過實驗,我發現如果年份前面有兩個零,那一年就有效。 因此,我實際發送的是22070020220056

    input_field = driver.find_element(By.XPATH, "//div[@role='dialog']//input[@type='datetime-local']")
    input_field.click()
    input_field.clear()
    input_field.send_keys(22070020220056)

 <input _ngcontent-pau-c188="" clrinput="" type="datetime-local" name="expiry" aria-describedby="clr-form-control-9-helper" id="clr-form-control-9" class="clr-input ng-pristine ng-valid ng-touched"> #shadow-root (user-agent) == $0 <div pseudo="-webkit-datetime-edit" id="date-time-edit" datetimeformat="dd/MM/y, HH:mm"> <div pseudo="-webkit-datetime-edit-fields-wrapper"> <span role="spinbutton" aria-placeholder="dd" aria-valuemin="1" aria-valuemax="31" aria-label="Day" pseudo="-webkit-datetime-edit-day-field" aria-valuenow="25" aria-valuetext="25">25</span> <div pseudo="-webkit-datetime-edit-text">/</div> <span role="spinbutton" aria-placeholder="mm" aria-valuemin="1" aria-valuemax="12" aria-label="Month" pseudo="-webkit-datetime-edit-month-field" aria-valuenow="7" aria-valuetext="07">07</span> <div pseudo="-webkit-datetime-edit-text">/</div> <span role="spinbutton" aria-placeholder="yyyy" aria-valuemin="1" aria-valuemax="275760" aria-label="Year" pseudo="-webkit-datetime-edit-year-field" aria-valuenow="2022" aria-valuetext="2022">2022</span> <div pseudo="-webkit-datetime-edit-text">, </div> <span role="spinbutton" aria-placeholder="--" aria-valuemin="0" aria-valuemax="23" aria-label="Hours" pseudo="-webkit-datetime-edit-hour-field" aria-valuenow="0" aria-valuetext="00">00</span> <div pseudo="-webkit-datetime-edit-text">:</div> <span role="spinbutton" aria-placeholder="--" aria-valuemin="0" aria-valuemax="59" aria-label="Minutes" pseudo="-webkit-datetime-edit-minute-field" aria-valuenow="1" aria-valuetext="01">01</span> </div> </div> </input>

在此處輸入圖像描述

字段如下所示: 在此處輸入圖像描述

我嘗試了一些其他選項來使測試更穩定。

選項1。

試圖直接設置值。

driver.execute_script(f"arguments[0].setAttribute('value', '{my_timestamp}')", input_field)

選項 2

試圖訪問影子根:

date_field = driver.execute_script("return document.querySelector('input[type=datetime-local]').shadowRoot.getElementById('#date-time-edit')")
date_field.send_keys(my_timestamp)

選項 3

嘗試使用execute_script而不是 Selenium 獲取父元素並發送值:

date_field = driver.execute_script("return document.querySelector('input[type=datetime-local]')")
date_field.send_keys(my_timestamp)

選項 4

嘗試在每個字母之前稍稍延遲發送文本:

    for letter in timestamp:
        time.sleep(0.1)
        print(f"Sending letter {letter}")
        date_field.send_keys(letter)

這些方法都不適用於 CICD,只有初始方法和選項 3 始終在本地工作。

我認為唯一穩定的解決方案是使用 Javascipt 代碼,但仍不確定。

任何建議將不勝感激。

啊,是的,影子根。 對我來說,有效的方法如下:

shadowRootElement = driver.execute_script('''return document.querySelector("selector for shadowRoot's parent").shadowRoot''')

shadowRootChild = driver.execute_script('''return arguments[0].querySelector("selector for shadowRoot's parent").shadowRoot''', shadowRootElement)

shadowRootChild.find_element(By.CSS_SELECTOR, 'input[type=datetime-local]').send_keys("This is a test");

<input>看起來完全超出了#shadow-root (user-agent) 的范圍。

<input _ngcontent-pau-c188="" clrinput="" type="datetime-local" name="expiry" aria-describedby="clr-form-control-9-helper" id="clr-form-control-9" class="clr-input ng-pristine ng-valid ng-touched">
#shadow-root (user-agent) == $0
    <div pseudo="-webkit-datetime-edit" id="date-time-edit" datetimeformat="dd/MM/y, HH:mm">
        <div pseudo="-webkit-datetime-edit-fields-wrapper">
        .
        .
        .
        </div>
    </div>
</input>

但是,所需的元素是Angular元素,因此理想情況下,要將字符序列發送到需要為element_to_be_clickable()誘導WebDriverWait的元素,您可以使用以下定位器策略

  • 使用XPATH

     input_field = WebDriverWait(driver, 20).until(EC.element_to_be_clickable((By.XPATH, "//input[@class='clr-input ng-pristine ng-valid ng-touched' and @name='expiry'][@type='datetime-local']"))) driver.execute_script(f"arguments[0].setAttribute('value', '{my_timestamp}')", input_field)
  • 注意:您必須添加以下導入:

     from selenium.webdriver.support.ui import WebDriverWait from selenium.webdriver.common.by import By from selenium.webdriver.support import expected_conditions as EC

暫無
暫無

聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.

 
粵ICP備18138465號  © 2020-2024 STACKOOM.COM