1

I've got a script writing values into a web page, and all values write except for one field that keeps throwing up the following error: enter image description here (Screenshot provided b/c in other similar questions many comments said this is impossible to happen on a web page.) "Please enter a numeric value."

Here's my code:

workcenter_to_add = {}
workcenter_to_add['BatchCycle'] = str(2.78)
# driver = my_chrome_webpage
WebDriverWait(driver, wait_time).until(EC.presence_of_element_located((By.XPATH, "//input[@id='BatchSize']"))).send_keys(workcenter_to_add['BatchCycle'])

As everyone knows, if I do not input the 2.78 value in as a string WebDriver throws an error. But my page demands a numeric value. I'm stuck.

I've Googled around and not found a usable answer to this. It seems if you're using Java there's a setAttribute method you can use, but if you're using Pythonyou've got to figure something out.

For example, the question here looked promising but I could not find the String or how to import it to get it to work. There's a couple of other much older questions that talk about executing java but I have had no luck getting them to work.

I've got the page-source HTML here: https://drive.google.com/open?id=1xRNPfc5E65dbif_44BQ_z_4fMYVJNPcs

TylerH
  • 20,799
  • 66
  • 75
  • 101
Programming_Learner_DK
  • 1,509
  • 4
  • 23
  • 49
  • 1
    `2.78` is not numeric value change to `278` instead `2.78` – KunduK Mar 23 '20 at 16:03
  • @KunduK, Interesting observation... the 2.78 is a valid entry when I either type it in or copy and paste it in, and also when I look at existing values I see many decimal values entered. In other fields on the same page I'm entering similar values (decimal values) but this is the only one that is throwing an error... – Programming_Learner_DK Mar 23 '20 at 17:19

4 Answers4

2

I am sure though you are passing the value .send_keys('2.78'), still the value will be numeric. So, ideally you should not get this issue.

Here is the sample html and script to confirm the same.

<html><head>

<script>
function validateOnClick(evt) {
  var theEvent = evt || window.event;
  // Handle paste
  if (theEvent.type === 'click') {
      key = document.querySelector('input').value.toString();
  } else {
  // Handle key press
      var key = theEvent.keyCode || theEvent.which;
      key = String.fromCharCode(key);
  }
  var regex = /[0-9]|\./;
console.log(key);
  if( !regex.test(key) ) {
    alert("Please enter numeric value");
    theEvent.returnValue = false;
    if(theEvent.preventDefault) theEvent.preventDefault();
  }
}
</script>
</head>

<body>
<input placeholder='check'></input>
<button type='submit' onClick='validateOnClick(event)'>Submit</button>
</body></html>

Script to check:

driver.get(url)
# check with string (not integer)
driver.find_element_by_tag_name('input').send_keys('Hello')
driver.find_element_by_tag_name('button').click()
print(driver.switch_to.alert.text)
driver.switch_to.alert.dismiss()
# now check with integer
driver.find_element_by_tag_name('input').clear()
driver.find_element_by_tag_name('input').send_keys(workcenter_to_add['BatchCycle'])
driver.find_element_by_tag_name('button').click()

Screenshot: enter image description here

So, We have to check what's the js/method implemented to validate the value entered in the field. As you can see passing integer with in quotes from python script does not make any difference to the field and it's data type.

supputuri
  • 13,644
  • 2
  • 21
  • 39
  • I got the page source and put in up here: https://drive.google.com/open?id=1xRNPfc5E65dbif_44BQ_z_4fMYVJNPcs - hopefully that helps. Thank you. – Programming_Learner_DK Mar 27 '20 at 11:58
  • I believe I understand what you are saying - essentially there is some kind of validation going on that's causing this to fail. I know zero js, so I posted the source code of the page b/c that's the only place I can think it's available. Running into the same issue on another page in my project (I have no access this web application developers) and willing to bet it's the same issue behind me not being able to write in either of these fields. – Programming_Learner_DK Mar 27 '20 at 13:04
2

I'm sure this is going to be an unpopular answer, but this is how I got it work.

The field in this question and another field on another page in the same ERP system were throwing the same error. send_keys() would not work no matter what I tried.

That's when I put on my thinking cap and starting trying other ways.

I tried entering the information into another field on the page that would accept numbers via send_keys() and then cutting and pasting the values into the field that would not accept the value had I used send_keys(). It worked!

Here's a code snippet I used on the different page with the same issue:

                    elem1 = driver.find_element_by_id('txtNote')
                    elem1.send_keys(rm['txtGross_Weight'])
                    elem1.send_keys(Keys.CONTROL, 'a') #highlight all in box
                    elem1.send_keys(Keys.CONTROL, 'x') #cut
                    elem2 = driver.find_element_by_id('txtGross_Weight')
                    elem2.send_keys(Keys.CONTROL, 'v') #paste

I was looking for a high tech answer when a low tech work around sufficed.

Is it code or methodology I'd write on a job resume? Probably not. Did it work and can I live with it? Yes. Thank you for the people who tried to answer.

halfer
  • 19,824
  • 17
  • 99
  • 186
Programming_Learner_DK
  • 1,509
  • 4
  • 23
  • 49
  • Did you checked the possibility that value is set to another hidden field when you type in but sometimes send keys is not suffice to replace manual entry as javascript is not able to monitor it correctly failing to populate hidden field. I am not sure why its working fine when you do cut and paste but there is something to do with validation javascript. If you can check the javascript for the validation, it will give more hint and better solution. I was not able to find validation code in your drive code though, it might be in one of the imported JS. – Sariq Shaikh Apr 02 '20 at 10:10
  • Suggestion: there is no obligation to award the bounty during or at the end of the bounty period. As you found, if you do not award it manually, half will go to the leading answer at that time. However, if you wish, you may award it even though you found the answer yourself. Awarding it can be for effort, or whatever other metric you determine, rather than because the post was useful. – halfer Apr 08 '20 at 18:28
  • Again it is not mandatory, but given that you have used your own answer, you can also "accept" it, by clicking on the tick/check mark. – halfer Apr 08 '20 at 18:28
1

It looks a lot like a comma vs dot problem?

But I could be wrong.

It depends on the browser locale of the machine that your selenium is running on.

So a simple test could be to enter the text '2,78' or '2.78' into the field.

Python converts the number to a string, and that is not a localized number. When it is sent as keys, it is sent as four characters '2' '.' '7' '8'. It then ends in the Javascript scope of your browser, that depending on the OS and Language settings will be either using comma or dot as a decimal separator.

AndreasM_DK
  • 302
  • 1
  • 8
0

The dialog box with the notification

notification

possibly is the outcome of Constraint API's element.setCustomValidity() method.


I had been through the page-source HTML which you have shared. But as per your code trials:

By.XPATH, "//input[@id='BatchSize']"

I didn't find any <input> tag within the pagesource. The text based relevant HTML would have helped us to construct an answer in a better way. However, you need to consider a few things as follows:

  • As you are dealing with an <input> tag, instead of presence_of_element_located() you should be using element_to_be_clickable().
  • You haven't told us about the error WebDriver throws if you do not input the 2.78 value as a string. Still, as str(2.78) works so you can stick to it.
  • Effectively your line of code will be:

    workcenter_to_add = {}
    workcenter_to_add['BatchCycle'] = str(2.78)
    WebDriverWait(driver, wait_time).until(EC.element_to_be_clickable((By.XPATH, "//input[@id='BatchSize']"))).send_keys(workcenter_to_add['BatchCycle'])   
    

References

You can find a couple of relevant discussions on Constraint_validation in:

undetected Selenium
  • 183,867
  • 41
  • 278
  • 352