source: src-qt4/pc-softwaremanager/processManager.cpp @ 5cb32e6

releng/10.0.1releng/10.0.2releng/10.0.3releng/10.1
Last change on this file since 5cb32e6 was 5cb32e6, checked in by Ken Moore <ken@…>, 9 months ago

Convert the AppCafe? backend to use the new DLProcess class within libpcbsd-utils for download parsing/notifications. Seems to work just fine.

  • Property mode set to 100644
File size: 11.4 KB
Line 
1/***************************************************************************
2 *   Copyright (C) 2011 - iXsystems                                       *
3 *   kris@pcbsd.org  *
4 *   tim@pcbsd.org   *
5 *   ken@pcbsd.org   *
6 *                                                                         *
7 *   Permission is hereby granted, free of charge, to any person obtaining *
8 *   a copy of this software and associated documentation files (the       *
9 *   "Software"), to deal in the Software without restriction, including   *
10 *   without limitation the rights to use, copy, modify, merge, publish,   *
11 *   distribute, sublicense, and/or sell copies of the Software, and to    *
12 *   permit persons to whom the Software is furnished to do so, subject to *
13 *   the following conditions:                                             *
14 *                                                                         *
15 *   The above copyright notice and this permission notice shall be        *
16 *   included in all copies or substantial portions of the Software.       *
17 *                                                                         *
18 *   THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND,       *
19 *   EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF    *
20 *   MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. *
21 *   IN NO EVENT SHALL THE AUTHORS BE LIABLE FOR ANY CLAIM, DAMAGES OR     *
22 *   OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, *
23 *   ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR *
24 *   OTHER DEALINGS IN THE SOFTWARE.                                       *
25 ***************************************************************************/
26 #include "processManager.h"
27
28ProcessManager::ProcessManager(){
29    //Initialize the UPDATE Process
30    upProc = new DLProcess(this);
31        upProc->setDLType("PBI");
32    connect(upProc, SIGNAL(UpdateMessage(QString)), this, SLOT(slotUpProcMessage(QString)) );
33    connect(upProc, SIGNAL(UpdatePercent(QString, QString, QString)), this, SLOT(slotUpProcStats(QString,QString, QString)) );
34    connect(upProc, SIGNAL(finished(int,QProcess::ExitStatus)),this,SLOT(slotUpProcFinished()) );
35       
36    //Initialize the REMOVE Process
37    remProc = new DLProcess(this);
38        //remProc->setDLType("PBI"); //Does not need download parsing - just use standard message output
39    connect(remProc, SIGNAL(UpdateMessage(QString)), this, SLOT(slotRemProcMessage(QString)) );
40    connect(remProc, SIGNAL(finished(int,QProcess::ExitStatus)),this,SLOT(slotRemProcFinished()) );
41       
42    //Initialize the DOWNLOAD Process
43    dlProc = new DLProcess(this);
44        dlProc->setDLType("PBI");
45    connect(dlProc, SIGNAL(UpdateMessage(QString)), this, SLOT(slotDlProcMessage(QString)) );
46    connect(dlProc, SIGNAL(UpdatePercent(QString, QString, QString)), this, SLOT(slotDlProcStats(QString,QString, QString)) );
47    connect(dlProc, SIGNAL(finished(int,QProcess::ExitStatus)),this,SLOT(slotDlProcFinished()) );
48       
49    //Initialize the INSTALL Process
50    inProc = new DLProcess(this);
51        //inProc->setDLType("PBI"); //Does not need download parsing - just use standard message output
52    connect(inProc, SIGNAL(UpdateMessage(QString)), this, SLOT(slotInProcMessage(QString)) );
53    connect(inProc, SIGNAL(finished(int,QProcess::ExitStatus)),this,SLOT(slotInProcFinished()) );
54   
55    //Initialize the OTHER Process
56    otProc = new DLProcess(this);
57        //otProc->setDLType("PBI"); //Does not need download parsing - just use standard message output
58    connect(otProc, SIGNAL(UpdateMessage(QString)), this, SLOT(slotOtProcMessage(QString)) );
59    connect(otProc, SIGNAL(finished(int,QProcess::ExitStatus)),this,SLOT(slotOtProcFinished()) );
60}
61
62ProcessManager::~ProcessManager(){
63}
64
65void ProcessManager::goToDirectory(ProcessID ID, QString dir){
66  if( ID == UPDATE ){
67    upProc->setWorkingDirectory(dir);     
68  }else if( ID == REMOVE ){
69    remProc->setWorkingDirectory(dir);           
70  }else if( ID == DOWNLOAD ){
71    dlProc->setWorkingDirectory(dir);     
72  }else if( ID == INSTALL ){
73    inProc->setWorkingDirectory(dir);             
74  }else if( ID == OTHER ){
75    otProc->setWorkingDirectory(dir);             
76  }     
77}
78
79// =========================
80// ===== PUBLIC ACCESS =====
81// =========================
82void ProcessManager::startProcess(ProcessID ID, QString cmd){
83  if( ID == UPDATE ){
84    qDebug() << "Update Process Started:" << cmd;
85    upLog.clear(); //clear the log for action
86    upProc->start(cmd);   
87  }else if( ID == REMOVE ){
88    qDebug() << "Removal Process Started:" << cmd;
89    remLog.clear();
90    if( cmd.contains("pbi_delete") ){ remStrictErrChecking = true; }
91    else{ remStrictErrChecking=false; }
92    remProc->start(cmd);                 
93  }else if( ID == DOWNLOAD ){
94    qDebug() << "Download Process Started:" << cmd;
95    dlLog.clear();
96    dlProc->start(cmd);           
97  }else if( ID == INSTALL ){
98    qDebug() << "Install Process Started:" << cmd;
99    inLog.clear();
100    inProc->start(cmd);           
101  }else if( ID == OTHER ){
102    qDebug() << "Other Process Started:" << cmd;
103    otProc->start(cmd);           
104  }
105       
106}
107
108void ProcessManager::stopProcess(ProcessID ID){
109  if((ID == ALL) || (ID == UPDATE)){
110    upProc->terminate();         
111  }
112  if((ID == ALL) || (ID == REMOVE)){
113    remProc->terminate();         
114  }
115  if((ID == ALL) || (ID == DOWNLOAD)){
116    dlProc->terminate();         
117  }
118  if((ID == ALL) || (ID == INSTALL)){
119    inProc->terminate();         
120  }
121  if((ID == ALL) || (ID == OTHER)){
122    otProc->terminate();         
123  }     
124}
125
126QStringList ProcessManager::getProcessLog(ProcessID ID){
127  if( ID == UPDATE ){ return upLog; }
128  else if( ID == REMOVE ){ return remLog; }
129  else if( ID == DOWNLOAD ){ return dlLog; }
130  else if( ID == INSTALL ){ return inLog; }
131  else{ return QStringList(); }
132}
133
134// =========================
135// ===== PRIVATE SLOTS =====
136// =========================
137//QString ProcessManager::parseDlLine(QString line){
138  /*DOWNLOAD NOTIFICATION CODES:
139  Download complete: "DLDONE"
140  Download running: "DLSTAT::<percent>::<total size>::<download speed>"
141        -- A value of "??" means that it is unknown
142  Download starting: "DLSTART"
143  */
144/*
145  QString out;
146  if( line.startsWith("FETCH:") ){ return "DLSTART"; }
147  else if( line == "FETCHDONE"){ return "DLDONE"; }
148  else if(!line.startsWith("SIZE:")){ return out; }
149  //qDebug() << "parse Download Line:" << line;
150  //Line format: SIZE:  <KB> DOWNLOADED:  <KB> SPEED:  <KB/s> KB/s
151  line = line.simplified();
152  line.replace("SIZE: ","");
153  line.replace("DOWNLOADED: ", "");
154  line.replace("SPEED: ","");
155  line.replace("KB/s","");
156  bool totok, curok, spdok;
157  double tot, cur, spd;
158  tot = line.section(" ",0,0).toDouble(&totok);
159  cur = line.section(" ",1,1).toDouble(&curok);
160  spd = line.section(" ",2,2).toDouble(&spdok);
161  //qDebug() << " - DownloadStats:" << tot << cur << spd;
162  if(totok && tot==0){totok=FALSE;}
163  if(curok && cur==0){curok=FALSE;}
164  if(spdok && spd==0){spdok=FALSE;}
165  //Now format the output string
166  QString stats;
167  out = "DLSTAT::";
168  //Get percent and totals
169  if(totok && curok){
170    bool totErr = (tot==cur); //catch for a display error where the cur is always identical to the tot
171    if(!totErr){         
172      //Calculate the percentage
173      double percent = (cur/tot)*100;
174      percent = int(percent*10)/10.0;
175      out.append(QString::number(percent)+"::");
176      //Now list the total
177      out.append( Extras::sizeKToDisplay(QString::number(tot)) +"::" );
178    }else{
179      //Only Total/Current is known (unknown percentage since not complete yet)
180      out.append("??::"+Extras::sizeKToDisplay(QString::number(tot))+"::");
181    }       
182  }else if(curok){
183    //Only Total/Current is known (unknown percentage since not complete yet)
184    out.append("??::"+Extras::sizeKToDisplay(QString::number(cur))+"::");
185  }else if(totok){
186    //Only Total/Current is known (unknown percentage since not complete yet)
187    out.append("??::"+Extras::sizeKToDisplay(QString::number(tot))+"::");
188  }else{
189    //Unknown Total and Current
190    out.append("??::??::");
191  }
192  //Now get the speed
193  if(spdok){
194    out.append( Extras::sizeKToDisplay(QString::number(spd))+"/s" );
195  }else{
196    out.append("??");
197  }
198  return out;
199}
200*/
201// == UPDATE PROCESS ==
202void ProcessManager::slotUpProcMessage(QString msg){
203  //Check for DL start/finish messages
204  if(msg.startsWith("FETCH:")){ msg = "DLSTART"; }
205  else if(msg.startsWith("FETCHDONE")){ msg = "DLDONE"; }
206  else{
207    //Add the message to the log
208    upLog << msg;
209  }
210  //Now send it out
211  emit ProcessMessage(UPDATE, msg);
212}
213
214void ProcessManager::slotUpProcStats(QString percent, QString size, QString speed){
215  //Format the display string for output
216  QString out = "DLSTAT::"+percent+"::"+size+"::"+speed;
217  emit ProcessMessage(UPDATE, out);
218}
219
220void ProcessManager::slotUpProcFinished(){
221  if(upProc->exitStatus() != QProcess::NormalExit || upProc->exitCode() != 0){
222    //Emit the command log
223    qDebug() << "Update Process Error Log:\n"<<upLog.join("\n");
224    emit ProcessError(UPDATE, upLog);
225  }else{
226    qDebug() << "Update Process Finished";
227    emit ProcessFinished(UPDATE);         
228  }
229}
230
231// == REMOVE PROCESS ==
232void ProcessManager::slotRemProcMessage(QString msg){
233  //Add the message to the log
234  remLog << msg;
235  //Now send it out
236  emit ProcessMessage(REMOVE, msg);
237}
238
239void ProcessManager::slotRemProcFinished(){
240  if(remProc->exitStatus() != QProcess::NormalExit || (remProc->exitCode() != 0 && remStrictErrChecking) ){
241    qDebug() << "Removal Process Error Log:\n"<<remLog.join("\n");
242    emit ProcessError(REMOVE, remLog);
243  }else{
244    qDebug() << "Removal Process Finished";
245    emit ProcessFinished(REMOVE);         
246  }
247}
248
249// == DOWNLOAD PROCESS ==
250void ProcessManager::slotDlProcMessage(QString msg){
251  //Check for DL start/finish messages
252  if(msg.startsWith("FETCH:")){ msg = "DLSTART"; }
253  else if(msg.startsWith("FETCHDONE")){ msg = "DLDONE"; }
254  else{
255    //Add the message to the log
256    dlLog << msg;
257  }
258  //Now send it out
259  emit ProcessMessage(DOWNLOAD, msg);
260}
261
262void ProcessManager::slotDlProcStats(QString percent, QString size, QString speed){
263  //Format the display string for output
264  QString out = "DLSTAT::"+percent+"::"+size+"::"+speed;
265  emit ProcessMessage(DOWNLOAD, out);
266}
267
268void ProcessManager::slotDlProcFinished(){
269  if(dlProc->exitStatus() != QProcess::NormalExit || dlProc->exitCode() != 0){
270    qDebug() << "Download Process Error Log:\n"<<dlLog.join("\n");
271    emit ProcessError(DOWNLOAD, dlLog);
272  }else{
273    qDebug() << "Download Process Finished";
274    emit ProcessFinished(DOWNLOAD);       
275  }
276}
277
278// == INSTALL PROCESS ==
279void ProcessManager::slotInProcMessage(QString msg){
280  //Add the message to the log
281  inLog << msg;
282  //Now send it out
283  emit ProcessMessage(INSTALL, msg);
284}
285
286void ProcessManager::slotInProcFinished(){
287  if(inProc->exitStatus() != QProcess::NormalExit || inProc->exitCode() != 0){
288    qDebug() << "Install Process Error Log:\n"<<inLog.join("\n");
289    emit ProcessError(INSTALL, inLog);
290  }else{
291    qDebug() << "Install Process Finished";
292    emit ProcessFinished(INSTALL);       
293  }
294}
295
296// == OTHER PROCESS ==
297void ProcessManager::slotOtProcMessage(QString msg){
298  //send it out (no logging - this channel is for quick commands with almost no output)
299  emit ProcessMessage(OTHER, msg);
300}
301
302void ProcessManager::slotOtProcFinished(){
303  if(otProc->exitStatus() != QProcess::NormalExit){
304    QString msg = otProc->readAllStandardError();
305    if(msg.isEmpty()){ msg = otProc->readAllStandardOutput(); }
306    if(msg.isEmpty()){ msg = tr("Unknown Error"); }
307    qDebug() << "Other Process Error:"<<msg;
308    emit ProcessError(OTHER, QStringList(msg));
309  }else{
310    qDebug() << "Other Process Finished";
311    emit ProcessFinished(OTHER);         
312  }
313}
314
Note: See TracBrowser for help on using the repository browser.