mirror of
				https://gitee.com/gitea/gitea
				synced 2025-11-04 08:30:25 +08:00 
			
		
		
		
	@@ -3,7 +3,7 @@ Gogs - Go Git Service [
 | 
					
 | 
				
			||||||
 | 
					
 | 
				
			||||||
##### Current version: 0.9.8
 | 
					##### Current version: 0.9.9
 | 
				
			||||||
 | 
					
 | 
				
			||||||
| Web | UI  | Preview  |
 | 
					| Web | UI  | Preview  |
 | 
				
			||||||
|:-------------:|:-------:|:-------:|
 | 
					|:-------------:|:-------:|:-------:|
 | 
				
			||||||
 
 | 
				
			|||||||
@@ -88,7 +88,7 @@ func checkVersion() {
 | 
				
			|||||||
		{"gopkg.in/ini.v1", ini.Version, "1.8.4"},
 | 
							{"gopkg.in/ini.v1", ini.Version, "1.8.4"},
 | 
				
			||||||
		{"gopkg.in/macaron.v1", macaron.Version, "1.1.2"},
 | 
							{"gopkg.in/macaron.v1", macaron.Version, "1.1.2"},
 | 
				
			||||||
		{"github.com/gogits/git-module", git.Version, "0.2.9"},
 | 
							{"github.com/gogits/git-module", git.Version, "0.2.9"},
 | 
				
			||||||
		{"github.com/gogits/go-gogs-client", gogs.Version, "0.7.3"},
 | 
							{"github.com/gogits/go-gogs-client", gogs.Version, "0.7.4"},
 | 
				
			||||||
	}
 | 
						}
 | 
				
			||||||
	for _, c := range checkers {
 | 
						for _, c := range checkers {
 | 
				
			||||||
		if !version.Compare(c.Version(), c.Expected, ">=") {
 | 
							if !version.Compare(c.Version(), c.Expected, ">=") {
 | 
				
			||||||
 
 | 
				
			|||||||
							
								
								
									
										4
									
								
								glide.lock
									
									
									
										generated
									
									
									
								
							
							
						
						
									
										4
									
								
								glide.lock
									
									
									
										generated
									
									
									
								
							@@ -35,7 +35,7 @@ imports:
 | 
				
			|||||||
- name: github.com/go-xorm/core
 | 
					- name: github.com/go-xorm/core
 | 
				
			||||||
  version: 502158401cde814951eae62f064d9e5ff39e13ce
 | 
					  version: 502158401cde814951eae62f064d9e5ff39e13ce
 | 
				
			||||||
- name: github.com/go-xorm/xorm
 | 
					- name: github.com/go-xorm/xorm
 | 
				
			||||||
  version: bb8c5c04d7d65453c3f0176a307276857dccc3b0
 | 
					  version: 99686972253975273816d1ebb4cdb0a53bf39100
 | 
				
			||||||
- name: github.com/gogits/chardet
 | 
					- name: github.com/gogits/chardet
 | 
				
			||||||
  version: 2404f777256163ea3eadb273dada5dcb037993c0
 | 
					  version: 2404f777256163ea3eadb273dada5dcb037993c0
 | 
				
			||||||
- name: github.com/gogits/cron
 | 
					- name: github.com/gogits/cron
 | 
				
			||||||
@@ -43,7 +43,7 @@ imports:
 | 
				
			|||||||
- name: github.com/gogits/git-module
 | 
					- name: github.com/gogits/git-module
 | 
				
			||||||
  version: 76e8cce6c7ef3ba1cf75752261c721ebf14cd129
 | 
					  version: 76e8cce6c7ef3ba1cf75752261c721ebf14cd129
 | 
				
			||||||
- name: github.com/gogits/go-gogs-client
 | 
					- name: github.com/gogits/go-gogs-client
 | 
				
			||||||
  version: d584b1e0fb4d8ad0e8cf2fae2368838f2526b408
 | 
					  version: 788ec59749df076b98e208909b44fdef02779deb
 | 
				
			||||||
- name: github.com/issue9/identicon
 | 
					- name: github.com/issue9/identicon
 | 
				
			||||||
  version: f8c0d2ce04db79c663b1da33d3a9f62be753ee88
 | 
					  version: f8c0d2ce04db79c663b1da33d3a9f62be753ee88
 | 
				
			||||||
- name: github.com/klauspost/compress
 | 
					- name: github.com/klauspost/compress
 | 
				
			||||||
 
 | 
				
			|||||||
							
								
								
									
										2
									
								
								gogs.go
									
									
									
									
									
								
							
							
						
						
									
										2
									
								
								gogs.go
									
									
									
									
									
								
							@@ -17,7 +17,7 @@ import (
 | 
				
			|||||||
	"github.com/gogits/gogs/modules/setting"
 | 
						"github.com/gogits/gogs/modules/setting"
 | 
				
			||||||
)
 | 
					)
 | 
				
			||||||
 | 
					
 | 
				
			||||||
const APP_VER = "0.9.8.0312"
 | 
					const APP_VER = "0.9.9.0313"
 | 
				
			||||||
 | 
					
 | 
				
			||||||
func init() {
 | 
					func init() {
 | 
				
			||||||
	runtime.GOMAXPROCS(runtime.NumCPU())
 | 
						runtime.GOMAXPROCS(runtime.NumCPU())
 | 
				
			||||||
 
 | 
				
			|||||||
@@ -88,6 +88,23 @@ func (i *Issue) AfterSet(colName string, _ xorm.Cell) {
 | 
				
			|||||||
			log.Error(3, "GetCommentsByIssueID[%d]: %v", i.ID, err)
 | 
								log.Error(3, "GetCommentsByIssueID[%d]: %v", i.ID, err)
 | 
				
			||||||
		}
 | 
							}
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
							i.Labels, err = GetLabelsByIssueID(i.ID)
 | 
				
			||||||
 | 
							if err != nil {
 | 
				
			||||||
 | 
								log.Error(3, "GetLabelsByIssueID[%d]: %v", i.ID, err)
 | 
				
			||||||
 | 
							}
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
						case "poster_id":
 | 
				
			||||||
 | 
							i.Poster, err = GetUserByID(i.PosterID)
 | 
				
			||||||
 | 
							if err != nil {
 | 
				
			||||||
 | 
								if IsErrUserNotExist(err) {
 | 
				
			||||||
 | 
									i.PosterID = -1
 | 
				
			||||||
 | 
									i.Poster = NewFakeUser()
 | 
				
			||||||
 | 
								} else {
 | 
				
			||||||
 | 
									log.Error(3, "GetUserByID[%d]: %v", i.ID, err)
 | 
				
			||||||
 | 
								}
 | 
				
			||||||
 | 
								return
 | 
				
			||||||
 | 
							}
 | 
				
			||||||
 | 
					
 | 
				
			||||||
	case "milestone_id":
 | 
						case "milestone_id":
 | 
				
			||||||
		if i.MilestoneID == 0 {
 | 
							if i.MilestoneID == 0 {
 | 
				
			||||||
			return
 | 
								return
 | 
				
			||||||
@@ -97,6 +114,7 @@ func (i *Issue) AfterSet(colName string, _ xorm.Cell) {
 | 
				
			|||||||
		if err != nil {
 | 
							if err != nil {
 | 
				
			||||||
			log.Error(3, "GetMilestoneById[%d]: %v", i.ID, err)
 | 
								log.Error(3, "GetMilestoneById[%d]: %v", i.ID, err)
 | 
				
			||||||
		}
 | 
							}
 | 
				
			||||||
 | 
					
 | 
				
			||||||
	case "assignee_id":
 | 
						case "assignee_id":
 | 
				
			||||||
		if i.AssigneeID == 0 {
 | 
							if i.AssigneeID == 0 {
 | 
				
			||||||
			return
 | 
								return
 | 
				
			||||||
@@ -106,6 +124,7 @@ func (i *Issue) AfterSet(colName string, _ xorm.Cell) {
 | 
				
			|||||||
		if err != nil {
 | 
							if err != nil {
 | 
				
			||||||
			log.Error(3, "GetUserByID[%d]: %v", i.ID, err)
 | 
								log.Error(3, "GetUserByID[%d]: %v", i.ID, err)
 | 
				
			||||||
		}
 | 
							}
 | 
				
			||||||
 | 
					
 | 
				
			||||||
	case "deadline_unix":
 | 
						case "deadline_unix":
 | 
				
			||||||
		i.Deadline = time.Unix(i.DeadlineUnix, 0).Local()
 | 
							i.Deadline = time.Unix(i.DeadlineUnix, 0).Local()
 | 
				
			||||||
	case "created_unix":
 | 
						case "created_unix":
 | 
				
			||||||
@@ -120,21 +139,19 @@ func (i *Issue) HashTag() string {
 | 
				
			|||||||
	return "issue-" + com.ToStr(i.ID)
 | 
						return "issue-" + com.ToStr(i.ID)
 | 
				
			||||||
}
 | 
					}
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					// State returns string representation of issue status.
 | 
				
			||||||
 | 
					func (i *Issue) State() string {
 | 
				
			||||||
 | 
						if i.IsClosed {
 | 
				
			||||||
 | 
							return "closed"
 | 
				
			||||||
 | 
						}
 | 
				
			||||||
 | 
						return "open"
 | 
				
			||||||
 | 
					}
 | 
				
			||||||
 | 
					
 | 
				
			||||||
// IsPoster returns true if given user by ID is the poster.
 | 
					// IsPoster returns true if given user by ID is the poster.
 | 
				
			||||||
func (i *Issue) IsPoster(uid int64) bool {
 | 
					func (i *Issue) IsPoster(uid int64) bool {
 | 
				
			||||||
	return i.PosterID == uid
 | 
						return i.PosterID == uid
 | 
				
			||||||
}
 | 
					}
 | 
				
			||||||
 | 
					
 | 
				
			||||||
func (i *Issue) GetPoster() (err error) {
 | 
					 | 
				
			||||||
	i.Poster, err = GetUserByID(i.PosterID)
 | 
					 | 
				
			||||||
	if IsErrUserNotExist(err) {
 | 
					 | 
				
			||||||
		i.PosterID = -1
 | 
					 | 
				
			||||||
		i.Poster = NewFakeUser()
 | 
					 | 
				
			||||||
		return nil
 | 
					 | 
				
			||||||
	}
 | 
					 | 
				
			||||||
	return err
 | 
					 | 
				
			||||||
}
 | 
					 | 
				
			||||||
 | 
					 | 
				
			||||||
func (i *Issue) hasLabel(e Engine, labelID int64) bool {
 | 
					func (i *Issue) hasLabel(e Engine, labelID int64) bool {
 | 
				
			||||||
	return hasIssueLabel(e, i.ID, labelID)
 | 
						return hasIssueLabel(e, i.ID, labelID)
 | 
				
			||||||
}
 | 
					}
 | 
				
			||||||
@@ -175,11 +192,6 @@ func (i *Issue) getLabels(e Engine) (err error) {
 | 
				
			|||||||
	return nil
 | 
						return nil
 | 
				
			||||||
}
 | 
					}
 | 
				
			||||||
 | 
					
 | 
				
			||||||
// GetLabels retrieves all labels of issue and assign to corresponding field.
 | 
					 | 
				
			||||||
func (i *Issue) GetLabels() error {
 | 
					 | 
				
			||||||
	return i.getLabels(x)
 | 
					 | 
				
			||||||
}
 | 
					 | 
				
			||||||
 | 
					 | 
				
			||||||
func (i *Issue) removeLabel(e *xorm.Session, label *Label) error {
 | 
					func (i *Issue) removeLabel(e *xorm.Session, label *Label) error {
 | 
				
			||||||
	return deleteIssueLabel(e, i, label)
 | 
						return deleteIssueLabel(e, i, label)
 | 
				
			||||||
}
 | 
					}
 | 
				
			||||||
@@ -303,6 +315,19 @@ func (i *Issue) GetPullRequest() (err error) {
 | 
				
			|||||||
 | 
					
 | 
				
			||||||
// It's caller's responsibility to create action.
 | 
					// It's caller's responsibility to create action.
 | 
				
			||||||
func newIssue(e *xorm.Session, repo *Repository, issue *Issue, labelIDs []int64, uuids []string, isPull bool) (err error) {
 | 
					func newIssue(e *xorm.Session, repo *Repository, issue *Issue, labelIDs []int64, uuids []string, isPull bool) (err error) {
 | 
				
			||||||
 | 
						issue.Name = strings.TrimSpace(issue.Name)
 | 
				
			||||||
 | 
						issue.Index = repo.NextIssueIndex()
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
						if issue.AssigneeID > 0 {
 | 
				
			||||||
 | 
							// Silently drop invalid assignee
 | 
				
			||||||
 | 
							valid, err := hasAccess(e, &User{Id: issue.AssigneeID}, repo, ACCESS_MODE_WRITE)
 | 
				
			||||||
 | 
							if err != nil {
 | 
				
			||||||
 | 
								return fmt.Errorf("hasAccess: %v", err)
 | 
				
			||||||
 | 
							} else if !valid {
 | 
				
			||||||
 | 
								issue.AssigneeID = 0
 | 
				
			||||||
 | 
							}
 | 
				
			||||||
 | 
						}
 | 
				
			||||||
 | 
					
 | 
				
			||||||
	if _, err = e.Insert(issue); err != nil {
 | 
						if _, err = e.Insert(issue); err != nil {
 | 
				
			||||||
		return err
 | 
							return err
 | 
				
			||||||
	}
 | 
						}
 | 
				
			||||||
@@ -325,6 +350,10 @@ func newIssue(e *xorm.Session, repo *Repository, issue *Issue, labelIDs []int64,
 | 
				
			|||||||
		}
 | 
							}
 | 
				
			||||||
 | 
					
 | 
				
			||||||
		for _, label := range labels {
 | 
							for _, label := range labels {
 | 
				
			||||||
 | 
								if label.RepoID != repo.ID {
 | 
				
			||||||
 | 
									continue
 | 
				
			||||||
 | 
								}
 | 
				
			||||||
 | 
					
 | 
				
			||||||
			if err = issue.addLabel(e, label); err != nil {
 | 
								if err = issue.addLabel(e, label); err != nil {
 | 
				
			||||||
				return fmt.Errorf("addLabel: %v", err)
 | 
									return fmt.Errorf("addLabel: %v", err)
 | 
				
			||||||
			}
 | 
								}
 | 
				
			||||||
@@ -377,6 +406,10 @@ func NewIssue(repo *Repository, issue *Issue, labelIDs []int64, uuids []string)
 | 
				
			|||||||
		return fmt.Errorf("newIssue: %v", err)
 | 
							return fmt.Errorf("newIssue: %v", err)
 | 
				
			||||||
	}
 | 
						}
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
						if err = sess.Commit(); err != nil {
 | 
				
			||||||
 | 
							return fmt.Errorf("Commit: %v", err)
 | 
				
			||||||
 | 
						}
 | 
				
			||||||
 | 
					
 | 
				
			||||||
	// Notify watchers.
 | 
						// Notify watchers.
 | 
				
			||||||
	act := &Action{
 | 
						act := &Action{
 | 
				
			||||||
		ActUserID:    issue.Poster.Id,
 | 
							ActUserID:    issue.Poster.Id,
 | 
				
			||||||
@@ -389,11 +422,11 @@ func NewIssue(repo *Repository, issue *Issue, labelIDs []int64, uuids []string)
 | 
				
			|||||||
		RepoName:     repo.Name,
 | 
							RepoName:     repo.Name,
 | 
				
			||||||
		IsPrivate:    repo.IsPrivate,
 | 
							IsPrivate:    repo.IsPrivate,
 | 
				
			||||||
	}
 | 
						}
 | 
				
			||||||
	if err = notifyWatchers(sess, act); err != nil {
 | 
						if err = NotifyWatchers(act); err != nil {
 | 
				
			||||||
		return err
 | 
							log.Error(4, "notifyWatchers: %v", err)
 | 
				
			||||||
	}
 | 
						}
 | 
				
			||||||
 | 
					
 | 
				
			||||||
	return sess.Commit()
 | 
						return nil
 | 
				
			||||||
}
 | 
					}
 | 
				
			||||||
 | 
					
 | 
				
			||||||
// GetIssueByRef returns an Issue specified by a GFM reference.
 | 
					// GetIssueByRef returns an Issue specified by a GFM reference.
 | 
				
			||||||
@@ -467,6 +500,10 @@ type IssuesOptions struct {
 | 
				
			|||||||
 | 
					
 | 
				
			||||||
// Issues returns a list of issues by given conditions.
 | 
					// Issues returns a list of issues by given conditions.
 | 
				
			||||||
func Issues(opts *IssuesOptions) ([]*Issue, error) {
 | 
					func Issues(opts *IssuesOptions) ([]*Issue, error) {
 | 
				
			||||||
 | 
						if opts.Page <= 0 {
 | 
				
			||||||
 | 
							opts.Page = 1
 | 
				
			||||||
 | 
						}
 | 
				
			||||||
 | 
					
 | 
				
			||||||
	sess := x.Limit(setting.IssuePagingNum, (opts.Page-1)*setting.IssuePagingNum)
 | 
						sess := x.Limit(setting.IssuePagingNum, (opts.Page-1)*setting.IssuePagingNum)
 | 
				
			||||||
 | 
					
 | 
				
			||||||
	if opts.RepoID > 0 {
 | 
						if opts.RepoID > 0 {
 | 
				
			||||||
@@ -997,6 +1034,9 @@ func (m *Milestone) BeforeUpdate() {
 | 
				
			|||||||
 | 
					
 | 
				
			||||||
func (m *Milestone) AfterSet(colName string, _ xorm.Cell) {
 | 
					func (m *Milestone) AfterSet(colName string, _ xorm.Cell) {
 | 
				
			||||||
	switch colName {
 | 
						switch colName {
 | 
				
			||||||
 | 
						case "num_closed_issues":
 | 
				
			||||||
 | 
							m.NumOpenIssues = m.NumIssues - m.NumClosedIssues
 | 
				
			||||||
 | 
					
 | 
				
			||||||
	case "deadline_unix":
 | 
						case "deadline_unix":
 | 
				
			||||||
		m.Deadline = time.Unix(m.DeadlineUnix, 0).Local()
 | 
							m.Deadline = time.Unix(m.DeadlineUnix, 0).Local()
 | 
				
			||||||
		if m.Deadline.Year() == 9999 {
 | 
							if m.Deadline.Year() == 9999 {
 | 
				
			||||||
@@ -1007,14 +1047,18 @@ func (m *Milestone) AfterSet(colName string, _ xorm.Cell) {
 | 
				
			|||||||
		if time.Now().Local().After(m.Deadline) {
 | 
							if time.Now().Local().After(m.Deadline) {
 | 
				
			||||||
			m.IsOverDue = true
 | 
								m.IsOverDue = true
 | 
				
			||||||
		}
 | 
							}
 | 
				
			||||||
 | 
					
 | 
				
			||||||
	case "closed_date_unix":
 | 
						case "closed_date_unix":
 | 
				
			||||||
		m.ClosedDate = time.Unix(m.ClosedDateUnix, 0).Local()
 | 
							m.ClosedDate = time.Unix(m.ClosedDateUnix, 0).Local()
 | 
				
			||||||
	}
 | 
						}
 | 
				
			||||||
}
 | 
					}
 | 
				
			||||||
 | 
					
 | 
				
			||||||
// CalOpenIssues calculates the open issues of milestone.
 | 
					// State returns string representation of milestone status.
 | 
				
			||||||
func (m *Milestone) CalOpenIssues() {
 | 
					func (m *Milestone) State() string {
 | 
				
			||||||
	m.NumOpenIssues = m.NumIssues - m.NumClosedIssues
 | 
						if m.IsClosed {
 | 
				
			||||||
 | 
							return "closed"
 | 
				
			||||||
 | 
						}
 | 
				
			||||||
 | 
						return "open"
 | 
				
			||||||
}
 | 
					}
 | 
				
			||||||
 | 
					
 | 
				
			||||||
// NewMilestone creates new milestone of repository.
 | 
					// NewMilestone creates new milestone of repository.
 | 
				
			||||||
 
 | 
				
			|||||||
@@ -5,10 +5,15 @@
 | 
				
			|||||||
package context
 | 
					package context
 | 
				
			||||||
 | 
					
 | 
				
			||||||
import (
 | 
					import (
 | 
				
			||||||
 | 
						"fmt"
 | 
				
			||||||
 | 
						"strings"
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
						"github.com/Unknwon/paginater"
 | 
				
			||||||
	"gopkg.in/macaron.v1"
 | 
						"gopkg.in/macaron.v1"
 | 
				
			||||||
 | 
					
 | 
				
			||||||
	"github.com/gogits/gogs/modules/base"
 | 
						"github.com/gogits/gogs/modules/base"
 | 
				
			||||||
	"github.com/gogits/gogs/modules/log"
 | 
						"github.com/gogits/gogs/modules/log"
 | 
				
			||||||
 | 
						"github.com/gogits/gogs/modules/setting"
 | 
				
			||||||
)
 | 
					)
 | 
				
			||||||
 | 
					
 | 
				
			||||||
type APIContext struct {
 | 
					type APIContext struct {
 | 
				
			||||||
@@ -35,6 +40,27 @@ func (ctx *APIContext) Error(status int, title string, obj interface{}) {
 | 
				
			|||||||
	})
 | 
						})
 | 
				
			||||||
}
 | 
					}
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					func (ctx *APIContext) SetLinkHeader(total, pageSize int) {
 | 
				
			||||||
 | 
						page := paginater.New(total, pageSize, ctx.QueryInt("page"), 0)
 | 
				
			||||||
 | 
						links := make([]string, 0, 4)
 | 
				
			||||||
 | 
						if page.HasNext() {
 | 
				
			||||||
 | 
							links = append(links, fmt.Sprintf("<%s%s?page=%d>; rel=\"next\"", setting.AppUrl, ctx.Req.URL.Path[1:], page.Next()))
 | 
				
			||||||
 | 
						}
 | 
				
			||||||
 | 
						if !page.IsLast() {
 | 
				
			||||||
 | 
							links = append(links, fmt.Sprintf("<%s%s?page=%d>; rel=\"last\"", setting.AppUrl, ctx.Req.URL.Path[1:], page.TotalPages()))
 | 
				
			||||||
 | 
						}
 | 
				
			||||||
 | 
						if !page.IsFirst() {
 | 
				
			||||||
 | 
							links = append(links, fmt.Sprintf("<%s%s?page=1>; rel=\"first\"", setting.AppUrl, ctx.Req.URL.Path[1:]))
 | 
				
			||||||
 | 
						}
 | 
				
			||||||
 | 
						if page.HasPrevious() {
 | 
				
			||||||
 | 
							links = append(links, fmt.Sprintf("<%s%s?page=%d>; rel=\"prev\"", setting.AppUrl, ctx.Req.URL.Path[1:], page.Previous()))
 | 
				
			||||||
 | 
						}
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
						if len(links) > 0 {
 | 
				
			||||||
 | 
							ctx.Header().Set("Link", strings.Join(links, ","))
 | 
				
			||||||
 | 
						}
 | 
				
			||||||
 | 
					}
 | 
				
			||||||
 | 
					
 | 
				
			||||||
func APIContexter() macaron.Handler {
 | 
					func APIContexter() macaron.Handler {
 | 
				
			||||||
	return func(c *Context) {
 | 
						return func(c *Context) {
 | 
				
			||||||
		ctx := &APIContext{
 | 
							ctx := &APIContext{
 | 
				
			||||||
 
 | 
				
			|||||||
@@ -40,5 +40,5 @@ func CreateOrg(ctx *context.APIContext, form api.CreateOrgOption) {
 | 
				
			|||||||
		return
 | 
							return
 | 
				
			||||||
	}
 | 
						}
 | 
				
			||||||
 | 
					
 | 
				
			||||||
	ctx.JSON(201, convert.ToApiOrganization(org))
 | 
						ctx.JSON(201, convert.ToOrganization(org))
 | 
				
			||||||
}
 | 
					}
 | 
				
			||||||
 
 | 
				
			|||||||
@@ -69,7 +69,7 @@ func CreateUser(ctx *context.APIContext, form api.CreateUserOption) {
 | 
				
			|||||||
		mailer.SendRegisterNotifyMail(ctx.Context.Context, u)
 | 
							mailer.SendRegisterNotifyMail(ctx.Context.Context, u)
 | 
				
			||||||
	}
 | 
						}
 | 
				
			||||||
 | 
					
 | 
				
			||||||
	ctx.JSON(201, convert.ToApiUser(u))
 | 
						ctx.JSON(201, convert.ToUser(u))
 | 
				
			||||||
}
 | 
					}
 | 
				
			||||||
 | 
					
 | 
				
			||||||
// https://github.com/gogits/go-gogs-client/wiki/Administration-Users#edit-an-existing-user
 | 
					// https://github.com/gogits/go-gogs-client/wiki/Administration-Users#edit-an-existing-user
 | 
				
			||||||
@@ -118,7 +118,7 @@ func EditUser(ctx *context.APIContext, form api.EditUserOption) {
 | 
				
			|||||||
	}
 | 
						}
 | 
				
			||||||
	log.Trace("Account profile updated by admin (%s): %s", ctx.User.Name, u.Name)
 | 
						log.Trace("Account profile updated by admin (%s): %s", ctx.User.Name, u.Name)
 | 
				
			||||||
 | 
					
 | 
				
			||||||
	ctx.JSON(200, convert.ToApiUser(u))
 | 
						ctx.JSON(200, convert.ToUser(u))
 | 
				
			||||||
}
 | 
					}
 | 
				
			||||||
 | 
					
 | 
				
			||||||
// https://github.com/gogits/go-gogs-client/wiki/Administration-Users#delete-a-user
 | 
					// https://github.com/gogits/go-gogs-client/wiki/Administration-Users#delete-a-user
 | 
				
			||||||
 
 | 
				
			|||||||
@@ -62,16 +62,18 @@ func RepoAssignment() macaron.Handler {
 | 
				
			|||||||
			return
 | 
								return
 | 
				
			||||||
		}
 | 
							}
 | 
				
			||||||
 | 
					
 | 
				
			||||||
		mode, err := models.AccessLevel(ctx.User, repo)
 | 
							if ctx.IsSigned && ctx.User.IsAdmin {
 | 
				
			||||||
		if err != nil {
 | 
								ctx.Repo.AccessMode = models.ACCESS_MODE_OWNER
 | 
				
			||||||
			ctx.Error(500, "AccessLevel", err)
 | 
							} else {
 | 
				
			||||||
			return
 | 
								mode, err := models.AccessLevel(ctx.User, repo)
 | 
				
			||||||
 | 
								if err != nil {
 | 
				
			||||||
 | 
									ctx.Error(500, "AccessLevel", err)
 | 
				
			||||||
 | 
									return
 | 
				
			||||||
 | 
								}
 | 
				
			||||||
 | 
								ctx.Repo.AccessMode = mode
 | 
				
			||||||
		}
 | 
							}
 | 
				
			||||||
 | 
					
 | 
				
			||||||
		ctx.Repo.AccessMode = mode
 | 
							if !ctx.Repo.HasAccess() {
 | 
				
			||||||
 | 
					 | 
				
			||||||
		// Check access.
 | 
					 | 
				
			||||||
		if ctx.Repo.AccessMode == models.ACCESS_MODE_NONE {
 | 
					 | 
				
			||||||
			ctx.Status(404)
 | 
								ctx.Status(404)
 | 
				
			||||||
			return
 | 
								return
 | 
				
			||||||
		}
 | 
							}
 | 
				
			||||||
@@ -193,9 +195,9 @@ func RegisterRoutes(m *macaron.Macaron) {
 | 
				
			|||||||
					m.Combo("/:id").Get(repo.GetDeployKey).
 | 
										m.Combo("/:id").Get(repo.GetDeployKey).
 | 
				
			||||||
						Delete(repo.DeleteDeploykey)
 | 
											Delete(repo.DeleteDeploykey)
 | 
				
			||||||
				})
 | 
									})
 | 
				
			||||||
				m.Group("/issue", func() {
 | 
									m.Group("/issues", func() {
 | 
				
			||||||
					m.Combo("").Get().Post()
 | 
										m.Combo("").Get(repo.ListIssues).Post(bind(api.CreateIssueOption{}), repo.CreateIssue)
 | 
				
			||||||
					m.Combo("/:index").Get().Patch()
 | 
										m.Combo("/:index").Get(repo.GetIssue).Patch(bind(api.EditIssueOption{}), repo.EditIssue)
 | 
				
			||||||
				})
 | 
									})
 | 
				
			||||||
			}, RepoAssignment())
 | 
								}, RepoAssignment())
 | 
				
			||||||
		}, ReqToken())
 | 
							}, ReqToken())
 | 
				
			||||||
 
 | 
				
			|||||||
@@ -9,15 +9,19 @@ import (
 | 
				
			|||||||
 | 
					
 | 
				
			||||||
	"github.com/Unknwon/com"
 | 
						"github.com/Unknwon/com"
 | 
				
			||||||
 | 
					
 | 
				
			||||||
	api "github.com/gogits/go-gogs-client"
 | 
					 | 
				
			||||||
	"github.com/gogits/git-module"
 | 
						"github.com/gogits/git-module"
 | 
				
			||||||
 | 
						api "github.com/gogits/go-gogs-client"
 | 
				
			||||||
 | 
					
 | 
				
			||||||
	"github.com/gogits/gogs/models"
 | 
						"github.com/gogits/gogs/models"
 | 
				
			||||||
 | 
						"github.com/gogits/gogs/modules/log"
 | 
				
			||||||
	"github.com/gogits/gogs/modules/setting"
 | 
						"github.com/gogits/gogs/modules/setting"
 | 
				
			||||||
)
 | 
					)
 | 
				
			||||||
 | 
					
 | 
				
			||||||
// ToApiUser converts user to its API format.
 | 
					func ToUser(u *models.User) *api.User {
 | 
				
			||||||
func ToApiUser(u *models.User) *api.User {
 | 
						if u == nil {
 | 
				
			||||||
 | 
							return nil
 | 
				
			||||||
 | 
						}
 | 
				
			||||||
 | 
					
 | 
				
			||||||
	return &api.User{
 | 
						return &api.User{
 | 
				
			||||||
		ID:        u.Id,
 | 
							ID:        u.Id,
 | 
				
			||||||
		UserName:  u.Name,
 | 
							UserName:  u.Name,
 | 
				
			||||||
@@ -27,7 +31,7 @@ func ToApiUser(u *models.User) *api.User {
 | 
				
			|||||||
	}
 | 
						}
 | 
				
			||||||
}
 | 
					}
 | 
				
			||||||
 | 
					
 | 
				
			||||||
func ToApiEmail(email *models.EmailAddress) *api.Email {
 | 
					func ToEmail(email *models.EmailAddress) *api.Email {
 | 
				
			||||||
	return &api.Email{
 | 
						return &api.Email{
 | 
				
			||||||
		Email:    email.Email,
 | 
							Email:    email.Email,
 | 
				
			||||||
		Verified: email.IsActivated,
 | 
							Verified: email.IsActivated,
 | 
				
			||||||
@@ -35,12 +39,11 @@ func ToApiEmail(email *models.EmailAddress) *api.Email {
 | 
				
			|||||||
	}
 | 
						}
 | 
				
			||||||
}
 | 
					}
 | 
				
			||||||
 | 
					
 | 
				
			||||||
// ToApiRepository converts repository to API format.
 | 
					func ToRepository(owner *models.User, repo *models.Repository, permission api.Permission) *api.Repository {
 | 
				
			||||||
func ToApiRepository(owner *models.User, repo *models.Repository, permission api.Permission) *api.Repository {
 | 
					 | 
				
			||||||
	cl := repo.CloneLink()
 | 
						cl := repo.CloneLink()
 | 
				
			||||||
	return &api.Repository{
 | 
						return &api.Repository{
 | 
				
			||||||
		Id:          repo.ID,
 | 
							ID:          repo.ID,
 | 
				
			||||||
		Owner:       *ToApiUser(owner),
 | 
							Owner:       ToUser(owner),
 | 
				
			||||||
		FullName:    owner.Name + "/" + repo.Name,
 | 
							FullName:    owner.Name + "/" + repo.Name,
 | 
				
			||||||
		Private:     repo.IsPrivate,
 | 
							Private:     repo.IsPrivate,
 | 
				
			||||||
		Fork:        repo.IsFork,
 | 
							Fork:        repo.IsFork,
 | 
				
			||||||
@@ -51,30 +54,27 @@ func ToApiRepository(owner *models.User, repo *models.Repository, permission api
 | 
				
			|||||||
	}
 | 
						}
 | 
				
			||||||
}
 | 
					}
 | 
				
			||||||
 | 
					
 | 
				
			||||||
// ToApiBranch converts user to its API format.
 | 
					func ToBranch(b *models.Branch, c *git.Commit) *api.Branch {
 | 
				
			||||||
func ToApiBranch(b *models.Branch,c *git.Commit) *api.Branch {
 | 
					 | 
				
			||||||
	return &api.Branch{
 | 
						return &api.Branch{
 | 
				
			||||||
			Name: b.Name,
 | 
							Name:   b.Name,
 | 
				
			||||||
			Commit: ToApiCommit(c),
 | 
							Commit: ToCommit(c),
 | 
				
			||||||
		}
 | 
						}
 | 
				
			||||||
}
 | 
					}
 | 
				
			||||||
 | 
					
 | 
				
			||||||
// ToApiCommit converts user to its API format.
 | 
					func ToCommit(c *git.Commit) *api.PayloadCommit {
 | 
				
			||||||
func ToApiCommit(c *git.Commit) *api.PayloadCommit {
 | 
					 | 
				
			||||||
	return &api.PayloadCommit{
 | 
						return &api.PayloadCommit{
 | 
				
			||||||
		ID: c.ID.String(),
 | 
							ID:      c.ID.String(),
 | 
				
			||||||
		Message: c.Message(),
 | 
							Message: c.Message(),
 | 
				
			||||||
		URL: "Not implemented",
 | 
							URL:     "Not implemented",
 | 
				
			||||||
		Author: &api.PayloadAuthor{
 | 
							Author: &api.PayloadAuthor{
 | 
				
			||||||
			Name: c.Committer.Name,
 | 
								Name:  c.Committer.Name,
 | 
				
			||||||
			Email: c.Committer.Email,
 | 
								Email: c.Committer.Email,
 | 
				
			||||||
			/* UserName: c.Committer.UserName, */
 | 
								/* UserName: c.Committer.UserName, */
 | 
				
			||||||
		},
 | 
							},
 | 
				
			||||||
	}
 | 
						}
 | 
				
			||||||
}
 | 
					}
 | 
				
			||||||
 | 
					
 | 
				
			||||||
// ToApiPublicKey converts public key to its API format.
 | 
					func ToPublicKey(apiLink string, key *models.PublicKey) *api.PublicKey {
 | 
				
			||||||
func ToApiPublicKey(apiLink string, key *models.PublicKey) *api.PublicKey {
 | 
					 | 
				
			||||||
	return &api.PublicKey{
 | 
						return &api.PublicKey{
 | 
				
			||||||
		ID:      key.ID,
 | 
							ID:      key.ID,
 | 
				
			||||||
		Key:     key.Content,
 | 
							Key:     key.Content,
 | 
				
			||||||
@@ -84,8 +84,7 @@ func ToApiPublicKey(apiLink string, key *models.PublicKey) *api.PublicKey {
 | 
				
			|||||||
	}
 | 
						}
 | 
				
			||||||
}
 | 
					}
 | 
				
			||||||
 | 
					
 | 
				
			||||||
// ToApiHook converts webhook to its API format.
 | 
					func ToHook(repoLink string, w *models.Webhook) *api.Hook {
 | 
				
			||||||
func ToApiHook(repoLink string, w *models.Webhook) *api.Hook {
 | 
					 | 
				
			||||||
	config := map[string]string{
 | 
						config := map[string]string{
 | 
				
			||||||
		"url":          w.URL,
 | 
							"url":          w.URL,
 | 
				
			||||||
		"content_type": w.ContentType.Name(),
 | 
							"content_type": w.ContentType.Name(),
 | 
				
			||||||
@@ -110,8 +109,7 @@ func ToApiHook(repoLink string, w *models.Webhook) *api.Hook {
 | 
				
			|||||||
	}
 | 
						}
 | 
				
			||||||
}
 | 
					}
 | 
				
			||||||
 | 
					
 | 
				
			||||||
// ToApiDeployKey converts deploy key to its API format.
 | 
					func ToDeployKey(apiLink string, key *models.DeployKey) *api.DeployKey {
 | 
				
			||||||
func ToApiDeployKey(apiLink string, key *models.DeployKey) *api.DeployKey {
 | 
					 | 
				
			||||||
	return &api.DeployKey{
 | 
						return &api.DeployKey{
 | 
				
			||||||
		ID:       key.ID,
 | 
							ID:       key.ID,
 | 
				
			||||||
		Key:      key.Content,
 | 
							Key:      key.Content,
 | 
				
			||||||
@@ -122,7 +120,72 @@ func ToApiDeployKey(apiLink string, key *models.DeployKey) *api.DeployKey {
 | 
				
			|||||||
	}
 | 
						}
 | 
				
			||||||
}
 | 
					}
 | 
				
			||||||
 | 
					
 | 
				
			||||||
func ToApiOrganization(org *models.User) *api.Organization {
 | 
					func ToLabel(label *models.Label) *api.Label {
 | 
				
			||||||
 | 
						return &api.Label{
 | 
				
			||||||
 | 
							Name:  label.Name,
 | 
				
			||||||
 | 
							Color: label.Color,
 | 
				
			||||||
 | 
						}
 | 
				
			||||||
 | 
					}
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					func ToMilestone(milestone *models.Milestone) *api.Milestone {
 | 
				
			||||||
 | 
						if milestone == nil {
 | 
				
			||||||
 | 
							return nil
 | 
				
			||||||
 | 
						}
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
						apiMilestone := &api.Milestone{
 | 
				
			||||||
 | 
							ID:           milestone.ID,
 | 
				
			||||||
 | 
							State:        milestone.State(),
 | 
				
			||||||
 | 
							Title:        milestone.Name,
 | 
				
			||||||
 | 
							Description:  milestone.Content,
 | 
				
			||||||
 | 
							OpenIssues:   milestone.NumOpenIssues,
 | 
				
			||||||
 | 
							ClosedIssues: milestone.NumClosedIssues,
 | 
				
			||||||
 | 
						}
 | 
				
			||||||
 | 
						if milestone.IsClosed {
 | 
				
			||||||
 | 
							apiMilestone.Closed = &milestone.ClosedDate
 | 
				
			||||||
 | 
						}
 | 
				
			||||||
 | 
						if milestone.Deadline.Year() < 9999 {
 | 
				
			||||||
 | 
							apiMilestone.Deadline = &milestone.Deadline
 | 
				
			||||||
 | 
						}
 | 
				
			||||||
 | 
						return apiMilestone
 | 
				
			||||||
 | 
					}
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					func ToIssue(issue *models.Issue) *api.Issue {
 | 
				
			||||||
 | 
						apiLabels := make([]*api.Label, len(issue.Labels))
 | 
				
			||||||
 | 
						for i := range issue.Labels {
 | 
				
			||||||
 | 
							apiLabels[i] = ToLabel(issue.Labels[i])
 | 
				
			||||||
 | 
						}
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
						apiIssue := &api.Issue{
 | 
				
			||||||
 | 
							ID:        issue.ID,
 | 
				
			||||||
 | 
							Index:     issue.Index,
 | 
				
			||||||
 | 
							State:     issue.State(),
 | 
				
			||||||
 | 
							Title:     issue.Name,
 | 
				
			||||||
 | 
							Body:      issue.Content,
 | 
				
			||||||
 | 
							User:      ToUser(issue.Poster),
 | 
				
			||||||
 | 
							Labels:    apiLabels,
 | 
				
			||||||
 | 
							Assignee:  ToUser(issue.Assignee),
 | 
				
			||||||
 | 
							Milestone: ToMilestone(issue.Milestone),
 | 
				
			||||||
 | 
							Comments:  issue.NumComments,
 | 
				
			||||||
 | 
							Created:   issue.Created,
 | 
				
			||||||
 | 
							Updated:   issue.Updated,
 | 
				
			||||||
 | 
						}
 | 
				
			||||||
 | 
						if issue.IsPull {
 | 
				
			||||||
 | 
							if err := issue.GetPullRequest(); err != nil {
 | 
				
			||||||
 | 
								log.Error(4, "GetPullRequest", err)
 | 
				
			||||||
 | 
							} else {
 | 
				
			||||||
 | 
								apiIssue.PullRequest = &api.PullRequestMeta{
 | 
				
			||||||
 | 
									HasMerged: issue.PullRequest.HasMerged,
 | 
				
			||||||
 | 
								}
 | 
				
			||||||
 | 
								if issue.PullRequest.HasMerged {
 | 
				
			||||||
 | 
									apiIssue.PullRequest.Merged = &issue.PullRequest.Merged
 | 
				
			||||||
 | 
								}
 | 
				
			||||||
 | 
							}
 | 
				
			||||||
 | 
						}
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
						return apiIssue
 | 
				
			||||||
 | 
					}
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					func ToOrganization(org *models.User) *api.Organization {
 | 
				
			||||||
	return &api.Organization{
 | 
						return &api.Organization{
 | 
				
			||||||
		ID:          org.Id,
 | 
							ID:          org.Id,
 | 
				
			||||||
		AvatarUrl:   org.AvatarLink(),
 | 
							AvatarUrl:   org.AvatarLink(),
 | 
				
			||||||
 
 | 
				
			|||||||
@@ -21,7 +21,7 @@ func listUserOrgs(ctx *context.APIContext, u *models.User, all bool) {
 | 
				
			|||||||
 | 
					
 | 
				
			||||||
	apiOrgs := make([]*api.Organization, len(u.Orgs))
 | 
						apiOrgs := make([]*api.Organization, len(u.Orgs))
 | 
				
			||||||
	for i := range u.Orgs {
 | 
						for i := range u.Orgs {
 | 
				
			||||||
		apiOrgs[i] = convert.ToApiOrganization(u.Orgs[i])
 | 
							apiOrgs[i] = convert.ToOrganization(u.Orgs[i])
 | 
				
			||||||
	}
 | 
						}
 | 
				
			||||||
	ctx.JSON(200, &apiOrgs)
 | 
						ctx.JSON(200, &apiOrgs)
 | 
				
			||||||
}
 | 
					}
 | 
				
			||||||
@@ -46,7 +46,7 @@ func Get(ctx *context.APIContext) {
 | 
				
			|||||||
	if ctx.Written() {
 | 
						if ctx.Written() {
 | 
				
			||||||
		return
 | 
							return
 | 
				
			||||||
	}
 | 
						}
 | 
				
			||||||
	ctx.JSON(200, convert.ToApiOrganization(org))
 | 
						ctx.JSON(200, convert.ToOrganization(org))
 | 
				
			||||||
}
 | 
					}
 | 
				
			||||||
 | 
					
 | 
				
			||||||
// https://github.com/gogits/go-gogs-client/wiki/Organizations#edit-an-organization
 | 
					// https://github.com/gogits/go-gogs-client/wiki/Organizations#edit-an-organization
 | 
				
			||||||
@@ -70,5 +70,5 @@ func Edit(ctx *context.APIContext, form api.EditOrgOption) {
 | 
				
			|||||||
		return
 | 
							return
 | 
				
			||||||
	}
 | 
						}
 | 
				
			||||||
 | 
					
 | 
				
			||||||
	ctx.JSON(200, convert.ToApiOrganization(org))
 | 
						ctx.JSON(200, convert.ToOrganization(org))
 | 
				
			||||||
}
 | 
					}
 | 
				
			||||||
 
 | 
				
			|||||||
@@ -25,7 +25,7 @@ func GetBranch(ctx *context.APIContext) {
 | 
				
			|||||||
		return
 | 
							return
 | 
				
			||||||
	}
 | 
						}
 | 
				
			||||||
 | 
					
 | 
				
			||||||
	ctx.JSON(200, convert.ToApiBranch(branch, c))
 | 
						ctx.JSON(200, convert.ToBranch(branch, c))
 | 
				
			||||||
}
 | 
					}
 | 
				
			||||||
 | 
					
 | 
				
			||||||
// https://github.com/gogits/go-gogs-client/wiki/Repositories#list-branches
 | 
					// https://github.com/gogits/go-gogs-client/wiki/Repositories#list-branches
 | 
				
			||||||
@@ -43,7 +43,7 @@ func ListBranches(ctx *context.APIContext) {
 | 
				
			|||||||
			ctx.Error(500, "GetCommit", err)
 | 
								ctx.Error(500, "GetCommit", err)
 | 
				
			||||||
			return
 | 
								return
 | 
				
			||||||
		}
 | 
							}
 | 
				
			||||||
		apiBranches[i] = convert.ToApiBranch(branches[i], c)
 | 
							apiBranches[i] = convert.ToBranch(branches[i], c)
 | 
				
			||||||
	}
 | 
						}
 | 
				
			||||||
 | 
					
 | 
				
			||||||
	ctx.JSON(200, &apiBranches)
 | 
						ctx.JSON(200, &apiBranches)
 | 
				
			||||||
 
 | 
				
			|||||||
@@ -26,9 +26,8 @@ func ListHooks(ctx *context.APIContext) {
 | 
				
			|||||||
 | 
					
 | 
				
			||||||
	apiHooks := make([]*api.Hook, len(hooks))
 | 
						apiHooks := make([]*api.Hook, len(hooks))
 | 
				
			||||||
	for i := range hooks {
 | 
						for i := range hooks {
 | 
				
			||||||
		apiHooks[i] = convert.ToApiHook(ctx.Repo.RepoLink, hooks[i])
 | 
							apiHooks[i] = convert.ToHook(ctx.Repo.RepoLink, hooks[i])
 | 
				
			||||||
	}
 | 
						}
 | 
				
			||||||
 | 
					 | 
				
			||||||
	ctx.JSON(200, &apiHooks)
 | 
						ctx.JSON(200, &apiHooks)
 | 
				
			||||||
}
 | 
					}
 | 
				
			||||||
 | 
					
 | 
				
			||||||
@@ -94,7 +93,7 @@ func CreateHook(ctx *context.APIContext, form api.CreateHookOption) {
 | 
				
			|||||||
		return
 | 
							return
 | 
				
			||||||
	}
 | 
						}
 | 
				
			||||||
 | 
					
 | 
				
			||||||
	ctx.JSON(201, convert.ToApiHook(ctx.Repo.RepoLink, w))
 | 
						ctx.JSON(201, convert.ToHook(ctx.Repo.RepoLink, w))
 | 
				
			||||||
}
 | 
					}
 | 
				
			||||||
 | 
					
 | 
				
			||||||
// https://github.com/gogits/go-gogs-client/wiki/Repositories#edit-a-hook
 | 
					// https://github.com/gogits/go-gogs-client/wiki/Repositories#edit-a-hook
 | 
				
			||||||
@@ -161,5 +160,5 @@ func EditHook(ctx *context.APIContext, form api.EditHookOption) {
 | 
				
			|||||||
		return
 | 
							return
 | 
				
			||||||
	}
 | 
						}
 | 
				
			||||||
 | 
					
 | 
				
			||||||
	ctx.JSON(200, convert.ToApiHook(ctx.Repo.RepoLink, w))
 | 
						ctx.JSON(200, convert.ToHook(ctx.Repo.RepoLink, w))
 | 
				
			||||||
}
 | 
					}
 | 
				
			||||||
 
 | 
				
			|||||||
							
								
								
									
										165
									
								
								routers/api/v1/repo/issue.go
									
									
									
									
									
										Normal file
									
								
							
							
						
						
									
										165
									
								
								routers/api/v1/repo/issue.go
									
									
									
									
									
										Normal file
									
								
							@@ -0,0 +1,165 @@
 | 
				
			|||||||
 | 
					// Copyright 2016 The Gogs Authors. All rights reserved.
 | 
				
			||||||
 | 
					// Use of this source code is governed by a MIT-style
 | 
				
			||||||
 | 
					// license that can be found in the LICENSE file.
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					package repo
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					import (
 | 
				
			||||||
 | 
						"fmt"
 | 
				
			||||||
 | 
						"strings"
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
						api "github.com/gogits/go-gogs-client"
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
						"github.com/gogits/gogs/models"
 | 
				
			||||||
 | 
						"github.com/gogits/gogs/modules/context"
 | 
				
			||||||
 | 
						"github.com/gogits/gogs/modules/setting"
 | 
				
			||||||
 | 
						"github.com/gogits/gogs/routers/api/v1/convert"
 | 
				
			||||||
 | 
						"github.com/gogits/gogs/routers/repo"
 | 
				
			||||||
 | 
					)
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					func ListIssues(ctx *context.APIContext) {
 | 
				
			||||||
 | 
						issues, err := models.Issues(&models.IssuesOptions{
 | 
				
			||||||
 | 
							RepoID: ctx.Repo.Repository.ID,
 | 
				
			||||||
 | 
							Page:   ctx.QueryInt("page"),
 | 
				
			||||||
 | 
						})
 | 
				
			||||||
 | 
						if err != nil {
 | 
				
			||||||
 | 
							ctx.Error(500, "Issues", err)
 | 
				
			||||||
 | 
							return
 | 
				
			||||||
 | 
						}
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
						apiIssues := make([]*api.Issue, len(issues))
 | 
				
			||||||
 | 
						for i := range issues {
 | 
				
			||||||
 | 
							apiIssues[i] = convert.ToIssue(issues[i])
 | 
				
			||||||
 | 
						}
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
						ctx.SetLinkHeader(ctx.Repo.Repository.NumIssues, setting.IssuePagingNum)
 | 
				
			||||||
 | 
						ctx.JSON(200, &apiIssues)
 | 
				
			||||||
 | 
					}
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					func GetIssue(ctx *context.APIContext) {
 | 
				
			||||||
 | 
						issue, err := models.GetIssueByIndex(ctx.Repo.Repository.ID, ctx.ParamsInt64(":index"))
 | 
				
			||||||
 | 
						if err != nil {
 | 
				
			||||||
 | 
							if models.IsErrIssueNotExist(err) {
 | 
				
			||||||
 | 
								ctx.Status(404)
 | 
				
			||||||
 | 
							} else {
 | 
				
			||||||
 | 
								ctx.Error(500, "GetIssueByIndex", err)
 | 
				
			||||||
 | 
							}
 | 
				
			||||||
 | 
							return
 | 
				
			||||||
 | 
						}
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
						ctx.JSON(200, convert.ToIssue(issue))
 | 
				
			||||||
 | 
					}
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					func CreateIssue(ctx *context.APIContext, form api.CreateIssueOption) {
 | 
				
			||||||
 | 
						issue := &models.Issue{
 | 
				
			||||||
 | 
							RepoID:   ctx.Repo.Repository.ID,
 | 
				
			||||||
 | 
							Name:     form.Title,
 | 
				
			||||||
 | 
							PosterID: ctx.User.Id,
 | 
				
			||||||
 | 
							Poster:   ctx.User,
 | 
				
			||||||
 | 
							Content:  form.Body,
 | 
				
			||||||
 | 
						}
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
						if ctx.Repo.IsWriter() {
 | 
				
			||||||
 | 
							if len(form.Assignee) > 0 {
 | 
				
			||||||
 | 
								assignee, err := models.GetUserByName(form.Assignee)
 | 
				
			||||||
 | 
								if err != nil {
 | 
				
			||||||
 | 
									if models.IsErrUserNotExist(err) {
 | 
				
			||||||
 | 
										ctx.Error(422, "", fmt.Sprintf("Assignee does not exist: [name: %s]", form.Assignee))
 | 
				
			||||||
 | 
									} else {
 | 
				
			||||||
 | 
										ctx.Error(500, "GetUserByName", err)
 | 
				
			||||||
 | 
									}
 | 
				
			||||||
 | 
									return
 | 
				
			||||||
 | 
								}
 | 
				
			||||||
 | 
								issue.AssigneeID = assignee.Id
 | 
				
			||||||
 | 
							}
 | 
				
			||||||
 | 
							issue.MilestoneID = form.Milestone
 | 
				
			||||||
 | 
						} else {
 | 
				
			||||||
 | 
							form.Labels = nil
 | 
				
			||||||
 | 
						}
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
						if err := models.NewIssue(ctx.Repo.Repository, issue, form.Labels, nil); err != nil {
 | 
				
			||||||
 | 
							ctx.Error(500, "NewIssue", err)
 | 
				
			||||||
 | 
							return
 | 
				
			||||||
 | 
						} else if err := repo.MailWatchersAndMentions(ctx.Context, issue); err != nil {
 | 
				
			||||||
 | 
							ctx.Error(500, "MailWatchersAndMentions", err)
 | 
				
			||||||
 | 
							return
 | 
				
			||||||
 | 
						}
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
						// Refetch from database to assign some automatic values
 | 
				
			||||||
 | 
						var err error
 | 
				
			||||||
 | 
						issue, err = models.GetIssueByID(issue.ID)
 | 
				
			||||||
 | 
						if err != nil {
 | 
				
			||||||
 | 
							ctx.Error(500, "GetIssueByID", err)
 | 
				
			||||||
 | 
							return
 | 
				
			||||||
 | 
						}
 | 
				
			||||||
 | 
						ctx.JSON(201, convert.ToIssue(issue))
 | 
				
			||||||
 | 
					}
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					func EditIssue(ctx *context.APIContext, form api.EditIssueOption) {
 | 
				
			||||||
 | 
						issue, err := models.GetIssueByIndex(ctx.Repo.Repository.ID, ctx.ParamsInt64(":index"))
 | 
				
			||||||
 | 
						if err != nil {
 | 
				
			||||||
 | 
							if models.IsErrIssueNotExist(err) {
 | 
				
			||||||
 | 
								ctx.Status(404)
 | 
				
			||||||
 | 
							} else {
 | 
				
			||||||
 | 
								ctx.Error(500, "GetIssueByIndex", err)
 | 
				
			||||||
 | 
							}
 | 
				
			||||||
 | 
							return
 | 
				
			||||||
 | 
						}
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
						if !issue.IsPoster(ctx.User.Id) && !ctx.Repo.IsWriter() {
 | 
				
			||||||
 | 
							ctx.Status(403)
 | 
				
			||||||
 | 
							return
 | 
				
			||||||
 | 
						}
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
						if len(form.Title) > 0 {
 | 
				
			||||||
 | 
							issue.Name = form.Title
 | 
				
			||||||
 | 
						}
 | 
				
			||||||
 | 
						if form.Body != nil {
 | 
				
			||||||
 | 
							issue.Content = *form.Body
 | 
				
			||||||
 | 
						}
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
						if ctx.Repo.IsWriter() && form.Assignee != nil &&
 | 
				
			||||||
 | 
							(issue.Assignee == nil || issue.Assignee.LowerName != strings.ToLower(*form.Assignee)) {
 | 
				
			||||||
 | 
							if len(*form.Assignee) == 0 {
 | 
				
			||||||
 | 
								issue.AssigneeID = 0
 | 
				
			||||||
 | 
							} else {
 | 
				
			||||||
 | 
								assignee, err := models.GetUserByName(*form.Assignee)
 | 
				
			||||||
 | 
								if err != nil {
 | 
				
			||||||
 | 
									if models.IsErrUserNotExist(err) {
 | 
				
			||||||
 | 
										ctx.Error(422, "", fmt.Sprintf("Assignee does not exist: [name: %s]", *form.Assignee))
 | 
				
			||||||
 | 
									} else {
 | 
				
			||||||
 | 
										ctx.Error(500, "GetUserByName", err)
 | 
				
			||||||
 | 
									}
 | 
				
			||||||
 | 
									return
 | 
				
			||||||
 | 
								}
 | 
				
			||||||
 | 
								issue.AssigneeID = assignee.Id
 | 
				
			||||||
 | 
							}
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
							if err = models.UpdateIssueUserByAssignee(issue); err != nil {
 | 
				
			||||||
 | 
								ctx.Error(500, "UpdateIssueUserByAssignee", err)
 | 
				
			||||||
 | 
								return
 | 
				
			||||||
 | 
							}
 | 
				
			||||||
 | 
						}
 | 
				
			||||||
 | 
						if ctx.Repo.IsWriter() && form.Milestone != nil &&
 | 
				
			||||||
 | 
							issue.MilestoneID != *form.Milestone {
 | 
				
			||||||
 | 
							oldMid := issue.MilestoneID
 | 
				
			||||||
 | 
							issue.MilestoneID = *form.Milestone
 | 
				
			||||||
 | 
							if err = models.ChangeMilestoneAssign(oldMid, issue); err != nil {
 | 
				
			||||||
 | 
								ctx.Error(500, "ChangeMilestoneAssign", err)
 | 
				
			||||||
 | 
								return
 | 
				
			||||||
 | 
							}
 | 
				
			||||||
 | 
						}
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
						if err = models.UpdateIssue(issue); err != nil {
 | 
				
			||||||
 | 
							ctx.Error(500, "UpdateIssue", err)
 | 
				
			||||||
 | 
							return
 | 
				
			||||||
 | 
						}
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
						// Refetch from database to assign some automatic values
 | 
				
			||||||
 | 
						issue, err = models.GetIssueByID(issue.ID)
 | 
				
			||||||
 | 
						if err != nil {
 | 
				
			||||||
 | 
							ctx.Error(500, "GetIssueByID", err)
 | 
				
			||||||
 | 
							return
 | 
				
			||||||
 | 
						}
 | 
				
			||||||
 | 
						ctx.JSON(201, convert.ToIssue(issue))
 | 
				
			||||||
 | 
					}
 | 
				
			||||||
@@ -34,7 +34,7 @@ func ListDeployKeys(ctx *context.APIContext) {
 | 
				
			|||||||
			ctx.Error(500, "GetContent", err)
 | 
								ctx.Error(500, "GetContent", err)
 | 
				
			||||||
			return
 | 
								return
 | 
				
			||||||
		}
 | 
							}
 | 
				
			||||||
		apiKeys[i] = convert.ToApiDeployKey(apiLink, keys[i])
 | 
							apiKeys[i] = convert.ToDeployKey(apiLink, keys[i])
 | 
				
			||||||
	}
 | 
						}
 | 
				
			||||||
 | 
					
 | 
				
			||||||
	ctx.JSON(200, &apiKeys)
 | 
						ctx.JSON(200, &apiKeys)
 | 
				
			||||||
@@ -58,7 +58,7 @@ func GetDeployKey(ctx *context.APIContext) {
 | 
				
			|||||||
	}
 | 
						}
 | 
				
			||||||
 | 
					
 | 
				
			||||||
	apiLink := composeDeployKeysAPILink(ctx.Repo.Owner.Name + "/" + ctx.Repo.Repository.Name)
 | 
						apiLink := composeDeployKeysAPILink(ctx.Repo.Owner.Name + "/" + ctx.Repo.Repository.Name)
 | 
				
			||||||
	ctx.JSON(200, convert.ToApiDeployKey(apiLink, key))
 | 
						ctx.JSON(200, convert.ToDeployKey(apiLink, key))
 | 
				
			||||||
}
 | 
					}
 | 
				
			||||||
 | 
					
 | 
				
			||||||
func HandleCheckKeyStringError(ctx *context.APIContext, err error) {
 | 
					func HandleCheckKeyStringError(ctx *context.APIContext, err error) {
 | 
				
			||||||
@@ -96,7 +96,7 @@ func CreateDeployKey(ctx *context.APIContext, form api.CreateKeyOption) {
 | 
				
			|||||||
 | 
					
 | 
				
			||||||
	key.Content = content
 | 
						key.Content = content
 | 
				
			||||||
	apiLink := composeDeployKeysAPILink(ctx.Repo.Owner.Name + "/" + ctx.Repo.Repository.Name)
 | 
						apiLink := composeDeployKeysAPILink(ctx.Repo.Owner.Name + "/" + ctx.Repo.Repository.Name)
 | 
				
			||||||
	ctx.JSON(201, convert.ToApiDeployKey(apiLink, key))
 | 
						ctx.JSON(201, convert.ToDeployKey(apiLink, key))
 | 
				
			||||||
}
 | 
					}
 | 
				
			||||||
 | 
					
 | 
				
			||||||
// https://github.com/gogits/go-gogs-client/wiki/Repositories-Deploy-Keys#remove-a-deploy-key
 | 
					// https://github.com/gogits/go-gogs-client/wiki/Repositories-Deploy-Keys#remove-a-deploy-key
 | 
				
			||||||
 
 | 
				
			|||||||
@@ -69,7 +69,7 @@ func Search(ctx *context.APIContext) {
 | 
				
			|||||||
			return
 | 
								return
 | 
				
			||||||
		}
 | 
							}
 | 
				
			||||||
		results[i] = &api.Repository{
 | 
							results[i] = &api.Repository{
 | 
				
			||||||
			Id:       repos[i].ID,
 | 
								ID:       repos[i].ID,
 | 
				
			||||||
			FullName: path.Join(repos[i].Owner.Name, repos[i].Name),
 | 
								FullName: path.Join(repos[i].Owner.Name, repos[i].Name),
 | 
				
			||||||
		}
 | 
							}
 | 
				
			||||||
	}
 | 
						}
 | 
				
			||||||
@@ -97,12 +97,12 @@ func ListMyRepos(ctx *context.APIContext) {
 | 
				
			|||||||
 | 
					
 | 
				
			||||||
	repos := make([]*api.Repository, numOwnRepos+len(accessibleRepos))
 | 
						repos := make([]*api.Repository, numOwnRepos+len(accessibleRepos))
 | 
				
			||||||
	for i := range ownRepos {
 | 
						for i := range ownRepos {
 | 
				
			||||||
		repos[i] = convert.ToApiRepository(ctx.User, ownRepos[i], api.Permission{true, true, true})
 | 
							repos[i] = convert.ToRepository(ctx.User, ownRepos[i], api.Permission{true, true, true})
 | 
				
			||||||
	}
 | 
						}
 | 
				
			||||||
	i := numOwnRepos
 | 
						i := numOwnRepos
 | 
				
			||||||
 | 
					
 | 
				
			||||||
	for repo, access := range accessibleRepos {
 | 
						for repo, access := range accessibleRepos {
 | 
				
			||||||
		repos[i] = convert.ToApiRepository(repo.Owner, repo, api.Permission{
 | 
							repos[i] = convert.ToRepository(repo.Owner, repo, api.Permission{
 | 
				
			||||||
			Admin: access >= models.ACCESS_MODE_ADMIN,
 | 
								Admin: access >= models.ACCESS_MODE_ADMIN,
 | 
				
			||||||
			Push:  access >= models.ACCESS_MODE_WRITE,
 | 
								Push:  access >= models.ACCESS_MODE_WRITE,
 | 
				
			||||||
			Pull:  true,
 | 
								Pull:  true,
 | 
				
			||||||
@@ -139,7 +139,7 @@ func CreateUserRepo(ctx *context.APIContext, owner *models.User, opt api.CreateR
 | 
				
			|||||||
		return
 | 
							return
 | 
				
			||||||
	}
 | 
						}
 | 
				
			||||||
 | 
					
 | 
				
			||||||
	ctx.JSON(201, convert.ToApiRepository(owner, repo, api.Permission{true, true, true}))
 | 
						ctx.JSON(201, convert.ToRepository(owner, repo, api.Permission{true, true, true}))
 | 
				
			||||||
}
 | 
					}
 | 
				
			||||||
 | 
					
 | 
				
			||||||
// https://github.com/gogits/go-gogs-client/wiki/Repositories#create
 | 
					// https://github.com/gogits/go-gogs-client/wiki/Repositories#create
 | 
				
			||||||
@@ -239,7 +239,7 @@ func Migrate(ctx *context.APIContext, form auth.MigrateRepoForm) {
 | 
				
			|||||||
	}
 | 
						}
 | 
				
			||||||
 | 
					
 | 
				
			||||||
	log.Trace("Repository migrated: %s/%s", ctxUser.Name, form.RepoName)
 | 
						log.Trace("Repository migrated: %s/%s", ctxUser.Name, form.RepoName)
 | 
				
			||||||
	ctx.JSON(201, convert.ToApiRepository(ctxUser, repo, api.Permission{true, true, true}))
 | 
						ctx.JSON(201, convert.ToRepository(ctxUser, repo, api.Permission{true, true, true}))
 | 
				
			||||||
}
 | 
					}
 | 
				
			||||||
 | 
					
 | 
				
			||||||
func parseOwnerAndRepo(ctx *context.APIContext) (*models.User, *models.Repository) {
 | 
					func parseOwnerAndRepo(ctx *context.APIContext) (*models.User, *models.Repository) {
 | 
				
			||||||
@@ -273,7 +273,7 @@ func Get(ctx *context.APIContext) {
 | 
				
			|||||||
		return
 | 
							return
 | 
				
			||||||
	}
 | 
						}
 | 
				
			||||||
 | 
					
 | 
				
			||||||
	ctx.JSON(200, convert.ToApiRepository(owner, repo, api.Permission{true, true, true}))
 | 
						ctx.JSON(200, convert.ToRepository(owner, repo, api.Permission{true, true, true}))
 | 
				
			||||||
}
 | 
					}
 | 
				
			||||||
 | 
					
 | 
				
			||||||
// https://github.com/gogits/go-gogs-client/wiki/Repositories#delete
 | 
					// https://github.com/gogits/go-gogs-client/wiki/Repositories#delete
 | 
				
			||||||
 
 | 
				
			|||||||
@@ -22,7 +22,7 @@ func ListEmails(ctx *context.APIContext) {
 | 
				
			|||||||
	}
 | 
						}
 | 
				
			||||||
	apiEmails := make([]*api.Email, len(emails))
 | 
						apiEmails := make([]*api.Email, len(emails))
 | 
				
			||||||
	for i := range emails {
 | 
						for i := range emails {
 | 
				
			||||||
		apiEmails[i] = convert.ToApiEmail(emails[i])
 | 
							apiEmails[i] = convert.ToEmail(emails[i])
 | 
				
			||||||
	}
 | 
						}
 | 
				
			||||||
	ctx.JSON(200, &apiEmails)
 | 
						ctx.JSON(200, &apiEmails)
 | 
				
			||||||
}
 | 
					}
 | 
				
			||||||
@@ -54,7 +54,7 @@ func AddEmail(ctx *context.APIContext, form api.CreateEmailOption) {
 | 
				
			|||||||
 | 
					
 | 
				
			||||||
	apiEmails := make([]*api.Email, len(emails))
 | 
						apiEmails := make([]*api.Email, len(emails))
 | 
				
			||||||
	for i := range emails {
 | 
						for i := range emails {
 | 
				
			||||||
		apiEmails[i] = convert.ToApiEmail(emails[i])
 | 
							apiEmails[i] = convert.ToEmail(emails[i])
 | 
				
			||||||
	}
 | 
						}
 | 
				
			||||||
	ctx.JSON(201, &apiEmails)
 | 
						ctx.JSON(201, &apiEmails)
 | 
				
			||||||
}
 | 
					}
 | 
				
			||||||
 
 | 
				
			|||||||
@@ -15,7 +15,7 @@ import (
 | 
				
			|||||||
func responseApiUsers(ctx *context.APIContext, users []*models.User) {
 | 
					func responseApiUsers(ctx *context.APIContext, users []*models.User) {
 | 
				
			||||||
	apiUsers := make([]*api.User, len(users))
 | 
						apiUsers := make([]*api.User, len(users))
 | 
				
			||||||
	for i := range users {
 | 
						for i := range users {
 | 
				
			||||||
		apiUsers[i] = convert.ToApiUser(users[i])
 | 
							apiUsers[i] = convert.ToUser(users[i])
 | 
				
			||||||
	}
 | 
						}
 | 
				
			||||||
	ctx.JSON(200, &apiUsers)
 | 
						ctx.JSON(200, &apiUsers)
 | 
				
			||||||
}
 | 
					}
 | 
				
			||||||
 
 | 
				
			|||||||
@@ -46,7 +46,7 @@ func listPublicKeys(ctx *context.APIContext, uid int64) {
 | 
				
			|||||||
	apiLink := composePublicKeysAPILink()
 | 
						apiLink := composePublicKeysAPILink()
 | 
				
			||||||
	apiKeys := make([]*api.PublicKey, len(keys))
 | 
						apiKeys := make([]*api.PublicKey, len(keys))
 | 
				
			||||||
	for i := range keys {
 | 
						for i := range keys {
 | 
				
			||||||
		apiKeys[i] = convert.ToApiPublicKey(apiLink, keys[i])
 | 
							apiKeys[i] = convert.ToPublicKey(apiLink, keys[i])
 | 
				
			||||||
	}
 | 
						}
 | 
				
			||||||
 | 
					
 | 
				
			||||||
	ctx.JSON(200, &apiKeys)
 | 
						ctx.JSON(200, &apiKeys)
 | 
				
			||||||
@@ -79,7 +79,7 @@ func GetPublicKey(ctx *context.APIContext) {
 | 
				
			|||||||
	}
 | 
						}
 | 
				
			||||||
 | 
					
 | 
				
			||||||
	apiLink := composePublicKeysAPILink()
 | 
						apiLink := composePublicKeysAPILink()
 | 
				
			||||||
	ctx.JSON(200, convert.ToApiPublicKey(apiLink, key))
 | 
						ctx.JSON(200, convert.ToPublicKey(apiLink, key))
 | 
				
			||||||
}
 | 
					}
 | 
				
			||||||
 | 
					
 | 
				
			||||||
// CreateUserPublicKey creates new public key to given user by ID.
 | 
					// CreateUserPublicKey creates new public key to given user by ID.
 | 
				
			||||||
@@ -96,7 +96,7 @@ func CreateUserPublicKey(ctx *context.APIContext, form api.CreateKeyOption, uid
 | 
				
			|||||||
		return
 | 
							return
 | 
				
			||||||
	}
 | 
						}
 | 
				
			||||||
	apiLink := composePublicKeysAPILink()
 | 
						apiLink := composePublicKeysAPILink()
 | 
				
			||||||
	ctx.JSON(201, convert.ToApiPublicKey(apiLink, key))
 | 
						ctx.JSON(201, convert.ToPublicKey(apiLink, key))
 | 
				
			||||||
}
 | 
					}
 | 
				
			||||||
 | 
					
 | 
				
			||||||
// https://github.com/gogits/go-gogs-client/wiki/Users-Public-Keys#create-a-public-key
 | 
					// https://github.com/gogits/go-gogs-client/wiki/Users-Public-Keys#create-a-public-key
 | 
				
			||||||
 
 | 
				
			|||||||
@@ -195,16 +195,6 @@ func Issues(ctx *context.Context) {
 | 
				
			|||||||
 | 
					
 | 
				
			||||||
	// Get posters.
 | 
						// Get posters.
 | 
				
			||||||
	for i := range issues {
 | 
						for i := range issues {
 | 
				
			||||||
		if err = issues[i].GetPoster(); err != nil {
 | 
					 | 
				
			||||||
			ctx.Handle(500, "GetPoster", fmt.Errorf("[#%d]%v", issues[i].ID, err))
 | 
					 | 
				
			||||||
			return
 | 
					 | 
				
			||||||
		}
 | 
					 | 
				
			||||||
 | 
					 | 
				
			||||||
		if err = issues[i].GetLabels(); err != nil {
 | 
					 | 
				
			||||||
			ctx.Handle(500, "GetLabels", fmt.Errorf("[#%d]%v", issues[i].ID, err))
 | 
					 | 
				
			||||||
			return
 | 
					 | 
				
			||||||
		}
 | 
					 | 
				
			||||||
 | 
					 | 
				
			||||||
		if !ctx.IsSigned {
 | 
							if !ctx.IsSigned {
 | 
				
			||||||
			issues[i].IsRead = true
 | 
								issues[i].IsRead = true
 | 
				
			||||||
			continue
 | 
								continue
 | 
				
			||||||
@@ -405,7 +395,7 @@ func ValidateRepoMetas(ctx *context.Context, form auth.CreateIssueForm) ([]int64
 | 
				
			|||||||
	return labelIDs, milestoneID, assigneeID
 | 
						return labelIDs, milestoneID, assigneeID
 | 
				
			||||||
}
 | 
					}
 | 
				
			||||||
 | 
					
 | 
				
			||||||
func notifyWatchersAndMentions(ctx *context.Context, issue *models.Issue) {
 | 
					func MailWatchersAndMentions(ctx *context.Context, issue *models.Issue) error {
 | 
				
			||||||
	// Update mentions
 | 
						// Update mentions
 | 
				
			||||||
	mentions := markdown.MentionPattern.FindAllString(issue.Content, -1)
 | 
						mentions := markdown.MentionPattern.FindAllString(issue.Content, -1)
 | 
				
			||||||
	if len(mentions) > 0 {
 | 
						if len(mentions) > 0 {
 | 
				
			||||||
@@ -414,8 +404,7 @@ func notifyWatchersAndMentions(ctx *context.Context, issue *models.Issue) {
 | 
				
			|||||||
		}
 | 
							}
 | 
				
			||||||
 | 
					
 | 
				
			||||||
		if err := models.UpdateMentions(mentions, issue.ID); err != nil {
 | 
							if err := models.UpdateMentions(mentions, issue.ID); err != nil {
 | 
				
			||||||
			ctx.Handle(500, "UpdateMentions", err)
 | 
								return fmt.Errorf("UpdateMentions: %v", err)
 | 
				
			||||||
			return
 | 
					 | 
				
			||||||
		}
 | 
							}
 | 
				
			||||||
	}
 | 
						}
 | 
				
			||||||
 | 
					
 | 
				
			||||||
@@ -425,8 +414,7 @@ func notifyWatchersAndMentions(ctx *context.Context, issue *models.Issue) {
 | 
				
			|||||||
	if setting.Service.EnableNotifyMail {
 | 
						if setting.Service.EnableNotifyMail {
 | 
				
			||||||
		tos, err := mailer.SendIssueNotifyMail(ctx.User, ctx.Repo.Owner, repo, issue)
 | 
							tos, err := mailer.SendIssueNotifyMail(ctx.User, ctx.Repo.Owner, repo, issue)
 | 
				
			||||||
		if err != nil {
 | 
							if err != nil {
 | 
				
			||||||
			ctx.Handle(500, "SendIssueNotifyMail", err)
 | 
								return fmt.Errorf("SendIssueNotifyMail: %v", err)
 | 
				
			||||||
			return
 | 
					 | 
				
			||||||
		}
 | 
							}
 | 
				
			||||||
 | 
					
 | 
				
			||||||
		tos = append(tos, ctx.User.LowerName)
 | 
							tos = append(tos, ctx.User.LowerName)
 | 
				
			||||||
@@ -440,10 +428,11 @@ func notifyWatchersAndMentions(ctx *context.Context, issue *models.Issue) {
 | 
				
			|||||||
		}
 | 
							}
 | 
				
			||||||
		if err = mailer.SendIssueMentionMail(ctx.Render, ctx.User, ctx.Repo.Owner,
 | 
							if err = mailer.SendIssueMentionMail(ctx.Render, ctx.User, ctx.Repo.Owner,
 | 
				
			||||||
			repo, issue, models.GetUserEmailsByNames(newTos)); err != nil {
 | 
								repo, issue, models.GetUserEmailsByNames(newTos)); err != nil {
 | 
				
			||||||
			ctx.Handle(500, "SendIssueMentionMail", err)
 | 
								return fmt.Errorf("SendIssueMentionMail: %v", err)
 | 
				
			||||||
			return
 | 
					 | 
				
			||||||
		}
 | 
							}
 | 
				
			||||||
	}
 | 
						}
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
						return nil
 | 
				
			||||||
}
 | 
					}
 | 
				
			||||||
 | 
					
 | 
				
			||||||
func NewIssuePost(ctx *context.Context, form auth.CreateIssueForm) {
 | 
					func NewIssuePost(ctx *context.Context, form auth.CreateIssueForm) {
 | 
				
			||||||
@@ -471,9 +460,8 @@ func NewIssuePost(ctx *context.Context, form auth.CreateIssueForm) {
 | 
				
			|||||||
	}
 | 
						}
 | 
				
			||||||
 | 
					
 | 
				
			||||||
	issue := &models.Issue{
 | 
						issue := &models.Issue{
 | 
				
			||||||
		RepoID:      ctx.Repo.Repository.ID,
 | 
							RepoID:      repo.ID,
 | 
				
			||||||
		Index:       repo.NextIssueIndex(),
 | 
							Name:        form.Title,
 | 
				
			||||||
		Name:        strings.TrimSpace(form.Title),
 | 
					 | 
				
			||||||
		PosterID:    ctx.User.Id,
 | 
							PosterID:    ctx.User.Id,
 | 
				
			||||||
		Poster:      ctx.User,
 | 
							Poster:      ctx.User,
 | 
				
			||||||
		MilestoneID: milestoneID,
 | 
							MilestoneID: milestoneID,
 | 
				
			||||||
@@ -483,10 +471,8 @@ func NewIssuePost(ctx *context.Context, form auth.CreateIssueForm) {
 | 
				
			|||||||
	if err := models.NewIssue(repo, issue, labelIDs, attachments); err != nil {
 | 
						if err := models.NewIssue(repo, issue, labelIDs, attachments); err != nil {
 | 
				
			||||||
		ctx.Handle(500, "NewIssue", err)
 | 
							ctx.Handle(500, "NewIssue", err)
 | 
				
			||||||
		return
 | 
							return
 | 
				
			||||||
	}
 | 
						} else if err := MailWatchersAndMentions(ctx, issue); err != nil {
 | 
				
			||||||
 | 
							ctx.Handle(500, "MailWatchersAndMentions", err)
 | 
				
			||||||
	notifyWatchersAndMentions(ctx, issue)
 | 
					 | 
				
			||||||
	if ctx.Written() {
 | 
					 | 
				
			||||||
		return
 | 
							return
 | 
				
			||||||
	}
 | 
						}
 | 
				
			||||||
 | 
					
 | 
				
			||||||
@@ -586,10 +572,6 @@ func ViewIssue(ctx *context.Context) {
 | 
				
			|||||||
		ctx.Data["PageIsIssueList"] = true
 | 
							ctx.Data["PageIsIssueList"] = true
 | 
				
			||||||
	}
 | 
						}
 | 
				
			||||||
 | 
					
 | 
				
			||||||
	if err = issue.GetPoster(); err != nil {
 | 
					 | 
				
			||||||
		ctx.Handle(500, "GetPoster", err)
 | 
					 | 
				
			||||||
		return
 | 
					 | 
				
			||||||
	}
 | 
					 | 
				
			||||||
	issue.RenderedContent = string(markdown.Render([]byte(issue.Content), ctx.Repo.RepoLink,
 | 
						issue.RenderedContent = string(markdown.Render([]byte(issue.Content), ctx.Repo.RepoLink,
 | 
				
			||||||
		ctx.Repo.Repository.ComposeMetas()))
 | 
							ctx.Repo.Repository.ComposeMetas()))
 | 
				
			||||||
 | 
					
 | 
				
			||||||
@@ -610,10 +592,6 @@ func ViewIssue(ctx *context.Context) {
 | 
				
			|||||||
 | 
					
 | 
				
			||||||
	// Metas.
 | 
						// Metas.
 | 
				
			||||||
	// Check labels.
 | 
						// Check labels.
 | 
				
			||||||
	if err = issue.GetLabels(); err != nil {
 | 
					 | 
				
			||||||
		ctx.Handle(500, "GetLabels", err)
 | 
					 | 
				
			||||||
		return
 | 
					 | 
				
			||||||
	}
 | 
					 | 
				
			||||||
	labelIDMark := make(map[int64]bool)
 | 
						labelIDMark := make(map[int64]bool)
 | 
				
			||||||
	for i := range issue.Labels {
 | 
						for i := range issue.Labels {
 | 
				
			||||||
		labelIDMark[issue.Labels[i].ID] = true
 | 
							labelIDMark[issue.Labels[i].ID] = true
 | 
				
			||||||
@@ -698,7 +676,7 @@ func ViewIssue(ctx *context.Context) {
 | 
				
			|||||||
	ctx.Data["Participants"] = participants
 | 
						ctx.Data["Participants"] = participants
 | 
				
			||||||
	ctx.Data["NumParticipants"] = len(participants)
 | 
						ctx.Data["NumParticipants"] = len(participants)
 | 
				
			||||||
	ctx.Data["Issue"] = issue
 | 
						ctx.Data["Issue"] = issue
 | 
				
			||||||
	ctx.Data["IsIssueOwner"] = ctx.Repo.IsWriter() || (ctx.IsSigned && (issue.IsPoster(ctx.User.Id) || ctx.User.IsAdmin))
 | 
						ctx.Data["IsIssueOwner"] = ctx.Repo.IsWriter() || (ctx.IsSigned && issue.IsPoster(ctx.User.Id))
 | 
				
			||||||
	ctx.Data["SignInLink"] = setting.AppSubUrl + "/user/login"
 | 
						ctx.Data["SignInLink"] = setting.AppSubUrl + "/user/login"
 | 
				
			||||||
 | 
					
 | 
				
			||||||
	ctx.Data["RequireHighlightJS"] = true
 | 
						ctx.Data["RequireHighlightJS"] = true
 | 
				
			||||||
@@ -725,7 +703,7 @@ func UpdateIssueTitle(ctx *context.Context) {
 | 
				
			|||||||
		return
 | 
							return
 | 
				
			||||||
	}
 | 
						}
 | 
				
			||||||
 | 
					
 | 
				
			||||||
	if !ctx.IsSigned || (ctx.User.Id != issue.PosterID && !ctx.Repo.IsWriter() && !ctx.User.IsAdmin) {
 | 
						if !ctx.IsSigned || (!issue.IsPoster(ctx.User.Id) && !ctx.Repo.IsWriter()) {
 | 
				
			||||||
		ctx.Error(403)
 | 
							ctx.Error(403)
 | 
				
			||||||
		return
 | 
							return
 | 
				
			||||||
	}
 | 
						}
 | 
				
			||||||
@@ -752,7 +730,7 @@ func UpdateIssueContent(ctx *context.Context) {
 | 
				
			|||||||
		return
 | 
							return
 | 
				
			||||||
	}
 | 
						}
 | 
				
			||||||
 | 
					
 | 
				
			||||||
	if !ctx.IsSigned || (ctx.User.Id != issue.PosterID && !ctx.Repo.IsWriter() && !ctx.User.IsAdmin) {
 | 
						if !ctx.IsSigned || (ctx.User.Id != issue.PosterID && !ctx.Repo.IsWriter()) {
 | 
				
			||||||
		ctx.Error(403)
 | 
							ctx.Error(403)
 | 
				
			||||||
		return
 | 
							return
 | 
				
			||||||
	}
 | 
						}
 | 
				
			||||||
@@ -955,7 +933,7 @@ func NewComment(ctx *context.Context, form auth.CreateCommentForm) {
 | 
				
			|||||||
		return
 | 
							return
 | 
				
			||||||
	}
 | 
						}
 | 
				
			||||||
 | 
					
 | 
				
			||||||
	notifyWatchersAndMentions(ctx, &models.Issue{
 | 
						MailWatchersAndMentions(ctx, &models.Issue{
 | 
				
			||||||
		ID:      issue.ID,
 | 
							ID:      issue.ID,
 | 
				
			||||||
		Index:   issue.Index,
 | 
							Index:   issue.Index,
 | 
				
			||||||
		Name:    issue.Name,
 | 
							Name:    issue.Name,
 | 
				
			||||||
@@ -1099,7 +1077,6 @@ func Milestones(ctx *context.Context) {
 | 
				
			|||||||
	}
 | 
						}
 | 
				
			||||||
	for _, m := range miles {
 | 
						for _, m := range miles {
 | 
				
			||||||
		m.RenderedContent = string(markdown.Render([]byte(m.Content), ctx.Repo.RepoLink, ctx.Repo.Repository.ComposeMetas()))
 | 
							m.RenderedContent = string(markdown.Render([]byte(m.Content), ctx.Repo.RepoLink, ctx.Repo.Repository.ComposeMetas()))
 | 
				
			||||||
		m.CalOpenIssues()
 | 
					 | 
				
			||||||
	}
 | 
						}
 | 
				
			||||||
	ctx.Data["Milestones"] = miles
 | 
						ctx.Data["Milestones"] = miles
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 
 | 
				
			|||||||
@@ -156,10 +156,7 @@ func checkPullInfo(ctx *context.Context) *models.Issue {
 | 
				
			|||||||
		return nil
 | 
							return nil
 | 
				
			||||||
	}
 | 
						}
 | 
				
			||||||
 | 
					
 | 
				
			||||||
	if err = issue.GetPoster(); err != nil {
 | 
						if err = issue.GetPullRequest(); err != nil {
 | 
				
			||||||
		ctx.Handle(500, "GetPoster", err)
 | 
					 | 
				
			||||||
		return nil
 | 
					 | 
				
			||||||
	} else if err = issue.GetPullRequest(); err != nil {
 | 
					 | 
				
			||||||
		ctx.Handle(500, "GetPullRequest", err)
 | 
							ctx.Handle(500, "GetPullRequest", err)
 | 
				
			||||||
		return nil
 | 
							return nil
 | 
				
			||||||
	} else if err = issue.GetHeadRepo(); err != nil {
 | 
						} else if err = issue.GetHeadRepo(); err != nil {
 | 
				
			||||||
@@ -682,10 +679,8 @@ func CompareAndPullRequestPost(ctx *context.Context, form auth.CreateIssueForm)
 | 
				
			|||||||
	} else if err := pullRequest.PushToBaseRepo(); err != nil {
 | 
						} else if err := pullRequest.PushToBaseRepo(); err != nil {
 | 
				
			||||||
		ctx.Handle(500, "PushToBaseRepo", err)
 | 
							ctx.Handle(500, "PushToBaseRepo", err)
 | 
				
			||||||
		return
 | 
							return
 | 
				
			||||||
	}
 | 
						} else if err := MailWatchersAndMentions(ctx, pullIssue); err != nil {
 | 
				
			||||||
 | 
							ctx.Handle(500, "MailWatchersAndMentions", err)
 | 
				
			||||||
	notifyWatchersAndMentions(ctx, pullIssue)
 | 
					 | 
				
			||||||
	if ctx.Written() {
 | 
					 | 
				
			||||||
		return
 | 
							return
 | 
				
			||||||
	}
 | 
						}
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 
 | 
				
			|||||||
@@ -284,11 +284,6 @@ func Issues(ctx *context.Context) {
 | 
				
			|||||||
			ctx.Handle(500, "GetOwner", fmt.Errorf("[#%d]%v", issues[i].ID, err))
 | 
								ctx.Handle(500, "GetOwner", fmt.Errorf("[#%d]%v", issues[i].ID, err))
 | 
				
			||||||
			return
 | 
								return
 | 
				
			||||||
		}
 | 
							}
 | 
				
			||||||
 | 
					 | 
				
			||||||
		if err = issues[i].GetPoster(); err != nil {
 | 
					 | 
				
			||||||
			ctx.Handle(500, "GetPoster", fmt.Errorf("[#%d]%v", issues[i].ID, err))
 | 
					 | 
				
			||||||
			return
 | 
					 | 
				
			||||||
		}
 | 
					 | 
				
			||||||
	}
 | 
						}
 | 
				
			||||||
	ctx.Data["Issues"] = issues
 | 
						ctx.Data["Issues"] = issues
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 
 | 
				
			|||||||
@@ -1 +1 @@
 | 
				
			|||||||
0.9.8.0312
 | 
					0.9.9.0313
 | 
				
			||||||
		Reference in New Issue
	
	Block a user