Grails Mail Plugin: Absolute Path to View
I need to开发者_StackOverflow store my email templates in a location that can be edited without redeploying the grails application. I'm looking for a way to render these templates as views for the mail plugin based on an absolute path. Currently both the built in 'view' and the grails render method are based on the grails-app/views location.
UPDATE: For now, I'm going to use the SimpleTemplateEngine and just feed the string into the body. I'd still like to know if there is a more "grails" way of pulling this off.
Not working yet, but this question doesn't seem to be getting many answers so I don't think having this here is too distracting.
Here's what I tried in resources.groovy:
mailMessageContentRenderer(gregg.stackoverflow.CustomPathMailMessageContentRenderer) {
groovyPagesTemplateEngine = ref('groovyPagesTemplateEngine')
groovyPagesUriService = ref('groovyPagesUriService')
grailsApplication = ref('grailsApplication')
}
If you look through mail-plugin, there are two beans mailMessageBuidlerFactory
and mailMessageContentRenderer
defined. Based on what other people have done I really expected this to override the renderer and let you customize the behavior. When I put in logging to see the class of the mailService.mailMessageBuilderFactory.mailMessageContentRenderer
it is the custom one so wiring appears to work correctly. I created the following custom renderer:
package gregg.stackoverflow
import org.codehaus.groovy.grails.commons.ConfigurationHolder
class CustomPathMailMessageContentRenderer extends grails.plugin.mail.MailMessageContentRenderer {
@Override
protected createTemplate(String templateName, String controllerName, String pluginName) {
def gspOverride = ConfigurationHolder.config.mailtemplate.gsp.dir
println "Custom one!"
if (!gspOverride) {
return super.createTemplate(templateName, controllerName, pluginName)
}
else {
def contextPath = gspOverride + templateName +".gsp"
def gspFile = new File(contextPath)
def template = groovyPagesTemplateEngine.createTemplate(gspFile)
if (!template) {
if (pluginName) {
throw new IllegalArgumentException("Could not locate email view ${templateName} in plugin [$pluginName]")
} else {
throw new IllegalArgumentException("Could not locate mail body ${templateName}. Is it in a plugin? If so you must pass the plugin name in the [plugin] variable")
}
}
return template
}
}
}
Also, I added a property to Config.groovy
to indicate the GSP directory called mailtemplate.gsp.dir
that would switch between default functionality and the custom directory.
But println statement I put in there doesn't display. I was messing with this as a distraction after a very long day, so it's possible that my brain was just fried but I won't have time to figure it out today so sorry for posting non-working, very unpolished code. Hope you figure it out.
Upate
Okay, because I'm OCD once I get started on things like this and can live for long periods on caffeine and no food, I got this working over lunch... sort of, most of the way... :-) You have to use GSP views but I'm not sure templates will work (I'm guessing including templates in your GSP views will not work either). So the sendMail
calls look like this:
mailService.sendMail {
to "name@domain.tld"
body (view:"/test", model:[name:"Chris"])
// subject, from, etc still work
}
So with all the above code and the line:
mailtemplate.gsp.dir=C:\\gsptest
and a GSP called C:\gsptest\test.gsp
I was able to successfully send myself an email from an externalized GSP.
精彩评论