0

I've tried selecting a dropdown menu (that has no id) on a page by selecting it by CSS selector, but I can't get it to work. Here is the dropdown code:

<select style="margin: 5px auto; width: 146px;" onchange="document.getElementById('11qq').src=this.options[this.selectedIndex].value;">
<option value="https://player.vimeo.com/video/158733095">Shakedown</option>
<option value="x">Placeholder</option>
<option value="https://player.vimeo.com/video/158815551">Race</option>
</select>

I tried using the following code to select each dropdown element, after which I want to find relevant video data (Note, I'm assuming that I do not know what is in the dropdown to begin with, since I'd like it to work for any dropdown on this site):

from bs4 import BeautifulSoup
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
from selenium.webdriver.support.ui import Select
import urllib2

url = "http://racing4everyone.eu/2016/03/12/formula-e-201516-round05-mexico/"
page = urllib2.urlopen(url)
soup = BeautifulSoup(page.read(), "html.parser")

dropdown = [x.text for x in soup.find_all('option')]

driver = webdriver.Firefox()
driver.get("http://racing4everyone.eu/2016/03/12/formula-e-201516-round05-mexico/")

for x in dropdown:
    Select droplist = new Select(driver.findElement(By.CSS_SELECTOR("select")));
    droplist.selectByVisibleText(x);

    frame_video = wait.until(EC.presence_of_element_located((By.CSS_SELECTOR, "iframe[src*=video]")))
    driver.switch_to.frame(frame_video)
    wait.until(EC.presence_of_element_located((By.CSS_SELECTOR, ".controls")))
    page_source = driver.page_source
    driver.close()

    soup = BeautifulSoup(page_source, "html.parser")
    script = soup.find_all("script")
    # A couple of other operations follow to isolate the relevant data from the script data

The Select droplist part I got from the following stackoverflow discussion (Second answer). However, I get the following error:

Select droplist = new Select(driver.findElement(By.CSS_SELECTOR("select")));
                  ^
SyntaxError: invalid syntax
Community
  • 1
  • 1

3 Answers3

2

maybe you use the java methond in python. The following is the Java method:

Select droplist = new Select(driver.findElement(By.CSS_SELECTOR("select")));

The following is the Python method:

droplist = driver.find_element_by_css_selector('select')
gavinsun
  • 36
  • 4
  • `droplist.selectByVisibleText(x)` also does not seem to be valid, what would be the Python equivalent of this? –  Mar 25 '16 at 10:27
  • As 'Florent,B' said, – gavinsun Mar 25 '16 at 12:52
  • As 'Florent,B' said,you could refer the following method: `Select(driver.find_element_by_xpath("//select[option='" + x + "']")).select_by_visible_text(x)` The following it the API of Python: [python's API](http://seleniumhq.github.io/selenium/docs/api/py/api.html) i hope it can help you. [select_by_visible_text](http://seleniumhq.github.io/selenium/docs/api/py/webdriver_support/selenium.webdriver.support.select.html#selenium.webdriver.support.select.Select.select_by_visible_text) – gavinsun Mar 25 '16 at 13:18
  • 1
    as you can see, Java and python are different in naming conventions. eg: 1. getName() //Java 2.get_name() #Python – gavinsun Mar 25 '16 at 13:24
  • I had to select a Web element which looked like this and for some reason it didn't work with By.tagName("select") , but it worked with cssSelector. I am clueless, but thank you for the answer anyway :) – Player1 Jun 26 '19 at 09:17
0

You cab try to use the onchange attribute

driver.find_element_by_css_selector('onchange*="document.getElementById('11qq')"')

This will give you the element witch has onchange attribute witch contains "document.getElementById('11qq')".

Guy
  • 46,488
  • 10
  • 44
  • 88
0

I would use the value of an item to locate the drop down list. Here is a working example with your page:

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
from selenium.webdriver.support.ui import Select

driver = webdriver.Firefox()
wait = WebDriverWait(driver, 10)

driver.get("http://racing4everyone.eu/2016/03/12/formula-e-201516-round05-mexico/")

for x in ["Shakedown", "Race"]:
  # select the option
  Select(driver.find_element_by_xpath("//select[option='" + x + "']")).select_by_visible_text(x)

  # set context on the video frame
  frame_video = wait.until(EC.presence_of_element_located((By.CSS_SELECTOR, "iframe[src*=video]")))
  driver.switch_to.frame(frame_video)

  # set the default context
  driver.switch_to_default_content()

driver.quit()

Note that the second item "PlaceHolder" has no link.

Florent B.
  • 41,537
  • 7
  • 86
  • 101
  • Hmmm, might there be a way to check for the existence of the video, and if the video is not present: continue to the next `x` in the loop? I won't be able to manually enter the `x` values unfortunately. –  Mar 25 '16 at 14:43
  • To check the existence of the video, just loop over the "option" elements where the value starts with "http". And no need to enter manually the x, this was just an example to demonstrate the usage of a select in your case, which was the question. – Florent B. Mar 25 '16 at 19:28