2014-10-01 73 views
0

我的问题是:为什么Gmail为我的错误:德尔福XE2印92年5月10日的GMail SMTP错误“的用户名和密码不被接受”

用户名和密码不被接受。了解更多在 http://support.google.com/mail/bin/answer.py?answer=14257 lp8sm18275694wic.17 - gsmtp

我尝试了一切,大量的选项:SSL,TSL,SASL和什么都没有。在某处我发现Google要求在Indy中完成一些OAUTH2 SASL方法。

当然,在Delphi 6和Indy 9上使用适当的eay dlls,可以在端口465上使用ssl。 任何人都有一些想法该怎么做?

Ø当然,我安装http://slproweb.com/products/Win32OpenSSL.html我有人问...

这里是代码:

procedure send(Recipientemail, AccountName, Pass, EmailSMTP,EmailPortNo :string); 
var 
    lTextPart: TIdText; 
    lImagePart: TIdAttachmentfile; 
    IdSMTP1: TIdSMTP; 
    IdMsg: TIdMessage; 
    SSLHandler:TIdSSLIOHandlerSocketOpenSSL; 
    IdUserPassProv1: TIdUserPassProvider; 

    IdSASLLogin1: TIdSASLLogin; 
    IdSASLCRAMMD5: TIdSASLCRAMMD5; 
    IdSASLCRAMSHA1: TIdSASLCRAMSHA1; 
    IdSASLPlain: TIdSASLPlain; 
    IdSASLLogin: TIdSASLLogin; 
    IdSASLSKey: TIdSASLSKey; 
    IdSASLOTP: TIdSASLOTP; 
    IdSASLAnonymous: TIdSASLAnonymous; 
    IdSASLExternal: TIdSASLExternal; 
begin 

    IdSMTP1:=TIdSMTP.Create(nil); 
    IdMsg:=TIdMessage.Create(nil); 
    IdSMTP1.Host:=EmailSMTP; 
    IdSMTP1.Port:=EmailPortNo; 
    //IdSMTP1.Username:=trim(AccountName);//tried with or without 
    //IdSMTP1.Password:=trim(Pass);//tried with or without 



    TIdSSLContext.Create.Free; 
    SSLHandler:=TIdSSLIOHandlerSocketOpenSSL.Create(IdSMTP1); 
    SSLHandler.SSLOptions.Method := sslvSSLv3; 
    SSLHandler.SSLOptions.Mode := sslmClient; 
    IdSMTP1.IOHandler := SSLHandler; 

    if (IdSMTP1.port = 465) then 
     IdSMTP1.UseTLS := utUseImplicitTLS 
     else 
     IdSMTP1.UseTLS := utUseExplicitTLS; 

    IdSASLLogin1:=TIdSASLLogin.Create(IdSMTP1); 
    IdUserPassProv1:=TIdUserPassProvider.Create(IdSMTP1); 
    IdUserPassProv1.Password:=trim(EmailHasloKonta); 
    IdUserPassProv1.Username:=trim(EmailNazwaKonta); 

    IdSMTP1.AuthType:=satSASL; 

    IdSASLCRAMSHA1 := TIdSASLCRAMSHA1.Create(idSMTP1); 
    IdSASLCRAMSHA1.UserPassProvider := IdUserPassProv1; 
    IdSASLCRAMMD5 := TIdSASLCRAMMD5.Create(idSMTP1); 
    IdSASLCRAMMD5.UserPassProvider := IdUserPassProv1; 
    IdSASLSKey := TIdSASLSKey.Create(idSMTP1); 
    IdSASLSKey.UserPassProvider := IdUserPassProv1; 
    IdSASLOTP := TIdSASLOTP.Create(idSMTP1); 
    IdSASLOTP.UserPassProvider := IdUserPassProv1; 
    IdSASLAnonymous := TIdSASLAnonymous.Create(idSMTP1); 
    IdSASLExternal := TIdSASLExternal.Create(idSMTP1); 
    IdSASLLogin := TIdSASLLogin.Create(idSMTP1); 
    IdSASLLogin1.UserPassProvider:=IdUserPassProv1; 
    IdSASLPlain := TIdSASLPlain.Create(idSMTP1); 
    IdSASLPlain.UserPassProvider := IdUserPassProv1; 

    IdSMTP1.SASLMechanisms.Add.SASL := IdSASLCRAMSHA1; 
    IdSMTP1.SASLMechanisms.Add.SASL := IdSASLCRAMMD5; 
    IdSMTP1.SASLMechanisms.Add.SASL := IdSASLSKey; 
    IdSMTP1.SASLMechanisms.Add.SASL := IdSASLOTP; 
    IdSMTP1.SASLMechanisms.Add.SASL := IdSASLAnonymous; 
    IdSMTP1.SASLMechanisms.Add.SASL := IdSASLExternal; 
    IdSMTP1.SASLMechanisms.Add.SASL := IdSASLLogin1; 
    IdSMTP1.SASLMechanisms.Add.SASL := IdSASLPlain; 

    IdMsg.CharSet:=CmbEncod.Text; 
    IdMsg.From.Address:=EmailAdresNadawcy; 
    IdMsg.From.Name:=ToISO_8859_2(true, EmailNadawca); 

    IdMsg.Recipients.Add.Address:=email; 
    if EmailDoWiad<>'' then IdMsg.BccList.Add.Address:=EmailDoWiad; 

    IdMsg.ContentType:='multipart/relative';//; charset='+CmbEncod.Text; 
    IdMsg.Subject:=ifthen(TytulEmaila='',translate('Potwierdzenie rezerwacji'),TytulEmaila); 
    IdMsg.Body.Clear; 
    IdMsg.Body.Text:=''; 

    lTextPart := TIdText.Create(IdMsg.MessageParts); 
    lTextPart.Body.text:='Some body text'; 
    lTextPart.ContentType := 'text/plain'; 

    try 
    IdSMTP1.Connect;  
    //IdSMTP1.Authenticate; //tried with or without 

    try 

     try 
     IdSMTP1.Send(IdMsg); 
     except 
     on e: exception do 
     MessageDlg('Sending error:'#13+ 
        e.message, 
        mtinformation,[mbok],0); 
     end; 
    finally 
     IdSMTP1.Disconnect; 
    end; 
    finally 
    IdSMTP1.Disconnect; 
    IdUserPassProv1.free; 
    IdSASLLogin1.free; 
    IdSASLCRAMMD5.free; 
    IdSASLCRAMSHA1.free; 
    IdSASLPlain.free; 
    IdSASLLogin.free; 
    IdSASLSKey.free; 
    IdSASLOTP.free; 
    IdSASLAnonymous.free; 
    IdSASLExternal.free; 
    lTextPart.Free; 
    lImagePart.Free; 
    SSLHandler.free; 
    IdSMTP1.Free; 
    IdMsg.Free; 
    SSLHandler.Free; 
    end; 
end; 

回答

4

使用最新版本的Indy(10.6.1),我可以成功连接和认证TIdSMTP到使用Indy的SASL组件的Gmail(使用端口号为465的UseTLS=utUseImplicitTLS)和TLS(端口号为587的UseTLS=utUseExplicitTLS)使用与您所显示的类似的代码。尽管流行的观点,OAUTH2是而不是还需要。

事实上,你得到一个人类可读的认证错误意味着SSL/TLS部分工作正常,所以这是一个严格的SASL问题。

如果您的Gmail帐户使用两步验证,请确保您在您的Gmail帐户设置中创建了应用程序密码,但无法使用您的主Gmail密码。阅读Gmail的文档了解更多信息:

Application-specific password required

Sign in using App Passwords

虽这么说,唯一的变化,我建议您对您所显示的代码是:

  1. 设置UseTLS属性可能会更改Port属性值,所以您应该先设置UseTLS,然后再将Port设置为所需的值算账:

    if (EmailPortNo = 465) then 
        IdSMTP1.UseTLS := utUseImplicitTLS 
    else 
        IdSMTP1.UseTLS := utUseExplicitTLS; 
    IdSMTP1.Port := EmailPortNo; 
    
  2. 你不需要创建和销毁TIdSSLContext对象,因此摆脱了这一点。手动创建TIdSSLContext的唯一原因是它可以调用IdSSLOpenSSL.LoadOpenSSLLibrary()函数,该函数是公开的,因此如果需要可以直接调用它(在这种情况下您并不需要这样做)。

  3. multipart/relative不是有效的ContentType。你的意思是multipart/related?您的TIdMessage不包含多个部分,因此您不应使用multipart ContentType开头。

  4. 由于您将TIdSMTP指定为除TIdMessage之外的所有者,因此您拨打Free()的大部分电话都是多余的。你不需要手动释放SASL组件,你可以让TIdSMTP为你做。

  5. 您打电话给IdSMTP1.Disconnect()两次。你不需要那个。

0

这里是解决方案:

所有尝试后,似乎我有两个DLL的版本错误libeay.dll和ssleay.dll。