Imported Upstream version 3.3.0
[debian/amanda] / perl / Amanda / Script_App.pm
1 # vim:ft=perl
2 # Copyright (c) 2008,2009 Zmanda, Inc.  All Rights Reserved.
3 #
4 # This program is free software; you can redistribute it and/or modify it
5 # under the terms of the GNU General Public License version 2 as published
6 # by the Free Software Foundation.
7 #
8 # This program is distributed in the hope that it will be useful, but
9 # WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY
10 # or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
11 # for more details.
12 #
13 # You should have received a copy of the GNU General Public License along
14 # with this program; if not, write to the Free Software Foundation, Inc.,
15 # 59 Temple Place, Suite 330, Boston, MA  02111-1307 USA
16 #
17 # Contact information: Zmanda Inc., 465 S. Mathilda Ave., Suite 300
18 # Sunnyvale, CA 94085, USA, or: http://www.zmanda.com
19
20 package Amanda::Script_App;
21
22 no warnings;
23 no strict;
24 $GOOD  = 0;
25 $ERROR = 1;
26 $FAILURE = 2;
27
28 use strict;
29 use warnings;
30 use Amanda::Constants;
31 use Amanda::Config qw( :init :getconf  config_dir_relative );
32 use Amanda::Debug qw( :logging );
33 use Amanda::Paths;
34 use Amanda::Util qw( :constants );
35 use Carp;
36
37 =head1 NAME
38
39 Amanda::Script_App - perl utility functions for Scripts.
40
41 =head1 SYNOPSIS
42
43 This module should not be used directly. Instead, use C<Amanda::Application> or
44 C<Amanda::Script>.
45
46 =cut
47
48 sub new {
49     my $class = shift;
50     my ($execute_where, $type, $config_name) = @_;
51
52     my $self = {};
53     bless ($self, $class);
54
55     # extract the last component of the class name
56     my $name = $class;
57     $name =~ s/^.*:://;
58     $self->{'name'} = $name;
59
60     if(!defined $execute_where) {
61         $execute_where = "client";
62     }
63     Amanda::Util::setup_application($name, $execute_where, $CONTEXT_DAEMON);
64
65     #initialize config client to get values from amanda-client.conf
66     config_init($CONFIG_INIT_CLIENT, undef);
67     my ($cfgerr_level, @cfgerr_errors) = config_errors();
68     if ($cfgerr_level >= $CFGERR_WARNINGS) {
69         config_print_errors();
70         if ($cfgerr_level >= $CFGERR_ERRORS) {
71             confess("errors processing config file");
72         }
73     }
74     if ($config_name) {
75         config_init($CONFIG_INIT_CLIENT | $CONFIG_INIT_EXPLICIT_NAME | $CONFIG_INIT_OVERLAY, $config_name);
76         ($cfgerr_level, @cfgerr_errors) = config_errors();
77         if ($cfgerr_level >= $CFGERR_WARNINGS) {
78             config_print_errors();
79             if ($cfgerr_level >= $CFGERR_ERRORS) {
80                 confess("errors processing config file for $config_name");
81             }
82         }
83     }
84
85     Amanda::Util::finish_setup($RUNNING_AS_ANY);
86
87     $self->{error_status} = $Amanda::Script_App::GOOD;
88     $self->{type} = $type;
89     $self->{known_commands} = {};
90
91     debug("$type: $name\n");
92
93     return $self;
94 }
95
96
97 #$_[0] message
98 #$_[1] status: GOOD or ERROR
99 sub print_to_server {
100     my $self = shift;
101     my($msg, $status) = @_;
102     if ($status != 0) {
103         $self->{error_status} = $status;
104     }
105     if ($self->{action} eq "check") {
106         if ($status == $Amanda::Script_App::GOOD) {
107             print STDOUT "OK $msg\n";
108         } else {
109             print STDOUT "ERROR $msg\n";
110         }
111     } elsif ($self->{action} eq "estimate") {
112         if ($status == $Amanda::Script_App::GOOD) {
113             #do nothing
114         } else {
115             print STDERR "ERROR $msg\n";
116         }
117     } elsif ($self->{action} eq "backup") {
118         if ($status == $Amanda::Script_App::GOOD) {
119             print {$self->{mesgout}} "| $msg\n";
120         } elsif ($status == $Amanda::Script_App::ERROR) {
121             print {$self->{mesgout}} "? $msg\n";
122         } else {
123             print {$self->{mesgout}} "sendbackup: error $msg\n";
124         }
125     } elsif ($self->{action} eq "restore") {
126         print STDERR "$msg\n";
127     } elsif ($self->{action} eq "validate") {
128         print STDERR "$msg\n";
129     } else {
130         print STDERR "$msg\n";
131     }
132 }
133
134 #$_[0] message
135 #$_[1] status: GOOD or ERROR
136 sub print_to_server_and_die {
137     my $self = shift;
138
139     $self->print_to_server( @_ );
140     if (!defined $self->{die} && $self->can("check_for_backup_failure")) {
141         $self->{die} = 1;
142         $self->check_for_backup_failure();
143     }
144     exit 1;
145 }
146
147
148 sub do {
149     my $self = shift;
150     my $command  = shift;
151
152     if (!defined $command) {
153         $self->print_to_server_and_die("check", "no command",
154                                        $Amanda::Script_App::ERROR);
155         return;
156     }
157     $command =~ tr/A-Z-/a-z_/;
158     debug("command: $command");
159
160     # first make sure this is a valid command.
161     if (!exists($self->{known_commands}->{$command})) {
162         print STDERR "Unknown command `$command'.\n";
163         exit 1;
164     }
165
166     my $action = $command;
167     $action =~ s/^pre_//;
168     $action =~ s/^post_//;
169     $action =~ s/^inter_//;
170     $action =~ s/^dle_//;
171     $action =~ s/^host_//;
172     $action =~ s/^level_//;
173
174     if ($action eq 'amcheck' || $action eq 'selfcheck') {
175         $self->{action} = 'check';
176     } elsif ($action eq 'estimate') {
177         $self->{action} = 'estimate';
178     } elsif ($action eq 'backup') {
179         $self->{action} = 'backup';
180     } elsif ($action eq 'recover' || $action eq 'restore') {
181         $self->{action} = 'restore';
182     } elsif ($action eq 'validate') {
183         $self->{action} = 'validate';
184     }
185
186     if ($action eq 'backup') {
187         $self->_set_mesgout();
188     }
189
190     # now convert it to a function name and see if it's
191     # defined
192     my $function_name = "command_$command";
193     my $default_name = "default_$command";
194
195     if (!$self->can($function_name)) {
196         if (!$self->can($default_name)) {
197             print STDERR "command `$command' is not supported by the '" .
198                          $self->{name} . "' " . $self->{type} . ".\n";
199             exit 1;
200         }
201         $self->$default_name();
202         return;
203     }
204
205     # it exists -- call it
206     $self->$function_name();
207 }
208
209 1;