Skip to content

Calling Node#set with empty string doesn't trigger the input event #156

Closed as duplicate

Description

@janko

Hi, thank you for building this great gem, it's so nice not to have to go through selenium and chromedriver 🙏🏻

When switching to Cuprite, I noticed that calling Node#set with an empty string doesn't trigger the input event. In my app I'm using Stimulus to listen to input event on a search field, and triggering requests when the field value changes. I had code like this:

visit "/products"
find("#query").set("Foo") # input event is correctly triggered
expect(page).to have_current_path("/products?q=Foo")
find("#query").set("") # input event is not triggered
expect(page).to have_current_path("/products?q=") # it's still on /products?q=Foo

Here is a self-contained example showing the input event is not being triggered:

require "roda"

class App < Roda
  plugin :render, layout: false

  route do |r|
    r.root do
      render(inline: <<~HTML)
        <html>
          <head></head>
          <body>
            <input type="text" id="field" />
            <div id="events"></div>
            <script>
              document.querySelector('#field').addEventListener('input', function() {
                document.querySelector('#events').append(document.createTextNode('input event'))
              })
            </script>
          </body>
        </html>
      HTML
    end
  end
end

require "capybara/cuprite"

Capybara.current_driver = :cuprite
Capybara.register_driver :cuprite do |app|
  Capybara::Cuprite::Driver.new(app, js_errors: true)
end

session = Capybara::Session.new(:cuprite, App)
session.visit "/"
session.find("#field").set("value")
puts session.find("#events").text
session.find("#field").set("")
puts session.find("#events").text

Is there some other idiomatic way for clearing the field? I noticed that Selenium triggers some special clearing when an empty string is passed in to Node#set.

Activity

  1. tomekchime commented on Feb 21, 2024

    @tomekchime

    This looks related to #238. Curious if you were able to find a workaround @janko?

  2. janko commented on Feb 21, 2024

    @janko
    Author

    @tomekchime I don't remember from the top of my head, I think I just triggered the input event manually, possibly by calling trigger(:input) on the node.

  3. route commented on Oct 15, 2026

    @route
    Member

    Fixed in #336 (same bug as #164): clearing a non-empty text field with node.set("") / fill_in "field", with: "" now dispatches an input event (inputType: "deleteContentBackward") before change, so the trigger(:input) workaround is no longer needed. It will ship in the next release; until then you can use main.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Metadata

Metadata

Assignees

No one assigned

    Labels

    No labels
    No labels

    Type

    No type

    Projects

    No projects

      Milestone

      No milestone

      Relationships

      None yet

      Development

      No branches or pull requests

      Issue actions