add autodetection, rewrite c/clive verification.
[abby.git] / src / util.cpp
blob362e3e2fb2e078ad23b15563e14170937b422bd1
1 /*
2 * abby Copyright (C) 2009 Toni Gundogdu.
3 * This file is part of abby.
5 * abby is free software: you can redistribute it and/or modify
6 * it under the terms of the GNU General Public License as published by
7 * the Free Software Foundation, either version 3 of the License, or
8 * (at your option) any later version.
10 * abby is distributed in the hope that it will be useful,
11 * but WITHOUT ANY WARRANTY; without even the implied warranty of
12 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
13 * GNU General Public License for more details.
15 * You should have received a copy of the GNU General Public License
16 * along with this program. If not, see <http://www.gnu.org/licenses/>.
19 #include <QString>
20 #include <QProcess>
21 #include <QMessageBox>
22 #include <QFile>
23 #include <QTranslator>
24 #include <QDir>
25 #include <QDebug>
27 #include "util.h"
29 static QString
30 check_path(const QStringList& paths, const QString& exec) {
31 QList<QString>::const_iterator iter;
32 QString path;
34 for (iter=paths.constBegin();
35 iter!=paths.constEnd();
36 ++iter)
38 QString tmp =
39 QString( "%1/%2" )
40 .arg(QDir::fromNativeSeparators(*iter))
41 .arg(exec);
43 tmp = QDir::toNativeSeparators(tmp);
45 if (QFile::exists(tmp)) {
46 path = tmp;
47 break;
50 return path;
53 static void
54 verify_version_output(
55 const QString& path,
56 QString& ccliveVersion,
57 QString& curlVersion,
58 QString& curlMod,
59 bool *isCcliveFlag)
62 ccliveVersion.clear();
63 curlVersion.clear();
65 QProcess proc;
66 proc.setEnvironment(QStringList() << "CCLIVE_NO_CONFIG=1");
67 proc.setProcessChannelMode(QProcess::MergedChannels);
68 proc.start(path, QStringList() << "--version");
70 if (isCcliveFlag)
71 *isCcliveFlag = false;
73 if (!proc.waitForFinished()) {
74 throw NoCcliveException(path,
75 proc.exitCode(), proc.errorString());
77 else {
78 const QString output =
79 QString::fromLocal8Bit( proc.readAll() );
81 const int exitCode =
82 proc.exitCode();
84 if (exitCode == 0) {
85 const QString versionOutput = output;
86 // qDebug() << versionOutput;
88 const QStringList tmp =
89 versionOutput.split("\n", QString::SkipEmptyParts);
91 bool enoughOutputFlag = false;
93 if (tmp.size() >= 1) {
95 const QStringList lst =
96 tmp[0].split(" ", QString::SkipEmptyParts);
98 if (lst.size() >= 6) {
99 if (isCcliveFlag)
100 *isCcliveFlag = (lst[0] == "cclive");
101 ccliveVersion = lst[2];
102 curlMod = lst[4];
103 curlVersion = lst[6];
105 enoughOutputFlag = true;
109 if (!enoughOutputFlag) {
110 throw NoCcliveException(path,
111 QObject::
112 tr("Not c/clive or it is an unsupported "
113 "version of it"));
116 else
117 throw NoCcliveException(path, exitCode, output);
121 void
122 Util::detectCclive(
123 QString& path,
124 QString& ccliveVersion,
125 QString& curlVersion,
126 QString& curlMod,
127 bool *isCcliveFlag)
130 const QStringList env =
131 QProcess::systemEnvironment();
133 QRegExp re("^PATH=(.*)", Qt::CaseInsensitive);
134 env.indexOf(re);
136 const QString capt = re.capturedTexts()[1].simplified();
137 QStringList paths = capt.split(":");
139 if (paths.size() < 2) // w32
140 paths = capt.split(";");
142 if (paths.size() < 2)
143 return;
145 path = check_path(paths, "cclive");
146 if (path.isEmpty())
147 path = check_path(paths, "clive");
149 if (path.isEmpty()) {
150 // Detection from $PATH failed. Prompt user
151 // to specify the path in preferences manually.
152 throw NoCcliveException(
153 QObject::tr(
154 "Neither cclive or clive not was found in the path.\n"
155 "Please specify the path to either command in the abby\n"
156 "preferences."
160 else {
161 // Check --version output.
162 verify_version_output(
163 path,
164 ccliveVersion,
165 curlVersion,
166 curlMod,
167 isCcliveFlag
172 void
173 Util::verifyCclivePath(
174 const QString& path,
175 QString& ccliveVersion,
176 QString& curlVersion,
177 QString& curlMod,
178 bool *isCcliveFlag/*=NULL*/)
180 verify_version_output(
181 path,
182 ccliveVersion,
183 curlVersion,
184 curlMod,
185 isCcliveFlag
189 NoCcliveException::NoCcliveException(const QString& errmsg)
190 : errmsg(errmsg)
194 static const QString defmsg =
195 QObject::tr("Undefined path to c/clive command");
197 NoCcliveException::NoCcliveException(
198 const QString& path,
199 const QString& errmsg)
200 : errmsg(defmsg)
202 if (!path.isEmpty()) {
203 this->errmsg =
204 QString("error: %1:\n%2").arg(path).arg(errmsg);
208 NoCcliveException::NoCcliveException(
209 const QString& path,
210 const int& exitCode,
211 const QString& output)
212 : errmsg(defmsg)
214 if (!path.isEmpty()) {
215 this->errmsg = QString(
216 QObject::
217 tr("%1 exited with %2:\n%3")
218 .arg(path)
219 .arg(exitCode)
220 .arg(output)
225 const QString&
226 NoCcliveException::what() const {
227 return errmsg;