|parrotcode: Preempt STDIN during testing.|
|Contents | Tests|
Tie::Filehandle::Preempt::Stdin - Preempt STDIN during testing.
use Tie::Filehandle::Preempt::Stdin; @prompts = qw| alpha beta gamma |; $object = tie *STDIN, 'Tie::Filehandle::Preempt::Stdin', @prompts;
Suppose a program requires manual input from the keyboard operator. How do we test that we have properly handled operator input? More specifically, how do we incorporate testing for user input in files built on Perl's standard testing apparatus (
Tie::Filehandle::Preempt::Stdin offers one way to do it -- a relatively simple and unsophisticated todo it. The most difficult part is analyzing the program to be tested so that you recognize all the points at which input is needed via STDIN. This in turn requires an understanding of all the different branches your program flow can take in response to standard input. Once you know that, you construct a list of dummy data that will be fed to each test at the points the program, when put into production, would normally prompt for operator input. This list of dummy data 'pre-empts' standard input via a tie of filehandle STDIN; hence, the module's name.
@prompts = qw| alpha beta gamma |; $object = tie *STDIN, 'Tie::Filehandle::Preempt::Stdin', @prompts; print "Enter item 1: "; chomp($entry = <STDIN>); # 'alpha' is supplied in lieu of standard input; # do something with $entry print "Enter item 2: "; chomp($entry = <STDIN>); # 'beta' is supplied in lieu of standard input; # do something with $entry print "Enter item 3: "; chomp($entry = <STDIN>); # 'gamma' is supplied in lieu of standard input; # do something with $entry
Should the number of elements in
@prompts be less than the number of points at which a given test prompts for operator input, you will get an error message:
"List of prompt responses has been exhausted"
and the program will
Tie::Filehandle::Preempt::Stdin does not work properly when the source code being tested uses only the Perl diamond operator for standard input.
print "Enter room whose data you wish to enter: "; chomp ($try = <>);
This doesn't work; your program will hang. You have to hard-code
chomp ($try = <STDIN>);
I don't know why this happens. If this bothers you, look at
IO::Scalar which is reported to handle the diamond operator properly, but which, IMHO, has a more complex interface.
Contact author or post on email@example.com.
James E Keenan. CPAN ID: JKEENAN. Mail to: jkeenan [at] cpan [dot] org.
The author benefitted from -- but did not always agree with -- comments from the following members of Perlmonks: chromatic, Revelation, tmoertel, NiJo and dragonchild.
Thanks to Michael G Schwern and Kevin Scaldeferri for answering questions on the perl.qa mailing list.
Copyright 2005 James E Keenan. This program is free software; you can redistribute it and/or modify it under the same terms as Perl itself.
The full text of the license can be found in the LICENSE file included with this module.
Last revision: Apr 17 2005.
Programming Perl (3rd ed.), Larry Wall, Tom Christiansen and Jon Orwant. O'Reilly & Associates, 1991. Chapter 14: Tied Variables: section on ''Tying Filehandles,'' p. 384 ff.
Perlmonks discussion starting at: http://www.perlmonks.org/index.pl?node_id=430997.