gitea源码

mail_release.go 2.8KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899
  1. // Copyright 2020 The Gitea Authors. All rights reserved.
  2. // SPDX-License-Identifier: MIT
  3. package mailer
  4. import (
  5. "bytes"
  6. "context"
  7. "fmt"
  8. "code.gitea.io/gitea/models/renderhelper"
  9. repo_model "code.gitea.io/gitea/models/repo"
  10. user_model "code.gitea.io/gitea/models/user"
  11. "code.gitea.io/gitea/modules/log"
  12. "code.gitea.io/gitea/modules/markup/markdown"
  13. "code.gitea.io/gitea/modules/setting"
  14. "code.gitea.io/gitea/modules/templates"
  15. "code.gitea.io/gitea/modules/translation"
  16. sender_service "code.gitea.io/gitea/services/mailer/sender"
  17. )
  18. const tplNewReleaseMail templates.TplName = "repo/release"
  19. func generateMessageIDForRelease(release *repo_model.Release) string {
  20. return fmt.Sprintf("<%s/releases/%d@%s>", release.Repo.FullName(), release.ID, setting.Domain)
  21. }
  22. // MailNewRelease send new release notify to all repo watchers.
  23. func MailNewRelease(ctx context.Context, rel *repo_model.Release) {
  24. if setting.MailService == nil {
  25. // No mail service configured
  26. return
  27. }
  28. watcherIDList, err := repo_model.GetRepoWatchersIDs(ctx, rel.RepoID)
  29. if err != nil {
  30. log.Error("GetRepoWatchersIDs(%d): %v", rel.RepoID, err)
  31. return
  32. }
  33. recipients, err := user_model.GetMailableUsersByIDs(ctx, watcherIDList, false)
  34. if err != nil {
  35. log.Error("user_model.GetMailableUsersByIDs: %v", err)
  36. return
  37. }
  38. langMap := make(map[string][]*user_model.User)
  39. for _, user := range recipients {
  40. if user.ID != rel.PublisherID {
  41. langMap[user.Language] = append(langMap[user.Language], user)
  42. }
  43. }
  44. for lang, tos := range langMap {
  45. mailNewRelease(ctx, lang, tos, rel)
  46. }
  47. }
  48. func mailNewRelease(ctx context.Context, lang string, tos []*user_model.User, rel *repo_model.Release) {
  49. locale := translation.NewLocale(lang)
  50. var err error
  51. rctx := renderhelper.NewRenderContextRepoComment(ctx, rel.Repo).WithUseAbsoluteLink(true)
  52. rel.RenderedNote, err = markdown.RenderString(rctx,
  53. rel.Note)
  54. if err != nil {
  55. log.Error("markdown.RenderString(%d): %v", rel.RepoID, err)
  56. return
  57. }
  58. subject := locale.TrString("mail.release.new.subject", rel.TagName, rel.Repo.FullName())
  59. mailMeta := map[string]any{
  60. "locale": locale,
  61. "Release": rel,
  62. "Subject": subject,
  63. "Language": locale.Language(),
  64. "Link": rel.HTMLURL(),
  65. }
  66. var mailBody bytes.Buffer
  67. if err := LoadedTemplates().BodyTemplates.ExecuteTemplate(&mailBody, string(tplNewReleaseMail), mailMeta); err != nil {
  68. log.Error("ExecuteTemplate [%s]: %v", string(tplNewReleaseMail)+"/body", err)
  69. return
  70. }
  71. msgs := make([]*sender_service.Message, 0, len(tos))
  72. publisherName := fromDisplayName(rel.Publisher)
  73. msgID := generateMessageIDForRelease(rel)
  74. for _, to := range tos {
  75. msg := sender_service.NewMessageFrom(to.EmailTo(), publisherName, setting.MailService.FromEmail, subject, mailBody.String())
  76. msg.Info = subject
  77. msg.SetHeader("Message-ID", msgID)
  78. msgs = append(msgs, msg)
  79. }
  80. SendAsync(msgs...)
  81. }