mirror of
https://codeberg.org/forgejo/forgejo.git
synced 2025-05-14 05:52:43 +00:00
Repository transfer has to be confirmed, if user can not create repo for new owner (#14792)
* make repo as "pending transfer" if on transfer start doer has no right to create repo in new destination * if new pending transfer ocured, create UI & Mail notifications
This commit is contained in:
parent
e0900310c4
commit
a4148c0f12
32 changed files with 898 additions and 167 deletions
|
@ -39,6 +39,8 @@ const (
|
|||
NotificationSourcePullRequest
|
||||
// NotificationSourceCommit is a notification of a commit
|
||||
NotificationSourceCommit
|
||||
// NotificationSourceRepository is a notification for a repository
|
||||
NotificationSourceRepository
|
||||
)
|
||||
|
||||
// Notification represents a notification
|
||||
|
@ -119,6 +121,46 @@ func GetNotifications(opts FindNotificationOptions) (NotificationList, error) {
|
|||
return getNotifications(x, opts)
|
||||
}
|
||||
|
||||
// CreateRepoTransferNotification creates notification for the user a repository was transferred to
|
||||
func CreateRepoTransferNotification(doer, newOwner *User, repo *Repository) error {
|
||||
sess := x.NewSession()
|
||||
defer sess.Close()
|
||||
if err := sess.Begin(); err != nil {
|
||||
return err
|
||||
}
|
||||
var notify []*Notification
|
||||
|
||||
if newOwner.IsOrganization() {
|
||||
users, err := getUsersWhoCanCreateOrgRepo(sess, newOwner.ID)
|
||||
if err != nil || len(users) == 0 {
|
||||
return err
|
||||
}
|
||||
for i := range users {
|
||||
notify = append(notify, &Notification{
|
||||
UserID: users[i].ID,
|
||||
RepoID: repo.ID,
|
||||
Status: NotificationStatusUnread,
|
||||
UpdatedBy: doer.ID,
|
||||
Source: NotificationSourceRepository,
|
||||
})
|
||||
}
|
||||
} else {
|
||||
notify = []*Notification{{
|
||||
UserID: newOwner.ID,
|
||||
RepoID: repo.ID,
|
||||
Status: NotificationStatusUnread,
|
||||
UpdatedBy: doer.ID,
|
||||
Source: NotificationSourceRepository,
|
||||
}}
|
||||
}
|
||||
|
||||
if _, err := sess.InsertMulti(notify); err != nil {
|
||||
return err
|
||||
}
|
||||
|
||||
return sess.Commit()
|
||||
}
|
||||
|
||||
// CreateOrUpdateIssueNotifications creates an issue notification
|
||||
// for each watcher, or updates it if already exists
|
||||
// receiverID > 0 just send to reciver, else send to all watcher
|
||||
|
@ -363,7 +405,7 @@ func (n *Notification) loadRepo(e Engine) (err error) {
|
|||
}
|
||||
|
||||
func (n *Notification) loadIssue(e Engine) (err error) {
|
||||
if n.Issue == nil {
|
||||
if n.Issue == nil && n.IssueID != 0 {
|
||||
n.Issue, err = getIssueByID(e, n.IssueID)
|
||||
if err != nil {
|
||||
return fmt.Errorf("getIssueByID [%d]: %v", n.IssueID, err)
|
||||
|
@ -374,7 +416,7 @@ func (n *Notification) loadIssue(e Engine) (err error) {
|
|||
}
|
||||
|
||||
func (n *Notification) loadComment(e Engine) (err error) {
|
||||
if n.Comment == nil && n.CommentID > 0 {
|
||||
if n.Comment == nil && n.CommentID != 0 {
|
||||
n.Comment, err = getCommentByID(e, n.CommentID)
|
||||
if err != nil {
|
||||
return fmt.Errorf("GetCommentByID [%d] for issue ID [%d]: %v", n.CommentID, n.IssueID, err)
|
||||
|
@ -405,10 +447,18 @@ func (n *Notification) GetIssue() (*Issue, error) {
|
|||
|
||||
// HTMLURL formats a URL-string to the notification
|
||||
func (n *Notification) HTMLURL() string {
|
||||
if n.Comment != nil {
|
||||
return n.Comment.HTMLURL()
|
||||
switch n.Source {
|
||||
case NotificationSourceIssue, NotificationSourcePullRequest:
|
||||
if n.Comment != nil {
|
||||
return n.Comment.HTMLURL()
|
||||
}
|
||||
return n.Issue.HTMLURL()
|
||||
case NotificationSourceCommit:
|
||||
return n.Repository.HTMLURL() + "/commit/" + n.CommitID
|
||||
case NotificationSourceRepository:
|
||||
return n.Repository.HTMLURL()
|
||||
}
|
||||
return n.Issue.HTMLURL()
|
||||
return ""
|
||||
}
|
||||
|
||||
// APIURL formats a URL-string to the notification
|
||||
|
@ -562,8 +612,10 @@ func (nl NotificationList) LoadIssues() ([]int, error) {
|
|||
if notification.Issue == nil {
|
||||
notification.Issue = issues[notification.IssueID]
|
||||
if notification.Issue == nil {
|
||||
log.Error("Notification[%d]: IssueID: %d Not Found", notification.ID, notification.IssueID)
|
||||
failures = append(failures, i)
|
||||
if notification.IssueID != 0 {
|
||||
log.Error("Notification[%d]: IssueID: %d Not Found", notification.ID, notification.IssueID)
|
||||
failures = append(failures, i)
|
||||
}
|
||||
continue
|
||||
}
|
||||
notification.Issue.Repo = notification.Repository
|
||||
|
@ -683,7 +735,7 @@ func GetUIDsAndNotificationCounts(since, until timeutil.TimeStamp) ([]UserIDCoun
|
|||
return res, x.SQL(sql, since, until, NotificationStatusUnread).Find(&res)
|
||||
}
|
||||
|
||||
func setNotificationStatusReadIfUnread(e Engine, userID, issueID int64) error {
|
||||
func setIssueNotificationStatusReadIfUnread(e Engine, userID, issueID int64) error {
|
||||
notification, err := getIssueNotification(e, userID, issueID)
|
||||
// ignore if not exists
|
||||
if err != nil {
|
||||
|
@ -700,6 +752,16 @@ func setNotificationStatusReadIfUnread(e Engine, userID, issueID int64) error {
|
|||
return err
|
||||
}
|
||||
|
||||
func setRepoNotificationStatusReadIfUnread(e Engine, userID, repoID int64) error {
|
||||
_, err := e.Where(builder.Eq{
|
||||
"user_id": userID,
|
||||
"status": NotificationStatusUnread,
|
||||
"source": NotificationSourceRepository,
|
||||
"repo_id": repoID,
|
||||
}).Cols("status").Update(&Notification{Status: NotificationStatusRead})
|
||||
return err
|
||||
}
|
||||
|
||||
// SetNotificationStatus change the notification status
|
||||
func SetNotificationStatus(notificationID int64, user *User, status NotificationStatus) error {
|
||||
notification, err := getNotificationByID(x, notificationID)
|
||||
|
|
Loading…
Add table
Add a link
Reference in a new issue