From 28a0c29603ce5077a56d8161f5327e8729400d74 Mon Sep 17 00:00:00 2001 From: Andy Gallagher Date: Wed, 12 Jun 2024 16:05:30 +0100 Subject: [PATCH 1/4] add "withChannel" to SearchQuery --- .../model/Queries.scala | 19 ++++++++++++++++--- .../model/ContentApiQueryTest.scala | 10 ++++++++++ 2 files changed, 26 insertions(+), 3 deletions(-) diff --git a/client/src/main/scala/com.gu.contentapi.client/model/Queries.scala b/client/src/main/scala/com.gu.contentapi.client/model/Queries.scala index ddd659ae..8bcf5173 100644 --- a/client/src/main/scala/com.gu.contentapi.client/model/Queries.scala +++ b/client/src/main/scala/com.gu.contentapi.client/model/Queries.scala @@ -84,15 +84,28 @@ case class ItemQuery(id: String, parameterHolder: Map[String, Parameter] = Map.e override def pathSegment: String = id } -case class SearchQuery(parameterHolder: Map[String, Parameter] = Map.empty) +case class SearchQuery(parameterHolder: Map[String, Parameter] = Map.empty, channelId: Option[String] = None) extends PaginatedApiQuery[SearchResponse, Content] with SearchQueryBase[SearchQuery] { def setPaginationConsistentWith(response: SearchResponse): PaginatedApiQuery[SearchResponse, Content] = pageSize.setIfUndefined(response.pageSize).orderBy.setIfUndefined(response.orderBy) - def withParameters(parameterMap: Map[String, Parameter]): SearchQuery = copy(parameterMap) + def withParameters(parameterMap: Map[String, Parameter]): SearchQuery = copy(parameterMap, channelId) - override def pathSegment: String = "search" + /** + * Make this search on a CAPI channel rather than against web-only content + * For more information about channels, and the reason why your app should only be in one channel, + * content the Content API team + * @param channelId the channel to search against, or "all" to search across all channels. + */ + def withChannel(channelId:String):SearchQuery = copy(parameterHolder, Some(channelId)) + + def withoutChannel(): SearchQuery = copy(parameterHolder, None) + + override def pathSegment: String = channelId match { + case None=>"search" + case Some(chnl)=>s"channel/$chnl/search" + } protected override def followingQueryGivenFull(response: SearchResponse, direction: Direction) = for { lastResultInResponse <- response.results.lastOption diff --git a/client/src/test/scala/com.gu.contentapi.client/model/ContentApiQueryTest.scala b/client/src/test/scala/com.gu.contentapi.client/model/ContentApiQueryTest.scala index 2c82dabe..3ffadc76 100644 --- a/client/src/test/scala/com.gu.contentapi.client/model/ContentApiQueryTest.scala +++ b/client/src/test/scala/com.gu.contentapi.client/model/ContentApiQueryTest.scala @@ -29,6 +29,16 @@ class ContentApiQueryTest extends AnyFlatSpec with Matchers { "/search?paths=path%2Fone%2Cpath%2Ftwo" } + "SearchQuery" should "include a channel if asked" in { + SearchQuery().withChannel("my-channel").paths("path/one").getUrl("") shouldEqual + "/channel/my-channel/search?paths=path%2Fone" + } + + "SearchQuery" should "drop the included channel if asked" in { + SearchQuery().withChannel("my-channel").withoutChannel().paths("path/one").getUrl("") shouldEqual + "/search?paths=path%2Fone" + } + "SectionsQuery" should "be beautiful" in { SectionsQuery().getUrl("") shouldEqual "/sections" } From 40cbea1def48891a4f500b741763c210a1d14cdf Mon Sep 17 00:00:00 2001 From: Andy Gallagher Date: Wed, 12 Jun 2024 16:17:52 +0100 Subject: [PATCH 2/4] add "withChannel" to ItemQuery --- .../ContentApiClient.scala | 1 - .../model/Queries.scala | 23 ++++++++----------- .../model/ContentApiQueryTest.scala | 10 ++++++++ 3 files changed, 20 insertions(+), 14 deletions(-) diff --git a/client/src/main/scala/com.gu.contentapi.client/ContentApiClient.scala b/client/src/main/scala/com.gu.contentapi.client/ContentApiClient.scala index e4fdfe5a..5a6b0454 100644 --- a/client/src/main/scala/com.gu.contentapi.client/ContentApiClient.scala +++ b/client/src/main/scala/com.gu.contentapi.client/ContentApiClient.scala @@ -165,7 +165,6 @@ trait ContentApiQueries { val editions = EditionsQuery() val atoms = AtomsQuery() def atomUsage(atomType: AtomType, atomId: String) = AtomUsageQuery(atomType, atomId) - val recipes = RecipesQuery() val reviews = ReviewsQuery() val gameReviews = GameReviewsQuery() val restaurantReviews = RestaurantReviewsQuery() diff --git a/client/src/main/scala/com.gu.contentapi.client/model/Queries.scala b/client/src/main/scala/com.gu.contentapi.client/model/Queries.scala index 8bcf5173..7fac7670 100644 --- a/client/src/main/scala/com.gu.contentapi.client/model/Queries.scala +++ b/client/src/main/scala/com.gu.contentapi.client/model/Queries.scala @@ -63,7 +63,7 @@ trait SearchQueryBase[Self <: SearchQueryBase[Self]] this: Self => } -case class ItemQuery(id: String, parameterHolder: Map[String, Parameter] = Map.empty) +case class ItemQuery(id: String, parameterHolder: Map[String, Parameter] = Map.empty, channelId: Option[String]=None) extends ContentApiQuery[ItemResponse] with EditionParameters[ItemQuery] with ShowParameters[ItemQuery] @@ -76,12 +76,19 @@ case class ItemQuery(id: String, parameterHolder: Map[String, Parameter] = Map.e with FilterExtendedParameters[ItemQuery] with FilterSearchParameters[ItemQuery] { - def withParameters(parameterMap: Map[String, Parameter]) = copy(id, parameterMap) + def withParameters(parameterMap: Map[String, Parameter]) = copy(id, parameterMap, channelId) + + def withChannelId(newChannel:String) = copy(id, parameterHolder, Some(newChannel)) + + def withoutChannelId() = copy(id, parameterHolder, None) def itemId(contentId: String): ItemQuery = copy(id = contentId) - override def pathSegment: String = id + override def pathSegment: String = channelId match { + case None => id + case Some(chl) => s"channel/$chl/item/$id" + } } case class SearchQuery(parameterHolder: Map[String, Parameter] = Map.empty, channelId: Option[String] = None) @@ -187,16 +194,6 @@ case class AtomUsageQuery(atomType: AtomType, atomId: String, parameterHolder: M override def pathSegment: String = s"atom/${atomType.toString.toLowerCase}/$atomId/usage" } -case class RecipesQuery(parameterHolder: Map[String, Parameter] = Map.empty) - extends ContentApiQuery[AtomsResponse] - with PaginationParameters[RecipesQuery] - with RecipeParameters[RecipesQuery] { - - def withParameters(parameterMap: Map[String, Parameter]) = copy(parameterMap) - - override def pathSegment: String = "atoms/recipes" -} - case class ReviewsQuery(parameterHolder: Map[String, Parameter] = Map.empty) extends ContentApiQuery[AtomsResponse] with PaginationParameters[ReviewsQuery] diff --git a/client/src/test/scala/com.gu.contentapi.client/model/ContentApiQueryTest.scala b/client/src/test/scala/com.gu.contentapi.client/model/ContentApiQueryTest.scala index 3ffadc76..c7c8ab26 100644 --- a/client/src/test/scala/com.gu.contentapi.client/model/ContentApiQueryTest.scala +++ b/client/src/test/scala/com.gu.contentapi.client/model/ContentApiQueryTest.scala @@ -14,6 +14,16 @@ class ContentApiQueryTest extends AnyFlatSpec with Matchers { "/profile/justin-pinner?show-alias-paths=true" } + "ItemQuery" should "accept a channel" in { + ItemQuery("lifeandstyle/thing").withChannelId("recipes").getUrl("") shouldEqual + "/channel/recipes/item/lifeandstyle/thing" + } + + "ItemQuery" should "drop the included channel if asked" in { + ItemQuery("lifeandstyle/thing").withChannelId("recipes").withoutChannelId().getUrl("") shouldEqual + "/lifeandstyle/thing" + } + "SearchQuery" should "also be excellent" in { SearchQuery().tag("profile/robert-berry").showElements("all").contentType("article").queryFields("body").getUrl("") shouldEqual "/search?tag=profile%2Frobert-berry&show-elements=all&type=article&query-fields=body" From 45bea490edca0613edb9c857e51b8251b2287022 Mon Sep 17 00:00:00 2001 From: Andy Gallagher Date: Wed, 12 Jun 2024 16:55:12 +0100 Subject: [PATCH 3/4] fix typo, deprecate rather than remove recipe atom shortcut --- .../com.gu.contentapi.client/ContentApiClient.scala | 2 ++ .../com.gu.contentapi.client/model/Queries.scala | 13 ++++++++++++- 2 files changed, 14 insertions(+), 1 deletion(-) diff --git a/client/src/main/scala/com.gu.contentapi.client/ContentApiClient.scala b/client/src/main/scala/com.gu.contentapi.client/ContentApiClient.scala index 5a6b0454..a9c6fb9e 100644 --- a/client/src/main/scala/com.gu.contentapi.client/ContentApiClient.scala +++ b/client/src/main/scala/com.gu.contentapi.client/ContentApiClient.scala @@ -165,6 +165,8 @@ trait ContentApiQueries { val editions = EditionsQuery() val atoms = AtomsQuery() def atomUsage(atomType: AtomType, atomId: String) = AtomUsageQuery(atomType, atomId) + @deprecated("Recipe atoms no longer exist and should not be relied upon. No data will be returned and this query will be removed in a future iteration of the library") + val recipes = RecipesQuery() val reviews = ReviewsQuery() val gameReviews = GameReviewsQuery() val restaurantReviews = RestaurantReviewsQuery() diff --git a/client/src/main/scala/com.gu.contentapi.client/model/Queries.scala b/client/src/main/scala/com.gu.contentapi.client/model/Queries.scala index 7fac7670..399d5e96 100644 --- a/client/src/main/scala/com.gu.contentapi.client/model/Queries.scala +++ b/client/src/main/scala/com.gu.contentapi.client/model/Queries.scala @@ -102,7 +102,7 @@ case class SearchQuery(parameterHolder: Map[String, Parameter] = Map.empty, chan /** * Make this search on a CAPI channel rather than against web-only content * For more information about channels, and the reason why your app should only be in one channel, - * content the Content API team + * contact the Content API team * @param channelId the channel to search against, or "all" to search across all channels. */ def withChannel(channelId:String):SearchQuery = copy(parameterHolder, Some(channelId)) @@ -194,6 +194,17 @@ case class AtomUsageQuery(atomType: AtomType, atomId: String, parameterHolder: M override def pathSegment: String = s"atom/${atomType.toString.toLowerCase}/$atomId/usage" } +@deprecated("Recipe atoms no longer exist and should not be relied upon. No data will be returned and this class will be removed in a future iteration of the library") +case class RecipesQuery(parameterHolder: Map[String, Parameter] = Map.empty) + extends ContentApiQuery[AtomsResponse] + with PaginationParameters[RecipesQuery] + with RecipeParameters[RecipesQuery] { + + def withParameters(parameterMap: Map[String, Parameter]) = copy(parameterMap) + + override def pathSegment: String = "atoms/recipes" +} + case class ReviewsQuery(parameterHolder: Map[String, Parameter] = Map.empty) extends ContentApiQuery[AtomsResponse] with PaginationParameters[ReviewsQuery] From 5c271885507018587524cccca9f2769a7681ed4f Mon Sep 17 00:00:00 2001 From: Andy Gallagher Date: Wed, 12 Jun 2024 17:03:37 +0100 Subject: [PATCH 4/4] add "show-channels" param --- .../src/main/scala/com.gu.contentapi.client/model/Queries.scala | 1 + 1 file changed, 1 insertion(+) diff --git a/client/src/main/scala/com.gu.contentapi.client/model/Queries.scala b/client/src/main/scala/com.gu.contentapi.client/model/Queries.scala index 399d5e96..2341c9c4 100644 --- a/client/src/main/scala/com.gu.contentapi.client/model/Queries.scala +++ b/client/src/main/scala/com.gu.contentapi.client/model/Queries.scala @@ -305,6 +305,7 @@ trait ShowParameters[Owner <: Parameters[Owner]] extends Parameters[Owner] { thi def showStats = BoolParameter("show-stats") def showAliasPaths = BoolParameter("show-alias-paths") def showSchemaOrg = BoolParameter("show-schemaorg") + def showChannels = StringParameter("show-channels") } trait ShowReferencesParameters[Owner <: Parameters[Owner]] extends Parameters[Owner] { this: Owner =>