]> git.sur5r.net Git - bacula/bacula/blob - bacula/src/qt-console/storage/content.cpp
bat: fix sql with volreadtime volwritetime
[bacula/bacula] / bacula / src / qt-console / storage / content.cpp
1 /*
2    Bacula® - The Network Backup Solution
3
4    Copyright (C) 2007-2009 Free Software Foundation Europe e.V.
5
6    The main author of Bacula is Kern Sibbald, with contributions from
7    many others, a complete list can be found in the file AUTHORS.
8    This program is Free Software; you can redistribute it and/or
9    modify it under the terms of version two of the GNU General Public
10    License as published by the Free Software Foundation and included
11    in the file LICENSE.
12
13    This program is distributed in the hope that it will be useful, but
14    WITHOUT ANY WARRANTY; without even the implied warranty of
15    MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
16    General Public License for more details.
17
18    You should have received a copy of the GNU General Public License
19    along with this program; if not, write to the Free Software
20    Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA
21    02110-1301, USA.
22
23    Bacula® is a registered trademark of Kern Sibbald.
24    The licensor of Bacula is the Free Software Foundation Europe
25    (FSFE), Fiduciary Program, Sumatrastrasse 25, 8006 Zürich,
26    Switzerland, email:ftf@fsfeurope.org.
27 */
28  
29 #include "bat.h"
30 #include <QAbstractEventDispatcher>
31 #include <QMenu>
32 #include "content.h"
33 #include "label/label.h"
34 #include "mount/mount.h"
35 #include "util/fmtwidgetitem.h"
36 #include "status/storstat.h"
37
38 // 
39 // TODO: List tray
40 //       List drives in autochanger
41 //       use user selection to add slot= argument
42 // 
43
44 Content::Content(QString storage, QTreeWidgetItem *parentWidget)
45 {
46    setupUi(this);
47    pgInitialize(storage, parentWidget);
48    QTreeWidgetItem* thisitem = mainWin->getFromHash(this);
49    thisitem->setIcon(0,QIcon(QString::fromUtf8(":images/package-x-generic.png")));
50
51    m_populated = false;
52    m_firstpopulation = true;
53    m_checkcurwidget = true;
54    m_closeable = true;
55    m_currentStorage = storage;
56
57    connect(pbUpdate, SIGNAL(clicked()), this,
58            SLOT(consoleUpdateSlots()));
59
60    connect(pbLabel, SIGNAL(clicked()), this,
61            SLOT(consoleLabelStorage()));
62
63    connect(pbMount, SIGNAL(clicked()), this,
64            SLOT(consoleMountStorage()));
65
66    connect(pbUnmount, SIGNAL(clicked()), this,
67            SLOT(consoleUnMountStorage()));
68
69    connect(pbStatus, SIGNAL(clicked()), this,
70            SLOT(statusStorageWindow()));
71
72    connect(pbRelease, SIGNAL(clicked()), this,
73            SLOT(consoleRelease()));
74
75    dockPage();
76    setCurrent();
77 }
78
79 void table_get_selection(QTableWidget *table, QString &sel)
80 {
81    QTableWidgetItem *item;
82    int current;
83
84    /* The QT selection returns each cell, so you
85     * have x times the same row number...
86     * We take only one instance
87     */
88    int s = table->rowCount();
89    bool *tab = (bool *)malloc(s * sizeof(bool));
90    memset(tab, 0, s); 
91
92    foreach (item, table->selectedItems()) {
93       current = item->row();
94       tab[current]=true;
95    }
96
97    sel += "=";
98
99    for(int i=0; i<s; i++) {
100       if (tab[i]) {
101          sel += table->item(i, 0)->text();
102          sel += ",";
103       }
104    }
105    sel.chop(1);                 // remove trailing , or useless =
106    free(tab);
107 }
108
109 /* Label Media populating current storage by default */
110 void Content::consoleLabelStorage()
111 {
112    QString sel;
113    table_get_selection(tableContent, sel);
114    if (sel == "") {
115       new labelPage(m_currentStorage);
116    } else {
117       QString cmd = "label barcodes slots";
118       cmd += sel;
119       cmd += " storage=" + m_currentStorage;
120       consoleCommand(cmd);
121    }
122 }
123
124 /* Mount currently selected storage */
125 void Content::consoleMountStorage()
126 {
127    setConsoleCurrent();
128    /* if this storage is an autochanger, lets ask for the slot */
129    new mountDialog(m_console, m_currentStorage);
130 }
131
132 /* Unmount Currently selected storage */
133 void Content::consoleUnMountStorage()
134 {
135    QString cmd("umount storage=");
136    cmd += m_currentStorage;
137    consoleCommand(cmd);
138 }
139
140 void Content::statusStorageWindow()
141 {
142    /* if one exists, then just set it current */
143    bool found = false;
144    foreach(Pages *page, mainWin->m_pagehash) {
145       if (mainWin->currentConsole() == page->console()) {
146          if (page->name() == tr("Storage Status %1").arg(m_currentStorage)) {
147             found = true;
148             page->setCurrent();
149          }
150       }
151    }
152    if (!found) {
153       QTreeWidgetItem *parentItem = mainWin->getFromHash(this);
154       new StorStat(m_currentStorage, parentItem);
155    }
156 }
157
158 /*
159  * The main meat of the class!!  The function that querries the director and 
160  * creates the widgets with appropriate values.
161  */
162 void Content::populateContent()
163 {
164    char buf[200];
165    time_t t;
166    struct tm tm;
167
168    QStringList results_all;
169    QString cmd("status slots drive=0 storage=\"" + m_currentStorage + "\"");
170    m_console->dir_cmd(cmd, results_all);
171
172    Freeze frz(*tableContent); /* disable updating*/
173    tableContent->clearContents();
174
175    // take only valid records
176    QStringList results = results_all.filter(QRegExp("^[0-9]+\\|"));
177    tableContent->setRowCount(results.size());
178
179    QString resultline;
180    QStringList fieldlist;
181    int row = 0;
182
183    foreach (resultline, results) {
184       fieldlist = resultline.split("|");
185       if (fieldlist.size() < 9)
186          continue; /* some fields missing, ignore row */
187
188       int index=0;
189       QStringListIterator fld(fieldlist);
190       TableItemFormatter slotitem(*tableContent, row);
191
192       /* Slot */
193       slotitem.setNumericFld(index++, fld.next()); 
194
195       /* Real Slot */
196       if (fld.next() != "") {
197
198          /* Volume */
199          slotitem.setTextFld(index++, fld.next());
200          
201          /* Bytes */
202          slotitem.setBytesFld(index++, fld.next());
203          
204          /* Status */
205          slotitem.setVolStatusFld(index++, fld.next());
206          
207          /* MediaType */
208          slotitem.setTextFld(index++, fld.next());
209          
210          /* Pool */
211          slotitem.setTextFld(index++, fld.next());
212          
213          t = fld.next().toInt();
214          if (t > 0) {
215             /* LastW */
216             localtime_r(&t, &tm);
217             strftime(buf, sizeof(buf), "%Y-%m-%d %H:%M:%S", &tm);
218             slotitem.setTextFld(index++, QString(buf));
219             
220             /* Expire */
221             t = fld.next().toInt();
222             localtime_r(&t, &tm);
223             strftime(buf, sizeof(buf), "%Y-%m-%d %H:%M:%S", &tm);
224             slotitem.setTextFld(index++, QString(buf));
225          }
226       }
227       row++;
228    }
229
230
231    tableContent->verticalHeader()->hide();
232    tableContent->sortByColumn(0, Qt::AscendingOrder);
233    tableContent->setSortingEnabled(true);
234    tableContent->resizeColumnsToContents();
235    tableContent->resizeRowsToContents();
236
237    /* make read only */
238    int rcnt = tableContent->rowCount();
239    int ccnt = tableContent->columnCount();
240    for(int r=0; r < rcnt; r++) {
241       for(int c=0; c < ccnt; c++) {
242          QTableWidgetItem* item = tableContent->item(r, c);
243          if (item) {
244             item->setFlags(Qt::ItemFlags(item->flags() & (~Qt::ItemIsEditable)));
245          }
246       }
247    }
248    m_populated = true;
249
250    tableTray->verticalHeader()->hide();
251    tableDrive->verticalHeader()->hide();
252 }
253
254 /*
255  * Virtual function which is called when this page is visible on the stack
256  */
257 void Content::currentStackItem()
258 {
259    if(!m_populated) {
260       populateContent();
261    }
262 }
263
264 void Content::treeItemChanged(QTreeWidgetItem *, QTreeWidgetItem *)
265 {
266
267 }
268
269 /* Update Slots */
270 void Content::consoleUpdateSlots()
271 {
272    QString sel = "";
273    table_get_selection(tableContent, sel);
274    
275    QString cmd("update slots");
276    if (sel != "") {
277       cmd += sel;
278    }
279    cmd += " drive=0 storage=" + m_currentStorage;
280
281    Pmsg1(0, "cmd=%s\n", cmd.toUtf8().data());
282
283    consoleCommand(cmd);
284    populateContent();
285 }
286
287 /* Release a tape in the drive */
288 void Content::consoleRelease()
289 {
290    QString cmd("release storage=");
291    cmd += m_currentStorage;
292    consoleCommand(cmd);
293 }