diff --git a/app/uk/gov/hmrc/cataloguefrontend/BobbyExplorerController.scala b/app/uk/gov/hmrc/cataloguefrontend/BobbyExplorerController.scala new file mode 100644 index 000000000..1f07a7150 --- /dev/null +++ b/app/uk/gov/hmrc/cataloguefrontend/BobbyExplorerController.scala @@ -0,0 +1,34 @@ +/* + * Copyright 2019 HM Revenue & Customs + * + * Licensed under the Apache License, Version 2.0 (the "License"); + * you may not use this file except in compliance with the License. + * You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + */ + +package uk.gov.hmrc.cataloguefrontend + +import javax.inject.Inject +import play.api.mvc.{Action, AnyContent, MessagesControllerComponents} +import uk.gov.hmrc.cataloguefrontend.service.BobbyService +import uk.gov.hmrc.play.bootstrap.controller.FrontendController +import views.html.BobbyExplorerPage + +import scala.concurrent.ExecutionContext + +class BobbyExplorerController @Inject() (mcc : MessagesControllerComponents, + page : BobbyExplorerPage, + bobbyService: BobbyService + )( implicit val ec: ExecutionContext) extends FrontendController(mcc) { + def list(): Action[AnyContent] = Action.async { implicit request => + bobbyService.getRules().map(r => Ok(page(r))) + } +} diff --git a/app/uk/gov/hmrc/cataloguefrontend/CatalogueFrontendModule.scala b/app/uk/gov/hmrc/cataloguefrontend/CatalogueFrontendModule.scala index 9406e1f07..8eb72031d 100644 --- a/app/uk/gov/hmrc/cataloguefrontend/CatalogueFrontendModule.scala +++ b/app/uk/gov/hmrc/cataloguefrontend/CatalogueFrontendModule.scala @@ -16,12 +16,15 @@ package uk.gov.hmrc.cataloguefrontend +import java.time.Clock + import com.google.inject.AbstractModule import uk.gov.hmrc.cataloguefrontend.service.EventsReloadScheduler class CatalogueFrontendModule extends AbstractModule { - override def configure(): Unit = + override def configure(): Unit = { + bind(classOf[Clock]).toInstance(Clock.systemDefaultZone) bind(classOf[EventsReloadScheduler]).asEagerSingleton() - -} + } +} \ No newline at end of file diff --git a/app/uk/gov/hmrc/cataloguefrontend/connector/ConfigConnector.scala b/app/uk/gov/hmrc/cataloguefrontend/connector/ConfigConnector.scala index 3e38452f3..2ed0cafb4 100644 --- a/app/uk/gov/hmrc/cataloguefrontend/connector/ConfigConnector.scala +++ b/app/uk/gov/hmrc/cataloguefrontend/connector/ConfigConnector.scala @@ -18,12 +18,13 @@ package uk.gov.hmrc.cataloguefrontend.connector import javax.inject.{Inject, Singleton} import play.api.libs.json._ +import uk.gov.hmrc.cataloguefrontend.connector.model.BobbyRuleSet import uk.gov.hmrc.cataloguefrontend.service.ConfigService._ import uk.gov.hmrc.http.{HeaderCarrier, HttpReads, HttpResponse} import uk.gov.hmrc.play.bootstrap.config.ServicesConfig import uk.gov.hmrc.play.bootstrap.http.HttpClient -import scala.concurrent.ExecutionContext +import scala.concurrent.{ExecutionContext, Future} @Singleton class ConfigConnector @Inject()( @@ -50,4 +51,6 @@ class ConfigConnector @Inject()( def configByKey(service: String)(implicit hc: HeaderCarrier) = http.GET[ConfigByKey](s"$serviceConfigsBaseUrl/config-by-key/$service") + + def bobbyRules()(implicit hc: HeaderCarrier): Future[BobbyRuleSet] = http.GET[BobbyRuleSet](s"$serviceConfigsBaseUrl/bobby/rules") } diff --git a/app/uk/gov/hmrc/cataloguefrontend/connector/model/BobbyRule.scala b/app/uk/gov/hmrc/cataloguefrontend/connector/model/BobbyRule.scala new file mode 100644 index 000000000..05bd2bc5b --- /dev/null +++ b/app/uk/gov/hmrc/cataloguefrontend/connector/model/BobbyRule.scala @@ -0,0 +1,36 @@ +/* + * Copyright 2019 HM Revenue & Customs + * + * Licensed under the Apache License, Version 2.0 (the "License"); + * you may not use this file except in compliance with the License. + * You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + */ + +package uk.gov.hmrc.cataloguefrontend.connector.model + +import java.time.LocalDate + +import play.api.libs.json.{Json, Reads} + +case class BobbyRule(organisation: String, name: String, range: String, reason: String, from: LocalDate) { + val groupArtifactName: String = { + val wildcard = "*" + if (organisation == wildcard && name == wildcard) "*" else s"$organisation:$name" + } +} +object BobbyRule { + implicit val reader: Reads[BobbyRule] = Json.reads[BobbyRule] +} + +case class BobbyRuleSet(libraries: Seq[BobbyRule], plugins: Seq[BobbyRule]) +object BobbyRuleSet { + implicit val reader: Reads[BobbyRuleSet] = Json.reads[BobbyRuleSet] +} \ No newline at end of file diff --git a/app/uk/gov/hmrc/cataloguefrontend/service/BobbyService.scala b/app/uk/gov/hmrc/cataloguefrontend/service/BobbyService.scala new file mode 100644 index 000000000..75ad8c7a6 --- /dev/null +++ b/app/uk/gov/hmrc/cataloguefrontend/service/BobbyService.scala @@ -0,0 +1,46 @@ +/* + * Copyright 2019 HM Revenue & Customs + * + * Licensed under the Apache License, Version 2.0 (the "License"); + * you may not use this file except in compliance with the License. + * You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + */ + +package uk.gov.hmrc.cataloguefrontend.service + +import java.time.{Clock, LocalDate} + +import javax.inject.Inject +import uk.gov.hmrc.cataloguefrontend.connector.ConfigConnector +import uk.gov.hmrc.cataloguefrontend.connector.model.{BobbyRule, BobbyRuleSet} +import uk.gov.hmrc.cataloguefrontend.service.model.BobbyRulesView +import uk.gov.hmrc.http.HeaderCarrier + +import scala.concurrent.{ExecutionContext, Future} + +class BobbyService @Inject()(configConnector: ConfigConnector, clock: Clock)(implicit val ec: ExecutionContext) { + + def getRules()(implicit hc: HeaderCarrier) : Future[BobbyRulesView] = { + val today = LocalDate.now(clock) + def filterUpcoming(rule: BobbyRule) = rule.from.isAfter(today) + def filterActive(rule: BobbyRule) = rule.from.isBefore(today) || rule.from.isEqual(today) + def compareUpcoming(rule1: BobbyRule, rule2: BobbyRule) = compareRules(rule1, rule2)(_ isBefore _) + def compareActive(rule1: BobbyRule, rule2: BobbyRule) = compareRules(rule1, rule2)(_ isAfter _) + def compareRules(x: BobbyRule, y: BobbyRule)(sortDirection: (LocalDate, LocalDate) => Boolean) = + if (x.from == y.from) x.groupArtifactName < y.groupArtifactName else sortDirection(x.from, y.from) + + configConnector.bobbyRules().map(r => BobbyRulesView( + upcoming = BobbyRuleSet(libraries = r.libraries.filter(filterUpcoming).sortWith(compareUpcoming), plugins = r.plugins.filter(filterUpcoming).sortWith(compareUpcoming)), + active = BobbyRuleSet(libraries = r.libraries.filter(filterActive).sortWith(compareActive), plugins = r.plugins.filter(filterActive).sortWith(compareActive))) + ) + } + +} \ No newline at end of file diff --git a/app/uk/gov/hmrc/cataloguefrontend/service/model/BobbyRulesView.scala b/app/uk/gov/hmrc/cataloguefrontend/service/model/BobbyRulesView.scala new file mode 100644 index 000000000..14711e569 --- /dev/null +++ b/app/uk/gov/hmrc/cataloguefrontend/service/model/BobbyRulesView.scala @@ -0,0 +1,21 @@ +/* + * Copyright 2019 HM Revenue & Customs + * + * Licensed under the Apache License, Version 2.0 (the "License"); + * you may not use this file except in compliance with the License. + * You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + */ + +package uk.gov.hmrc.cataloguefrontend.service.model + +import uk.gov.hmrc.cataloguefrontend.connector.model.BobbyRuleSet + +case class BobbyRulesView (upcoming: BobbyRuleSet, active: BobbyRuleSet) \ No newline at end of file diff --git a/app/views/BobbyExplorerPage.scala.html b/app/views/BobbyExplorerPage.scala.html new file mode 100644 index 000000000..a54459bd4 --- /dev/null +++ b/app/views/BobbyExplorerPage.scala.html @@ -0,0 +1,68 @@ +@* + * Copyright 2019 HM Revenue & Customs + * + * Licensed under the Apache License, Version 2.0 (the "License"); + * you may not use this file except in compliance with the License. + * You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + *@ + +@import uk.gov.hmrc.cataloguefrontend.ViewMessages +@import uk.gov.hmrc.cataloguefrontend.connector.model.{BobbyRule, BobbyRuleSet} +@import uk.gov.hmrc.cataloguefrontend.service.model.BobbyRulesView + +@this(viewMessages: ViewMessages) + +@(rules: BobbyRulesView)(implicit request: Request[_]) + +@standard_layout(s"Bobby rules") { +
+

Bobby Rules

+
+ @bobbyRulesTimeSection(rules.upcoming, "Upcoming", "table table-striped") + @bobbyRulesTimeSection(rules.active, "Active", "table table-striped-warning") +} + +@bobbyRulesTimeSection(rulesByTime: BobbyRuleSet, heading: String, cssClass: String) = { + @if(rulesByTime.libraries.nonEmpty || rulesByTime.plugins.nonEmpty) { +

@heading

+ @bobbyRulesArtifactTypeSection(rulesByTime.libraries, "Library", cssClass) + @bobbyRulesArtifactTypeSection(rulesByTime.plugins, "Plugin", cssClass) + } +} + +@bobbyRulesArtifactTypeSection(rulesByArtifactType: Seq[BobbyRule], artifactType: String, cssClass: String) = { + @if(rulesByArtifactType.nonEmpty) { +
+ + + + + + + + + + + @rulesByArtifactType.map(bobbyRuleRow) + +
@artifactTypeVersionReasonActive from
+
+ } +} + +@bobbyRuleRow(rule: BobbyRule) = { + + @rule.groupArtifactName + @rule.range + @rule.reason + @rule.from + +} \ No newline at end of file diff --git a/app/views/standard_layout.scala.html b/app/views/standard_layout.scala.html index 4b9be2009..1380f4165 100644 --- a/app/views/standard_layout.scala.html +++ b/app/views/standard_layout.scala.html @@ -83,6 +83,7 @@ Tools