NAME
Test::WWW::Mechanize::Driver::Manual - Writing Tests for Test::WWW::Mechanize::Driver
DESCRIPTION
Test::WWW::Mechanize::Driver Allows one to write Test::WWW::Mechanize tests in YAML. This module will load the tests make a plan and run the tests. Supports every-page tests, SKIP, TODO, and any object supporting the Test::WWW::Mechanize interface.
# sample .t file:
use strict; use warnings;
use Test::WWW::Mechanize::Driver;
use Test::More;
my $tester = Test::WWW::Mechanize::Driver->new(
load => [ glob( "t/*.yaml" ) ],
add_to_plan => 10, # optional
);
ok( ... ); # ... 10 of your own tests
$tester->run;
This document focuses on the test data format. See the Test::WWW::Mechanize::Driver documentation for information about writing the perl test driver (*.t) files if you need something more fancy than the above example. Examples in this document use YAML syntax though it is possible with alternate loaders to store tests in another format such as raw perl code.
Test File Structure
Each file is called a "stream" which may consist of one or more "documents" (this is consistent with YAML terminology). Each document may be any of a scalar, hash (mapping in YAMLspeak), or array (sequence). Plain scalar documents are treated as comments and are completely ignored by the driver module. Hash documents may be used to set default settings for test documents following the hash document. Finally, array documents are test documents and contain a list of hashes which define the tests.
A simple example showing all three document types:
--- |
This is a comment document (denoted by the | following the document
separator), ignored by Test::WWW::Mechanize::Driver. It might be used to
describe the test file or to disable blocks of tests.
---
# This is a default settings document. YAML comments (such as this one)
# may appear here. The following line will set a default "tag" for each
# test in this file following this document (it would not affect tests
# before this point). [note: tags are not used by the driver, but may be
# used by a custom "after_response" callback.]
tag: basic_tests
---
# This is a test document. Each item defines an arbitrary number of
# subtests.
# check title and contents in random order
- uri: http://google.com/
description: Google main page
title_is: Google
contains:
- Advanced Search
- Preferences
# Ensure title is tested before contents
- uri: http://yahoo.com/
description: Yahoo main page
actions:
- title_is: Yahoo!
- contains:
- My Yahoo!
- '<li class="mailstatus">Check your mail status:'
Test Documents
The core keys of a test group are.
- uri | url
-
The only required parameter. Specifies the origin URI for the test group. This page will be automatically loaded by the mechanize object. "url" is an alias for "uri".
- parameters | parms | params
-
Optional hash of parameters to send with the request.
- method
-
Optional HTTP request method. One of GET, POST, PUT, DELETE.
- description
-
Optional test description. Will be added to test messages.
- actions
-
List of mechanize tests and actions to perform. As a convenience, action items may be placed in the top-level hash (along with "uri", etc.). Note, however, that actions at the top level will be executed in an arbitrary order, therefore, any actions involving form submission or that otherwise alter the mechanize object's state should be placed in the actions array.
- SKIP
- TODO
-
If included, the entire test group will be skipped or marked TODO. The value of these options will be used as the message passed to Test::Builder.
Action Items
Action item keys are Test::WWW::Mechanize test method names. The values are given as parameters to the corresponding method. The test driver defines a few aliases so that any of the content_*
methoids may leave off the "content_" part. Further, the test driver knows which methods operate on only a single item (such as content_contains
, title_like
, ...) and will automatically and properly hand array values.
Example:
- uri: http://google.com/
actions:
- title_is: Google
- contains:
- Advanced Search
- Preferences
- submit_form_ok:
q: foo
btnG: Google Search
- contains:
- en.wikipedia.org/wiki/Foo
is equivalent to:
$mech->get_ok("http://google.com/");
$mech->title_is("Google");
$mech->content_contains("Advanced Search");
$mech->content_contains("Preferences");
$mech->submit_form_ok({ q => "foo", btnG => "Google Search" });
$mech->content_contains("en.wikipedia.org/wiki/Foo");
Note, the above YAML could have been written:
- uri: http://google.com/
title_is: Google
contains:
- Advanced Search
- Preferences
actions:
- submit_form_ok:
q: foo
btnG: Google Search
- contains:
- en.wikipedia.org/wiki/Foo
In which case the title_is and first pair of content_contains tests would have run first in random order, but the form submission and final content_contains test would be performed afterward in the proper order.
Mechanize Actions
Mechanize actions may be placed into the action list as long as they have a true value in %Test::WWW::Mechanize::Driver::mech_action
. ARRAY or HASH values undergo exactly one level of "unwrapping".
# calls $mechanize->foo( "bar", "baz" )
foo:
- bar
- baz
# calls $mechanize->foo( ["bar", "baz"] )
foo:
-
- bar
- baz
Magic Values (applying templates, posting files)
By placing object references which overload stringification into your test descriptions, you can upload external files or create dynamic templated parameters.
The YAML syntax for blessing an object is: !!perl/REFTYPE:PACKAGE
. Test::WWW::Mechanize::Driver defines three classes:
FileContents
Stringifies to file contents. Files are read in binmode. Sample usage:
- uri: http://example.com/uploader
method: PUT
parameters:
myfile: !!perl/scalar:FileContents t/test-file.pdf
ApplyTemplate
Fills in a string using Template.pm.
- uri: http://example.com/schedule
parameters:
date: !!perl/scalar:ApplyTemplate '[% today.strftime("%Y-%m-%d") %]'
Some variables will be made available to the template:
- t
-
The test group object. Includes all keys defined in the test suite (uri, parameters, description, ...) including custom keys. Is the same object passed to the after_request callback so any modifications made there will be available as well.
- now
-
The current date as a DateTime object.
Stacked
This class takes an array reference and blesses the 0th entry into the class named in the 1st entry. It then stringifies the result and repeats the process with the class given in the next entry. Arbitrarily many classes may be stacked in this way.
- uri: http://example.com/message
method: POST
user_name: Bob Smiley
parameters:
message: !!perl/array:Stacked [ t/test-message.tt, FileContents, ApplyTemplate ]
Sample contents of test-message.tt:
Dude, this webpage rocks! - [% t.user_name %]
AUTHOR
The original version of this code written by Dean Serenevy while under contract with National Financial Management who graciously allowed me to release it to the public.
Dean Serenevy
dean@serenevy.net
https://serenevy.net/
LICENSE
This software is hereby placed into the public domain. If you use this code, a simple comment in your code giving credit and an email letting me know that you find it useful would be courteous but is not required.
The software is provided "as is" without warranty of any kind, either expressed or implied including, but not limited to, the implied warranties of merchantability and fitness for a particular purpose. In no event shall the authors or copyright holders be liable for any claim, damages or other liability, whether in an action of contract, tort or otherwise, arising from, out of or in connection with the software or the use or other dealings in the software.
SEE ALSO
WWW::Mechanize, Test::WWW::Mechanize, Test::WWW::Mechanize::Driver