kdeprint Library API Documentation

lprngtoolhandler.cpp

00001 /* 00002 * This file is part of the KDE libraries 00003 * Copyright (c) 2001 Michael Goffioul <kdeprint@swing.be> 00004 * 00005 * This library is free software; you can redistribute it and/or 00006 * modify it under the terms of the GNU Library General Public 00007 * License version 2 as published by the Free Software Foundation. 00008 * 00009 * This library is distributed in the hope that it will be useful, 00010 * but WITHOUT ANY WARRANTY; without even the implied warranty of 00011 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU 00012 * Library General Public License for more details. 00013 * 00014 * You should have received a copy of the GNU Library General Public License 00015 * along with this library; see the file COPYING.LIB. If not, write to 00016 * the Free Software Foundation, Inc., 59 Temple Place - Suite 330, 00017 * Boston, MA 02111-1307, USA. 00018 **/ 00019 00020 #include "lprngtoolhandler.h" 00021 #include "printcapentry.h" 00022 #include "kmprinter.h" 00023 #include "util.h" 00024 #include "lprsettings.h" 00025 #include "driver.h" 00026 #include "kmmanager.h" 00027 #include "kprinter.h" 00028 00029 #include <qfile.h> 00030 #include <qtextstream.h> 00031 #include <klocale.h> 00032 #include <kdebug.h> 00033 #include <kstandarddirs.h> 00034 00035 LPRngToolHandler::LPRngToolHandler(KMManager *mgr) 00036 : LprHandler("lprngtool", mgr) 00037 { 00038 } 00039 00040 bool LPRngToolHandler::validate(PrintcapEntry *entry) 00041 { 00042 if (entry->comment.startsWith("##LPRNGTOOL##") && 00043 entry->comment.find("UNKNOWN") == -1) 00044 return true; 00045 return false; 00046 } 00047 00048 bool LPRngToolHandler::completePrinter(KMPrinter *prt, PrintcapEntry *entry, bool shortmode) 00049 { 00050 QString str, lp; 00051 00052 // look for type in comment 00053 QStringList l = QStringList::split(' ', entry->comment, false); 00054 lp = entry->field("lp"); 00055 if (l.count() < 1) 00056 return false; 00057 00058 if (l[1] == "DEVICE" || l[1] == "SOCKET" || l[1] == "QUEUE") 00059 LprHandler::completePrinter(prt, entry, shortmode); 00060 else if (l[1] == "SMB") 00061 { 00062 QMap<QString,QString> opts = parseXferOptions(entry->field("xfer_options")); 00063 QString user, pass; 00064 loadAuthFile(LprSettings::self()->baseSpoolDir() + "/" + entry->name + "/" + opts["authfile"], user, pass); 00065 QString uri = buildSmbURI( 00066 opts[ "workgroup" ], 00067 opts[ "host" ], 00068 opts[ "printer" ], 00069 user, 00070 pass ); 00071 prt->setDevice( uri ); 00072 prt->setLocation(i18n("Network printer (%1)").arg("smb")); 00073 } 00074 00075 // look for comment 00076 if (!(str=entry->field("cm")).isEmpty()) 00077 prt->setDescription(str); 00078 00079 // driver 00080 //if (!shortmode) 00081 //{ 00082 if (!(str=entry->field("ifhp")).isEmpty()) 00083 { 00084 QString model; 00085 int p = str.find("model"); 00086 if (p != -1) 00087 { 00088 p = str.find('=', p); 00089 if (p != -1) 00090 { 00091 p++; 00092 int q = str.find(',', p); 00093 if (q == -1) 00094 model = str.mid(p); 00095 else 00096 model = str.mid(p, q-p); 00097 } 00098 } 00099 prt->setDriverInfo(i18n("IFHP Driver (%1)").arg((model.isEmpty() ? i18n("unknown") : model))); 00100 prt->setOption("driverID", model); 00101 } 00102 //} 00103 return true; 00104 } 00105 00106 QMap<QString,QString> LPRngToolHandler::parseXferOptions(const QString& str) 00107 { 00108 uint p(0), q; 00109 QMap<QString,QString> opts; 00110 QString key, val; 00111 00112 while (p < str.length()) 00113 { 00114 key = val = QString::null; 00115 // skip spaces 00116 while (p < str.length() && str[p].isSpace()) 00117 p++; 00118 q = p; 00119 while (q < str.length() && str[q] != '=') 00120 q++; 00121 key = str.mid(p, q-p); 00122 p = q+2; 00123 while (p < str.length() && str[p] != '"') 00124 p++; 00125 val = str.mid(q+2, p-q-2); 00126 if (!key.isEmpty()) 00127 opts[key] = val; 00128 p++; 00129 } 00130 return opts; 00131 } 00132 00133 void LPRngToolHandler::loadAuthFile(const QString& filename, QString& user, QString& pass) 00134 { 00135 QFile f(filename); 00136 if (f.open(IO_ReadOnly)) 00137 { 00138 QTextStream t(&f); 00139 QString line; 00140 while (!t.atEnd()) 00141 { 00142 line = t.readLine().stripWhiteSpace(); 00143 if (line.isEmpty()) 00144 continue; 00145 int p = line.find('='); 00146 if (p != -1) 00147 { 00148 QString key = line.left(p); 00149 if (key == "username") 00150 user = line.mid(p+1); 00151 else if (key == "password") 00152 pass = line.mid(p+1); 00153 } 00154 } 00155 } 00156 } 00157 00158 DrMain* LPRngToolHandler::loadDriver(KMPrinter *prt, PrintcapEntry *entry, bool config) 00159 { 00160 if (entry->field("lprngtooloptions").isEmpty()) 00161 { 00162 manager()->setErrorMsg(i18n("No driver defined for that printer. It might be a raw printer.")); 00163 return NULL; 00164 } 00165 00166 DrMain* driver = loadToolDriver(locate("data", "kdeprint/lprngtooldriver1")); 00167 if (driver) 00168 { 00169 QString model = prt->option("driverID"); 00170 driver->set("text", i18n("LPRngTool Common Driver (%1)").arg((model.isEmpty() ? i18n("unknown") : model))); 00171 if (!model.isEmpty()) 00172 driver->set("driverID", model); 00173 QMap<QString,QString> opts = parseZOptions(entry->field("prefix_z")); 00174 opts["lpr"] = entry->field("lpr"); 00175 driver->setOptions(opts); 00176 // if not configuring, don't show the "lpr" options 00177 if (!config) 00178 driver->removeOptionGlobally("lpr"); 00179 } 00180 return driver; 00181 } 00182 00183 DrMain* LPRngToolHandler::loadDbDriver(const QString& s) 00184 { 00185 int p = s.find('/'); 00186 DrMain* driver = loadToolDriver(locate("data", "kdeprint/lprngtooldriver1")); 00187 if (driver) 00188 driver->set("driverID", s.mid(p+1)); 00189 return driver; 00190 } 00191 00192 QValueList< QPair<QString,QStringList> > LPRngToolHandler::loadChoiceDict(const QString& filename) 00193 { 00194 QFile f(filename); 00195 QValueList< QPair<QString,QStringList> > dict; 00196 if (f.open(IO_ReadOnly)) 00197 { 00198 QTextStream t(&f); 00199 QString line, key; 00200 QStringList l; 00201 while (!t.atEnd()) 00202 { 00203 line = t.readLine().stripWhiteSpace(); 00204 if (line.startsWith("OPTION")) 00205 { 00206 if (l.count() > 0 && !key.isEmpty()) 00207 dict << QPair<QString,QStringList>(key, l); 00208 l.clear(); 00209 key = QString::null; 00210 if (line.contains('|') == 2 || line.right(7) == "BOOLEAN") 00211 { 00212 int p = line.find('|', 7); 00213 key = line.mid(7, p-7); 00214 } 00215 } 00216 else if (line.startsWith("CHOICE")) 00217 { 00218 int p = line.find('|', 7); 00219 l << line.mid(7, p-7); 00220 } 00221 } 00222 } 00223 return dict; 00224 } 00225 00226 QMap<QString,QString> LPRngToolHandler::parseZOptions(const QString& optstr) 00227 { 00228 QMap<QString,QString> opts; 00229 QStringList l = QStringList::split(',', optstr, false); 00230 if (l.count() == 0) 00231 return opts; 00232 00233 if (m_dict.count() == 0) 00234 m_dict = loadChoiceDict(locate("data", "kdeprint/lprngtooldriver1")); 00235 00236 QString unknown; 00237 for (QStringList::ConstIterator it=l.begin(); it!=l.end(); ++it) 00238 { 00239 bool found(false); 00240 for (QValueList< QPair<QString,QStringList> >::ConstIterator p=m_dict.begin(); p!=m_dict.end() && !found; ++p) 00241 { 00242 if ((*p).second.find(*it) != (*p).second.end()) 00243 { 00244 opts[(*p).first] = (*it); 00245 found = true; 00246 } 00247 } 00248 if (!found) 00249 { 00250 unknown.append(*it).append(','); 00251 } 00252 } 00253 if (!unknown.isEmpty()) 00254 { 00255 unknown.truncate(unknown.length()-1); 00256 opts["filter"] = unknown; 00257 } 00258 return opts; 00259 } 00260 00261 QString LPRngToolHandler::filterDir() 00262 { 00263 return driverDirectory(); 00264 } 00265 00266 QString LPRngToolHandler::driverDirInternal() 00267 { 00268 return locateDir("filters", "/usr/lib:/usr/local/lib:/opt/lib:/usr/libexec:/usr/local/libexec:/opt/libexec"); 00269 } 00270 00271 PrintcapEntry* LPRngToolHandler::createEntry(KMPrinter *prt) 00272 { 00273 QString prot = prt->deviceProtocol(); 00274 if (prot != "parallel" && prot != "lpd" && prot != "smb" && prot != "socket") 00275 { 00276 manager()->setErrorMsg(i18n("Unsupported backend: %1.").arg(prot)); 00277 return NULL; 00278 } 00279 PrintcapEntry *entry = new PrintcapEntry; 00280 entry->addField("cm", Field::String, prt->description()); 00281 QString lp, comment("##LPRNGTOOL## "); 00282 if (prot == "parallel") 00283 { 00284 comment.append("DEVICE "); 00285 lp = prt->device().mid( 9 ); 00286 entry->addField("rw@", Field::Boolean); 00287 } 00288 else if (prot == "socket") 00289 { 00290 comment.append("SOCKET "); 00291 KURL url( prt->device() ); 00292 lp = url.host(); 00293 if (url.port() == 0) 00294 lp.append("%9100"); 00295 else 00296 lp.append("%").append(QString::number(url.port())); 00297 } 00298 else if (prot == "lpd") 00299 { 00300 comment.append("QUEUE "); 00301 KURL url( prt->device() ); 00302 lp = url.path().mid(1) + "@" + url.host(); 00303 } 00304 else if (prot == "smb") 00305 { 00306 comment.append("SMB "); 00307 lp = "| " + filterDir() + "/smbprint"; 00308 QString work, server, printer, user, passwd; 00309 if ( splitSmbURI( prt->device(), work, server, printer, user, passwd ) ) 00310 { 00311 entry->addField("xfer_options", Field::String, QString::fromLatin1("authfile=\"auth\" crlf=\"0\" hostip=\"\" host=\"%1\" printer=\"%2\" remote_mode=\"SMB\" share=\"//%3/%4\" workgroup=\"%5\"").arg(server).arg(printer).arg(server).arg(printer).arg(work)); 00312 QFile authfile(LprSettings::self()->baseSpoolDir() + "/" + prt->printerName() + "/auth"); 00313 if (authfile.open(IO_WriteOnly)) 00314 { 00315 QTextStream t(&authfile); 00316 t << "username=" << user << endl; 00317 t << "password=" << passwd << endl; 00318 authfile.close(); 00319 } 00320 } 00321 else 00322 { 00323 manager()->setErrorMsg( i18n( "Invalid printer backend specification: %1" ).arg( prt->device() ) ); 00324 delete entry; 00325 return NULL; 00326 } 00327 } 00328 00329 if (prt->driver()) 00330 { 00331 DrMain *driver = prt->driver(); 00332 comment.append("filtertype=IFHP ifhp_options=status@,sync@,pagecount@,waitend@ printerdb_entry="); 00333 comment.append(driver->get("driverID")); 00334 entry->addField("ifhp", Field::String, QString::fromLatin1("model=%1,status@,sync@,pagecount@,waitend@").arg(driver->get("driverID"))); 00335 entry->addField("lprngtooloptions", Field::String, QString::fromLatin1("FILTERTYPE=\"IFHP\" IFHP_OPTIONS=\"status@,sync@,pagecount@,waitend@\" PRINTERDB_ENTRY=\"%1\"").arg(driver->get("driverID"))); 00336 QMap<QString,QString> opts; 00337 QString optstr; 00338 driver->getOptions(opts, false); 00339 for (QMap<QString,QString>::ConstIterator it=opts.begin(); it!=opts.end(); ++it) 00340 if (it.key() != "lpr") 00341 optstr.append(*it).append(","); 00342 if (!optstr.isEmpty()) 00343 { 00344 optstr.truncate(optstr.length()-1); 00345 entry->addField("prefix_z", Field::String, optstr); 00346 } 00347 if (!opts["lpr"].isEmpty()) 00348 entry->addField("lpr", Field::String, opts["lpr"]); 00349 } 00350 00351 entry->addField("lp", Field::String, lp); 00352 entry->comment = comment; 00353 00354 return entry; 00355 } 00356 00357 bool LPRngToolHandler::savePrinterDriver(KMPrinter*, PrintcapEntry *entry, DrMain *driver, bool *mustSave) 00358 { 00359 // save options in the "prefix_z" field and tell the manager to save the printcap file 00360 QMap<QString,QString> opts; 00361 QString optstr; 00362 driver->getOptions(opts, false); 00363 for (QMap<QString,QString>::ConstIterator it=opts.begin(); it!=opts.end(); ++it) 00364 if (it.key() != "lpr") 00365 optstr.append(*it).append(","); 00366 if (!optstr.isEmpty()) 00367 optstr.truncate(optstr.length()-1); 00368 // save options in any case, otherwise nothing will happen whn 00369 // options are reset to their default value 00370 entry->addField("prefix_z", Field::String, optstr); 00371 entry->addField("lpr", Field::String, opts["lpr"]); 00372 if (mustSave) 00373 *mustSave = true; 00374 return true; 00375 } 00376 00377 QString LPRngToolHandler::printOptions(KPrinter *printer) 00378 { 00379 QString optstr; 00380 QMap<QString,QString> opts = printer->options(); 00381 for (QMap<QString,QString>::ConstIterator it=opts.begin(); it!=opts.end(); ++it) 00382 { 00383 if (it.key().startsWith("kde-") || it.key().startsWith("_kde-") || it.key() == "lpr" || it.key().startsWith( "app-" )) 00384 continue; 00385 optstr.append(*it).append(","); 00386 } 00387 if (!optstr.isEmpty()) 00388 { 00389 optstr.truncate(optstr.length()-1); 00390 optstr.prepend("-Z '").append("'"); 00391 } 00392 return optstr; 00393 }
KDE Logo
This file is part of the documentation for kdeprint Library Version 3.2.3.
Documentation copyright © 1996-2004 the KDE developers.
Generated on Fri Oct 8 11:15:40 2004 by doxygen 1.3.7 written by Dimitri van Heesch, © 1997-2003