-
Notifications
You must be signed in to change notification settings - Fork 93
Caching Support
Selenium-WebDriver provides some developer-facing caching facilities, specifically when leveraging their built-in PageObject
design pattern API. However, this does not mesh with Clojure as naturally as it does in the Java API.
For this reason, clj-webdriver provides element caching on a per-page basis via Clojure's core.cache library. Read on for usage details.
By default, clj-webdriver allows you to initialize an empty element cache by passing a "cache spec" to the new-driver
function. This spec requires the following bits of information:
- The caching strategy that should be used (all strategies supported by Fogus' clache library are supported by clj-webdriver)
- Arguments that should be passed to the respective clache constructor for the caching strategy chosen
- Either an
:include
or:exclude
seq (vector), which should contain cache rules for inclusion or exclusion (whitelisting or blacklisting respectively)
Here is an example from clj-webdriver's unit tests, showing the initialization of a new Driver record using the :basic
cache strategy, no additional arguments (because BasicCache
doesn't take any) and a couple of :include
rules:
(def dr (new-driver
{:browser :firefox,
:cache-spec {:strategy :basic,
:args [],
:include [{:css "ol#pages"}]}}))
For a list of available strategies, take a look at the core.cache library. In terms of the storage strategy, clj-webdriver simply uses an atom
that wraps one of the supported cache types. By specifying the :strategy
and by providing a vector of :args
to feed to the constructor of that strategy (again, look at the core.cache API), clj-webdriver will instantiate the appropriate store inside the :element-cache
attribute of your Driver record.
Here are the keyword shortcuts for the currently-available caching strategies:
-
:basic
- A basic cache -
:fifo
- First In First Out cache -
:lru
- Least Recently Used cache -
:lirs
- Low Inter-reference Recency Set replacement cache -
:ttl
- Time To Live cache -
:lu
- Least Used cache
Unless you have specific needs to the contrary, you're probably safe just using :basic
. Depending on your application, a time-based :ttl
cache might also be appropriate, if you elements change over determined periods of time on a given page load. Considering the amount of data generally displayed on a single web page, the other strategies are probably "overkill" in terms of their algorithms for efficiently storing and returning cached values.
Cache rules are the heart of the clj-webdriver cache system. If caching is enabled (i.e. you've defined a cache strategy), then the find-element
function automatically checks for cache rules in your :cache-spec
and performs caching automatically based on those rules. You must choose either a whitelisting approach (:include
) or a blacklisting one (:exclude
). For either approach, your :include
/:exclude
entry consists of a vector of individual cache rules. See the above code snippet for an example.
These cache rules can be one of the following:
- A map. If you think about the
find-element
function, then a map represents afind-element
query. For the sake of consistency, map entries must match exactly to enable/disable caching for a given map structure. - A vector. Again, thinking back to the
find-element
function, a vector represents an ancestry-based query. Just like a map, this query must match exactly.
The protocol used to implement clj-webdriver's caching support is exposed publicly, so you can manipulate the cache safely by looking at the IElementCache
protocol and calling its functions. These functions massage different Clojure data structures to provide uniform keys for insertion and retrieval, due to the complexities of the find-element
function's parameters. For this reason, CRUD-style operations should be executed via the protocol functions and not via standard Clojure hash functions, unless you have a good reason to do otherwise.
The clj-webdriver Wiki by Daniel Gregoire and community is licensed under a Creative Commons Attribution 4.0 International License. Based on a work at https://github.com/semperos/clj-webdriver/wiki.