code code code
[php-bacula-disk-changer.git] / bin / pbdc.php
1 <?php
2
3 $BASE_LIB="../lib";
4 $BASE_DATA="../db";
5 $BACULA_USER="paulr";
6
7 global $BASE_DATA, $BASE_LIB, $BACULA_USER;
8
9 require_once "$BASE_LIB/lib.php";
10
11 if(!isset($argv[2])) {
12         echo "Usage: ".$argv[0]." changer_name command\n";
13         echo "\tbacula-config - outputs bacula config\n";
14         echo "\tinit - inits the bacula php changer stuff\n";
15         echo "\tadd-disk - adds a disk\n";
16         echo "\tdisks - lists currently (known) disks\n";
17         echo "\tstatus - prints status (whats where in which slot, drive, etc)\n";
18         exit(0);
19 }
20
21 $command = $argv[2];
22
23 switch($command) {
24         case "init":
25                 init();
26                 break;
27         case "bacula-config":
28                 bacula_config();
29                 break;
30         case "add-disk":
31                 add_disk();
32                 break;
33         case "disks":
34                 list_disks();
35                 break;
36         case "status":
37                 pbdc_status();
38                 break;
39         default:
40                 echo "invalid command\n";
41 }
42
43 function bacula_config()
44 {
45         global $BASE_DATA, $BASE_LIB, $BACULA_USER, $argv;
46         
47         check_init_and_fail($argv[1]);
48         $changer = $argv[1];
49
50         $db = db_getDB($argv[1]);
51         
52         // TODO: do this bit
53 }
54
55 function pbdc_status()
56 {
57         global $BASE_DATA, $BASE_LIB, $BACULA_USER, $argv;
58         
59         check_init_and_fail($argv[1]);
60         $changer = $argv[1];
61
62         $db = db_getDB($argv[1]);
63         
64         $res = $db->query("select * from disk_list");
65         
66         $tapeloc = conf_getVal($changer, "drivelocation");
67         $amloc = conf_getVal($changer, "automountdir");
68         
69         $ret = false;
70         foreach($res as $row) {
71                 echo "Listing tapes for disk ".$row["disk_id"].", ".$row["disk_name"]."\n";
72                 //echo "dir: $amloc/".$row["disk_name"]."/pbdc/".$argv[1]."/tapes/\n";
73                 //exit(0);
74                 $dh = opendir("$amloc/".$row["disk_name"]."/pbdc/".$argv[1]."/tapes/");
75                 while(($file = readdir($dh)) !== false) {
76                         if(ereg("d[0-9]+_vol[0-9]+", $file)!=false) {
77                                 echo "Tape: $file\n";
78                         } else {
79                                 //echo "didnt match: $file\n";
80                         }
81                         //exit(0);
82                 }
83                 closedir($dh);
84         }
85         
86         $nt = (int)(conf_getVal($changer, "ndrives"));
87         for($i = 0; $i < $nt; $i++) {
88                 if(file_exists("$tapeloc/$changer-drive$i")) {
89                         $rl = basename(readlink("$tapeloc/$changer-drive$i"));
90                         echo "drive $i points has tape $rl loaded\n";
91                 } else {
92                         echo "drive $i is unloaded\n";
93                 }
94         }
95 }
96
97 function list_disks()
98 {
99         global $BASE_DATA, $BASE_LIB, $BACULA_USER, $argv;
100         
101         check_init_and_fail($argv[1]);
102         
103         $db = db_getDB($argv[1]);
104         
105         $res = $db->query("select * from disk_list");
106         
107         $ret = false;
108         foreach($res as $row) {
109                 echo "Disk ".$row["disk_id"].": ".$row["disk_name"]."\n";
110                 $ret = true;    
111         }
112         
113         if(!$ret) {
114                 echo "No disks defined yet for this changer\n";
115         }
116         
117         
118         return;
119 }
120
121 function init()
122 {
123         global $BASE_DATA, $BASE_LIB, $BACULA_USER, $argv;
124         
125         // check if we are the bacula user
126         $user = posix_getlogin();
127         if($user != $BACULA_USER) {
128                 echo "This command must be run as the bacula user\n";
129                 exit(0);
130         }
131         
132         $changer_name = $argv[1];
133         
134         echo "This command will init the data for $changer_name\n";
135         
136         if(file_exists("$BASE_DATA/$changer_name.db")&&check_init($changer_name)) {
137                 //echo "Daemon is already init'd, are you sure you wish to do this, it will loose all config [y/n]:";
138                 $r = readline("Daemon is already init'd, are you sure you wish to do this, it will loose all config [y/n]:");
139                 if($r == "y") {
140                         echo "Ok, but its your disaster, waiting 5 seconds prior to init'ing the database (hit ctrl-c to exit)\n";
141                         sleep(5);
142                 } else {
143                         echo "Ok, not doing it, so long chum\n";
144                         exit(0);
145                 }
146         }
147         
148         echo "Creating database\n";
149         $ra = readline("Directory where automount occurs [/changer/]:");
150         $rb = readline("Number of drives [1]:");
151         $rc = readline("Size of tapes [20] (in gb):");
152         $rd = readline("Where to store drive pointers [/var/run/bacula/]:");
153         
154         if($ra == "") $ra = "/changer/";
155         if($rb == "") $rb = 1;
156         if($rc == "") $rc = 20;
157         if($rd == "") $rd = "/var/run/bacula/";
158         
159         conf_setVal($changer_name, "automountdir", "$ra");
160         conf_setVal($changer_name, "ndrives", "$rb");
161         conf_setVal($changer_name, "tapesize", "$rc");
162         conf_setVal($changer_name, "drivelocation", "$rd");
163         
164         // check if they were set
165         echo "got: ".conf_getVal($changer_name, "automountdir").", and ".conf_getVal($changer_name, "tapesize").", and ".conf_getVal($changer_name, "ndrives")."\n";
166 }
167
168 function check_init_and_fail($changer)
169 {
170         $lk = conf_getVal($changer, "automountdir");
171         if(!$lk) {
172                 echo "DB not init'd yet, please run init first\n";
173                 exit(0);
174         } 
175 }
176
177 function check_init($changer)
178 {
179         $lk = conf_getVal($changer, "automountdir");
180         if(!$lk) {
181                 return false;
182         } 
183         
184         return true;
185 }
186
187 function add_disk()
188 {
189         // disks get inited by going to /changer_dir/disk_uuid/ then:
190         // creating pbdc/changer_name/stuff.
191         global $BASE_DATA, $BASE_LIB, $BACULA_USER, $argv;
192         
193         check_init_and_fail($argv[1]);
194         
195         $dh = opendir("/dev/disk/by-uuid");
196         
197         $disk = "";
198         $i = 0;
199         
200         while(($file = readdir($dh)) !== false) {
201                 if($file != "." && $file != "..") {
202                         $st = stat("/dev/disk/by-uuid/".$file);
203                         $realname = basename(readlink("/dev/disk/by-uuid/".$file));
204                         
205                         // now get the size
206                         $fh = fopen("/sys/class/block/$realname/size", "r");
207                         $rl = fgets($fh);
208                         fclose($fh);
209                         $realsize = (int)(((($rl/1024)*512)/1024)/1024);
210                         
211                         echo "disk $i: /dev/$realname or /dev/disk/by-uuid/$file of size ".$realsize."gb\n";
212                         $disk[$i]["real"] = "/dev/$realname";
213                         $disk[$i]["syml"] = "/dev/disk/by-uuid/".$file;
214                         $disk[$i]["size"] = $realsize;
215                         $i++;
216                 }
217         }
218         
219         closedir($dh);
220         
221         $i = readline("Choose a disk from the list above:");
222         if(isset($disk[$i]["real"])) {
223                 echo "you have chosen, ".$disk[$i]["syml"]." (".$disk[$i]["real"].") of size ".$disk[$i]["size"]."gb\n";
224                 $ans = readline("is this correct? [y/n]:");
225                 if($ans != "y") {
226                         echo "you said no, i bail\n";
227                         exit(0);
228                 }
229         } else {
230                 echo "invalid selection\n";
231                 exit(0);
232         }
233
234         // now we try and init the disk
235         // we have to get automount directory config
236         $dir = conf_getVal($argv[1], "automountdir");
237         if(!is_dir($dir)) {
238                 echo "cant find automount directory, $dir\n";
239         }
240         $mkd = "$dir/".basename($disk[$i]["syml"])."/pbdc/".$argv[1]."/tapes/";
241         $k = mkdir($mkd, 0700, true);
242         
243         if(!is_dir($mkd)) {
244                 echo "Error, couldn't create directory, check permissions on $mkd?\n";
245         }
246         
247         $ts = conf_getVal($argv[1], "tapesize");
248         $max = (int)($disk[$i]["size"]/$ts);
249         
250         $kt = (int)(readline("No of tapes to create [max:$max] @ ".$ts."gb each:"));
251         if($kt > $max) {
252                 echo "Sorry, max number of tapes is $max, creating $max instead\n";
253                 $kt = $max;
254         }
255         
256         $did = add_diskToDB($argv[1], basename($disk[$i]["syml"]));
257         
258         if(!$did) {
259                 echo "Disk already exists, doing nothing\n";
260                 exit(0);
261         }
262         
263         // disk names are d.$did_vol0000x
264         //echo "did: $did\n";
265         for($ii=0; $ii < $kt; $ii++) {
266                 $tid = sprintf("d%d_vol%04d", $did, $ii);
267                 //echo "would create $tid\n";
268                 $tp = "$dir/".basename($disk[$i]["syml"])."/pbdc/".$argv[1]."/tapes/$tid";
269                 if(!file_exists($tp)) {
270                         fopen($tp, "w");
271                         echo "created tape $tid\n";
272                 } else {
273                         echo "tape $tid already existed\n";
274                 }
275         }
276 }
277 ?>