kmtransport.cpp
00001 00020 #include <config.h> 00021 #include <assert.h> 00022 00023 #include "kmtransport.h" 00024 00025 #include <tqbuttongroup.h> 00026 #include <tqcheckbox.h> 00027 #include <tqlayout.h> 00028 #include <klineedit.h> 00029 #include <tqradiobutton.h> 00030 #include <tqtabwidget.h> 00031 #include <tqvalidator.h> 00032 #include <tqlabel.h> 00033 #include <tqpushbutton.h> 00034 #include <tqwhatsthis.h> 00035 00036 #include <tdefiledialog.h> 00037 #include <tdelocale.h> 00038 #include <tdemessagebox.h> 00039 #include <kseparator.h> 00040 #include <kdebug.h> 00041 #include <tdewallet.h> 00042 using TDEWallet::Wallet; 00043 #include <kprotocolinfo.h> 00044 00045 #include "kmkernel.h" 00046 #include "kmservertest.h" 00047 #include "kmaccount.h" 00048 #include "protocols.h" 00049 #include "transportmanager.h" 00050 using namespace KMail; 00051 00052 KMTransportInfo::KMTransportInfo() : mPasswdDirty( false ), 00053 mStorePasswd( false ), mStorePasswdInConfig( false ), mId( 0 ) 00054 { 00055 name = i18n("Unnamed"); 00056 port = "25"; 00057 auth = false; 00058 specifyHostname = false; 00059 } 00060 00061 00062 KMTransportInfo::~KMTransportInfo() 00063 { 00064 } 00065 00066 00067 void KMTransportInfo::readConfig(int id) 00068 { 00069 TDEConfig *config = KMKernel::config(); 00070 TDEConfigGroupSaver saver(config, "Transport " + TQString::number(id)); 00071 mId = config->readUnsignedNumEntry( "id", 0 ); 00072 type = config->readEntry("type", "smtp"); 00073 name = config->readEntry("name", i18n("Unnamed")); 00074 host = config->readEntry("host", "localhost"); 00075 port = config->readEntry("port", "25"); 00076 user = config->readEntry("user"); 00077 mPasswd = KMAccount::decryptStr(config->readEntry("pass")); 00078 precommand = config->readPathEntry("precommand"); 00079 encryption = config->readEntry("encryption"); 00080 authType = config->readEntry("authtype"); 00081 auth = config->readBoolEntry("auth"); 00082 mStorePasswd = config->readBoolEntry("storepass"); 00083 specifyHostname = config->readBoolEntry("specifyHostname", false); 00084 localHostname = config->readEntry("localHostname"); 00085 00086 if ( !storePasswd() ) 00087 return; 00088 00089 if ( !mPasswd.isEmpty() ) { 00090 // migration to tdewallet if available 00091 if ( Wallet::isEnabled() ) { 00092 config->deleteEntry( "pass" ); 00093 mPasswdDirty = true; 00094 mStorePasswdInConfig = false; 00095 writeConfig( id ); 00096 } else 00097 mStorePasswdInConfig = true; 00098 } else { 00099 // read password if wallet is open, defer otherwise 00100 if ( Wallet::isOpen( Wallet::NetworkWallet() ) ) 00101 readPassword(); 00102 } 00103 } 00104 00105 00106 void KMTransportInfo::writeConfig(int id) 00107 { 00108 TDEConfig *config = KMKernel::config(); 00109 TDEConfigGroupSaver saver(config, "Transport " + TQString::number(id)); 00110 if (!mId) 00111 mId = TransportManager::createId(); 00112 config->writeEntry("id", mId); 00113 config->writeEntry("type", type); 00114 config->writeEntry("name", name); 00115 config->writeEntry("host", host); 00116 config->writeEntry("port", port); 00117 config->writeEntry("user", user); 00118 config->writePathEntry("precommand", precommand); 00119 config->writeEntry("encryption", encryption); 00120 config->writeEntry("authtype", authType); 00121 config->writeEntry("auth", auth); 00122 config->writeEntry("storepass", storePasswd()); 00123 config->writeEntry("specifyHostname", specifyHostname); 00124 config->writeEntry("localHostname", localHostname); 00125 00126 if ( storePasswd() ) { 00127 // write password into the wallet if possible and necessary 00128 bool passwdStored = false; 00129 Wallet *wallet = kmkernel->wallet(); 00130 if ( mPasswdDirty ) { 00131 if ( wallet && wallet->writePassword( "transport-" + TQString::number(mId), passwd() ) == 0 ) { 00132 passwdStored = true; 00133 mPasswdDirty = false; 00134 mStorePasswdInConfig = false; 00135 } 00136 } else { 00137 passwdStored = wallet ? !mStorePasswdInConfig /*already in the wallet*/ : config->hasKey("pass"); 00138 } 00139 // wallet not available, ask the user if we should use the config file instead 00140 if ( !passwdStored && ( mStorePasswdInConfig || KMessageBox::warningYesNo( 0, 00141 i18n("TDEWallet is not available. It is strongly recommended to use " 00142 "TDEWallet for managing your passwords.\n" 00143 "However, KMail can store the password in its configuration " 00144 "file instead. The password is stored in an obfuscated format, " 00145 "but should not be considered secure from decryption efforts " 00146 "if access to the configuration file is obtained.\n" 00147 "Do you want to store the password for account '%1' in the " 00148 "configuration file?").arg( name ), 00149 i18n("TDEWallet Not Available"), 00150 KGuiItem( i18n("Store Password") ), 00151 KGuiItem( i18n("Do Not Store Password") ) ) 00152 == KMessageBox::Yes ) ) { 00153 config->writeEntry( "pass", KMAccount::encryptStr( passwd() ) ); 00154 mStorePasswdInConfig = true; 00155 } 00156 } 00157 00158 // delete already stored password if password storage is disabled 00159 if ( !storePasswd() ) { 00160 if ( !Wallet::keyDoesNotExist( 00161 Wallet::NetworkWallet(), "kmail", "transport-" + TQString::number(mId) ) ) { 00162 Wallet *wallet = kmkernel->wallet(); 00163 if ( wallet ) 00164 wallet->removeEntry( "transport-" + TQString::number(mId) ); 00165 } 00166 config->deleteEntry( "pass" ); 00167 } 00168 } 00169 00170 00171 int KMTransportInfo::findTransport(const TQString &name) 00172 { 00173 TDEConfig *config = KMKernel::config(); 00174 TDEConfigGroupSaver saver(config, "General"); 00175 int numTransports = config->readNumEntry("transports", 0); 00176 for (int i = 1; i <= numTransports; i++) 00177 { 00178 TDEConfigGroupSaver saver(config, "Transport " + TQString::number(i)); 00179 if (config->readEntry("name") == name) return i; 00180 } 00181 return 0; 00182 } 00183 00184 00185 TQStringList KMTransportInfo::availableTransports() 00186 { 00187 TQStringList result; 00188 TDEConfig *config = KMKernel::config(); 00189 TDEConfigGroupSaver saver(config, "General"); 00190 int numTransports = config->readNumEntry("transports", 0); 00191 for (int i = 1; i <= numTransports; i++) 00192 { 00193 TDEConfigGroupSaver saver(config, "Transport " + TQString::number(i)); 00194 result.append(config->readEntry("name")); 00195 } 00196 return result; 00197 } 00198 00199 00200 TQString KMTransportInfo::passwd() const 00201 { 00202 if ( auth && storePasswd() && mPasswd.isEmpty() ) 00203 readPassword(); 00204 return mPasswd; 00205 } 00206 00207 00208 void KMTransportInfo::setPasswd( const TQString &passwd ) 00209 { 00210 if ( passwd != mPasswd ) { 00211 mPasswd = passwd; 00212 mPasswdDirty = true; 00213 } 00214 } 00215 00216 00217 void KMTransportInfo::setStorePasswd( bool store ) 00218 { 00219 if ( mStorePasswd != store && store ) 00220 mPasswdDirty = true; 00221 mStorePasswd = store; 00222 } 00223 00224 00225 void KMTransportInfo::readPassword() const 00226 { 00227 if ( !storePasswd() || !auth ) 00228 return; 00229 00230 // ### workaround for broken Wallet::keyDoesNotExist() which returns wrong 00231 // results for new entries without closing and reopening the wallet 00232 if ( Wallet::isOpen( Wallet::NetworkWallet() ) ) { 00233 Wallet* wallet = kmkernel->wallet(); 00234 if ( !wallet || !wallet->hasEntry( "transport-" + TQString::number(mId) ) ) 00235 return; 00236 } else { 00237 if ( Wallet::keyDoesNotExist( Wallet::NetworkWallet(), "kmail", "transport-" + TQString::number(mId) ) ) 00238 return; 00239 } 00240 00241 if ( kmkernel->wallet() ) 00242 kmkernel->wallet()->readPassword( "transport-" + TQString::number(mId), mPasswd ); 00243 } 00244 00245 00246 KMTransportSelDlg::KMTransportSelDlg( TQWidget *parent, const char *name, 00247 bool modal ) 00248 : KDialogBase( parent, name, modal, i18n("Add Transport"), Ok|Cancel, Ok ) 00249 { 00250 TQFrame *page = makeMainWidget(); 00251 TQVBoxLayout *topLayout = new TQVBoxLayout( page, 0, spacingHint() ); 00252 00253 TQButtonGroup *group = new TQButtonGroup( i18n("Transport"), page ); 00254 connect(group, TQT_SIGNAL(clicked(int)), TQT_SLOT(buttonClicked(int)) ); 00255 00256 topLayout->addWidget( group, 10 ); 00257 TQVBoxLayout *vlay = new TQVBoxLayout( group, spacingHint()*2, spacingHint() ); 00258 vlay->addSpacing( fontMetrics().lineSpacing() ); 00259 00260 TQRadioButton *radioButton1 = new TQRadioButton( i18n("SM&TP"), group ); 00261 vlay->addWidget( radioButton1 ); 00262 TQRadioButton *radioButton2 = new TQRadioButton( i18n("&Sendmail"), group ); 00263 vlay->addWidget( radioButton2 ); 00264 00265 vlay->addStretch( 10 ); 00266 00267 radioButton1->setChecked(true); // Pop is most common ? 00268 buttonClicked(0); 00269 } 00270 00271 void KMTransportSelDlg::buttonClicked( int id ) 00272 { 00273 mSelectedButton = id; 00274 } 00275 00276 00277 int KMTransportSelDlg::selected( void ) const 00278 { 00279 return mSelectedButton; 00280 } 00281 00282 00283 KMTransportDialog::KMTransportDialog( const TQString & caption, 00284 KMTransportInfo *transportInfo, 00285 TQWidget *parent, const char *name, 00286 bool modal ) 00287 : KDialogBase( parent, name, modal, caption, Ok|Cancel, Ok, true ), 00288 mServerTest( 0 ), 00289 mTransportInfo( transportInfo ), 00290 mAuthNone( AllAuth ), mAuthSSL( AllAuth ), mAuthTLS( AllAuth ) 00291 { 00292 assert(transportInfo != 0); 00293 00294 if( transportInfo->type == TQString::fromLatin1("sendmail") ) 00295 { 00296 makeSendmailPage(); 00297 } else { 00298 makeSmtpPage(); 00299 } 00300 00301 setupSettings(); 00302 } 00303 00304 00305 KMTransportDialog::~KMTransportDialog() 00306 { 00307 } 00308 00309 00310 void KMTransportDialog::makeSendmailPage() 00311 { 00312 TQFrame *page = makeMainWidget(); 00313 TQVBoxLayout *topLayout = new TQVBoxLayout( page, 0, spacingHint() ); 00314 00315 mSendmail.titleLabel = new TQLabel( page ); 00316 mSendmail.titleLabel->setText( i18n("Transport: Sendmail") ); 00317 TQFont titleFont( mSendmail.titleLabel->font() ); 00318 titleFont.setBold( true ); 00319 mSendmail.titleLabel->setFont( titleFont ); 00320 topLayout->addWidget( mSendmail.titleLabel ); 00321 KSeparator *hline = new KSeparator( KSeparator::HLine, page); 00322 topLayout->addWidget( hline ); 00323 00324 TQGridLayout *grid = new TQGridLayout( topLayout, 3, 3, spacingHint() ); 00325 grid->addColSpacing( 1, fontMetrics().maxWidth()*15 ); 00326 grid->setRowStretch( 2, 10 ); 00327 grid->setColStretch( 1, 10 ); 00328 00329 TQLabel *label = new TQLabel( i18n("&Name:"), page ); 00330 grid->addWidget( label, 0, 0 ); 00331 mSendmail.nameEdit = new KLineEdit( page ); 00332 label->setBuddy( mSendmail.nameEdit ); 00333 grid->addWidget( mSendmail.nameEdit, 0, 1 ); 00334 00335 label = new TQLabel( i18n("&Location:"), page ); 00336 grid->addWidget( label, 1, 0 ); 00337 mSendmail.locationEdit = new KLineEdit( page ); 00338 label->setBuddy(mSendmail.locationEdit); 00339 grid->addWidget( mSendmail.locationEdit, 1, 1 ); 00340 mSendmail.chooseButton = 00341 new TQPushButton( i18n("Choos&e..."), page ); 00342 connect( mSendmail.chooseButton, TQT_SIGNAL(clicked()), 00343 this, TQT_SLOT(slotSendmailChooser()) ); 00344 00345 connect( mSendmail.locationEdit, TQT_SIGNAL(textChanged ( const TQString & )), 00346 this, TQT_SLOT(slotSendmailEditPath(const TQString &)) ); 00347 00348 mSendmail.chooseButton->setAutoDefault( false ); 00349 grid->addWidget( mSendmail.chooseButton, 1, 2 ); 00350 slotSendmailEditPath(mSendmail.locationEdit->text()); 00351 } 00352 00353 void KMTransportDialog::slotSendmailEditPath(const TQString & _text) 00354 { 00355 enableButtonOK( !_text.isEmpty() ); 00356 } 00357 00358 void KMTransportDialog::makeSmtpPage() 00359 { 00360 TQFrame *page = makeMainWidget(); 00361 TQVBoxLayout *topLayout = new TQVBoxLayout( page, 0, spacingHint() ); 00362 00363 mSmtp.titleLabel = new TQLabel( page ); 00364 mSmtp.titleLabel->setText( i18n("Transport: SMTP") ); 00365 TQFont titleFont( mSmtp.titleLabel->font() ); 00366 titleFont.setBold( true ); 00367 mSmtp.titleLabel->setFont( titleFont ); 00368 topLayout->addWidget( mSmtp.titleLabel ); 00369 KSeparator *hline = new KSeparator( KSeparator::HLine, page); 00370 topLayout->addWidget( hline ); 00371 00372 TQTabWidget *tabWidget = new TQTabWidget(page); 00373 topLayout->addWidget( tabWidget ); 00374 00375 TQWidget *page1 = new TQWidget( tabWidget ); 00376 tabWidget->addTab( page1, i18n("&General") ); 00377 00378 TQGridLayout *grid = new TQGridLayout( page1, 14, 2, spacingHint() ); 00379 grid->addColSpacing( 1, fontMetrics().maxWidth()*15 ); 00380 grid->setRowStretch( 13, 10 ); 00381 grid->setColStretch( 1, 10 ); 00382 00383 TQLabel *label = new TQLabel( i18n("&Name:"), page1 ); 00384 grid->addWidget( label, 0, 0 ); 00385 mSmtp.nameEdit = new KLineEdit( page1 ); 00386 TQWhatsThis::add(mSmtp.nameEdit, 00387 i18n("The name that KMail will use when " 00388 "referring to this server.")); 00389 label->setBuddy( mSmtp.nameEdit ); 00390 grid->addWidget( mSmtp.nameEdit, 0, 1 ); 00391 00392 label = new TQLabel( i18n("&Host:"), page1 ); 00393 grid->addWidget( label, 3, 0 ); 00394 mSmtp.hostEdit = new KLineEdit( page1 ); 00395 TQWhatsThis::add(mSmtp.hostEdit, 00396 i18n("The domain name or numerical address " 00397 "of the SMTP server.")); 00398 label->setBuddy( mSmtp.hostEdit ); 00399 grid->addWidget( mSmtp.hostEdit, 3, 1 ); 00400 00401 label = new TQLabel( i18n("&Port:"), page1 ); 00402 grid->addWidget( label, 4, 0 ); 00403 mSmtp.portEdit = new KLineEdit( page1 ); 00404 mSmtp.portEdit->setValidator( new TQIntValidator(TQT_TQOBJECT(this)) ); 00405 TQWhatsThis::add(mSmtp.portEdit, 00406 i18n("The port number that the SMTP server " 00407 "is listening on. The default port is 25.")); 00408 label->setBuddy( mSmtp.portEdit ); 00409 grid->addWidget( mSmtp.portEdit, 4, 1 ); 00410 00411 label = new TQLabel( i18n("Preco&mmand:"), page1 ); 00412 grid->addWidget( label, 5, 0 ); 00413 mSmtp.precommand = new KLineEdit( page1 ); 00414 TQWhatsThis::add(mSmtp.precommand, 00415 i18n("A command to run locally, prior " 00416 "to sending email. This can be used " 00417 "to set up ssh tunnels, for example. " 00418 "Leave it empty if no command should be run.")); 00419 label->setBuddy(mSmtp.precommand); 00420 grid->addWidget( mSmtp.precommand, 5, 1 ); 00421 00422 TQFrame* line = new TQFrame( page1 ); 00423 line->setFrameStyle( TQFrame::HLine | TQFrame::Plain ); 00424 grid->addMultiCellWidget( line, 6, 6, 0, 1 ); 00425 00426 mSmtp.authCheck = 00427 new TQCheckBox( i18n("Server &requires authentication"), page1 ); 00428 TQWhatsThis::add(mSmtp.authCheck, 00429 i18n("Check this option if your SMTP server " 00430 "requires authentication before accepting " 00431 "mail. This is known as " 00432 "'Authenticated SMTP' or simply ASMTP.")); 00433 connect(mSmtp.authCheck, TQT_SIGNAL(clicked()), 00434 TQT_SLOT(slotRequiresAuthClicked())); 00435 grid->addMultiCellWidget( mSmtp.authCheck, 7, 7, 0, 1 ); 00436 00437 mSmtp.loginLabel = new TQLabel( i18n("&Login:"), page1 ); 00438 grid->addWidget( mSmtp.loginLabel, 8, 0 ); 00439 mSmtp.loginEdit = new KLineEdit( page1 ); 00440 mSmtp.loginLabel->setBuddy( mSmtp.loginEdit ); 00441 TQWhatsThis::add(mSmtp.loginEdit, 00442 i18n("The user name to send to the server " 00443 "for authorization")); 00444 grid->addWidget( mSmtp.loginEdit, 8, 1 ); 00445 00446 mSmtp.passwordLabel = new TQLabel( i18n("P&assword:"), page1 ); 00447 grid->addWidget( mSmtp.passwordLabel, 9, 0 ); 00448 mSmtp.passwordEdit = new KLineEdit( page1 ); 00449 mSmtp.passwordEdit->setEchoMode( TQLineEdit::Password ); 00450 mSmtp.passwordLabel->setBuddy( mSmtp.passwordEdit ); 00451 TQWhatsThis::add(mSmtp.passwordEdit, 00452 i18n("The password to send to the server " 00453 "for authorization")); 00454 grid->addWidget( mSmtp.passwordEdit, 9, 1 ); 00455 00456 mSmtp.storePasswordCheck = 00457 new TQCheckBox( i18n("&Store SMTP password"), page1 ); 00458 TQWhatsThis::add(mSmtp.storePasswordCheck, 00459 i18n("Check this option to have KMail store " 00460 "the password.\nIf TDEWallet is available " 00461 "the password will be stored there which is considered " 00462 "safe.\nHowever, if TDEWallet is not available, " 00463 "the password will be stored in KMail's configuration " 00464 "file. The password is stored in an " 00465 "obfuscated format, but should not be " 00466 "considered secure from decryption efforts " 00467 "if access to the configuration file is obtained.")); 00468 grid->addMultiCellWidget( mSmtp.storePasswordCheck, 10, 10, 0, 1 ); 00469 00470 line = new TQFrame( page1 ); 00471 line->setFrameStyle( TQFrame::HLine | TQFrame::Plain ); 00472 grid->addMultiCellWidget( line, 11, 11, 0, 1 ); 00473 00474 mSmtp.specifyHostnameCheck = 00475 new TQCheckBox( i18n("Sen&d custom hostname to server"), page1 ); 00476 grid->addMultiCellWidget( mSmtp.specifyHostnameCheck, 12, 12, 0, 1 ); 00477 TQWhatsThis::add(mSmtp.specifyHostnameCheck, 00478 i18n("Check this option to have KMail use " 00479 "a custom hostname when identifying itself " 00480 "to the mail server." 00481 "<p>This is useful when your system's hostname " 00482 "may not be set correctly or to mask your " 00483 "system's true hostname.")); 00484 00485 mSmtp.localHostnameLabel = new TQLabel( i18n("Hos&tname:"), page1 ); 00486 grid->addWidget( mSmtp.localHostnameLabel, 13, 0); 00487 mSmtp.localHostnameEdit = new KLineEdit( page1 ); 00488 TQWhatsThis::add(mSmtp.localHostnameEdit, 00489 i18n("Enter the hostname KMail should use when " 00490 "identifying itself to the server.")); 00491 mSmtp.localHostnameLabel->setBuddy( mSmtp.localHostnameEdit ); 00492 grid->addWidget( mSmtp.localHostnameEdit, 13, 1 ); 00493 connect( mSmtp.specifyHostnameCheck, TQT_SIGNAL(toggled(bool)), 00494 mSmtp.localHostnameEdit, TQT_SLOT(setEnabled(bool))); 00495 connect( mSmtp.specifyHostnameCheck, TQT_SIGNAL(toggled(bool)), 00496 mSmtp.localHostnameLabel, TQT_SLOT(setEnabled(bool))); 00497 00498 TQWidget *page2 = new TQWidget( tabWidget ); 00499 tabWidget->addTab( page2, i18n("S&ecurity") ); 00500 TQVBoxLayout *vlay = new TQVBoxLayout( page2, spacingHint() ); 00501 mSmtp.encryptionGroup = new TQButtonGroup( 1, Qt::Horizontal, 00502 i18n("Encryption"), page2 ); 00503 mSmtp.encryptionNone = 00504 new TQRadioButton( i18n("&None"), mSmtp.encryptionGroup ); 00505 mSmtp.encryptionSSL = 00506 new TQRadioButton( i18n("&SSL"), mSmtp.encryptionGroup ); 00507 mSmtp.encryptionTLS = 00508 new TQRadioButton( i18n("&TLS"), mSmtp.encryptionGroup ); 00509 connect(mSmtp.encryptionGroup, TQT_SIGNAL(clicked(int)), 00510 TQT_SLOT(slotSmtpEncryptionChanged(int))); 00511 vlay->addWidget( mSmtp.encryptionGroup ); 00512 00513 mSmtp.authGroup = new TQButtonGroup( 1, Qt::Horizontal, 00514 i18n("Authentication Method"), page2 ); 00515 mSmtp.authLogin = new TQRadioButton( i18n("Please translate this " 00516 "authentication method only if you have a good reason", "&LOGIN"), 00517 mSmtp.authGroup ); 00518 mSmtp.authPlain = new TQRadioButton( i18n("Please translate this " 00519 "authentication method only if you have a good reason", "&PLAIN"), 00520 mSmtp.authGroup ); 00521 mSmtp.authCramMd5 = new TQRadioButton( i18n("CRAM-MD&5"), mSmtp.authGroup ); 00522 mSmtp.authDigestMd5 = new TQRadioButton( i18n("&DIGEST-MD5"), mSmtp.authGroup ); 00523 mSmtp.authNTLM = new TQRadioButton( i18n("&NTLM"), mSmtp.authGroup ); 00524 mSmtp.authGSSAPI = new TQRadioButton( i18n("&GSSAPI"), mSmtp.authGroup ); 00525 if ( KProtocolInfo::capabilities("smtp").contains("SASL") == 0 ) { 00526 mSmtp.authNTLM->hide(); 00527 mSmtp.authGSSAPI->hide(); 00528 } 00529 vlay->addWidget( mSmtp.authGroup ); 00530 00531 vlay->addStretch(); 00532 00533 TQHBoxLayout *buttonLay = new TQHBoxLayout( vlay ); 00534 mSmtp.checkCapabilities = 00535 new TQPushButton( i18n("Check &What the Server Supports"), page2 ); 00536 connect(mSmtp.checkCapabilities, TQT_SIGNAL(clicked()), 00537 TQT_SLOT(slotCheckSmtpCapabilities())); 00538 buttonLay->addStretch(); 00539 buttonLay->addWidget( mSmtp.checkCapabilities ); 00540 } 00541 00542 00543 void KMTransportDialog::setupSettings() 00544 { 00545 if (mTransportInfo->type == "sendmail") 00546 { 00547 mSendmail.nameEdit->setText(mTransportInfo->name); 00548 mSendmail.locationEdit->setText(mTransportInfo->host); 00549 } else { 00550 mSmtp.nameEdit->setText(mTransportInfo->name); 00551 mSmtp.hostEdit->setText(mTransportInfo->host); 00552 mSmtp.portEdit->setText(mTransportInfo->port); 00553 mSmtp.authCheck->setChecked(mTransportInfo->auth); 00554 mSmtp.loginEdit->setText(mTransportInfo->user); 00555 mSmtp.passwordEdit->setText(mTransportInfo->passwd()); 00556 mSmtp.storePasswordCheck->setChecked(mTransportInfo->storePasswd()); 00557 mSmtp.precommand->setText(mTransportInfo->precommand); 00558 mSmtp.specifyHostnameCheck->setChecked(mTransportInfo->specifyHostname); 00559 mSmtp.localHostnameEdit->setText(mTransportInfo->localHostname); 00560 00561 if (mTransportInfo->encryption == "TLS") 00562 mSmtp.encryptionTLS->setChecked(true); 00563 else if (mTransportInfo->encryption == "SSL") 00564 mSmtp.encryptionSSL->setChecked(true); 00565 else mSmtp.encryptionNone->setChecked(true); 00566 00567 if (mTransportInfo->authType == "LOGIN") 00568 mSmtp.authLogin->setChecked(true); 00569 else if (mTransportInfo->authType == "CRAM-MD5") 00570 mSmtp.authCramMd5->setChecked(true); 00571 else if (mTransportInfo->authType == "DIGEST-MD5") 00572 mSmtp.authDigestMd5->setChecked(true); 00573 else if (mTransportInfo->authType == "NTLM") 00574 mSmtp.authNTLM->setChecked(true); 00575 else if (mTransportInfo->authType == "GSSAPI") 00576 mSmtp.authGSSAPI->setChecked(true); 00577 else mSmtp.authPlain->setChecked(true); 00578 00579 slotRequiresAuthClicked(); 00580 mSmtp.localHostnameEdit->setEnabled(mTransportInfo->specifyHostname); 00581 mSmtp.localHostnameLabel->setEnabled(mTransportInfo->specifyHostname); 00582 } 00583 } 00584 00585 00586 void KMTransportDialog::saveSettings() 00587 { 00588 if (mTransportInfo->type == "sendmail") 00589 { 00590 mTransportInfo->name = mSendmail.nameEdit->text().stripWhiteSpace(); 00591 mTransportInfo->host = mSendmail.locationEdit->text().stripWhiteSpace(); 00592 } else { 00593 mTransportInfo->name = mSmtp.nameEdit->text(); 00594 mTransportInfo->host = mSmtp.hostEdit->text().stripWhiteSpace(); 00595 mTransportInfo->port = mSmtp.portEdit->text().stripWhiteSpace(); 00596 mTransportInfo->auth = mSmtp.authCheck->isChecked(); 00597 mTransportInfo->user = mSmtp.loginEdit->text().stripWhiteSpace(); 00598 mTransportInfo->setPasswd( mSmtp.passwordEdit->text() ); 00599 mTransportInfo->setStorePasswd( mSmtp.storePasswordCheck->isChecked() ); 00600 mTransportInfo->precommand = mSmtp.precommand->text().stripWhiteSpace(); 00601 mTransportInfo->specifyHostname = mSmtp.specifyHostnameCheck->isChecked(); 00602 mTransportInfo->localHostname = mSmtp.localHostnameEdit->text().stripWhiteSpace(); 00603 00604 mTransportInfo->encryption = (mSmtp.encryptionTLS->isChecked()) ? "TLS" : 00605 (mSmtp.encryptionSSL->isChecked()) ? "SSL" : "NONE"; 00606 00607 mTransportInfo->authType = (mSmtp.authLogin->isChecked()) ? "LOGIN" : 00608 (mSmtp.authCramMd5->isChecked()) ? "CRAM-MD5" : 00609 (mSmtp.authDigestMd5->isChecked()) ? "DIGEST-MD5" : 00610 (mSmtp.authNTLM->isChecked()) ? "NTLM" : 00611 (mSmtp.authGSSAPI->isChecked()) ? "GSSAPI" : "PLAIN"; 00612 } 00613 } 00614 00615 00616 void KMTransportDialog::slotSendmailChooser() 00617 { 00618 KFileDialog dialog("/", TQString(), this, 0, true ); 00619 dialog.setCaption(i18n("Choose sendmail Location") ); 00620 00621 if( dialog.exec() == TQDialog::Accepted ) 00622 { 00623 KURL url = dialog.selectedURL(); 00624 if( url.isEmpty() == true ) 00625 { 00626 return; 00627 } 00628 00629 if( url.isLocalFile() == false ) 00630 { 00631 KMessageBox::sorry( 0, i18n( "Only local files allowed." ) ); 00632 return; 00633 } 00634 00635 mSendmail.locationEdit->setText( url.path() ); 00636 } 00637 } 00638 00639 00640 void KMTransportDialog::slotRequiresAuthClicked() 00641 { 00642 bool b = mSmtp.authCheck->isChecked(); 00643 mSmtp.loginLabel->setEnabled(b); 00644 mSmtp.loginEdit->setEnabled(b); 00645 mSmtp.passwordLabel->setEnabled(b); 00646 mSmtp.passwordEdit->setEnabled(b); 00647 mSmtp.storePasswordCheck->setEnabled(b); 00648 mSmtp.authGroup->setEnabled(b); 00649 } 00650 00651 00652 void KMTransportDialog::slotSmtpEncryptionChanged(int id) 00653 { 00654 kdDebug(5006) << "KMTransportDialog::slotSmtpEncryptionChanged( " << id << " )" << endl; 00655 // adjust SSL port: 00656 if (id == SSL || mSmtp.portEdit->text() == "465") 00657 mSmtp.portEdit->setText((id == SSL) ? "465" : "25"); 00658 00659 // switch supported auth methods: 00660 TQButton * old = mSmtp.authGroup->selected(); 00661 int authMethods = id == TLS ? mAuthTLS : id == SSL ? mAuthSSL : mAuthNone ; 00662 enableAuthMethods( authMethods ); 00663 if ( !old->isEnabled() ) 00664 checkHighest( mSmtp.authGroup ); 00665 } 00666 00667 void KMTransportDialog::enableAuthMethods( unsigned int auth ) { 00668 kdDebug(5006) << "KMTransportDialog::enableAuthMethods( " << auth << " )" << endl; 00669 mSmtp.authPlain->setEnabled( auth & PLAIN ); 00670 // LOGIN doesn't offer anything over PLAIN, requires more server 00671 // roundtrips and is not an official SASL mechanism, but a MS-ism, 00672 // so only enable it if PLAIN isn't available: 00673 mSmtp.authLogin->setEnabled( auth & LOGIN /*&& !(auth & PLAIN)*/); 00674 mSmtp.authCramMd5->setEnabled( auth & CRAM_MD5 ); 00675 mSmtp.authDigestMd5->setEnabled( auth & DIGEST_MD5 ); 00676 mSmtp.authNTLM->setEnabled( auth & NTLM ); 00677 mSmtp.authGSSAPI->setEnabled( auth & GSSAPI ); 00678 } 00679 00680 unsigned int KMTransportDialog::authMethodsFromString( const TQString & s ) { 00681 unsigned int result = 0; 00682 TQStringList sl = TQStringList::split( '\n', s.upper() ); 00683 for ( TQStringList::const_iterator it = sl.begin() ; it != sl.end() ; ++it ) 00684 if ( *it == "SASL/LOGIN" ) 00685 result |= LOGIN; 00686 else if ( *it == "SASL/PLAIN" ) 00687 result |= PLAIN; 00688 else if ( *it == "SASL/CRAM-MD5" ) 00689 result |= CRAM_MD5; 00690 else if ( *it == "SASL/DIGEST-MD5" ) 00691 result |= DIGEST_MD5; 00692 else if ( *it == "SASL/NTLM" ) 00693 result |= NTLM; 00694 else if ( *it == "SASL/GSSAPI" ) 00695 result |= GSSAPI; 00696 return result; 00697 } 00698 00699 unsigned int KMTransportDialog::authMethodsFromStringList( const TQStringList & sl ) { 00700 unsigned int result = 0; 00701 for ( TQStringList::const_iterator it = sl.begin() ; it != sl.end() ; ++it ) 00702 if ( *it == "LOGIN" ) 00703 result |= LOGIN; 00704 else if ( *it == "PLAIN" ) 00705 result |= PLAIN; 00706 else if ( *it == "CRAM-MD5" ) 00707 result |= CRAM_MD5; 00708 else if ( *it == "DIGEST-MD5" ) 00709 result |= DIGEST_MD5; 00710 else if ( *it == "NTLM" ) 00711 result |= NTLM; 00712 else if ( *it == "GSSAPI" ) 00713 result |= GSSAPI; 00714 return result; 00715 } 00716 00717 void KMTransportDialog::slotCheckSmtpCapabilities() 00718 { 00719 delete mServerTest; 00720 mServerTest = new KMServerTest(SMTP_PROTOCOL, mSmtp.hostEdit->text(), 00721 mSmtp.portEdit->text().toInt()); 00722 connect( mServerTest, 00723 TQT_SIGNAL( capabilities( const TQStringList &, const TQStringList &, 00724 const TQString &, const TQString &, 00725 const TQString & )), 00726 this, 00727 TQT_SLOT( slotSmtpCapabilities( const TQStringList &, 00728 const TQStringList &, const TQString &, 00729 const TQString &, const TQString & ) ) ); 00730 mSmtp.checkCapabilities->setEnabled(false); 00731 } 00732 00733 00734 void KMTransportDialog::checkHighest(TQButtonGroup *btnGroup) 00735 { 00736 for ( int i = btnGroup->count() - 1; i >= 0 ; --i ) 00737 { 00738 TQButton * btn = btnGroup->find(i); 00739 if (btn && btn->isEnabled()) 00740 { 00741 btn->animateClick(); 00742 return; 00743 } 00744 } 00745 } 00746 00747 00748 void KMTransportDialog::slotSmtpCapabilities( const TQStringList & capaNormal, 00749 const TQStringList & capaSSL, 00750 const TQString & authNone, 00751 const TQString & authSSL, 00752 const TQString & authTLS ) 00753 { 00754 mSmtp.checkCapabilities->setEnabled( true ); 00755 kdDebug(5006) << "KMTransportDialog::slotSmtpCapabilities( ..., " 00756 << authNone << ", " << authSSL << ", " << authTLS << " )" << endl; 00757 mSmtp.encryptionNone->setEnabled( !capaNormal.isEmpty() ); 00758 mSmtp.encryptionSSL->setEnabled( !capaSSL.isEmpty() ); 00759 mSmtp.encryptionTLS->setEnabled( capaNormal.findIndex("STARTTLS") != -1 ); 00760 if ( authNone.isEmpty() && authSSL.isEmpty() && authTLS.isEmpty() ) { 00761 // slave doesn't seem to support "* AUTH METHODS" metadata (or server can't do AUTH) 00762 mAuthNone = authMethodsFromStringList( capaNormal ); 00763 if ( mSmtp.encryptionTLS->isEnabled() ) 00764 mAuthTLS = mAuthNone; 00765 else 00766 mAuthTLS = 0; 00767 mAuthSSL = authMethodsFromStringList( capaSSL ); 00768 } 00769 else { 00770 mAuthNone = authMethodsFromString( authNone ); 00771 mAuthSSL = authMethodsFromString( authSSL ); 00772 mAuthTLS = authMethodsFromString( authTLS ); 00773 } 00774 kdDebug(5006) << "mAuthNone = " << mAuthNone 00775 << "; mAuthSSL = " << mAuthSSL 00776 << "; mAuthTLS = " << mAuthTLS << endl; 00777 checkHighest( mSmtp.encryptionGroup ); 00778 delete mServerTest; 00779 mServerTest = 0; 00780 } 00781 bool KMTransportDialog::sanityCheckSmtpInput() 00782 { 00783 // FIXME: add additional checks for all fields that needs it 00784 // this is only the beginning 00785 if ( mSmtp.hostEdit->text().isEmpty() ) { 00786 TQString errorMsg = i18n("The Host field cannot be empty. Please " 00787 "enter the name or the IP address of the SMTP server."); 00788 KMessageBox::sorry( this, errorMsg, i18n("Invalid Hostname or Address") ); 00789 return false; 00790 } 00791 return true; 00792 } 00793 00794 void KMTransportDialog::slotOk() 00795 { 00796 if (mTransportInfo->type != "sendmail") { 00797 if( !sanityCheckSmtpInput() ) { 00798 return; 00799 } 00800 } 00801 00802 saveSettings(); 00803 accept(); 00804 } 00805 00806 00807 #include "kmtransport.moc"