Skip to content

Commit

Permalink
consolidate duplicate code
Browse files Browse the repository at this point in the history
  • Loading branch information
CollinBeczak committed Nov 15, 2024
1 parent 05814f1 commit a48ab8e
Show file tree
Hide file tree
Showing 2 changed files with 61 additions and 113 deletions.
Original file line number Diff line number Diff line change
Expand Up @@ -120,6 +120,22 @@ class TaskClusterRepository @Inject() (override val db: Database, challengeDAL:
SQL(sql.toString).as(this.pointParser.*)
}
}
// sql query use to select list of ClusteredPoint data
private val selectTaskMarkersSQL = s"""
SELECT tasks.id, tasks.name, tasks.parent_id, c.name, tasks.instruction, tasks.status, tasks.mapped_on,
tasks.completed_time_spent, tasks.completed_by,
tasks.bundle_id, tasks.is_bundle_primary, tasks.cooperative_work_json::TEXT as cooperative_work,
task_review.review_status, task_review.review_requested_by, task_review.reviewed_by, task_review.reviewed_at,
task_review.review_started_at, task_review.meta_review_status, task_review.meta_reviewed_by,
task_review.meta_reviewed_at, task_review.additional_reviewers,
ST_AsGeoJSON(tasks.location) AS location, priority,
CASE WHEN task_review.review_started_at IS NULL
THEN 0
ELSE EXTRACT(epoch FROM (task_review.reviewed_at - task_review.review_started_at)) END
AS reviewDuration
FROM tasks
${joinClause.toString()}
"""

/**
* Querys tasks in a bounding box
Expand All @@ -141,30 +157,8 @@ class TaskClusterRepository @Inject() (override val db: Database, challengeDAL:
${joinClause.toString()}
""").as(SqlParser.int("count").single)

val results =
query
.copy(
order = order,
paging = paging
)
.build(
s"""
SELECT tasks.id, tasks.name, tasks.parent_id, c.name, tasks.instruction, tasks.status, tasks.mapped_on,
tasks.completed_time_spent, tasks.completed_by,
tasks.bundle_id, tasks.is_bundle_primary, tasks.cooperative_work_json::TEXT as cooperative_work,
task_review.review_status, task_review.review_requested_by, task_review.reviewed_by, task_review.reviewed_at,
task_review.review_started_at, task_review.meta_review_status, task_review.meta_reviewed_by,
task_review.meta_reviewed_at, task_review.additional_reviewers,
ST_AsGeoJSON(tasks.location) AS location, priority,
CASE WHEN task_review.review_started_at IS NULL
THEN 0
ELSE EXTRACT(epoch FROM (task_review.reviewed_at - task_review.review_started_at)) END
AS reviewDuration
FROM tasks
${joinClause.toString()}
"""
)
.as(this.pointParser.*)
val resultsQuery = query.copy(order = order, paging = paging).build(selectTaskMarkersSQL)
val results = resultsQuery.as(this.pointParser.*)

(count, results)
}
Expand All @@ -174,6 +168,7 @@ class TaskClusterRepository @Inject() (override val db: Database, challengeDAL:
* Querys task markers in a bounding box
*
* @param query Query to execute
* @param limit Maximum number of results to return
* @param c An available connection
* @return The list of Tasks found within the bounding box
*/
Expand All @@ -182,26 +177,8 @@ class TaskClusterRepository @Inject() (override val db: Database, challengeDAL:
limit: Int
): List[ClusteredPoint] = {
this.withMRTransaction { implicit c =>
val finalQuery = query.copy(finalClause = s"""LIMIT $limit""")
val results = finalQuery
.build(s"""
SELECT tasks.id, tasks.name, tasks.parent_id, c.name, tasks.instruction, tasks.status, tasks.mapped_on,
tasks.completed_time_spent, tasks.completed_by,
tasks.bundle_id, tasks.is_bundle_primary, tasks.cooperative_work_json::TEXT as cooperative_work,
task_review.review_status, task_review.review_requested_by, task_review.reviewed_by, task_review.reviewed_at,
task_review.review_started_at, task_review.meta_review_status, task_review.meta_reviewed_by,
task_review.meta_reviewed_at, task_review.additional_reviewers,
ST_AsGeoJSON(tasks.location) AS location, priority,
CASE WHEN task_review.review_started_at IS NULL
THEN 0
ELSE EXTRACT(epoch FROM (task_review.reviewed_at - task_review.review_started_at)) END
AS reviewDuration
FROM tasks
${joinClause.toString()}
""")
.as(this.pointParser.*)

results
val finalQuery = query.copy(finalClause = s"LIMIT $limit").build(selectTaskMarkersSQL)
finalQuery.as(this.pointParser.*)
}
}

Expand Down
109 changes: 40 additions & 69 deletions app/org/maproulette/framework/service/TaskClusterService.scala
Original file line number Diff line number Diff line change
Expand Up @@ -77,50 +77,8 @@ class TaskClusterService @Inject() (repository: TaskClusterRepository)
sort: String = "",
orderDirection: String = "ASC"
): (Int, List[ClusteredPoint]) = {
params.location match {
case Some(sl) => // params has location
case None =>
params.boundingGeometries match {
case Some(bp) => // params has bounding polygons
case None =>
throw new InvalidException(
"Bounding Box (or Bounding Polygons) required to retrieve tasks within a bounding box"
)
}
}

var query =
this.filterOutLocked(
user,
this.filterOutDeletedParents(this.filterOnSearchParameters(params)(false)),
ignoreLocked
)

query = params.taskParams.excludeTaskIds match {
case Some(excludedIds) if !excludedIds.isEmpty =>
//this.appendInWhereClause(whereClause, s"(tasks.id NOT IN (${excludedIds.mkString(",")}))")
query.addFilterGroup(
FilterGroup(
List(
BaseParameter(
Task.FIELD_ID,
excludedIds.mkString(","),
Operator.IN,
negate = true,
useValueDirectly = true,
table = Some("tasks")
)
)
)
)
case _ => query
}

this.repository.queryTasksInBoundingBox(
query,
this.getOrder(sort, orderDirection),
paging
)
val query = buildQueryForBoundingBox(user, params, ignoreLocked)
this.repository.queryTasksInBoundingBox(query, this.getOrder(sort, orderDirection), paging)
}

/**
Expand All @@ -136,29 +94,33 @@ class TaskClusterService @Inject() (repository: TaskClusterRepository)
params: SearchParameters,
limit: Int,
ignoreLocked: Boolean = false
): (List[ClusteredPoint]) = {
params.location match {
case Some(sl) => // params has location
case None =>
params.boundingGeometries match {
case Some(bp) => // params has bounding polygons
case None =>
throw new InvalidException(
"Bounding Box (or Bounding Polygons) required to retrieve tasks within a bounding box"
)
}
}
): List[ClusteredPoint] = {
val query = buildQueryForBoundingBox(user, params, ignoreLocked)
this.repository.queryTaskMarkerDataInBoundingBox(query, limit)
}

var query =
this.filterOutLocked(
user,
this.filterOutDeletedParents(this.filterOnSearchParameters(params)(false)),
ignoreLocked
)
/**
* Builds a query to retrieve tasks within a bounding box, applying search parameters.
*
* @param user The user making the request
* @param params Search parameters including location or bounding geometries
* @param ignoreLocked Whether to exclude tasks locked by other users
* @return The constructed query
*/
private def buildQueryForBoundingBox(
user: User,
params: SearchParameters,
ignoreLocked: Boolean
): Query = {
ensureBoundingBox(params)
var query = this.filterOutLocked(
user,
this.filterOutDeletedParents(this.filterOnSearchParameters(params)(false)),
ignoreLocked
)

query = params.taskParams.excludeTaskIds match {
case Some(excludedIds) if !excludedIds.isEmpty =>
//this.appendInWhereClause(whereClause, s"(tasks.id NOT IN (${excludedIds.mkString(",")}))")
params.taskParams.excludeTaskIds match {
case Some(excludedIds) if excludedIds.nonEmpty =>
query.addFilterGroup(
FilterGroup(
List(
Expand All @@ -175,10 +137,19 @@ class TaskClusterService @Inject() (repository: TaskClusterRepository)
)
case _ => query
}
}

this.repository.queryTaskMarkerDataInBoundingBox(
query,
limit
)
/**
* Ensures that either a location or bounding geometries are provided in the search parameters.
*
* @param params Search parameters
* @throws InvalidException if neither location nor bounding geometries are provided
*/
private def ensureBoundingBox(params: SearchParameters): Unit = {
if (params.location.isEmpty && params.boundingGeometries.isEmpty) {
throw new InvalidException(
"Bounding Box (or Bounding Polygons) required to retrieve tasks within a bounding box"
)
}
}
}

0 comments on commit a48ab8e

Please sign in to comment.