remove File::Slurp as we don't need it
[gitmo/MooseX-Daemonize.git] / lib / Test / MooseX / Daemonize.pm
CommitLineData
7d7115e5 1use strict;
3c3db18c 2
3package Test::MooseX::Daemonize;
7d7115e5 4use Proc::Daemon;
5
6# BEGIN CARGO CULTING
7use Sub::Exporter;
8use Test::Builder;
b3cd9b56 9our $VERSION = '0.02';
7d7115e5 10our $AUTHORITY = 'cpan:PERIGRIN';
11
b3cd9b56 12{
13 my @exports = qw[
14 daemonize_ok
15 check_test_output
16 ];
17
18 Sub::Exporter::setup_exporter(
19 {
20 exports => \@exports,
21 groups => { default => \@exports }
22 }
23 );
24}
7d7115e5 25
26our $Test = Test::Builder->new;
27
28sub daemonize_ok {
29 my ( $daemon, $msg ) = @_;
30 unless ( my $pid = Proc::Daemon::Fork ) {
31 $daemon->start();
32 exit;
33 }
34 else {
3543c999 35 sleep(1); # Punt on sleep time, 1 seconds should be enough
7a4ac6b2 36 $Test->ok( -e $daemon->pidfile->file, $msg )
b3cd9b56 37 || $Test->diag(
38 'Pidfile (' . $daemon->pidfile->file . ') not found.' );
3543c999 39 }
40}
41
42sub check_test_output {
43 my ($app) = @_;
44 open( my $stdout_in, '<', $app->test_output )
45 or die "can't open test output: $!";
46 while ( my $line = <$stdout_in> ) {
47 $line =~ s/\s+\z//;
48 my $label;
49 if ( $line =~ /\A((not\s+)?ok)(?:\s+-)(?:\s+(.*))\z/ ) {
50 my ( $status, $not, $text ) = ( $1, $2, $3 );
51 $text ||= '';
52
53 # We don't just call ok(!$not), because that generates diagnostics of
54 # its own for failures. We only want the diagnostics from the child.
55 my $num = $Test->current_test;
56 $Test->current_test( ++$num );
57 $Test->_print("$status $num - $text\n");
58 }
59 elsif ( $line =~ s/\A#\s?// ) {
60 $Test->diag($line);
61 }
62 else {
63 $Test->_print_diag("$label: $line (unrecognised)\n");
64 }
7d7115e5 65 }
66}
67
3c3db18c 68package Test::MooseX::Daemonize::Testable;
69use Moose::Role;
70
71has test_output => (
3543c999 72 isa => 'Str',
73 is => 'ro',
3c3db18c 74 required => 1,
75);
76
77after daemonize => sub {
78 $Test->use_numbers(0);
79 $Test->no_ending(1);
3543c999 80 open my $out, '>', $_[0]->test_output or die "Cannot open test output: $!";
81 my $fileno = fileno $out;
82 open STDERR, ">&=", $fileno
3c3db18c 83 or die "Can't redirect STDERR";
84
3543c999 85 open STDOUT, ">&=", $fileno
3c3db18c 86 or die "Can't redirect STDOUT";
87
3543c999 88 $Test->output($out);
89 $Test->failure_output($out);
90 $Test->todo_output($out);
3c3db18c 91};
92
7d7115e5 931;
94__END__
95
96
97=head1 NAME
98
99Test::MooseX::Daemonize - provides a Role that daemonizes your Moose based application.
100
101
102=head1 VERSION
103
104This document describes MooseX::Daemonize version 0.0.1
105
106
107=head1 SYNOPSIS
108
109 package main;
110 use Cwd;
111
112 ## Try to make sure we are in the test directory
113 chdir 't' if ( Cwd::cwd() !~ m|/t$| );
114 my $cwd = Cwd::cwd();
115
116 my $file = join( '/', $cwd, 'im_alive' );
117 my $daemon = FileMaker->new( pidbase => '.', filename => $file );
118
119 daemonize_ok( $daemon, 'child forked okay' );
120 ok( -e $file, "$file exists" );
121 unlink($file);
122
123=head1 DESCRIPTION
124
125Often you want to write a persistant daemon that has a pid file, and responds appropriately to Signals.
126This module helps provide the basic infrastructure to do that.
127
128=head1 ATTRIBUTES
129
130=over
131
132=item progname Str
133
134The name of our daemon, defaults to $0
135
136=item pidbase Str
137
138The base for our bid, defaults to /var/run/$progname
139
140=item pidfile Str
141
142The file we store our PID in, defaults to /var/run/$progname/
143
144=item foreground Bool
145
146If true, the process won't background. Useful for debugging. This option can be set via Getopt's -f.
147
148=back
149
150=head1 METHODS
151
152=over
153
154=item check()
155
156Check to see if an instance is already running.
157
158=item start()
159
160Setup a pidfile, fork, then setup the signal handlers.
161
162=item stop()
163
164Stop the process matching the pidfile, and unlinks the pidfile.
165
166=item restart()
167
168Litterally
169
170 $self->stop();
171 $self->start();
172
173=item daemonize()
174
175Calls C<Proc::Daemon::Init> to daemonize this process.
176
177=item kill($pid)
178
179Kills the process for $pid. This will try SIGINT, and SIGTERM before falling back to SIGKILL and finally giving up.
180
181=item setup_signals()
182
183Setup the signal handlers, by default it only sets up handlers for SIGINT and SIGHUP
184
185=item handle_sigint()
186
187Handle a INT signal, by default calls C<$self->stop()>;
188
189=item handle_sighup()
190
191Handle a HUP signal. Nothing is done by default.
192
193=item meta()
194
195the C<meta()> method from L<Class::MOP::Class>
196
3543c999 197=item daemonize_ok()
198
199=item check_test_output()
200
7d7115e5 201=back
202
203=head1 DEPENDENCIES
204
205=for author to fill in:
206 A list of all the other modules that this module relies upon,
207 including any restrictions on versions, and an indication whether
208 the module is part of the standard Perl distribution, part of the
209 module's distribution, or must be installed separately. ]
210
211Obviously L<Moose>, also L<Carp>, L<Proc::Daemon>, L<File::Flock>, L<File::Slurp>
212
213=head1 INCOMPATIBILITIES
214
215=for author to fill in:
216 A list of any modules that this module cannot be used in conjunction
217 with. This may be due to name conflicts in the interface, or
218 competition for system or program resources, or due to internal
219 limitations of Perl (for example, many modules that use source code
220 filters are mutually incompatible).
221
222None reported.
223
224
225=head1 BUGS AND LIMITATIONS
226
227=for author to fill in:
228 A list of known problems with the module, together with some
229 indication Whether they are likely to be fixed in an upcoming
230 release. Also a list of restrictions on the features the module
231 does provide: data types that cannot be handled, performance issues
232 and the circumstances in which they may arise, practical
233 limitations on the size of data sets, special cases that are not
234 (yet) handled, etc.
235
236No bugs have been reported.
237
238Please report any bugs or feature requests to
239C<bug-acme-dahut-call@rt.cpan.org>, or through the web interface at
240L<http://rt.cpan.org>.
241
242=head1 SEE ALSO
243
244L<Proc::Daemon>, L<Daemon::Generic>, L<MooseX::Getopt>
245
246=head1 AUTHOR
247
248Chris Prather C<< <perigrin@cpan.org> >>
249
250
251=head1 LICENCE AND COPYRIGHT
252
253Copyright (c) 2007, Chris Prather C<< <perigrin@cpan.org> >>. All rights reserved.
254
255This module is free software; you can redistribute it and/or
256modify it under the same terms as Perl itself. See L<perlartistic>.
257
258
259=head1 DISCLAIMER OF WARRANTY
260
261BECAUSE THIS SOFTWARE IS LICENSED FREE OF CHARGE, THERE IS NO WARRANTY
262FOR THE SOFTWARE, TO THE EXTENT PERMITTED BY APPLICABLE LAW. EXCEPT WHEN
263OTHERWISE STATED IN WRITING THE COPYRIGHT HOLDERS AND/OR OTHER PARTIES
264PROVIDE THE SOFTWARE "AS IS" WITHOUT WARRANTY OF ANY KIND, EITHER
265EXPRESSED OR IMPLIED, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
266WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE. THE
267ENTIRE RISK AS TO THE QUALITY AND PERFORMANCE OF THE SOFTWARE IS WITH
268YOU. SHOULD THE SOFTWARE PROVE DEFECTIVE, YOU ASSUME THE COST OF ALL
269NECESSARY SERVICING, REPAIR, OR CORRECTION.
270
271IN NO EVENT UNLESS REQUIRED BY APPLICABLE LAW OR AGREED TO IN WRITING
272WILL ANY COPYRIGHT HOLDER, OR ANY OTHER PARTY WHO MAY MODIFY AND/OR
273REDISTRIBUTE THE SOFTWARE AS PERMITTED BY THE ABOVE LICENCE, BE
274LIABLE TO YOU FOR DAMAGES, INCLUDING ANY GENERAL, SPECIAL, INCIDENTAL,
275OR CONSEQUENTIAL DAMAGES ARISING OUT OF THE USE OR INABILITY TO USE
276THE SOFTWARE (INCLUDING BUT NOT LIMITED TO LOSS OF DATA OR DATA BEING
277RENDERED INACCURATE OR LOSSES SUSTAINED BY YOU OR THIRD PARTIES OR A
278FAILURE OF THE SOFTWARE TO OPERATE WITH ANY OTHER SOFTWARE), EVEN IF
279SUCH HOLDER OR OTHER PARTY HAS BEEN ADVISED OF THE POSSIBILITY OF
3543c999 280SUCH DAMAGES.