package mailer import ( "bytes" "embed" "fmt" htmltemplate "html/template" texttemplate "text/template" ) //go:embed templates/password_reset.txt templates/password_reset.html var resetEmailFS embed.FS // ResetEmailVars is the data passed to the password reset templates. type ResetEmailVars struct { Username string ResetURL string ExpiryHours int } // RenderResetEmail returns (textBody, htmlBody) for the password // reset email, parameterized with the given vars. func RenderResetEmail(vars ResetEmailVars) (string, string, error) { textTpl, err := texttemplate.ParseFS(resetEmailFS, "templates/password_reset.txt") if err != nil { return "", "", fmt.Errorf("mailer: parse text template: %w", err) } htmlTpl, err := htmltemplate.ParseFS(resetEmailFS, "templates/password_reset.html") if err != nil { return "", "", fmt.Errorf("mailer: parse html template: %w", err) } var textBuf, htmlBuf bytes.Buffer if err := textTpl.Execute(&textBuf, vars); err != nil { return "", "", fmt.Errorf("mailer: render text: %w", err) } if err := htmlTpl.Execute(&htmlBuf, vars); err != nil { return "", "", fmt.Errorf("mailer: render html: %w", err) } return textBuf.String(), htmlBuf.String(), nil } // ResetEmailSubject is the subject line used by the forgot-password // flow. Exported so callers don't string-literal it independently. const ResetEmailSubject = "Minstrel password reset"