As you mentioned in your question that you had no issues with this until yesterday to locate the element through:
browser.find_elements_by_xpath('//*[@id="input_205"]').send_keys(viewId)
That's because the desired element was having a static id
assigned.
But now the element id
is dynamic and getting assigned through some JavaScript/AjaxCalls. So to identify the element you have to construct a dynamic Locator Strategy. But your code trials gives us the idea about the id
attribute only. To construct a dymanic locator you can use multiple items from the below mentioned items:
- The
<tagName>
tag e.g. <input>
- The
class
attribute e.g. class="input-full"
- Partial
id
attribute e.g. input_
from id="input_205"
- Angular attributes e.g.
ng-click="navigate('export',$event)"
Most importantly, as the element is a dynamic element to invoke send_keys()
you have to induce WebDriverWait in-conjuction with expected_conditions method set as element_to_be_clickable(locator).
As an example, if the element is represented in the HTML DOM as follows:
<div class="form-group clearfix">
<input id="input_205" class="input-full" type="text" ng-click="navigate('run',$event)">
</div>
Your effective locator will be:
CSS_SELECTOR
:
WebDriverWait(driver, 20).until(EC.element_to_be_clickable((By.CSS_SELECTOR, "input.input-full[id^='input_']"))).send_keys(viewId)
XPATH
:
WebDriverWait(driver, 20).until(EC.element_to_be_clickable((By.XPATH, "//input[@class='input-full' and starts-with(@id, 'input_')]"))).send_keys(viewId)
Note A : Reference of the wildcards used with cssSelectors:
^
: To indicate an attribute value starts with
*
: To indicate an attribute value contains
$
: To indicate an attribute value ends with
Note B : You have to add the following imports :
from selenium.webdriver.support.ui import WebDriverWait
from selenium.webdriver.common.by import By
from selenium.webdriver.support import expected_conditions as EC