File Coverage

blib/lib/Svsh/Perp.pm
Criterion Covered Total %
statement 6 12 50.0
branch n/a
condition 0 4 0.0
subroutine 2 5 40.0
pod 3 3 100.0
total 11 24 45.8


line stmt bran cond sub pod time code
1             package Svsh::Perp;
2              
3 1     1   1321 use Moo;
  1         1534  
  1         6  
4 1     1   662 use namespace::clean;
  1         71658  
  1         4  
5              
6             our $DEFAULT_BASEDIR = $ENV{PERP_BASE} || '/etc/perp';
7              
8             with 'Svsh';
9              
10             =head1 NAME
11              
12             Svsh::Perp - perp support for svsh
13              
14             =head1 DESCRIPTION
15              
16             This class provides support for L
17             to L - the supervisor shell.
18              
19             =head2 DEFAULT BASE DIRECTORY
20              
21             As per the L documentation,
22             C does not have a default base directory, but will check if a C environment
23             variable is set, and if not, will try C. This class will do the same if
24             a base directory is not provided to C.
25              
26             =head1 IMPLEMENTED METHODS
27              
28             Refer to L for complete explanation of these methods. Only changes from
29             the base specifications are listed here.
30              
31             =head2 status()
32              
33             C provides more information about service statuses then
34             other supervisors. C means the service is down but should be
35             up (unexpected down), C means the service is down because
36             it was manually stopped, C means the service is restarting,
37             and C means the service is attempting to start (possibly failing,
38             not necessarily).
39              
40             =cut
41              
42             sub status {
43             my $statuses = {};
44             foreach ($_[0]->run_cmd('perpls', '-b', $_[0]->basedir, '-g')) {
45             chomp;
46             my @m = m/^
47             \[
48             .\s # the perpd status
49             (.)(.)(.)\s # the process status
50             ... # the logger status
51             \]\s+
52             (\S+)\s+ # the process name
53             (?:
54             uptime:\s+
55             ([^\/]+)s # the process uptime
56             \/
57             \S+s # the logger uptime
58             \s+
59             pids:\s+
60             ([^\/]+) # the process pid
61             \/
62             \S+ # the logger pid
63             )? # optional because inactive services will not have this
64             /x;
65              
66             my $status = $m[0] eq '+' ? $m[2] eq 'r' ? 'resetting' : 'up' :
67             $m[0] eq '.' ? 'down' :
68             $m[0] eq '!' ? 'backoff' :
69             $m[0] eq '-' ? 'disabled' : 'unknown';
70              
71             $statuses->{$m[3]} = {
72             status => $status,
73             pid => $status eq 'up' ? $m[5] : '-',
74             duration => $status eq 'up' ? $m[4] eq '-' ? 0 : int($m[4]) : 0
75             };
76             }
77              
78             return $statuses;
79             }
80              
81             =head start( @services )
82              
83             This uses the C option of C instead of C or C, see
84             L why.
85              
86             =cut
87              
88             sub start {
89             $_[0]->run_cmd('perpctl', '-b', $_[0]->basedir, 'A', @{$_[2]->{args}});
90             }
91              
92             =head stop( @services )
93              
94             This uses the C option of C instead of C or C, as there
95             seems to be a bug(?) where processes stopped with this option failed to
96             start again when the L method is called.
97              
98             =cut
99              
100             sub stop {
101             $_[0]->run_cmd('perpctl', '-b', $_[0]->basedir, 'X', @{$_[2]->{args}});
102             }
103              
104             =head restart( @services )
105              
106             =cut
107              
108             sub restart {
109             $_[0]->run_cmd('perpctl', '-b', $_[0]->basedir, 'q', @{$_[2]->{args}});
110             }
111              
112             =head2 signal( $signal, @services )
113              
114             =cut
115              
116             sub signal {
117             my ($sign, @sv) = @{$_[2]->{args}};
118              
119             # convert signal to perpctl command
120             $sign =~ s/^sig//i;
121             my $cmd = $sign =~ m/^usr(1|2)$/i ? $1 : lc(substr($sign, 0, 1));
122              
123             $_[0]->run_cmd('perpctl', '-b', $_[0]->basedir, $cmd, @sv);
124             }
125              
126             =head2 fg( $service )
127              
128             =cut
129              
130             sub fg {
131             # find out the pid of the logging process
132 0     0 1   my $text = $_[0]->run_cmd('perpstat', '-b', $_[0]->basedir, $_[2]->{args}->[0]);
133 0   0       my $pid = ($text =~ m/log:.+\(pid (\d+)\)/)[0]
134             || die "Can't figure out pid of the logging process";
135              
136             # find out the current log file
137 0   0       my $logfile = $_[0]->find_logfile($pid)
138             || die "Can't find out process' log file";
139              
140 0           $_[0]->run_cmd('tail', '-f', $logfile, { as_system => 1 });
141             }
142              
143             =head2 rescan()
144              
145             =cut
146              
147             sub rescan {
148 0     0 1   $_[0]->run_cmd('perphup', $_[0]->basedir);
149             }
150              
151             =head2 terminate()
152              
153             =cut
154              
155             sub terminate {
156 0     0 1   $_[0]->run_cmd('perphup', '-t', $_[0]->basedir);
157             }
158              
159             =head1 BUGS AND LIMITATIONS
160              
161             No bugs have been reported.
162              
163             Please report any bugs or feature requests to
164             C, or through the web interface at
165             L.
166              
167             =head1 SUPPORT
168              
169             You can find documentation for this module with the perldoc command.
170              
171             perldoc Svsh::Perp
172              
173             You can also look for information at:
174              
175             =over 4
176            
177             =item * RT: CPAN's request tracker
178            
179             L
180            
181             =item * AnnoCPAN: Annotated CPAN documentation
182            
183             L
184            
185             =item * CPAN Ratings
186            
187             L
188            
189             =item * Search CPAN
190            
191             L
192            
193             =back
194              
195             =head1 AUTHOR
196              
197             Ido Perlmuter
198              
199             =head1 LICENSE AND COPYRIGHT
200              
201             Copyright (c) 2015, Ido Perlmuter C<< ido at ido50 dot net >>.
202              
203             This module is free software; you can redistribute it and/or
204             modify it under the same terms as Perl itself, either version
205             5.8.1 or any later version. See L
206             and L.
207              
208             The full text of the license can be found in the
209             LICENSE file included with this module.
210              
211             =head1 DISCLAIMER OF WARRANTY
212              
213             BECAUSE THIS SOFTWARE IS LICENSED FREE OF CHARGE, THERE IS NO WARRANTY
214             FOR THE SOFTWARE, TO THE EXTENT PERMITTED BY APPLICABLE LAW. EXCEPT WHEN
215             OTHERWISE STATED IN WRITING THE COPYRIGHT HOLDERS AND/OR OTHER PARTIES
216             PROVIDE THE SOFTWARE "AS IS" WITHOUT WARRANTY OF ANY KIND, EITHER
217             EXPRESSED OR IMPLIED, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
218             WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE. THE
219             ENTIRE RISK AS TO THE QUALITY AND PERFORMANCE OF THE SOFTWARE IS WITH
220             YOU. SHOULD THE SOFTWARE PROVE DEFECTIVE, YOU ASSUME THE COST OF ALL
221             NECESSARY SERVICING, REPAIR, OR CORRECTION.
222              
223             IN NO EVENT UNLESS REQUIRED BY APPLICABLE LAW OR AGREED TO IN WRITING
224             WILL ANY COPYRIGHT HOLDER, OR ANY OTHER PARTY WHO MAY MODIFY AND/OR
225             REDISTRIBUTE THE SOFTWARE AS PERMITTED BY THE ABOVE LICENCE, BE
226             LIABLE TO YOU FOR DAMAGES, INCLUDING ANY GENERAL, SPECIAL, INCIDENTAL,
227             OR CONSEQUENTIAL DAMAGES ARISING OUT OF THE USE OR INABILITY TO USE
228             THE SOFTWARE (INCLUDING BUT NOT LIMITED TO LOSS OF DATA OR DATA BEING
229             RENDERED INACCURATE OR LOSSES SUSTAINED BY YOU OR THIRD PARTIES OR A
230             FAILURE OF THE SOFTWARE TO OPERATE WITH ANY OTHER SOFTWARE), EVEN IF
231             SUCH HOLDER OR OTHER PARTY HAS BEEN ADVISED OF THE POSSIBILITY OF
232             SUCH DAMAGES.
233              
234             =cut
235              
236             1;
237             __END__