]> git.sur5r.net Git - bacula/bacula/commitdiff
Merge branch 'bwebII'
authorEric Bollengier <eric@eb.homelinux.org>
Tue, 21 Jul 2009 17:51:24 +0000 (17:51 +0000)
committerEric Bollengier <eric@eb.homelinux.org>
Tue, 21 Jul 2009 17:51:24 +0000 (17:51 +0000)
git-svn-id: https://bacula.svn.sourceforge.net/svnroot/bacula/trunk@9079 91ce42f0-d328-0410-95d8-f526ca767f89

gui/bweb/cgi/bresto.pl
gui/bweb/html/bresto.js
gui/bweb/html/bweb.js
gui/bweb/html/file_d.png [new file with mode: 0644]
gui/bweb/html/file_f.png [new file with mode: 0644]

index 3d3adab9cfdedbe32ea29f8f4281964f079b3809..a22d0a82e1de04b7a903db20b7a3c7a152f2702a 100755 (executable)
@@ -1,5 +1,5 @@
 #!/usr/bin/perl -w
-
+use strict;
 my $bresto_enable = 1;
 die "bresto is not enabled" if (not $bresto_enable);
 
@@ -373,7 +373,7 @@ sub ls_files
      ) AS listfiles
 WHERE File.FileId = listfiles.id";
 
-    print STDERR $query;
+#    print STDERR $query;
     $self->debug($query);
     my $result = $self->dbh_selectall_arrayref($query);
     $self->debug($result);
@@ -381,6 +381,68 @@ WHERE File.FileId = listfiles.id";
     return $result;
 }
 
+sub ls_special_dirs
+{
+    my ($self) = @_;
+    return undef unless ($self->{curjobids});
+
+    my $pathid = $self->{cwdid};
+    my $jobclause = $self->{curjobids};
+    my $dir_filenameid = $self->get_dir_filenameid();
+
+    my $sq1 =  
+"((SELECT PPathId AS PathId, '..' AS Path
+    FROM  brestore_pathhierarchy 
+   WHERE  PathId = $pathid)
+UNION
+ (SELECT $pathid AS PathId, '.' AS Path))";
+
+    my $sq2 = "
+SELECT tmp.PathId, tmp.Path, Lstat, JobId 
+  FROM $sq1 AS tmp  LEFT JOIN ( -- get attributes if any
+       SELECT File1.PathId, File1.JobId, File1.Lstat FROM File AS File1
+       WHERE File1.FilenameId = $dir_filenameid
+       AND File1.JobId IN ($jobclause)) AS listfile1
+  ON (tmp.PathId = listfile1.PathId)
+  ORDER BY tmp.Path, JobId DESC
+";
+
+    my $result = $self->dbh_selectall_arrayref($sq2);
+
+    my @return_list;
+    my $prev_dir='';
+    foreach my $refrow (@{$result})
+    {
+       my $dirid = $refrow->[0];
+        my $dir = $refrow->[1];
+        my $lstat = $refrow->[3];
+        my $jobid = $refrow->[2] || 0;
+        next if ($dirid eq $prev_dir);
+        my @return_array = ($dirid,$dir,$lstat,$jobid);
+        push @return_list,(\@return_array);
+        $prev_dir = $dirid;
+    }
+    return \@return_list;
+}
+
+# Let's retrieve the list of the visible dirs in this dir ...
+# First, I need the empty filenameid to locate efficiently
+# the dirs in the file table
+sub get_dir_filenameid
+{
+    my ($self) = @_;
+    if ($self->{dir_filenameid}) {
+        return $self->{dir_filenameid};
+    }
+    my $query = "SELECT FilenameId FROM Filename WHERE Name = ''";
+    my $sth = $self->dbh_prepare($query);
+    $sth->execute();
+    my $result = $sth->fetchrow_arrayref();
+    $sth->finish();
+    return $self->{dir_filenameid} = $result->[0];
+}
+
 # list all directories in a directory, accross curjobids
 # return ($dirid,$dir_basename,$lstat,$jobid)
 sub ls_dirs
@@ -395,15 +457,10 @@ sub ls_dirs
     # Let's retrieve the list of the visible dirs in this dir ...
     # First, I need the empty filenameid to locate efficiently
     # the dirs in the file table
-    my $query = "SELECT FilenameId FROM Filename WHERE Name = ''";
-    my $sth = $self->dbh_prepare($query);
-    $sth->execute();
-    my $result = $sth->fetchrow_arrayref();
-    $sth->finish();
-    my $dir_filenameid = $result->[0];
+    my $dir_filenameid = $self->get_dir_filenameid();
 
     # Then we get all the dir entries from File ...
-    $query = "
+    my $query = "
 SELECT PathId, Path, JobId, Lstat FROM (
 
     SELECT Path1.PathId, Path1.Path, lower(Path1.Path),
@@ -418,18 +475,18 @@ SELECT PathId, Path, JobId, Lstat FROM (
        WHERE brestore_pathhierarchy1.PPathId = $pathid
        AND brestore_pathvisibility1.jobid IN ($jobclause)) AS listpath1
    JOIN Path AS Path1 ON (listpath1.PathId = Path1.PathId)
-   LEFT JOIN (
+
+   LEFT JOIN ( -- get attributes if any
        SELECT File1.PathId, File1.JobId, File1.Lstat FROM File AS File1
        WHERE File1.FilenameId = $dir_filenameid
        AND File1.JobId IN ($jobclause)) AS listfile1
        ON (listpath1.PathId = listfile1.PathId)
      ) AS A ORDER BY 2,3 DESC LIMIT $self->{limit} OFFSET $self->{offset} 
 ";
-    $self->debug($query);
-    print STDERR $query;
-    $sth=$self->dbh_prepare($query);
+#    print STDERR $query;
+    my $sth=$self->dbh_prepare($query);
     $sth->execute();
-    $result = $sth->fetchall_arrayref();
+    my $result = $sth->fetchall_arrayref();
     my @return_list;
     my $prev_dir='';
     foreach my $refrow (@{$result})
@@ -836,7 +893,8 @@ sub fill_table_for_restore
     my $FileId = CGI::param('force')?",FileId":"";
 
     my $fileid = join(',', grep { /^\d+$/ } CGI::param('fileid'));
-    my @dirid = grep { /^\d+$/ } CGI::param('dirid');
+    # can get dirid=("10,11", 10, 11)
+    my @dirid = grep { /^\d+$/ } map { split(/,/) } CGI::param('dirid') ;
     my $inclause = join(',', @jobid);
 
     my @union;
@@ -952,7 +1010,7 @@ if (CGI::param('init')) { # used when choosing a job
     $bvfs->update_brestore_table(@jobid);
 }
 
-my $pathid = CGI::param('node') || '';
+my $pathid = CGI::param('node') || CGI::param('pathid') || '';
 my $path = CGI::param('path');
 
 if ($pathid =~ /^(\d+)$/) {
@@ -964,6 +1022,8 @@ if ($pathid =~ /^(\d+)$/) {
 }
 $bvfs->ch_dir($pathid);
 
+#print STDERR "pathid=$pathid\n";
+
 # permit to use a regex filter
 if ($args->{qpattern}) {
     $bvfs->set_pattern($args->{qpattern});
@@ -1010,13 +1070,71 @@ if ($action eq 'restore') {
 sub escape_quote
 {
     my ($str) = @_;
+    if (!$str) {
+        return '';
+    }
     $str =~ s/'/\\'/g;
     return $str;
 }
 
 print CGI::header('application/x-javascript');
 
-if ($action eq 'list_files') {
+
+if ($action eq 'list_files_dirs') {
+# fileid, filenameid, pathid, jobid, name, size, mtime
+    my $jids = join(",", @jobid);
+
+    my $files = $bvfs->ls_special_dirs();
+    # return ($dirid,$dir_basename,$lstat,$jobid)
+    print "[\n";
+    print join(',',
+              map { my @p=Bvfs::parse_lstat($_->[3]); 
+                    '[' . join(',', 
+                               0, # fileid
+                               0, # filenameid
+                               $_->[0], # pathid
+                               "'$jids'", # jobid
+                               "'" . escape_quote($_->[1]) . "'", # name
+                               "'" . $p[7] . "'",                 # size
+                               "'" . strftime('%Y-%m-%d %H:%m:%S', localtime($p[11])) .  "'") .
+                   ']'; 
+              } @$files);
+
+    print "," if (@$files);
+
+    $files = $bvfs->ls_dirs();
+    # return ($dirid,$dir_basename,$lstat,$jobid)
+    print join(',',
+              map { my @p=Bvfs::parse_lstat($_->[3]); 
+                    '[' . join(',', 
+                               0, # fileid
+                               0, # filenameid
+                               $_->[0], # pathid
+                               "'$jids'", # jobid
+                               "'" . escape_quote($_->[1]) . "'", # name
+                               "'" . $p[7] . "'",                 # size
+                               "'" . strftime('%Y-%m-%d %H:%m:%S', localtime($p[11])) .  "'") .
+                   ']'; 
+              } @$files);
+
+    print "," if (@$files);
+    $files = $bvfs->ls_files();
+    print join(',',
+              map { my @p=Bvfs::parse_lstat($_->[3]); 
+                    '[' . join(',', 
+                               $_->[1],
+                               $_->[0],
+                               $pathid,
+                               $_->[4],
+                               "'" . escape_quote($_->[2]) . "'",
+                               "'" . $p[7] . "'",
+                               "'" . strftime('%Y-%m-%d %H:%m:%S', localtime($p[11])) .  "'") .
+                   ']'; 
+              } @$files);
+    print "]\n";
+
+} elsif ($action eq 'list_files') {
     print "[[0,0,0,0,'.',4096,'1970-01-01 00:00:00'],";
     my $files = $bvfs->ls_files();
 #      [ 1, 2, 3, "Bill",  10, '2007-01-01 00:00:00'],
@@ -1072,6 +1190,7 @@ if ($action eq 'list_files') {
     my $lst;
 
     # in this mode, we compute the result to get all needed media
+#    print STDERR "force=", CGI::param('force'), "\n";
     if (CGI::param('force')) {
         $table = fill_table_for_restore(@jobid);
         if (!$table) {
@@ -1095,7 +1214,7 @@ if ($action eq 'list_files') {
     }
 
     if ($table) {
-        $bvfs->dbh_do("DROP TABLE $table");
+        #$bvfs->dbh_do("DROP TABLE $table");
     }
 
 }
index eec51c438eaafc62638566b1a93fe76d4d134011..c7c0e47e554f18ea62c0e13e2b03274029bb72b7 100644 (file)
@@ -1,7 +1,7 @@
 //   Bweb - A Bacula web interface
 //   Bacula® - The Network Backup Solution
 //
-//   Copyright (C) 2000-2008 Free Software Foundation Europe e.V.
+//   Copyright (C) 2000-2009 Free Software Foundation Europe e.V.
 //
 //   The main author of Bweb is Eric Bollengier.
 //   The main author of Bacula is Kern Sibbald, with contributions from
@@ -36,13 +36,42 @@ function rd_vol_is_online(val)
 // TODO: fichier ou rep
 function rd_file_or_dir(val)
 {
-   if (val == 'F') {
-      return '<img src="A.png">';
+   if (val > 0) {
+      return '<img src="file_f.png">';
    } else {
-      return '<img src="R.png">';
+      return '<img src="file_d.png">';
    }
 }
 
+function push_path()
+{
+    Ext.brestore.path_stack.push(Ext.brestore.path);
+    Ext.brestore.pathid_stack.push(Ext.brestore.pathid);
+    Ext.ComponentMgr.get('prevbp').enable();
+}
+function pop_path()
+{
+    var pathid = Ext.brestore.pathid_stack.pop();
+    var path = Ext.brestore.path_stack.pop();
+    if (!pathid) {
+        Ext.ComponentMgr.get('prevbp').disable();
+        return false;
+    }
+    Ext.ComponentMgr.get('wherefield').setValue(path);
+
+    Ext.brestore.pathid = pathid;
+    Ext.brestore.path = path;
+    return true;
+}
+
+function dirname(path) {
+    var a = path.match( /(^.*\/).+\// );
+    if (a) {
+        return a[1];
+    }
+    return path;
+}
+
 Ext.namespace('Ext.brestore');
 Ext.brestore.jobid=0;            // selected jobid
 Ext.brestore.jobdate='';         // selected date
@@ -59,9 +88,11 @@ Ext.brestore.option_vcopies = false;
 Ext.brestore.dlglaunch;
 Ext.brestore.fpattern;
 Ext.brestore.use_filerelocation=false;
-Ext.brestore.limit = 2000;
+Ext.brestore.limit = 500;
 Ext.brestore.offset = 0;
 Ext.brestore.force_reload = 0;
+Ext.brestore.path_stack = Array();
+Ext.brestore.pathid_stack = Array();
 
 function get_node_path(node)
 {
@@ -144,13 +175,15 @@ Ext.onReady(function(){
     Ext.brestore.tree = root;   // shortcut
 
     var click_cb = function(node, event) { 
+        push_path();
+
         Ext.brestore.path = get_node_path(node);
         Ext.brestore.pathid = node.id;
         Ext.brestore.offset=0;
         Ext.brestore.fpattern = Ext.get('txt-file-pattern').getValue();
         where_field.setValue(Ext.brestore.path);
         update_limits();       
-        file_store.load({params:init_params({action: 'list_files',
+        file_store.load({params:init_params({action: 'list_files_dirs',
                                              path:Ext.brestore.path,
                                              node:node.id})
                         });
@@ -188,11 +221,20 @@ Ext.onReady(function(){
           {name: 'jobid'     },
           {name: 'name'      },
           {name: 'size',     type: 'int'  },
-          {name: 'mtime',    type: 'date', dateFormat: 'Y-m-d h:i:s'}
+          {name: 'mtime',    type: 'date', dateFormat: 'Y-m-d h:i:s'},
+          {name: 'type'}
         ]))
     });
+    
     Ext.brestore.file_store=file_store;
     var cm = new Ext.grid.ColumnModel([{
+        id:        'type',
+        header:    'Type',
+        dataIndex: 'filenameid',
+        width:     30,
+        css:       'white-space:normal;',
+        renderer:   rd_file_or_dir
+    },{
         id:        'cm-id', // id assigned so we can apply custom css 
                            // (e.g. .x-grid-col-topic b { color:#333 })
         header:    'File',
@@ -251,7 +293,7 @@ Ext.onReady(function(){
 
     var file_paging_next = new Ext.Toolbar.Button({
         id: 'bp-file-next',
-        icon: '/bweb/ext/resources/images/default/grid/page-next.gif',
+        icon: 'ext/resources/images/default/grid/page-next.gif',
         cls: '.x-btn-icon',
         tooltip: 'Next',
         handler: function(a,b,c) {
@@ -260,7 +302,7 @@ Ext.onReady(function(){
                 Ext.brestore.offset += Ext.brestore.limit;
                 file_store.removeAll();
                 file_versions_store.removeAll();
-                file_store.load({params:init_params({action: 'list_files',
+                file_store.load({params:init_params({action: 'list_files_dirs',
                                                      path:Ext.brestore.path,
                                                      node:Ext.brestore.pathid})
                                 });
@@ -269,7 +311,7 @@ Ext.onReady(function(){
     });
     var file_paging_prev = new Ext.Toolbar.Button({
         id: 'bp-file-prev',
-        icon: '/bweb/ext/resources/images/default/grid/page-prev.gif',
+        icon: 'ext/resources/images/default/grid/page-prev.gif',
         cls: '.x-btn-icon',
         tooltip: 'Last',
         handler: function() {
@@ -281,7 +323,7 @@ Ext.onReady(function(){
                 }
                 file_store.removeAll();
                 file_versions_store.removeAll();
-                file_store.load({params:init_params({action: 'list_files',
+                file_store.load({params:init_params({action: 'list_files_dirs',
                                                      path:Ext.brestore.path,
                                                      node:Ext.brestore.pathid})
                                 });                        
@@ -323,14 +365,14 @@ Ext.onReady(function(){
             value: Ext.brestore.limit          
         }, file_paging_next, '->', file_paging_pattern, {
             id: 'bp-file-match',
-            icon: '/bweb/ext/resources/images/default/grid/refresh.gif',
+            icon: 'ext/resources/images/default/grid/refresh.gif',
             cls: '.x-btn-icon',
             tooltip: 'Refresh',
             handler: function(a,b,c) {
                 update_user_limits();
                 file_store.removeAll();
                 file_versions_store.removeAll();
-                file_store.load({params:init_params({action: 'list_files',
+                file_store.load({params:init_params({action: 'list_files_dirs',
                                                      path:Ext.brestore.path,
                                                      node:Ext.brestore.pathid})
                                 });
@@ -390,11 +432,38 @@ Ext.onReady(function(){
  *         console.info('Store count = ', store.getCount());
  *   });
  */
+    file_grid.on('celldblclick', function(e) {
+        var r = e.selModel.getSelected();
+
+        if (r.json[1] == 0) {   // select a directory
+           push_path();
+
+           if (r.json[4] == '..') {
+              Ext.brestore.path = dirname(Ext.brestore.path);
+           } else if (r.json[4] == '/') {
+              Ext.brestore.path = '/';
+           } else if (r.json[4] != '.') {
+              Ext.brestore.path = Ext.brestore.path + r.json[4] + '/';
+           }
+           Ext.brestore.pathid = r.json[2];
+           Ext.brestore.filename = '';
+           Ext.brestore.offset=0;
+           Ext.brestore.fpattern = Ext.get('txt-file-pattern').getValue();
+           where_field.setValue(Ext.brestore.path);
+           update_limits();
+           file_store.load({params:init_params({action: 'list_files_dirs',
+                          path:Ext.brestore.path,
+                          node:Ext.brestore.pathid})
+                    });
+        }
+        return true;
+    });
     // TODO: selection only when using dblclick
     file_grid.selModel.on('rowselect', function(e,i,r) { 
-        if (r.json[4] == '.') {
-            return true;
+        if (r.json[1] == 0) {   // select a directory
+           return true;
         }
+
         Ext.brestore.filename = r.json[4];
         file_versions_store.load({
             params:init_params({action: 'list_versions',
@@ -686,14 +755,19 @@ Ext.onReady(function(){
     job_combo.on('select', function(e,c) {
         Ext.brestore.jobid = c.json[0];
         Ext.brestore.jobdate = c.json[1];
-        Ext.brestore.root_path='';
         root.setText("Root");
         tree_loader.baseParams = init_params({init:1, action: 'list_dirs'});
         root.reload();
+
+        file_store.load({params:init_params({action: 'list_files_dirs',
+                                             path:Ext.brestore.path,
+                                             node:Ext.brestore.pathid})
+                        });
     });
 
     var where_field = new Ext.form.TextField({
             fieldLabel: 'Location',
+            id: 'wherefield',
             name: 'where',
             width:275,
             allowBlank:false
@@ -741,6 +815,24 @@ Ext.onReady(function(){
             client_combo,
             job_combo,
             '-',
+            {
+                id: 'prevbp',
+                cls: 'x-btn-icon',
+                icon: 'prev.png',
+                disabled: true,
+                handler: function() { 
+                    if (!pop_path()) {
+                        return;
+                    }
+                    Ext.brestore.offset=0;
+                    update_limits();       
+                    file_store.load({params:init_params({action: 'list_files_dirs',
+                                                         node:Ext.brestore.pathid})
+                                    });
+                    
+                }
+
+            },
             { 
               text: 'Change location',
               cls:'x-btn-text-icon',
@@ -771,7 +863,7 @@ Ext.onReady(function(){
             },
             '->',                     // Fill
             {                         // TODO: put this button on south panel
-                icon: '/bweb/mR.png', // icons can also be specified inline
+                icon: 'mR.png', // icons can also be specified inline
                 cls: 'x-btn-text-icon',
                 tooltip: 'Run restore',
                 text: 'Run restore',
@@ -851,12 +943,17 @@ Ext.onReady(function(){
             if (data.selections) {
                 if (data.grid.id == 'div-files') {
                     for(var i=0;i<data.selections.length;i++) {
+                        var name = data.selections[i].json[4];
+                        var fnid = data.selections[i].json[1];
+                        if (fnid == 0 && name != '..') {
+                            name = name + '/';
+                        }
                         r = new file_selection_record({
                             jobid:     data.selections[0].json[3],
                             fileid:    data.selections[i].json[0],
                             filenameid:data.selections[i].json[1],
                             pathid:    data.selections[i].json[2],
-                            name: Ext.brestore.path + data.selections[i].json[4],
+                            name: Ext.brestore.path + ((name=='..')?'':name),
                             size:      data.selections[i].json[5],
                             mtime:     data.selections[i].json[6]
                         });
@@ -902,6 +999,7 @@ Ext.onReady(function(){
     }
 
     function reload_media_store() {
+        Ext.brestore.media_store.removeAll();
         var items = file_selection_store.data.items;
         var tab_fileid=new Array();
         var tab_dirid=new Array();
index d2a960716152e58a301a7c420a68cbaa702773c0..de8f5b615c8cbdd899d84e78777ba56663e94e2d 100644 (file)
@@ -88,7 +88,6 @@ function bweb_refresh() {
 function bweb_add_refresh(){
        window.setInterval("bweb_refresh()",refresh_time);
 }
-
 function human_size(val)
 {   
    if (!val) {
diff --git a/gui/bweb/html/file_d.png b/gui/bweb/html/file_d.png
new file mode 100644 (file)
index 0000000..bfe04b1
Binary files /dev/null and b/gui/bweb/html/file_d.png differ
diff --git a/gui/bweb/html/file_f.png b/gui/bweb/html/file_f.png
new file mode 100644 (file)
index 0000000..dd82778
Binary files /dev/null and b/gui/bweb/html/file_f.png differ