A Ruby page class generator (for use with the page-object gem)
Normally, I’d advise against using a gem like this, because the page class shouldn't necessarily contain methods for every single HTML element on the page. In fact, if the page we are modeling is anything like the Google home page, our page class should only have one or 2 methods (a.k.a. PageObject::Accessors) for HTML elements: the search box and the submit button.
However, recently, almost all of the tests I have been writing have been for non-public facing sites, used by specialized, internal users who are trained on the platform. As a result, we end up with fairly dense webpages, with multiple different features and HTML elements that need interacting with, all on a single page.
Ultimately, this is the specific use case I am writing this gem for. Also, I wanted to learn a bit more about how a Ruby AST -- abstract syntax tree -- works and how the unparser gem allows me to generate working Ruby code from a dynamically generated AST.
This gem will follow semantic versioning. See changelog for changes in each version.
Ensure this gem and watir-webdriver are both in your Gemfile:
gem "page-objectify" gem "watir-webdriver"
And then execute:
The supported usage of this gem is to:
- create a
SomethingPageGeneratorclass that inherits from
- write a
SomethingPageGenerator#visitmethod that opens a browser and navigates to the page you want to generate a page class for.
- initialize the generator class & call
#generate!in some kind of Rake task (that is typically executed manually.)
Here's a complete example (using the Google homepage, which, as I mention above, is a horrible use case, but it works for a demo):
# Gemfile gem "chromedriver-helper", "~> 1.0" gem "page-objectify" gem "watir-webdriver", "~> 0.9.1"
# /generators/google_page_generator.rb require "page-objectify/generator" require "watir-webdriver" class GooglePageGenerator < :: def visit @browser = Watir::Browser.new :chrome @browser.goto "www.google.com" sleep 1 # Use `wait_for_ajax` instead of `sleep`, if jQuery is available on the page! end end
# Rakefile require "generators/google_page_generator" namespace :generate do task :po do # Specifying file path is optional GooglePageGenerator.new(file: "path/to/pages-dir/google_page.rb").generate! # and any other pages you want to generate programmatically end end
Then, upon executing the rake task
$ bundle exec rake generate:po, the following file will be generated:
class GooglePage < BasePage div(:viewport, id: "viewport") div(:"doc-info", id: "doc-info") div(:cst, id: "cst") text_area(:csi, id: "csi") div(:searchform, id: "searchform") # etc. end
Currently, only those HTML elements with a non-empty id attribute will have PageObject accessors generated for them.
For another example (using watir-webdriver and phantomjs via the
phantomjs gem), see this integration test.
Debugging & Development
The default log level is
2. Set this to a lower level to see helpful DEBUG level prints, i.e.
::..level = 0
After checking out the repo, run
bin/setup to install dependencies. Then, run
rake test to run the tests. You can also run
bin/console for an interactive prompt that will allow you to experiment.
To install this gem onto your local machine, run
bundle exec rake install.
To release a new version, I must:
- Update the version number in
rake release, which will create a git tag for the version, push git commits and tags, and push the
.gemfile to rubygems.org.
rake changelog, which will auto-generate a changelog of the PRs merged/Issues resolved in the newest release.
Bug reports and pull requests are welcome on GitHub at https://github.com/smoll/page-objectify.