SeleniumHQ/selenium · error · Error::UnsupportedOperationError

You may not select a disabled option

Error message

You may not select a disabled option

What it means

Selenium::WebDriver::Support::Select#select_option raises UnsupportedOperationError with the message 'You may not select a disabled option' when the target <option> reports option.enabled? == false (i.e. it carries the HTML disabled attribute). The guard exists because clicking a disabled option cannot change the control's state and browsers either ignore the click or raise their own error, so Selenium fails fast with a clear, language-level message rather than a flaky DOM interaction. The same path is reached by every public selector: select_by(...), select_options, and multi-select iteration all funnel through select_option. It is an operation-level guard, not a transport error, so it surfaces synchronously in the calling Ruby thread.

Source

Thrown at rb/lib/selenium/webdriver/support/select.rb:218

          opts = find_by_value value

          return deselect_options(opts) unless opts.empty?

          raise Error::NoSuchElementError, "cannot locate option with value: #{value.inspect}"
        end

        def deselect_by_index(index)
          raise Error::UnsupportedOperationError, 'you may only deselect option of a multi-select' unless multiple?

          opts = find_by_index index

          return deselect_option(opts.first) unless opts.empty?

          raise Error::NoSuchElementError, "cannot locate option with index: #{index}"
        end

        def select_option(option)
          raise Error::UnsupportedOperationError, 'You may not select a disabled option' unless option.enabled?

          option.click unless option.selected?
        end

        def deselect_option(option)
          option.click if option.selected?
        end

        def select_options(opts)
          if multiple?
            opts.each { |o| select_option o }
          else
            select_option opts.first
          end
        end

        def deselect_options(opts)
          if multiple?

View on GitHub (pinned to aa36b38e69)

Solutions

  1. Before selecting, assert/wait for the specific option to be enabled: wait.until { select.options.find { |o| o.value == v && o.enabled? } }, then select it.
  2. Pick a different enabled option that satisfies the test intent instead of the disabled one (e.g. the first enabled option).
  3. If the option is expected to be enabled, fix the precondition first: tick the controlling checkbox, dismiss the modal, or wait for the AJAX call that removes the disabled attribute.
  4. As a last resort only, if the test legitimately needs to force a disabled option, remove the attribute via execute_script and re-select, but treat this as a test smell since it diverges from real user behavior.

Example fix

# before
select = Selenium::WebDriver::Support::Select.new(el)
select.select_by(:value, 'restricted')   # raises UnsupportedOperationError if disabled

# after
opt = select.options.find { |o| o.value == 'restricted' }
wait.until { opt&.enabled? }
select.select_by(:value, 'restricted')
Defensive patterns

Strategy: validation

Validate before calling

# Run before calling select.select_by(...)
require 'selenium/webdriver'

def safe_select(select, by:, value:)
  opt = case by
        when :text  then select.options.find { |o| o.text == value }
        when :value then select.options.find { |o| o.value == value }
        when :index then select.options[value]
        end
  raise ArgumentError, "no option for #{by}=#{value.inspect}" unless opt
  raise Selenium::WebDriver::Error::UnsupportedOperationError, \
        "option #{by}=#{value.inspect} is disabled" unless opt.enabled?
  select.select_option(opt)
end

# With a wait for AJAX-enabled options:
wait = Selenium::WebDriver::Wait.new(timeout: 10)
wait.until do
  opt = select.options.find { |o| o.value == 'restricted' }
  opt && opt.enabled?
end
select.select_by(:value, 'restricted')

Type guard

# Ruby has no static types; emulate a guard proc to narrow an option element.
def selectable_option?(option)
  option.is_a?(Selenium::WebDriver::Element) &&
    option.enabled? &&
    option.tag_name.casecmp('option').zero?
end

raise 'not selectable' unless selectable_option?(opt)

Try / catch

begin
  select.select_by(:value, 'restricted')
rescue Selenium::WebDriver::Error::UnsupportedOperationError => e
  raise unless e.message.include?('disabled option')
  # the target option is disabled: pick the first enabled option or fail the test explicitly
  enabled = select.options.select(&:enabled?).reject(&:selected?)
  raise 'no enabled options to select' if enabled.empty?
  select.select_option(enabled.first)
end

Prevention

When it happens

Trigger: Calling select.select_by(:text, 'X'), select.select_by(:value, 'Y'), select.select_by(:index, N), or select.all_options.each { |o| select.select_option(o) } where the resolved option element has disabled="disabled". Also triggered indirectly when select_options iterates a multi-select whose matched opts array contains at least one disabled option, since opts.each { |o| select_option o } will hit the disabled one and abort the whole batch without selecting the rest.

Common situations: Forms whose options are disabled by the application based on permissions or other field state; placeholder/empty options marked disabled that a test tries to pick by index 0; options disabled via JS until a checkbox is ticked; selecting an option whose text matches a disabled duplicate; CI running before the page finishes enabling options after an AJAX round-trip.

Related errors


AI-assisted analysis of SeleniumHQ/selenium@aa36b38e69 (2026-08-14). Data as JSON: /api/errors/43e5206d71273f1d. Report an issue: GitHub.