diff --git a/app/controllers/CheckYourSuspensionDetailsController.scala b/app/controllers/CheckYourSuspensionDetailsController.scala index 1f192271..e8c5e113 100644 --- a/app/controllers/CheckYourSuspensionDetailsController.scala +++ b/app/controllers/CheckYourSuspensionDetailsController.scala @@ -50,7 +50,7 @@ class CheckYourSuspensionDetailsController @Inject() ( def onPageLoad(mode: Mode): Action[AnyContent] = (identify andThen getData andThen requireData) { implicit request => logger.info("Display suspension details confirmation page") val summaryList = buildSummaryList(request.userAnswers) - Ok(view(summaryList, mode, routes.SuspensionPeriodRangeDateController.onPageLoad(mode))) + Ok(view(summaryList, mode, routes.PaymentPlanSuspendedController.onPageLoad())) } def onSubmit(mode: Mode): Action[AnyContent] = diff --git a/app/controllers/PaymentPlanSuspendedController.scala b/app/controllers/PaymentPlanSuspendedController.scala new file mode 100644 index 00000000..480e6b89 --- /dev/null +++ b/app/controllers/PaymentPlanSuspendedController.scala @@ -0,0 +1,75 @@ +/* + * Copyright 2025 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 controllers + +import controllers.actions.* +import models.UserAnswers +import models.responses.PaymentPlanDetails +import pages.SuspensionPeriodRangeDatePage + +import javax.inject.Inject +import play.api.i18n.{I18nSupport, Messages, MessagesApi} +import play.api.mvc.{Action, AnyContent, MessagesControllerComponents} +import queries.{PaymentPlanDetailsQuery, PaymentPlanReferenceQuery} +import uk.gov.hmrc.govukfrontend.views.viewmodels.summarylist.SummaryListRow +import uk.gov.hmrc.play.bootstrap.frontend.controller.FrontendBaseController +import utils.Constants +import viewmodels.checkAnswers.{AmendPaymentAmountSummary, PaymentReferenceSummary, SuspensionPeriodRangeDateSummary} +import views.html.PaymentPlanSuspendedView + +import java.time.format.DateTimeFormatter + +class PaymentPlanSuspendedController @Inject() ( + override val messagesApi: MessagesApi, + identify: IdentifierAction, + getData: DataRetrievalAction, + requireData: DataRequiredAction, + val controllerComponents: MessagesControllerComponents, + view: PaymentPlanSuspendedView +) extends FrontendBaseController + with I18nSupport { + + def onPageLoad: Action[AnyContent] = (identify andThen getData andThen requireData) { implicit request => + val userAnswers = request.userAnswers + + val maybeResult = for { + planDetails <- userAnswers.get(PaymentPlanDetailsQuery) + paymentPlanReference <- userAnswers.get(PaymentPlanReferenceQuery) + suspensionPeriodRange <- userAnswers.get(SuspensionPeriodRangeDatePage) + } yield { + val formattedStartDate = suspensionPeriodRange.startDate.format(DateTimeFormatter.ofPattern(Constants.longDateTimeFormatPattern)) + val formattedEndDate = suspensionPeriodRange.endDate.format(DateTimeFormatter.ofPattern(Constants.longDateTimeFormatPattern)) + val rows = buildRows(paymentPlanReference, userAnswers, planDetails.paymentPlanDetails) + Ok(view(paymentPlanReference, formattedStartDate, formattedEndDate, routes.PaymentPlanDetailsController.onPageLoad(), rows)) + } + + maybeResult match { + case Some(result) => result + case _ => Redirect(routes.JourneyRecoveryController.onPageLoad()) + } + } + + private def buildRows(paymentPlanReference: String, userAnswers: UserAnswers, paymentPlanDetails: PaymentPlanDetails)(implicit + messages: Messages + ): Seq[SummaryListRow] = + Seq( + Some(PaymentReferenceSummary.row(paymentPlanReference)), + Some(AmendPaymentAmountSummary.row(paymentPlanDetails.planType, paymentPlanDetails.scheduledPaymentAmount)), + SuspensionPeriodRangeDateSummary.row(userAnswers) + ).flatten + +} diff --git a/app/navigation/Navigator.scala b/app/navigation/Navigator.scala index 1e01363e..2a3d208c 100644 --- a/app/navigation/Navigator.scala +++ b/app/navigation/Navigator.scala @@ -28,48 +28,50 @@ import models.PaymentPlanType.* class Navigator @Inject() () { private val normalRoutes: Page => UserAnswers => Call = { - case PaymentDatePage => _ => routes.CheckYourAnswersController.onPageLoad() - case PaymentReferencePage => userAnswers => checkPaymentReferenceLogic(userAnswers) - case PaymentAmountPage => _ => routes.PaymentDateController.onPageLoad(NormalMode) - case PersonalOrBusinessAccountPage => _ => routes.YourBankDetailsController.onPageLoad(NormalMode) - case YourBankDetailsPage => _ => routes.BankDetailsCheckYourAnswerController.onPageLoad(NormalMode) - case BankDetailsCheckYourAnswerPage => _ => routes.ConfirmAuthorityController.onPageLoad(NormalMode) - case ConfirmAuthorityPage => nextAfterConfirmAuthority(NormalMode) - case DirectDebitSourcePage => checkDirectDebitSource - case PaymentPlanTypePage => _ => routes.PaymentReferenceController.onPageLoad(NormalMode) - case PaymentsFrequencyPage => _ => routes.RegularPaymentAmountController.onPageLoad(NormalMode) - case RegularPaymentAmountPage => _ => routes.PlanStartDateController.onPageLoad(NormalMode) - case TotalAmountDuePage => _ => routes.PlanStartDateController.onPageLoad(NormalMode) - case PlanStartDatePage => userAnswers => checkPlanStartDateLogic(userAnswers) - case PlanEndDatePage => _ => routes.CheckYourAnswersController.onPageLoad() - case YearEndAndMonthPage => _ => routes.PaymentAmountController.onPageLoad(NormalMode) - case AmendPaymentAmountPage => userAnswers => checkPaymentPlanLogic(userAnswers, NormalMode) - case AmendPlanStartDatePage => _ => routes.AmendPaymentPlanConfirmationController.onPageLoad(NormalMode) - case AmendPlanEndDatePage => _ => routes.AmendPaymentPlanConfirmationController.onPageLoad(NormalMode) - case SuspensionPeriodRangeDatePage => _ => routes.CheckYourSuspensionDetailsController.onPageLoad(NormalMode) - case CancelPaymentPlanPage => navigateFromCancelPaymentPlanPage - case _ => _ => routes.LandingController.onPageLoad() + case PaymentDatePage => _ => routes.CheckYourAnswersController.onPageLoad() + case PaymentReferencePage => userAnswers => checkPaymentReferenceLogic(userAnswers) + case PaymentAmountPage => _ => routes.PaymentDateController.onPageLoad(NormalMode) + case PersonalOrBusinessAccountPage => _ => routes.YourBankDetailsController.onPageLoad(NormalMode) + case YourBankDetailsPage => _ => routes.BankDetailsCheckYourAnswerController.onPageLoad(NormalMode) + case BankDetailsCheckYourAnswerPage => _ => routes.ConfirmAuthorityController.onPageLoad(NormalMode) + case ConfirmAuthorityPage => nextAfterConfirmAuthority(NormalMode) + case DirectDebitSourcePage => checkDirectDebitSource + case PaymentPlanTypePage => _ => routes.PaymentReferenceController.onPageLoad(NormalMode) + case PaymentsFrequencyPage => _ => routes.RegularPaymentAmountController.onPageLoad(NormalMode) + case RegularPaymentAmountPage => _ => routes.PlanStartDateController.onPageLoad(NormalMode) + case TotalAmountDuePage => _ => routes.PlanStartDateController.onPageLoad(NormalMode) + case PlanStartDatePage => userAnswers => checkPlanStartDateLogic(userAnswers) + case PlanEndDatePage => _ => routes.CheckYourAnswersController.onPageLoad() + case YearEndAndMonthPage => _ => routes.PaymentAmountController.onPageLoad(NormalMode) + case AmendPaymentAmountPage => userAnswers => checkPaymentPlanLogic(userAnswers, NormalMode) + case AmendPlanStartDatePage => _ => routes.AmendPaymentPlanConfirmationController.onPageLoad(NormalMode) + case AmendPlanEndDatePage => _ => routes.AmendPaymentPlanConfirmationController.onPageLoad(NormalMode) + case SuspensionPeriodRangeDatePage => _ => routes.CheckYourSuspensionDetailsController.onPageLoad(NormalMode) + case SuspensionDetailsCheckYourAnswerPage => _ => routes.PaymentPlanSuspendedController.onPageLoad() + case CancelPaymentPlanPage => navigateFromCancelPaymentPlanPage + case _ => _ => routes.LandingController.onPageLoad() } private val checkRouteMap: Page => UserAnswers => Call = { - case YourBankDetailsPage => _ => routes.BankDetailsCheckYourAnswerController.onPageLoad(CheckMode) - case BankDetailsCheckYourAnswerPage => _ => routes.ConfirmAuthorityController.onPageLoad(CheckMode) - case ConfirmAuthorityPage => nextAfterConfirmAuthority(CheckMode) - case DirectDebitSourcePage => checkDirectDebitSource - case PaymentReferencePage => _ => routes.CheckYourAnswersController.onPageLoad() - case PaymentAmountPage => _ => routes.CheckYourAnswersController.onPageLoad() - case PaymentDatePage => _ => routes.CheckYourAnswersController.onPageLoad() - case PlanStartDatePage => _ => routes.CheckYourAnswersController.onPageLoad() - case PlanEndDatePage => _ => routes.CheckYourAnswersController.onPageLoad() - case TotalAmountDuePage => _ => routes.CheckYourAnswersController.onPageLoad() - case PaymentsFrequencyPage => _ => routes.CheckYourAnswersController.onPageLoad() - case RegularPaymentAmountPage => _ => routes.CheckYourAnswersController.onPageLoad() - case YearEndAndMonthPage => _ => routes.CheckYourAnswersController.onPageLoad() - case AmendPaymentAmountPage => userAnswers => checkPaymentPlanLogic(userAnswers, CheckMode) - case AmendPlanStartDatePage => _ => routes.AmendPaymentPlanConfirmationController.onPageLoad(CheckMode) - case AmendPlanEndDatePage => _ => routes.AmendPaymentPlanConfirmationController.onPageLoad(CheckMode) - case SuspensionPeriodRangeDatePage => _ => routes.CheckYourSuspensionDetailsController.onPageLoad(CheckMode) - case _ => _ => routes.LandingController.onPageLoad() + case YourBankDetailsPage => _ => routes.BankDetailsCheckYourAnswerController.onPageLoad(CheckMode) + case BankDetailsCheckYourAnswerPage => _ => routes.ConfirmAuthorityController.onPageLoad(CheckMode) + case ConfirmAuthorityPage => nextAfterConfirmAuthority(CheckMode) + case DirectDebitSourcePage => checkDirectDebitSource + case PaymentReferencePage => _ => routes.CheckYourAnswersController.onPageLoad() + case PaymentAmountPage => _ => routes.CheckYourAnswersController.onPageLoad() + case PaymentDatePage => _ => routes.CheckYourAnswersController.onPageLoad() + case PlanStartDatePage => _ => routes.CheckYourAnswersController.onPageLoad() + case PlanEndDatePage => _ => routes.CheckYourAnswersController.onPageLoad() + case TotalAmountDuePage => _ => routes.CheckYourAnswersController.onPageLoad() + case PaymentsFrequencyPage => _ => routes.CheckYourAnswersController.onPageLoad() + case RegularPaymentAmountPage => _ => routes.CheckYourAnswersController.onPageLoad() + case YearEndAndMonthPage => _ => routes.CheckYourAnswersController.onPageLoad() + case AmendPaymentAmountPage => userAnswers => checkPaymentPlanLogic(userAnswers, CheckMode) + case AmendPlanStartDatePage => _ => routes.AmendPaymentPlanConfirmationController.onPageLoad(CheckMode) + case AmendPlanEndDatePage => _ => routes.AmendPaymentPlanConfirmationController.onPageLoad(CheckMode) + case SuspensionPeriodRangeDatePage => _ => routes.CheckYourSuspensionDetailsController.onPageLoad(CheckMode) + case SuspensionDetailsCheckYourAnswerPage => _ => routes.PaymentPlanSuspendedController.onPageLoad() + case _ => _ => routes.LandingController.onPageLoad() } def nextPage(page: Page, mode: Mode, userAnswers: UserAnswers): Call = mode match { diff --git a/app/views/PaymentPlanSuspendedView.scala.html b/app/views/PaymentPlanSuspendedView.scala.html new file mode 100644 index 00000000..232faaae --- /dev/null +++ b/app/views/PaymentPlanSuspendedView.scala.html @@ -0,0 +1,61 @@ +@* + * Copyright 2025 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 views.html.components.* + +@this( + layout: templates.Layout, + confirmationPanel: ConfirmationPanel, + govukInsetText: GovukInsetText, + header2: Header2, + paragraph: Paragraph, + govukSummaryList: GovukSummaryList, + link: Link +) + +@(paymentPlanReference: String, startDate: String, endDate: String, call: Call, rows:Seq[SummaryListRow])(implicit request: Request[_], messages: Messages) + +@layout(pageTitle = titleForManageJourneyNoForm(messages("paymentPlanSuspended.title")), showBackLink = false) { + + @confirmationPanel( + title = messages("paymentPlanSuspended.panel.title"), + body = Html( + s"${messages("paymentPlanSuspended.panel.p", startDate, endDate)}" + ), + classes = "govuk-!-margin-bottom-2", + isAllContentStrong = false + ) + + @header2("paymentPlanSuspended.h1") + + @paragraph(messages("paymentPlanSuspended.p1", startDate, endDate)) + + @paragraph(messages("paymentPlanSuspended.p2")) + + @header2("paymentPlanSuspended.h2") + + @govukSummaryList(SummaryList( + rows = rows + )) + + @govukInsetText( + InsetText( + content = Text(messages("paymentPlanSuspended.pleaseNote")) + ) + ) + + @link("paymentPlanSuspended.link", call.url) +} diff --git a/app/views/components/ConfirmationPanel.scala.html b/app/views/components/ConfirmationPanel.scala.html index 3ce80fdc..6f1f1fb9 100644 --- a/app/views/components/ConfirmationPanel.scala.html +++ b/app/views/components/ConfirmationPanel.scala.html @@ -21,12 +21,15 @@ @this(govukPanel: GovukPanel) -@(title: String, body: Html = Html(emptyString), classes: String = emptyString) +@(title: String, body: Html = Html(emptyString), classes: String = emptyString, isAllContentStrong: Boolean = true) @govukPanel( Panel( title = HtmlContent(title), - content = HtmlContent(s"${body.body}"), + content = if (isAllContentStrong) + HtmlContent(s"${body.body}") + else + HtmlContent(body.body), classes = classes ) ) diff --git a/conf/app.routes b/conf/app.routes index 7011b673..49053962 100644 --- a/conf/app.routes +++ b/conf/app.routes @@ -159,3 +159,5 @@ POST /check-suspension-details controllers.CheckYou GET /change-check-suspension-details controllers.CheckYourSuspensionDetailsController.onPageLoad(mode: Mode = CheckMode) POST /change-check-suspension-details controllers.CheckYourSuspensionDetailsController.onSubmit(mode: Mode = CheckMode) + +GET /payment-plan-suspended controllers.PaymentPlanSuspendedController.onPageLoad() diff --git a/conf/messages.en b/conf/messages.en index 785ec3f6..6df58c0f 100644 --- a/conf/messages.en +++ b/conf/messages.en @@ -571,3 +571,14 @@ checkYourSuspensionDetails.heading = Check your suspension details checkYourSuspensionDetails.confirm = Confirm and continue + +paymentPlanSuspended.title = Payment plan suspended +paymentPlanSuspended.panel.title = Payment plan suspended +paymentPlanSuspended.panel.p = From
{0} to {1} +paymentPlanSuspended.pleaseNote = You can print this page for your records using the print function on your browser. +paymentPlanSuspended.h1 = What happens next +paymentPlanSuspended.p1 = This payment plan has now been suspended. No payments will be taken from {0} to {1}. +paymentPlanSuspended.p2 = When the suspension period ends, your payment plan will resume on the next working day. It may take up to 36 hours for this suspension to appear in your account. +paymentPlanSuspended.h2 = Suspension details +paymentPlanSuspended.paymentReference = Payment reference +paymentPlanSuspended.link = Return to payment plan diff --git a/test/controllers/CheckYourSuspensionDetailsControllerSpec.scala b/test/controllers/CheckYourSuspensionDetailsControllerSpec.scala index d6faac73..d47c36eb 100644 --- a/test/controllers/CheckYourSuspensionDetailsControllerSpec.scala +++ b/test/controllers/CheckYourSuspensionDetailsControllerSpec.scala @@ -75,7 +75,7 @@ class CheckYourSuspensionDetailsControllerSpec extends SpecBase with MockitoSuga val result = route(application, request).value status(result) mustEqual SEE_OTHER - redirectLocation(result).value mustEqual controllers.routes.LandingController.onPageLoad().url + redirectLocation(result).value mustEqual controllers.routes.PaymentPlanSuspendedController.onPageLoad().url } } diff --git a/test/controllers/PaymentPlanSuspendedControllerSpec.scala b/test/controllers/PaymentPlanSuspendedControllerSpec.scala new file mode 100644 index 00000000..19344fbc --- /dev/null +++ b/test/controllers/PaymentPlanSuspendedControllerSpec.scala @@ -0,0 +1,201 @@ +/* + * Copyright 2025 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 controllers + +import base.SpecBase +import models.responses.PaymentPlanDetails +import models.{PaymentPlanType, SuspensionPeriodRange, UserAnswers} +import org.scalatestplus.mockito.MockitoSugar +import pages.SuspensionPeriodRangeDatePage +import play.api.Application +import play.api.mvc.Call +import play.api.test.FakeRequest +import play.api.test.Helpers.* +import queries.{PaymentPlanDetailsQuery, PaymentPlanReferenceQuery} +import uk.gov.hmrc.govukfrontend.views.viewmodels.summarylist.SummaryListRow +import utils.Constants +import viewmodels.checkAnswers.{AmendPaymentAmountSummary, PaymentReferenceSummary, SuspensionPeriodRangeDateSummary} +import views.html.PaymentPlanSuspendedView + +import java.time.format.DateTimeFormatter + +class PaymentPlanSuspendedControllerSpec extends SpecBase with MockitoSugar { + + private lazy val paymentPlanSuspendedRoute = routes.PaymentPlanSuspendedController.onPageLoad().url + + private val suspensionRange = SuspensionPeriodRange( + startDate = java.time.LocalDate.of(2025, 10, 25), + endDate = java.time.LocalDate.of(2025, 11, 16) + ) + + private val paymentPlanReference = "ppReference" + + private val mockBudgetPaymentPlanDetailResponse = + dummyPlanDetailResponse.copy(paymentPlanDetails = + dummyPlanDetailResponse.paymentPlanDetails.copy(planType = PaymentPlanType.BudgetPaymentPlan.toString) + ) + + "PaymentPlanSuspended Controller" - { + + "must return OK and the correct view for a GET when UserAnswers has all required data" in { + + val userAnswersWithData: UserAnswers = + emptyUserAnswers + .set( + PaymentPlanReferenceQuery, + paymentPlanReference + ) + .success + .value + .set( + PaymentPlanDetailsQuery, + mockBudgetPaymentPlanDetailResponse + ) + .success + .value + .set(SuspensionPeriodRangeDatePage, suspensionRange) + .success + .value + + val application = applicationBuilder(userAnswers = Some(userAnswersWithData)).build() + + def summaryList(paymentPlanReference: String, + userAnswers: UserAnswers, + paymentPlanDetails: PaymentPlanDetails, + app: Application + ): Seq[SummaryListRow] = + Seq( + Some(PaymentReferenceSummary.row(paymentPlanReference)(messages(app))), + Some(AmendPaymentAmountSummary.row(paymentPlanDetails.planType, paymentPlanDetails.scheduledPaymentAmount)(messages(app))), + SuspensionPeriodRangeDateSummary.row(userAnswers)(messages(app)) + ).flatten + + running(application) { + val request = FakeRequest(GET, paymentPlanSuspendedRoute) + + val result = route(application, request).value + + val view = application.injector.instanceOf[PaymentPlanSuspendedView] + + val formattedStartDate = userAnswersWithData + .get(SuspensionPeriodRangeDatePage) + .get + .startDate + .format(DateTimeFormatter.ofPattern(Constants.longDateTimeFormatPattern)) + val formattedEndDate = + userAnswersWithData.get(SuspensionPeriodRangeDatePage).get.endDate.format(DateTimeFormatter.ofPattern(Constants.longDateTimeFormatPattern)) + + val summaryListRows = + summaryList(paymentPlanReference, userAnswersWithData, userAnswersWithData.get(PaymentPlanDetailsQuery).get.paymentPlanDetails, application) + + status(result) mustEqual OK + + contentAsString(result) mustEqual view(paymentPlanReference, + formattedStartDate, + formattedEndDate, + Call("GET", routes.PaymentPlanDetailsController.onPageLoad().url), + summaryListRows + )( + request, + messages(application) + ).toString + } + } + + "must return Journey Recover page for a GET when UserAnswers is missing PaymentPlanReference" in { + + val userAnswersWithData: UserAnswers = + emptyUserAnswers + .set( + PaymentPlanDetailsQuery, + mockBudgetPaymentPlanDetailResponse + ) + .success + .value + .set(SuspensionPeriodRangeDatePage, suspensionRange) + .success + .value + + val application = applicationBuilder(userAnswers = Some(userAnswersWithData)).build() + + running(application) { + val request = FakeRequest(GET, paymentPlanSuspendedRoute) + + val result = route(application, request).value + + status(result) mustEqual SEE_OTHER + redirectLocation(result).value mustEqual routes.JourneyRecoveryController.onPageLoad().url + } + } + + "must return Journey Recover page for a GET when UserAnswers is missing PaymentPlanDetails" in { + + val userAnswersWithData: UserAnswers = + emptyUserAnswers + .set( + PaymentPlanReferenceQuery, + paymentPlanReference + ) + .success + .value + .set(SuspensionPeriodRangeDatePage, suspensionRange) + .success + .value + + val application = applicationBuilder(userAnswers = Some(userAnswersWithData)).build() + + running(application) { + val request = FakeRequest(GET, paymentPlanSuspendedRoute) + + val result = route(application, request).value + + status(result) mustEqual SEE_OTHER + redirectLocation(result).value mustEqual routes.JourneyRecoveryController.onPageLoad().url + } + } + + "must return Journey Recover page for a GET when UserAnswers is missing SuspensionPeriodRangeDate" in { + + val userAnswersWithData: UserAnswers = + emptyUserAnswers + .set( + PaymentPlanReferenceQuery, + paymentPlanReference + ) + .success + .value + .set( + PaymentPlanDetailsQuery, + mockBudgetPaymentPlanDetailResponse + ) + .success + .value + + val application = applicationBuilder(userAnswers = Some(userAnswersWithData)).build() + + running(application) { + val request = FakeRequest(GET, paymentPlanSuspendedRoute) + + val result = route(application, request).value + + status(result) mustEqual SEE_OTHER + redirectLocation(result).value mustEqual routes.JourneyRecoveryController.onPageLoad().url + } + } + + } +}