rubycdp / ferrum

Headless Chrome Ruby API
https://ferrum.rubycdp.com
MIT License
1.74k stars 123 forks source link

Can't use single quotes in screenshot `:selector` #465

Open zavan opened 3 months ago

zavan commented 3 months ago

Describe the bug It raises if you try to use single quotes in a screenshot :selector.

To Reproduce

require "bundler/inline"

gemfile do
  source "https://rubygems.org"

  gem "ferrum", "0.15"
  gem "base64"
end

b = Ferrum::Browser.new(timeout: 120, headless: "new", window_size: [1920, 1080])
b.goto("https://en.wikipedia.org/wiki/Main_Page")
b.screenshot(encoding: :base64, selector: "[aria-labelledby='firstHeading']") # Note single quotes

This raises:

/Users/zavan/.asdf/installs/ruby/3.3.3/lib/ruby/gems/3.3.0/gems/ferrum-0.15/lib/ferrum/frame/runtime.rb:138:in `handle_error': SyntaxError: missing ) after argument list (Ferrum::JavaScriptError)
    from /Users/zavan/.asdf/installs/ruby/3.3.3/lib/ruby/gems/3.3.0/gems/ferrum-0.15/lib/ferrum/frame/runtime.rb:122:in `block in call'
    from /Users/zavan/.asdf/installs/ruby/3.3.3/lib/ruby/gems/3.3.0/gems/ferrum-0.15/lib/ferrum/utils/attempt.rb:10:in `with_retry'
    from /Users/zavan/.asdf/installs/ruby/3.3.3/lib/ruby/gems/3.3.0/gems/ferrum-0.15/lib/ferrum/frame/runtime.rb:105:in `call'
    from /Users/zavan/.asdf/installs/ruby/3.3.3/lib/ruby/gems/3.3.0/gems/ferrum-0.15/lib/ferrum/frame/runtime.rb:68:in `evaluate_async'
    from /Users/zavan/.asdf/installs/ruby/3.3.3/lib/ruby/3.3.0/forwardable.rb:240:in `evaluate_async'
    from /Users/zavan/.asdf/installs/ruby/3.3.3/lib/ruby/gems/3.3.0/gems/ferrum-0.15/lib/ferrum/page/screenshot.rb:253:in `bounding_rect'
    from /Users/zavan/.asdf/installs/ruby/3.3.3/lib/ruby/gems/3.3.0/gems/ferrum-0.15/lib/ferrum/page/screenshot.rb:230:in `area_options'
    from /Users/zavan/.asdf/installs/ruby/3.3.3/lib/ruby/gems/3.3.0/gems/ferrum-0.15/lib/ferrum/page/screenshot.rb:207:in `screenshot_options'
    from /Users/zavan/.asdf/installs/ruby/3.3.3/lib/ruby/gems/3.3.0/gems/ferrum-0.15/lib/ferrum/page/screenshot.rb:82:in `screenshot'
    from /Users/zavan/.asdf/installs/ruby/3.3.3/lib/ruby/3.3.0/forwardable.rb:240:in `screenshot'
    from screenshot.rb:26:in `<main>'

Using double quotes work:

b.screenshot(encoding: :base64, selector: '[aria-labelledby="firstHeading"]')

This happens because single quotes are already used to quote the selector itself here in line 255:

https://github.com/rubycdp/ferrum/blob/ac52ce960c681b1fa0bb9d448fc3d6a7e761f3a9/lib/ferrum/page/screenshot.rb#L252-L262

Maybe CSS.escape can help?

Expected behavior The quoting used in the selector shouldn't matter.

Desktop (please complete the following information):