mirror of
https://github.com/VinylDNS/vinyldns
synced 2025-08-22 02:02:14 +00:00
DNS Change detail notices (#901)
This commit is contained in:
parent
ea7c77951c
commit
e3da818101
@ -18,7 +18,7 @@ package controllers
|
||||
|
||||
import actions.SecuritySupport
|
||||
import javax.inject.{Inject, Singleton}
|
||||
import models.{CustomLinks, Meta}
|
||||
import models.{CustomLinks, DnsChangeNotices, Meta}
|
||||
import org.slf4j.LoggerFactory
|
||||
import play.api.Configuration
|
||||
import play.api.mvc._
|
||||
@ -87,10 +87,11 @@ class FrontendController @Inject() (
|
||||
def viewBatchChange(batchId: String): Action[AnyContent] = userAction.async { implicit request =>
|
||||
logger.info(s"View Batch Change for $batchId")
|
||||
val canReview = request.user.isSuper || request.user.isSupport
|
||||
val dnsChangeNotices = configuration.get[DnsChangeNotices]("dns-change-notices")
|
||||
Future(
|
||||
Ok(
|
||||
views.html.dnsChanges
|
||||
.dnsChangeDetail(request.user.userName, canReview)
|
||||
.dnsChangeDetail(request.user.userName, canReview, dnsChangeNotices)
|
||||
)
|
||||
)
|
||||
}
|
||||
|
69
modules/portal/app/models/DnsChangeNotices.scala
Normal file
69
modules/portal/app/models/DnsChangeNotices.scala
Normal file
@ -0,0 +1,69 @@
|
||||
/*
|
||||
* Copyright 2018 Comcast Cable Communications Management, LLC
|
||||
*
|
||||
* 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 models
|
||||
|
||||
import com.typesafe.config.Config
|
||||
import models.DnsChangeNoticeType.DnsChangeNoticeType
|
||||
import models.DnsChangeStatus.DnsChangeStatus
|
||||
import play.api.libs.json.{JsValue, Json, Writes}
|
||||
import play.api.ConfigLoader
|
||||
import net.ceedubs.ficus.Ficus._
|
||||
import net.ceedubs.ficus.readers.EnumerationReader._
|
||||
|
||||
import scala.collection.JavaConverters._
|
||||
|
||||
case class DnsChangeNotices(notices: JsValue)
|
||||
|
||||
object DnsChangeNotices {
|
||||
implicit val dnsChangeNoticeWrites: Writes[DnsChangeNotice] = Json.writes[DnsChangeNotice]
|
||||
implicit val configLoader: ConfigLoader[DnsChangeNotices] =
|
||||
new ConfigLoader[DnsChangeNotices] {
|
||||
def load(config: Config, path: String): DnsChangeNotices = {
|
||||
val notices = config
|
||||
.getConfigList(path)
|
||||
.asScala
|
||||
.map(formatDnsChangeNotice)
|
||||
DnsChangeNotices(Json.toJson(notices))
|
||||
}
|
||||
}
|
||||
|
||||
def formatDnsChangeNotice(config: Config): DnsChangeNotice = {
|
||||
val status = config.as[DnsChangeStatus]("status")
|
||||
val alertType = config.as[DnsChangeNoticeType]("alertType")
|
||||
val text = config.getString("text")
|
||||
val hrefText = config.getOrElse[String]("hrefText", "")
|
||||
val href = config.getOrElse[String]("href", "")
|
||||
DnsChangeNotice(status, alertType, text, hrefText, href)
|
||||
}
|
||||
}
|
||||
case class DnsChangeNotice(
|
||||
status: DnsChangeStatus,
|
||||
alertType: DnsChangeNoticeType,
|
||||
text: String,
|
||||
hrefText: String,
|
||||
href: String
|
||||
)
|
||||
|
||||
object DnsChangeStatus extends Enumeration {
|
||||
type DnsChangeStatus = Value
|
||||
val Cancelled, Complete, Failed, PartialFailure, PendingProcessing, PendingReview, Rejected, Scheduled = Value
|
||||
}
|
||||
|
||||
object DnsChangeNoticeType extends Enumeration {
|
||||
type DnsChangeNoticeType = Value
|
||||
val info, success, warning, danger = Value
|
||||
}
|
@ -1,8 +1,8 @@
|
||||
@(rootAccountName: String, rootAccountCanReview: Boolean)(implicit request: play.api.mvc.Request[Any], customLinks: models.CustomLinks, meta: models.Meta)
|
||||
@(rootAccountName: String, rootAccountCanReview: Boolean, dnsChangeNotices: DnsChangeNotices)(implicit request: play.api.mvc.Request[Any], customLinks: models.CustomLinks, meta: models.Meta)
|
||||
|
||||
@content = {
|
||||
<!-- PAGE CONTENT -->
|
||||
<div class="right_col" role="main">
|
||||
<div class="right_col" role="main" ng-init="notices = @dnsChangeNotices.notices;">
|
||||
|
||||
<!-- BREADCRUMB -->
|
||||
<ul class="breadcrumb">
|
||||
@ -36,6 +36,9 @@
|
||||
<notification ng-model="alert"></notification>
|
||||
</div>
|
||||
</div>
|
||||
|
||||
<notice ng-model="notice" ng-if="notice"></notice>
|
||||
|
||||
<div class="row">
|
||||
<div class="col-md-12">
|
||||
<p><strong>ID:</strong> {{batch.id}}</p>
|
||||
|
@ -169,6 +169,7 @@
|
||||
<script src="/public/lib/directives/directives.modals.modal.js"></script>
|
||||
<script src="/public/lib/directives/directives.modals.record.js"></script>
|
||||
<script src="/public/lib/directives/directives.modals.zoneconnection.js"></script>
|
||||
<script src="/public/lib/directives/directives.notices.js"></script>
|
||||
<script src="/public/lib/directives/directives.notifications.js"></script>
|
||||
<script src="/public/lib/directives/directives.validations.js"></script>
|
||||
<script src="/public/lib/directives/directives.validations.zones.js"></script>
|
||||
|
@ -151,6 +151,26 @@ links = [
|
||||
}
|
||||
]
|
||||
|
||||
dns-change-notices = [
|
||||
{
|
||||
status = "Complete"
|
||||
alertType = "info"
|
||||
text = "Your changes are fully implemented. Keep in mind it may take a few hours for the changes to fully propogate out."
|
||||
},
|
||||
{
|
||||
status = "PendingReview"
|
||||
alertType = "info"
|
||||
text = "Your DNS Change requires further review. It will be approved and processed following the review."
|
||||
hrefText = "See the docs for more information."
|
||||
href = "https://www.vinyldns.io/portal/manual-review-scheduling"
|
||||
},
|
||||
{
|
||||
status = "Scheduled"
|
||||
alertType = "info"
|
||||
text = "If there are any changes in your scheduled DNS Change with a status of Needs Review they will be addressed prior to the scheduled date and time."
|
||||
}
|
||||
]
|
||||
|
||||
play.modules.enabled += "modules.VinylDNSModule"
|
||||
|
||||
# base version this image is built on
|
||||
|
@ -166,3 +166,16 @@ ul.bar_tabs>li a {
|
||||
background-color: #e6e6e6!important;
|
||||
border: 1px solid #adadad!important;
|
||||
}
|
||||
|
||||
.alert-danger a, .alert-warning a, .alert-info a, .alert-success a {
|
||||
font-weight: 600;
|
||||
text-decoration: underline;
|
||||
}
|
||||
|
||||
.alert-danger a, .alert-warning a, .alert-info a {
|
||||
color: #E9EDEF!important;
|
||||
}
|
||||
|
||||
.alert-success a {
|
||||
color: #fff!important;
|
||||
}
|
||||
|
@ -14,4 +14,4 @@
|
||||
* limitations under the License.
|
||||
*/
|
||||
|
||||
angular.module('directives.module', ['directives.validations.module', 'directives.modals.module', 'directives.notifications.module']);
|
||||
angular.module('directives.module', ['directives.validations.module', 'directives.modals.module', 'directives.notifications.module', 'directives.notices.module']);
|
||||
|
27
modules/portal/public/lib/directives/directives.notices.js
Normal file
27
modules/portal/public/lib/directives/directives.notices.js
Normal file
@ -0,0 +1,27 @@
|
||||
/*
|
||||
* Copyright 2018 Comcast Cable Communications Management, LLC
|
||||
*
|
||||
* 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.
|
||||
*/
|
||||
|
||||
angular.module('directives.notices.module', [])
|
||||
.directive('notice', function($timeout) {
|
||||
return {
|
||||
restrict: 'E',
|
||||
replace: true,
|
||||
scope: {
|
||||
ngModel: '='
|
||||
},
|
||||
templateUrl: "/public/templates/notice.html"
|
||||
}
|
||||
});
|
@ -36,6 +36,7 @@
|
||||
if (response.data.reviewTimestamp) {
|
||||
$scope.batch.reviewTimestamp = utilityService.formatDateTime(response.data.reviewTimestamp);
|
||||
}
|
||||
$scope.notice = $scope.notices.find(notice => notice['status'] == $scope.batch.status)
|
||||
}
|
||||
|
||||
return dnsChangeService
|
||||
|
4
modules/portal/public/templates/notice.html
Normal file
4
modules/portal/public/templates/notice.html
Normal file
@ -0,0 +1,4 @@
|
||||
<div class="alert" ng-class="'alert-'+ngModel.alertType" role="alert">
|
||||
{{ngModel.text}}
|
||||
<a ng-if="ngModel.href && ngModel.hrefText" href="{{ngModel.href}}" target="_blank">{{ngModel.hrefText}}</a>
|
||||
</div>
|
219
modules/portal/test/models/DnsChangeNoticesSpec.scala
Normal file
219
modules/portal/test/models/DnsChangeNoticesSpec.scala
Normal file
@ -0,0 +1,219 @@
|
||||
/*
|
||||
* Copyright 2018 Comcast Cable Communications Management, LLC
|
||||
*
|
||||
* 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 models
|
||||
|
||||
import com.typesafe.config.ConfigException
|
||||
import org.specs2.mock.Mockito
|
||||
import org.specs2.mutable.Specification
|
||||
import play.api.Configuration
|
||||
import play.api.libs.json.{JsValue, Json}
|
||||
|
||||
class DnsChangeNoticesSpec extends Specification with Mockito {
|
||||
"DnsChangeNotices" should {
|
||||
"load valid notices from config" in {
|
||||
val config = Map(
|
||||
"dns-change-notices" -> List(
|
||||
Map(
|
||||
"status" -> "Cancelled",
|
||||
"alertType" -> "info",
|
||||
"text" -> "No href or hrefText provided."
|
||||
),
|
||||
Map(
|
||||
"status" -> "Complete",
|
||||
"alertType" -> "success",
|
||||
"text" -> "href and hrefText provided.",
|
||||
"href" -> "http://example.com",
|
||||
"hrefText" -> "See more."
|
||||
),
|
||||
Map(
|
||||
"status" -> "PendingReview",
|
||||
"alertType" -> "warning",
|
||||
"text" -> "No hrefText provided.",
|
||||
"href" -> "http://example.com"
|
||||
),
|
||||
Map(
|
||||
"status" -> "Failed",
|
||||
"alertType" -> "danger",
|
||||
"text" -> "No href provided.",
|
||||
"hrefText" -> "See more."
|
||||
)
|
||||
)
|
||||
)
|
||||
|
||||
val configFormatted = Json.toJson(
|
||||
List(
|
||||
Map(
|
||||
"status" -> "Cancelled",
|
||||
"alertType" -> "info",
|
||||
"text" -> "No href or hrefText provided.",
|
||||
"href" -> "",
|
||||
"hrefText" -> ""
|
||||
),
|
||||
Map(
|
||||
"status" -> "Complete",
|
||||
"alertType" -> "success",
|
||||
"text" -> "href and hrefText provided.",
|
||||
"href" -> "http://example.com",
|
||||
"hrefText" -> "See more."
|
||||
),
|
||||
Map(
|
||||
"status" -> "PendingReview",
|
||||
"alertType" -> "warning",
|
||||
"text" -> "No hrefText provided.",
|
||||
"href" -> "http://example.com",
|
||||
"hrefText" -> ""
|
||||
),
|
||||
Map(
|
||||
"status" -> "Failed",
|
||||
"alertType" -> "danger",
|
||||
"text" -> "No href provided.",
|
||||
"href" -> "",
|
||||
"hrefText" -> "See more."
|
||||
)
|
||||
)
|
||||
)
|
||||
|
||||
val dnsChangeNotices = Configuration.from(config).get[DnsChangeNotices]("dns-change-notices")
|
||||
dnsChangeNotices.notices must beEqualTo(configFormatted)
|
||||
}
|
||||
|
||||
"load valid notices from config" in {
|
||||
val config = Map(
|
||||
"dns-change-notices" -> List()
|
||||
)
|
||||
|
||||
val configFormatted = Json.arr()
|
||||
val dnsChangeNotices = Configuration.from(config).get[DnsChangeNotices]("dns-change-notices")
|
||||
dnsChangeNotices.notices must beEqualTo(configFormatted)
|
||||
}
|
||||
|
||||
"error if no dns-change-notices key is in the config" in {
|
||||
Configuration
|
||||
.from(Map())
|
||||
.get[DnsChangeNotices]("dns-change-notices") must
|
||||
throwA[ConfigException.Missing](
|
||||
"No configuration setting found for key 'dns-change-notices'"
|
||||
)
|
||||
}
|
||||
|
||||
"error if the dns-change-notices value is not a list" in {
|
||||
Configuration
|
||||
.from(Map("dns-change-notices" -> "invalid"))
|
||||
.get[DnsChangeNotices]("dns-change-notices") must
|
||||
throwA[ConfigException.WrongType]("dns-change-notices has type STRING rather than LIST")
|
||||
}
|
||||
|
||||
"error if no text value is given" in {
|
||||
val config = Map(
|
||||
"dns-change-notices" -> List(
|
||||
Map(
|
||||
"status" -> "Cancelled",
|
||||
"alertType" -> "info"
|
||||
)
|
||||
)
|
||||
)
|
||||
|
||||
Configuration
|
||||
.from(config)
|
||||
.get[DnsChangeNotices]("dns-change-notices") must
|
||||
throwA[ConfigException.Missing]("No configuration setting found for key 'text'")
|
||||
}
|
||||
|
||||
"error if the given text value is not a string" in {
|
||||
val config = Map(
|
||||
"dns-change-notices" -> List(
|
||||
Map(
|
||||
"text" -> List("all done."),
|
||||
"status" -> "Cancelled",
|
||||
"alertType" -> "info"
|
||||
)
|
||||
)
|
||||
)
|
||||
|
||||
Configuration
|
||||
.from(config)
|
||||
.get[DnsChangeNotices]("dns-change-notices") must
|
||||
throwA[ConfigException.WrongType]("text has type LIST rather than STRING")
|
||||
}
|
||||
|
||||
"error if no status is given" in {
|
||||
val config = Map(
|
||||
"dns-change-notices" -> List(
|
||||
Map(
|
||||
"alertType" -> "info",
|
||||
"text" -> "Invalid status value"
|
||||
)
|
||||
)
|
||||
)
|
||||
|
||||
Configuration
|
||||
.from(config)
|
||||
.get[DnsChangeNotices]("dns-change-notices") must
|
||||
throwA[ConfigException.Missing]("No configuration setting found for key 'status'")
|
||||
}
|
||||
|
||||
"error if an invalid status is given" in {
|
||||
val config = Map(
|
||||
"dns-change-notices" -> List(
|
||||
Map(
|
||||
"status" -> "Invalid",
|
||||
"alertType" -> "info",
|
||||
"text" -> "Invalid status value"
|
||||
)
|
||||
)
|
||||
)
|
||||
|
||||
Configuration
|
||||
.from(config)
|
||||
.get[DnsChangeNotices]("dns-change-notices") must
|
||||
throwA[ConfigException.BadValue]
|
||||
}
|
||||
|
||||
"error if no alertType is given" in {
|
||||
val config = Map(
|
||||
"dns-change-notices" -> List(
|
||||
Map(
|
||||
"status" -> "Complete",
|
||||
"text" -> "Invalid alertType value"
|
||||
)
|
||||
)
|
||||
)
|
||||
|
||||
Configuration
|
||||
.from(config)
|
||||
.get[DnsChangeNotices]("dns-change-notices") must
|
||||
throwA[ConfigException.Missing]("No configuration setting found for key 'alertType'")
|
||||
}
|
||||
|
||||
"error if an invalid status is given" in {
|
||||
val config = Map(
|
||||
"dns-change-notices" -> List(
|
||||
Map(
|
||||
"status" -> "Invalid",
|
||||
"alertType" -> "veryBad",
|
||||
"text" -> "Invalid status value"
|
||||
)
|
||||
)
|
||||
)
|
||||
|
||||
Configuration
|
||||
.from(config)
|
||||
.get[DnsChangeNotices]("dns-change-notices") must
|
||||
throwA[ConfigException.BadValue]
|
||||
}
|
||||
}
|
||||
}
|
@ -17,6 +17,7 @@ object Dependencies {
|
||||
lazy val jaxbV = "2.3.0"
|
||||
lazy val ip4sV = "1.1.1"
|
||||
lazy val fs2V = "2.0.1"
|
||||
lazy val ficusV = "1.4.3"
|
||||
|
||||
lazy val apiDependencies = Seq(
|
||||
"com.typesafe.akka" %% "akka-http" % akkaHttpV,
|
||||
@ -50,7 +51,7 @@ object Dependencies {
|
||||
"com.47deg" %% "github4s" % "0.18.6",
|
||||
"com.comcast" %% "ip4s-core" % ip4sV,
|
||||
"com.comcast" %% "ip4s-cats" % ip4sV,
|
||||
"com.iheart" %% "ficus" % "1.4.3",
|
||||
"com.iheart" %% "ficus" % ficusV,
|
||||
"com.sun.mail" % "javax.mail" % "1.6.2",
|
||||
"javax.mail" % "javax.mail-api" % "1.6.2",
|
||||
"com.amazonaws" % "aws-java-sdk-sns" % awsV withSources()
|
||||
@ -118,6 +119,7 @@ object Dependencies {
|
||||
"com.nimbusds" % "oauth2-oidc-sdk" % "6.5",
|
||||
"com.nimbusds" % "nimbus-jose-jwt" % "7.0",
|
||||
"co.fs2" %% "fs2-core" % fs2V,
|
||||
"de.leanovate.play-mockws" %% "play-mockws" % "2.7.1" % "test"
|
||||
"de.leanovate.play-mockws" %% "play-mockws" % "2.7.1" % "test",
|
||||
"com.iheart" %% "ficus" % ficusV
|
||||
)
|
||||
}
|
||||
|
Loading…
x
Reference in New Issue
Block a user