mirror of
				https://gitee.com/gitea/gitea
				synced 2025-11-04 08:30:25 +08:00 
			
		
		
		
	[API] Issue Search Add filter for MilestoneNames (#16173)
This commit is contained in:
		@@ -222,6 +222,20 @@ func TestAPISearchIssues(t *testing.T) {
 | 
			
		||||
	resp = session.MakeRequest(t, req, http.StatusOK)
 | 
			
		||||
	DecodeJSON(t, resp, &apiIssues)
 | 
			
		||||
	assert.Len(t, apiIssues, 1)
 | 
			
		||||
 | 
			
		||||
	query = url.Values{"milestones": {"milestone1"}, "state": {"all"}}
 | 
			
		||||
	link.RawQuery = query.Encode()
 | 
			
		||||
	req = NewRequest(t, "GET", link.String())
 | 
			
		||||
	resp = session.MakeRequest(t, req, http.StatusOK)
 | 
			
		||||
	DecodeJSON(t, resp, &apiIssues)
 | 
			
		||||
	assert.Len(t, apiIssues, 1)
 | 
			
		||||
 | 
			
		||||
	query = url.Values{"milestones": {"milestone1,milestone3"}, "state": {"all"}}
 | 
			
		||||
	link.RawQuery = query.Encode()
 | 
			
		||||
	req = NewRequest(t, "GET", link.String())
 | 
			
		||||
	resp = session.MakeRequest(t, req, http.StatusOK)
 | 
			
		||||
	DecodeJSON(t, resp, &apiIssues)
 | 
			
		||||
	assert.Len(t, apiIssues, 2)
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
func TestAPISearchIssuesWithLabels(t *testing.T) {
 | 
			
		||||
 
 | 
			
		||||
@@ -1100,6 +1100,7 @@ type IssuesOptions struct {
 | 
			
		||||
	LabelIDs           []int64
 | 
			
		||||
	IncludedLabelNames []string
 | 
			
		||||
	ExcludedLabelNames []string
 | 
			
		||||
	IncludeMilestones  []string
 | 
			
		||||
	SortType           string
 | 
			
		||||
	IssueIDs           []int64
 | 
			
		||||
	UpdatedAfterUnix   int64
 | 
			
		||||
@@ -1241,6 +1242,13 @@ func (opts *IssuesOptions) setupSession(sess *xorm.Session) {
 | 
			
		||||
	if len(opts.ExcludedLabelNames) > 0 {
 | 
			
		||||
		sess.And(builder.NotIn("issue.id", BuildLabelNamesIssueIDsCondition(opts.ExcludedLabelNames)))
 | 
			
		||||
	}
 | 
			
		||||
 | 
			
		||||
	if len(opts.IncludeMilestones) > 0 {
 | 
			
		||||
		sess.In("issue.milestone_id",
 | 
			
		||||
			builder.Select("id").
 | 
			
		||||
				From("milestone").
 | 
			
		||||
				Where(builder.In("name", opts.IncludeMilestones)))
 | 
			
		||||
	}
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
func applyReposCondition(sess *xorm.Session, repoIDs []int64) *xorm.Session {
 | 
			
		||||
 
 | 
			
		||||
@@ -42,6 +42,10 @@ func SearchIssues(ctx *context.APIContext) {
 | 
			
		||||
	//   in: query
 | 
			
		||||
	//   description: comma separated list of labels. Fetch only issues that have any of this labels. Non existent labels are discarded
 | 
			
		||||
	//   type: string
 | 
			
		||||
	// - name: milestones
 | 
			
		||||
	//   in: query
 | 
			
		||||
	//   description: comma separated list of milestone names. Fetch only issues that have any of this milestones. Non existent are discarded
 | 
			
		||||
	//   type: string
 | 
			
		||||
	// - name: q
 | 
			
		||||
	//   in: query
 | 
			
		||||
	//   description: search string
 | 
			
		||||
@@ -164,6 +168,12 @@ func SearchIssues(ctx *context.APIContext) {
 | 
			
		||||
		includedLabelNames = strings.Split(labels, ",")
 | 
			
		||||
	}
 | 
			
		||||
 | 
			
		||||
	milestones := strings.TrimSpace(ctx.Query("milestones"))
 | 
			
		||||
	var includedMilestones []string
 | 
			
		||||
	if len(milestones) > 0 {
 | 
			
		||||
		includedMilestones = strings.Split(milestones, ",")
 | 
			
		||||
	}
 | 
			
		||||
 | 
			
		||||
	// this api is also used in UI,
 | 
			
		||||
	// so the default limit is set to fit UI needs
 | 
			
		||||
	limit := ctx.QueryInt("limit")
 | 
			
		||||
@@ -175,7 +185,7 @@ func SearchIssues(ctx *context.APIContext) {
 | 
			
		||||
 | 
			
		||||
	// Only fetch the issues if we either don't have a keyword or the search returned issues
 | 
			
		||||
	// This would otherwise return all issues if no issues were found by the search.
 | 
			
		||||
	if len(keyword) == 0 || len(issueIDs) > 0 || len(includedLabelNames) > 0 {
 | 
			
		||||
	if len(keyword) == 0 || len(issueIDs) > 0 || len(includedLabelNames) > 0 || len(includedMilestones) > 0 {
 | 
			
		||||
		issuesOpt := &models.IssuesOptions{
 | 
			
		||||
			ListOptions: models.ListOptions{
 | 
			
		||||
				Page:     ctx.QueryInt("page"),
 | 
			
		||||
@@ -185,6 +195,7 @@ func SearchIssues(ctx *context.APIContext) {
 | 
			
		||||
			IsClosed:           isClosed,
 | 
			
		||||
			IssueIDs:           issueIDs,
 | 
			
		||||
			IncludedLabelNames: includedLabelNames,
 | 
			
		||||
			IncludeMilestones:  includedMilestones,
 | 
			
		||||
			SortType:           "priorityrepo",
 | 
			
		||||
			PriorityRepoID:     ctx.QueryInt64("priority_repo_id"),
 | 
			
		||||
			IsPull:             isPull,
 | 
			
		||||
 
 | 
			
		||||
@@ -1876,6 +1876,12 @@
 | 
			
		||||
            "name": "labels",
 | 
			
		||||
            "in": "query"
 | 
			
		||||
          },
 | 
			
		||||
          {
 | 
			
		||||
            "type": "string",
 | 
			
		||||
            "description": "comma separated list of milestone names. Fetch only issues that have any of this milestones. Non existent are discarded",
 | 
			
		||||
            "name": "milestones",
 | 
			
		||||
            "in": "query"
 | 
			
		||||
          },
 | 
			
		||||
          {
 | 
			
		||||
            "type": "string",
 | 
			
		||||
            "description": "search string",
 | 
			
		||||
 
 | 
			
		||||
		Reference in New Issue
	
	Block a user