SeleniumHQ/selenium · error · ArgumentError

#{button} is not a valid button!

Error message

#{button} is not a valid button!

What it means

Raised as ArgumentError by PointerPress#assert_button when button is a Symbol that is not a key in BUTTONS. Recognized Symbol buttons: :left, :touch, :pen_contact, :middle, :right, :pen_barrel, :x1, :back, :x2, :forward (mapped to integer codes 0–4).

Source

Thrown at rb/lib/selenium/webdriver/common/interactions/pointer_press.rb:65

          @button = assert_button(button)
          @type = @direction
          @opts = opts
        end

        def encode
          process_opts.merge('type' => type.to_s, 'button' => @button)
        end

        private

        def assert_source(source)
          raise TypeError, "#{source.type} is not a valid input type" unless source.is_a? PointerInput
        end

        def assert_button(button)
          case button
          when Symbol
            raise ArgumentError, "#{button} is not a valid button!" unless BUTTONS.key? button

            BUTTONS[button]
          when Integer
            raise ArgumentError, 'Button number cannot be negative!' if button.negative?

            button
          else
            raise TypeError, "button must be a positive integer or one of #{BUTTONS.keys}, not #{button.class}"
          end
        end

        def assert_direction(direction)
          raise ArgumentError, "#{direction.inspect} is not a valid button direction" unless DIRECTIONS.key? direction

          DIRECTIONS[direction]
        end
      end # PointerPress
    end # Interactions

View on GitHub (pinned to aa36b38e69)

Solutions

  1. Use one of the documented Symbols: :left, :middle, :right, :back, :forward, :x1, :x2, :touch, :pen_contact, :pen_barrel.
  2. Prefer the well-known aliases: :left (button 0), :middle (1), :right (2).
  3. If you need a non-standard code, pass a non-negative Integer instead of a Symbol.

Example fix

# before
driver.action.pointer_down(:center).perform # => ArgumentError: center is not a valid button!

# after
driver.action.pointer_down(:middle).perform
Defensive patterns

Strategy: validation

Validate before calling

BUTTONS = Selenium::WebDriver::Interactions::PointerPress::BUTTONS
button = button.to_sym if button.is_a?(String)
raise "unsupported button: #{button}" unless button.is_a?(Symbol) ? BUTTONS.key?(button) : button.is_a?(Integer)

driver.action.pointer_down(button).perform

Type guard

def valid_button?(b)
  case b
  when Symbol then Selenium::WebDriver::Interactions::PointerPress::BUTTONS.key?(b)
  when Integer then !b.negative?
  else false
  end
end

Prevention

When it happens

Trigger: Calling pointer_down/pointer_up (or PointerPress.new) with a Symbol like :center, :wheel, :side, or a typo such as :lef. Also when reusing a Symbol constant from another library (e.g. Appium's :finger).

Common situations: Guessing button names; copy-pasting button Symbols from a non-Selenium example; refactoring from integers to Symbols and choosing an unsupported name.

Related errors


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