(refs #508)Add search filter box to the dashboard

This commit is contained in:
Naoki Takezoe
2014-11-16 01:38:31 +09:00
parent 055f648ea2
commit e40e1fa6cd
16 changed files with 182 additions and 87 deletions

View File

@@ -1,8 +1,9 @@
package app
import service._
import util.{UsersAuthenticator, Keys}
import util.{StringUtil, UsersAuthenticator, Keys}
import util.Implicits._
import service.IssuesService.IssueSearchCondition
class DashboardController extends DashboardControllerBase
with IssuesService with PullRequestService with RepositoryService with AccountService
@@ -12,8 +13,21 @@ trait DashboardControllerBase extends ControllerBase {
self: IssuesService with PullRequestService with RepositoryService with AccountService
with UsersAuthenticator =>
get("/dashboard/issues/repos")(usersOnly {
searchIssues("created_by")
get("/dashboard/issues")(usersOnly {
val q = request.getParameter("q")
val account = context.loginAccount.get
Option(q).map { q =>
val condition = IssueSearchCondition(q, Map[String, Int]())
q match {
case q if(q.contains("is:pr")) => redirect(s"/dashboard/pulls?q=${StringUtil.urlEncode(q)}")
case q if(q.contains(s"author:${account.userName}")) => redirect(s"/dashboard/issues/created_by${condition.toURL}")
case q if(q.contains(s"assignee:${account.userName}")) => redirect(s"/dashboard/issues/assigned${condition.toURL}")
case q if(q.contains(s"mentions:${account.userName}")) => redirect(s"/dashboard/issues/mentioned${condition.toURL}")
case _ => searchIssues("created_by")
}
} getOrElse {
searchIssues("created_by")
}
})
get("/dashboard/issues/assigned")(usersOnly {
@@ -29,7 +43,20 @@ trait DashboardControllerBase extends ControllerBase {
})
get("/dashboard/pulls")(usersOnly {
searchPullRequests("created_by")
val q = request.getParameter("q")
val account = context.loginAccount.get
Option(q).map { q =>
val condition = IssueSearchCondition(q, Map[String, Int]())
q match {
case q if(q.contains("is:issue")) => redirect(s"/dashboard/issues?q=${StringUtil.urlEncode(q)}")
case q if(q.contains(s"author:${account.userName}")) => redirect(s"/dashboard/pulls/created_by${condition.toURL}")
case q if(q.contains(s"assignee:${account.userName}")) => redirect(s"/dashboard/pulls/assigned${condition.toURL}")
case q if(q.contains(s"mentions:${account.userName}")) => redirect(s"/dashboard/pulls/mentioned${condition.toURL}")
case _ => searchPullRequests("created_by")
}
} getOrElse {
searchPullRequests("created_by")
}
})
get("/dashboard/pulls/created_by")(usersOnly {
@@ -44,15 +71,21 @@ trait DashboardControllerBase extends ControllerBase {
searchPullRequests("mentioned")
})
private def getOrCreateCondition(key: String) = {
session.putAndGet(key, if(request.hasQueryString){
val q = request.getParameter("q")
if(q == null){
IssueSearchCondition(request)
} else {
IssueSearchCondition(q, Map[String, Int]())
}
} else session.getAs[IssueSearchCondition](key).getOrElse(IssueSearchCondition()))
}
private def searchIssues(filter: String) = {
import IssuesService._
// condition
val condition = session.putAndGet(Keys.Session.DashboardIssues,
if(request.hasQueryString) IssueSearchCondition(request)
else session.getAs[IssueSearchCondition](Keys.Session.DashboardIssues).getOrElse(IssueSearchCondition())
)
val condition = getOrCreateCondition(Keys.Session.DashboardIssues)
val userName = context.loginAccount.get.userName
val userRepos = getUserRepositories(userName, context.baseUrl, true).map(repo => repo.owner -> repo.name)
val filterUser = Map(filter -> userName)
@@ -63,7 +96,11 @@ trait DashboardControllerBase extends ControllerBase {
page,
countIssue(condition.copy(state = "open" ), filterUser, false, userRepos: _*),
countIssue(condition.copy(state = "closed"), filterUser, false, userRepos: _*),
condition,
filter match {
case "assigned" => condition.copy(assigned = Some(userName))
case "mentioned" => condition.copy(mentioned = Some(userName))
case _ => condition.copy(author = Some(userName))
},
filter,
getGroupNames(userName))
}
@@ -72,12 +109,7 @@ trait DashboardControllerBase extends ControllerBase {
import IssuesService._
import PullRequestService._
// condition
val condition = session.putAndGet(Keys.Session.DashboardPulls, {
if(request.hasQueryString) IssueSearchCondition(request)
else session.getAs[IssueSearchCondition](Keys.Session.DashboardPulls).getOrElse(IssueSearchCondition())
})
val condition = getOrCreateCondition(Keys.Session.DashboardPulls)
val userName = context.loginAccount.get.userName
val allRepos = getAllRepositories(userName)
val filterUser = Map(filter -> userName)
@@ -88,7 +120,11 @@ trait DashboardControllerBase extends ControllerBase {
page,
countIssue(condition.copy(state = "open" ), filterUser, true, allRepos: _*),
countIssue(condition.copy(state = "closed"), filterUser, true, allRepos: _*),
condition,
filter match {
case "assigned" => condition.copy(assigned = Some(userName))
case "mentioned" => condition.copy(mentioned = Some(userName))
case _ => condition.copy(author = Some(userName))
},
filter,
getGroupNames(userName))
}

View File

@@ -401,8 +401,7 @@ trait IssuesControllerBase extends ControllerBase {
} else {
IssueSearchCondition(q, getMilestones(owner, repoName).map(x => (x.title, x.milestoneId)).toMap)
}
}
else session.getAs[IssueSearchCondition](sessionKey).getOrElse(IssueSearchCondition())
} else session.getAs[IssueSearchCondition](sessionKey).getOrElse(IssueSearchCondition())
)
issues.html.list(

View File

@@ -326,6 +326,7 @@ object IssuesService {
milestoneId: Option[Option[Int]] = None,
author: Option[String] = None,
assigned: Option[String] = None,
mentioned: Option[String] = None,
state: String = "open",
sort: String = "created",
direction: String = "desc",
@@ -339,12 +340,14 @@ object IssuesService {
def nonEmpty: Boolean = !isEmpty
def toFilterString: String =
(List(
def toFilterString: String = (
List(
Some(s"is:${state}"),
author.map(author => s"author:${author}"),
assigned.map(assignee => s"assignee:${assignee}")
).flatten ++ labels.map(label => s"label:${label}") ++
assigned.map(assignee => s"assignee:${assignee}"),
mentioned.map(mentioned => s"mentions:${mentioned}")
).flatten ++
labels.map(label => s"label:${label}") ++
List(
milestoneId.map { _ match {
case Some(x) => s"milestone:${milestoneId}"
@@ -357,8 +360,11 @@ object IssuesService {
case ("comments", "asc" ) => Some("sort:comments-asc")
case ("updated" , "desc") => Some("sort:updated-desc")
case ("updated" , "asc" ) => Some("sort:updated-asc")
}
).flatten).mkString(" ")
},
visibility.map(visibility => s"visibility:${visibility}")
).flatten ++
groups.map(group => s"group:${group}")
).mkString(" ")
def toURL: String =
"?" + List(
@@ -410,15 +416,16 @@ object IssuesService {
conditions.get("milestone").flatMap(_.headOption) match {
case None => None
case Some("none") => Some(None)
case Some(x) => Some(milestones.get(x))
case Some(x) => milestones.get(x).map(x => Some(x))
},
conditions.get("author").flatMap(_.headOption),
conditions.get("assignee").flatMap(_.headOption),
None,
conditions.get("is").getOrElse(Seq.empty).filter(x => x == "open" || x == "closed").headOption.getOrElse("open"),
sort,
direction,
None, // TODO??
Set.empty // TODO??
conditions.get("visibility").flatMap(_.headOption),
conditions.get("group").map(_.toSet).getOrElse(Set.empty)
)
}
@@ -434,6 +441,7 @@ object IssuesService {
},
param(request, "author"),
param(request, "assigned"),
None,
param(request, "state", Seq("open", "closed")).getOrElse("open"),
param(request, "sort", Seq("created", "comments", "updated")).getOrElse("created"),
param(request, "direction", Seq("asc", "desc")).getOrElse("desc"),