1

我正在尝试从 grails 应用程序发送电子邮件。我尝试使用 gmail 推荐的设置,效果很好。我成功发送邮件。但我想动态覆盖用户名和密码。我不知道我该怎么做。有人可以帮忙吗?

    grails {
    mail {
        host = "smtp.gmail.com"
        port = 465
        username = "faruq@gmail.com"    // Want to change dynamically like variable ${branch.mail}
        password = "12345"              // Want to change dynamically like variable ${branch.pass}
        props = [
            "mail.smtp.auth":"true",
            "mail.smtp.socketFactory.port":"465",
            "mail.smtp.socketFactory.class":"javax.net.ssl.SSLSocketFactory",
            "mail.smtp.socketFactory.fallback":"false"
        ]
    }
}

我使用此过程从控制器覆盖用户名

grailsApplication.config.grails.mail.username = Branch.get(2).mail

通过此过程用户名成功更改

这里 Branch 是我的域类,mail 是属性

但是出现了身份验证问题:

javax.mail.AuthenticationFailedException: 535-5.7.8 Username and Password not accepted

现在我能做什么?

4

3 回答 3

1

You can use an external configuration file - put placeholder values in the main Config.groovy

grails {
    mail {
        host = "smtp.gmail.com"
        port = 465
        username = "<changeme>"
        password = "<changeme>"
        props = [
            "mail.smtp.auth":"true",
            "mail.smtp.socketFactory.port":"465",
            "mail.smtp.socketFactory.class":"javax.net.ssl.SSLSocketFactory",
            "mail.smtp.socketFactory.fallback":"false"
        ]
    }
}

and then override them with the correct values in the external config:

grails {
  mail {
    username = "faruq@gmail.com"
    password = "12345"
  }
}

To be able to change the credentials dynamically at run time it gets rather more complicated. Under the covers the mail plugin creates a Spring bean which is an instance of JavaMailSenderImpl to handle the actual sending of emails, and this bean is configured by default with static settings from the config. But at runtime this class appears to call its own getUsername() and getPassword() every time it needs to send a message. So you could replace this bean with your own custom subclass of JavaMailSenderImpl that overrides these methods to pull the details from the request context (code example, not tested, and imports/error handling omitted):

src/groovy/com/example/RequestCredentialsMailSender.groovy

class RequestCredentialsMailSender extends JavaMailSenderImpl {
  public String getUsername() {
    return RequestContextHolder.requestAttributes?.currentRequest?.mailUsername ?: super.getUsername()
  }

  public String getPassword() {
    return RequestContextHolder.requestAttributes?.currentRequest?.mailPassword ?: super.getPassword()
  }
}

You'd have to register this bean in your resources.groovy, and duplicate a fair bit of the configuration from the mail plugin itself, which is less than ideal:

grails-app/conf/spring/resources.groovy

beans = {
  mailSender(com.example.RequestCredentialsMailSender) {
    def mailConf = application.config.grails.mail
    host = mailConf.host
    port = mailConf.port
    username = mailConf.username // the default, if not set in request
    password = mailConf.password
    protocol = mailConf.protocol
    javaMailProperties = mailConf.props
  }
}

Now when you need to send mail from a controller you can do

request.mailUsername = Branch.get(2).mail
request.mailPassword = Branch.get(2).mailPassword
sendMail { ... }
于 2013-09-24T10:29:59.470 回答
0

只是想验证伊恩的答案并扩展它。

在默认的 Config.groovy 文件中,我添加了外部配置行:

 grails.config.locations = [
     "file:./${appName}-config.groovy",
     "classpath:${appName}-config.groovy"
     ]

....
// and here is the mail config as above
grails{
    mail{
.... 

在根级别的配置文件中,我有我的配置文件:TestApp-config.groovy(其中 TestApp 是我的应用程序的名称),如上:

grails {
  mail {
    username = "faruq@gmail.com"
    password = "12345"
  }
}

过去不需要任何东西,而且效果很好。

于 2014-08-07T00:06:35.507 回答
0

如果我们的目标只是获取特定电子邮件 ID 的回复,我们也可以使用replyTo字段。我们可以动态地将电子邮件 id 传递给“replyTo”字段,并且可以期待电子邮件回复。

例子 :

asynchronousMailService.sendMail { to ["xyz@gmail.com","pqr@gmail.com"] subject "Subject Text" if(ccs) cc ["xyz1@gmail.com","pqr1@gmail.com"] if(bccs) bcc ["xyz2@gmail.com","pqr2@gmail.com"] if(replyTo) replyTo "xyz@gmail.com" if(attachBytes) attachBytes attachBytes } 注意:添加“replyTo”只会让我们在指定的电子邮件 ID 上取回电子邮件,并且不会从配置的电子邮件发送电子邮件。

它适用于我的用例。希望能帮助到你 !

于 2018-12-27T12:57:01.733 回答