Test::WWW::Mechanize::Declare - flexible, declarative Web testing


This is a technology preview! I am releasing this module to solicit feedback from the community as I develop the interface and behavior of this code. Presently it is very small and simple and doesn't do anything more than what's described in the synopsis. However, it is useful for me, so perhaps it will be useful for someone else as well. I am not making any guarantees on the stability of the API at this time.


  my $mech = Test::WWW::Mechanize::Declare->new({
    base_uri  => 'http://localhost:8001',
    tests     => [
      path    => '/',
      method  => 'GET',
      validate => \&validate_root,
      path    => '/client',
      method  => 'GET',
      validate => \&validate_client,
      path    => '/stop',
      method  => 'GET',
      validate => \&validate_stop,


Test::WWW::Mechanize::Declare allows one to logically separate the description of what to test from the logic of the tests. Ideally, one can write a configuration file to specify what should be tested, read in this file, and then write the actual tests in Perl. I'm presently using it to do test-first development for a number of Web services I'm writing. The data structure I write describes the test, which will fail before any code exists for it as the Web server doesn't know to respond to that request yet. Then, after coding the Web service, the validate callback allows me to ensure that the behavior is correct.

Test::WWW::Mechanize::Declare doesn't run any tests on its own; the idea is that this module takes the boring part out of writing the code to do the actual requests. It simply calls the given method on the given URI and invokes the callback with the request and response objects. As such, it is best for testing Web servers that don't want or need to store state client-side.



new takes a hashref of arguments and returns an object (who'd have thought?). It recognizes the following keys and expects them to have the following values:


The base of the URI for your Web server.


A LWP::UserAgent-derived object, or at very least something that has methods like get and put which return an HTTP::Response object upon invocation. If not supplied, a Test::WWW::Mechanize object is used.


An arrayref of hashrefs. Expects the following key/value pairs:


The absolute path to test. Will be concatenated with the base_uri given above.


The HTTP method to call on the LWP::UserAgent object. Can be either all-uppercase or all-lowercase.


A hashref of params to pass to the UA. See LWP::UserAgent for what to use here. If all you're doing is GET, you probably don't need this.


A subref to invoke after calling the given method on the given path. Will be passed the HTTP::Request and HTTP::Response objects for this request/response cycle.


run_tests takes no arguments. When invoked, it iterates through the tests arrayref provided to new and makes a request of the given method against the provided path providing the given parameters. For each request, it then calls the validate sub with the HTTP::Request and HTTP::Response objects. It is important to note that the tests are run in the order given in the constructor, and the callbacks are invoked serially.


This is the section of the documentation where I waffle about things that may or may not happen in the development of this module.

Write tests

Yeah, I know. A test module without tests? Heresy and hypocrisy! I'll get to them, I promise.

A pre-request callback

Something that would be invoked before the request is made to the server. I've no idea what sort of information to pass to such a callback, however--maybe the HTTP::Request object?


Chris Nehren <>.


Copyright (c) 2009 Chris Nehren.


This library is free software and may be distributed under the same terms as perl itself.