Merge pull request #3273 from cisagov/rh/3129-domain-renewal-form

#3129 - Domain Renewal Form (Expiring Soon and Expired) - [AD]
This commit is contained in:
asaki222 2025-01-13 14:09:22 -05:00 committed by GitHub
commit a0a53ea855
No known key found for this signature in database
GPG key ID: B5690EEEBB952194
15 changed files with 444 additions and 37 deletions

View file

@ -103,3 +103,31 @@ response = registry._client.transport.receive()
```
This is helpful for debugging situations where epplib is not correctly or fully parsing the XML returned from the registry.
### Adding in a expiring soon domain
The below scenario is if you are NOT in org model mode (`organization_feature` waffle flag is off).
1. Go to the `staging` sandbox and to `/admin`
2. Go to Domains and find a domain that is actually expired by sorting the Expiration Date column
3. Click into the domain to check the expiration date
4. Click into Manage Domain to double check the expiration date as well
5. Now hold onto that domain name, and save it for the command below
6. In a terminal, run these commands:
```
cf ssh getgov-<your-intials>
/tmp/lifecycle/shell
./manage.py shell
from registrar.models import Domain, DomainInvitation
from registrar.models import User
user = User.objects.filter(first_name="<your-first-name>")
domain = Domain.objects.get_or_create(name="<that-domain-here>")
```
7. Go back to `/admin` and create Domain Information for that domain you just added in via the terminal
8. Go to Domain to find it
9. Click Manage Domain
10. Add yourself as domain manager
11. Go to the Registrar page and you should now see the expiring domain
If you want to be in the org model mode, turn the `organization_feature` waffle flag on, and add that domain via Django Admin to a portfolio to be able to view it.

View file

@ -345,6 +345,11 @@ urlpatterns = [
views.DomainSecurityEmailView.as_view(),
name="domain-security-email",
),
path(
"domain/<int:pk>/renewal",
views.DomainRenewalView.as_view(),
name="domain-renewal",
),
path(
"domain/<int:pk>/users/add",
views.DomainAddUserView.as_view(),

View file

@ -10,6 +10,7 @@ from .domain import (
DomainDsdataFormset,
DomainDsdataForm,
DomainSuborganizationForm,
DomainRenewalForm,
)
from .portfolio import (
PortfolioOrgAddressForm,

View file

@ -661,3 +661,15 @@ DomainDsdataFormset = formset_factory(
extra=0,
can_delete=True,
)
class DomainRenewalForm(forms.Form):
"""Form making sure domain renewal ack is checked"""
is_policy_acknowledged = forms.BooleanField(
required=True,
label="I have read and agree to the requirements for operating a .gov domain.",
error_messages={
"required": "Check the box if you read and agree to the requirements for operating a .gov domain."
},
)

View file

@ -326,9 +326,8 @@ class Domain(TimeStampedModel, DomainHelper):
exp_date = self.registry_expiration_date
except KeyError:
# if no expiration date from registry, set it to today
logger.warning("current expiration date not set; setting to today")
logger.warning("current expiration date not set; setting to today", exc_info=True)
exp_date = date.today()
# create RenewDomain request
request = commands.RenewDomain(name=self.name, cur_exp_date=exp_date, period=epp.Period(length, unit))
@ -338,13 +337,14 @@ class Domain(TimeStampedModel, DomainHelper):
self._cache["ex_date"] = registry.send(request, cleaned=True).res_data[0].ex_date
self.expiration_date = self._cache["ex_date"]
self.save()
except RegistryError as err:
# if registry error occurs, log the error, and raise it as well
logger.error(f"registry error renewing domain: {err}")
logger.error(f"Registry error renewing domain '{self.name}': {err}")
raise (err)
except Exception as e:
# exception raised during the save to registrar
logger.error(f"error updating expiration date in registrar: {e}")
logger.error(f"Error updating expiration date for domain '{self.name}' in registrar: {e}")
raise (e)
@Cache
@ -1575,7 +1575,7 @@ class Domain(TimeStampedModel, DomainHelper):
logger.info("Changing to DNS_NEEDED state")
logger.info("able to transition to DNS_NEEDED state")
def get_state_help_text(self) -> str:
def get_state_help_text(self, request=None) -> str:
"""Returns a str containing additional information about a given state.
Returns custom content for when the domain itself is expired."""
@ -1585,6 +1585,8 @@ class Domain(TimeStampedModel, DomainHelper):
help_text = (
"This domain has expired, but it is still online. " "To renew this domain, contact help@get.gov."
)
elif flag_is_active(request, "domain_renewal") and self.is_expiring():
help_text = "This domain will expire soon. Contact one of the listed domain managers to renew the domain."
else:
help_text = Domain.State.get_help_text(self.state)

View file

@ -1,5 +1,7 @@
{% extends "base.html" %}
{% load static %}
{% load static url_helpers %}
{% block title %}{{ domain.name }} | {% endblock %}
@ -53,8 +55,11 @@
{% endif %}
{% block domain_content %}
{% if request.path|endswith:"renewal"%}
<h1>Renew {{domain.name}} </h1>
{%else%}
<h1 class="break-word">Domain Overview</h1>
{% endif%}
{% endblock %} {# domain_content #}
{% endif %}
@ -62,4 +67,4 @@
</div>
</div>
</div>
{% endblock %} {# content #}
{% endblock %} {# content #}

View file

@ -49,10 +49,18 @@
</span>
{% if domain.get_state_help_text %}
<div class="padding-top-1 text-primary-darker">
{% if has_domain_renewal_flag and domain.is_expiring and is_domain_manager %}
This domain will expire soon. <a href="/not-available-yet">Renew to maintain access.</a>
{% if has_domain_renewal_flag and domain.is_expired and is_domain_manager %}
This domain has expired, but it is still online.
{% url 'domain-renewal' pk=domain.id as url %}
<a href="{{ url }}">Renew to maintain access.</a>
{% elif has_domain_renewal_flag and domain.is_expiring and is_domain_manager %}
This domain will expire soon.
{% url 'domain-renewal' pk=domain.id as url %}
<a href="{{ url }}">Renew to maintain access.</a>
{% elif has_domain_renewal_flag and domain.is_expiring and is_portfolio_user %}
This domain will expire soon. Contact one of the listed domain managers to renew the domain.
{% elif has_domain_renewal_flag and domain.is_expired and is_portfolio_user %}
This domain has expired, but it is still online. Contact one of the listed domain managers to renew the domain.
{% else %}
{{ domain.get_state_help_text }}
{% endif %}

View file

@ -0,0 +1,140 @@
{% extends "domain_base.html" %}
{% load static url_helpers %}
{% load custom_filters %}
{% block domain_content %}
{% block breadcrumb %}
<!-- Banner for if_policy_acknowledged -->
{% if form.is_policy_acknowledged.errors %}
<div class="usa-alert usa-alert--error usa-alert--slim margin-bottom-2">
<div class="usa-alert__body">
{% for error in form.is_policy_acknowledged.errors %}
<p class="usa-alert__text">{{ error }}</p>
{% endfor %}
</div>
</div>
{% endif %}
{% if portfolio %}
<!-- Navigation breadcrumbs -->
<nav class="usa-breadcrumb padding-top-0" aria-label="Domain breadcrumb">
<ol class="usa-breadcrumb__list">
<li class="usa-breadcrumb__list-item">
<a href="{% url 'domains' %}" class="usa-breadcrumb__link"><span>Domains</span></a>
</li>
<li class="usa-breadcrumb__list-item">
<a href="{% url 'domain' pk=domain.id %}" class="usa-breadcrumb__link"><span>{{domain.name}}</span></a>
</li>
<li class="usa-breadcrumb__list-item usa-current" aria-current="page">
<span>Renewal Form</span>
</li>
</ol>
</nav>
{% endif %}
{% endblock breadcrumb %}
{{ block.super }}
<div class="margin-top-4 tablet:grid-col-10">
<h2 class="text-bold text-primary-dark domain-name-wrap">Confirm the following information for accuracy</h2>
<p>Review these details below. We <a href="https://get.gov/domains/requirements/#what-.gov-domain-registrants-must-do" class="usa-link">
require</a> that you maintain accurate information for the domain.
The details you provide will only be used to support the administration of .gov and won't be made public.
</p>
<p>If you would like to retire your domain instead, please <a href="https://get.gov/contact/" class="usa-link">
contact us</a>. </p>
<p><em>Required fields are marked with an asterisk (<abbr class="usa-hint usa-hint--required" title="required">*</abbr>).</em>
</p>
{% url 'user-profile' as url %}
{% include "includes/summary_item.html" with title='Your contact information' value=request.user edit_link=url editable=is_editable contact='true' %}
{% if analyst_action != 'edit' or analyst_action_location != domain.pk %}
{% if is_portfolio_user and not is_domain_manager %}
<div class="usa-alert usa-alert--info usa-alert--slim">
<div class="usa-alert__body">
<p class="usa-alert__text ">
You don't have access to manage {{domain.name}}. If you need to make updates, contact one of the listed domain managers.
</p>
</div>
</div>
{% endif %}
{% endif %}
{% url 'domain-security-email' pk=domain.id as url %}
{% if security_email is not None and security_email not in hidden_security_emails%}
{% include "includes/summary_item.html" with title='Security email' value=security_email custom_text_for_value_none='We strongly recommend that you provide a security email. This email will allow the public to report observed or suspected security issues on your domain.' edit_link=url editable=is_editable %}
{% else %}
{% include "includes/summary_item.html" with title='Security email' value='None provided' custom_text_for_value_none='We strongly recommend that you provide a security email. This email will allow the public to report observed or suspected security issues on your domain.' edit_link=url editable=is_editable %}
{% endif %}
{% url 'domain-users' pk=domain.id as url %}
{% if portfolio %}
{% include "includes/summary_item.html" with title='Domain managers' domain_permissions=True value=domain edit_link=url editable=is_editable %}
{% else %}
{% include "includes/summary_item.html" with title='Domain managers' list=True users=True value=domain.permissions.all edit_link=url editable=is_editable %}
{% endif %}
<div class="border-top-1px border-primary-dark padding-top-1 margin-top-3 margin-bottom-2">
<fieldset class="usa-fieldset">
<legend>
<h3 class="summary-item__title
font-sans-md
text-primary-dark
text-semibold
margin-top-0
margin-bottom-05
padding-right-1">
Acknowledgement of .gov domain requirements </h3>
</legend>
<form method="post" action="{% url 'domain-renewal' pk=domain.id %}">
{% csrf_token %}
<div class="usa-checkbox">
{% if form.is_policy_acknowledged.errors %}
{% for error in form.is_policy_acknowledged.errors %}
<div class="usa-error-message display-flex" role="alert">
<svg class="usa-icon usa-icon--large" focusable="true" role="img" aria-label="Error">
<use xlink:href="{%static 'img/sprite.svg'%}#error"></use>
</svg>
<span class="margin-left-05">{{ error }}</span>
</div>
{% endfor %}
</div>
{% endif %}
<input type="hidden" name="is_policy_acknowledged" value="False">
<input
class="usa-checkbox__input"
id="renewal-checkbox"
type="checkbox"
name="is_policy_acknowledged"
value="True"
{% if form.is_policy_acknowledged.value %}checked{% endif %}
>
<label class="usa-checkbox__label" for="renewal-checkbox">
I read and agree to the
<a href="https://get.gov/domains/requirements/" class="usa-link">
requirements for operating a .gov domain
</a>.
<abbr class="usa-hint usa-hint--required" title="required">*</abbr>
</label>
</div>
<button
type="submit"
name="submit_button"
value="next"
class="usa-button margin-top-3"
> Submit
</button>
</form>
</fieldset>
</div> <!-- End of the acknowledgement section div -->
</div>
{% endblock %} {# domain_content #}

View file

@ -80,7 +80,16 @@
{% include "includes/domain_sidenav_item.html" with item_text="Domain managers" %}
{% endwith %}
{% if has_domain_renewal_flag and is_domain_manager%}
{% if domain.is_expiring or domain.is_expired %}
{% with url_name="domain-renewal" %}
{% include "includes/domain_sidenav_item.html" with item_text="Renewal form" %}
{% endwith %}
{% endif %}
{% endif %}
{% endif %}
</ul>
</nav>
</div>
</div>

View file

@ -172,7 +172,7 @@
>Deleted</label
>
</div>
{% if has_domain_renewal_flag and num_expiring_domains > 0 %}
{% if has_domain_renewal_flag %}
<div class="usa-checkbox">
<input
class="usa-checkbox__input"

View file

@ -127,15 +127,15 @@
</ul>
{% endif %}
{% else %}
<p class="margin-top-0 margin-bottom-0">
{% if custom_text_for_value_none %}
<p class="margin-top-0 text-base-dark">{{ custom_text_for_value_none }}</p>
{% endif %}
{% if value %}
{{ value }}
{% elif custom_text_for_value_none %}
{{ custom_text_for_value_none }}
{% else %}
{% endif %}
{% if not value %}
None
{% endif %}
</p>
{% endif %}
</div>

View file

@ -200,6 +200,7 @@ def is_domain_subpage(path):
"domain-users-add",
"domain-request-delete",
"domain-user-delete",
"domain-renewal",
"invitation-cancel",
]
return get_url_name(path) in url_names

View file

@ -439,35 +439,47 @@ class TestDomainDetailDomainRenewal(TestDomainOverview):
username="usertest",
)
self.expiringdomain, _ = Domain.objects.get_or_create(
name="expiringdomain.gov",
self.domaintorenew, _ = Domain.objects.get_or_create(
name="domainrenewal.gov",
)
UserDomainRole.objects.get_or_create(
user=self.user, domain=self.expiringdomain, role=UserDomainRole.Roles.MANAGER
user=self.user, domain=self.domaintorenew, role=UserDomainRole.Roles.MANAGER
)
DomainInformation.objects.get_or_create(creator=self.user, domain=self.expiringdomain)
DomainInformation.objects.get_or_create(creator=self.user, domain=self.domaintorenew)
self.portfolio, _ = Portfolio.objects.get_or_create(organization_name="Test org", creator=self.user)
self.user.save()
def custom_is_expired(self):
def expiration_date_one_year_out(self):
todays_date = datetime.today()
new_expiration_date = todays_date.replace(year=todays_date.year + 1)
return new_expiration_date
def custom_is_expired_false(self):
return False
def custom_is_expired_true(self):
return True
def custom_is_expiring(self):
return True
def custom_renew_domain(self):
self.domain_with_ip.expiration_date = self.expiration_date_one_year_out()
self.domain_with_ip.save()
@override_flag("domain_renewal", active=True)
def test_expiring_domain_on_detail_page_as_domain_manager(self):
self.client.force_login(self.user)
with patch.object(Domain, "is_expiring", self.custom_is_expiring), patch.object(
Domain, "is_expired", self.custom_is_expired
Domain, "is_expired", self.custom_is_expired_false
):
self.assertEquals(self.expiringdomain.state, Domain.State.UNKNOWN)
self.assertEquals(self.domaintorenew.state, Domain.State.UNKNOWN)
detail_page = self.client.get(
reverse("domain", kwargs={"pk": self.expiringdomain.id}),
reverse("domain", kwargs={"pk": self.domaintorenew.id}),
)
self.assertContains(detail_page, "Expiring soon")
@ -498,17 +510,17 @@ class TestDomainDetailDomainRenewal(TestDomainOverview):
UserPortfolioPermissionChoices.VIEW_ALL_DOMAINS,
],
)
expiringdomain2, _ = Domain.objects.get_or_create(name="bogusdomain2.gov")
domaintorenew2, _ = Domain.objects.get_or_create(name="bogusdomain2.gov")
DomainInformation.objects.get_or_create(
creator=non_dom_manage_user, domain=expiringdomain2, portfolio=self.portfolio
creator=non_dom_manage_user, domain=domaintorenew2, portfolio=self.portfolio
)
non_dom_manage_user.refresh_from_db()
self.client.force_login(non_dom_manage_user)
with patch.object(Domain, "is_expiring", self.custom_is_expiring), patch.object(
Domain, "is_expired", self.custom_is_expired
Domain, "is_expired", self.custom_is_expired_false
):
detail_page = self.client.get(
reverse("domain", kwargs={"pk": expiringdomain2.id}),
reverse("domain", kwargs={"pk": domaintorenew2.id}),
)
self.assertContains(detail_page, "Contact one of the listed domain managers to renew the domain.")
@ -517,20 +529,164 @@ class TestDomainDetailDomainRenewal(TestDomainOverview):
def test_expiring_domain_on_detail_page_in_org_model_as_a_domain_manager(self):
portfolio, _ = Portfolio.objects.get_or_create(organization_name="Test org2", creator=self.user)
expiringdomain3, _ = Domain.objects.get_or_create(name="bogusdomain3.gov")
domaintorenew3, _ = Domain.objects.get_or_create(name="bogusdomain3.gov")
UserDomainRole.objects.get_or_create(user=self.user, domain=expiringdomain3, role=UserDomainRole.Roles.MANAGER)
DomainInformation.objects.get_or_create(creator=self.user, domain=expiringdomain3, portfolio=portfolio)
UserDomainRole.objects.get_or_create(user=self.user, domain=domaintorenew3, role=UserDomainRole.Roles.MANAGER)
DomainInformation.objects.get_or_create(creator=self.user, domain=domaintorenew3, portfolio=portfolio)
self.user.refresh_from_db()
self.client.force_login(self.user)
with patch.object(Domain, "is_expiring", self.custom_is_expiring), patch.object(
Domain, "is_expired", self.custom_is_expired
Domain, "is_expired", self.custom_is_expired_false
):
detail_page = self.client.get(
reverse("domain", kwargs={"pk": expiringdomain3.id}),
reverse("domain", kwargs={"pk": domaintorenew3.id}),
)
self.assertContains(detail_page, "Renew to maintain access")
@override_flag("domain_renewal", active=True)
def test_domain_renewal_form_and_sidebar_expiring(self):
self.client.force_login(self.user)
with patch.object(Domain, "is_expiring", self.custom_is_expiring), patch.object(
Domain, "is_expiring", self.custom_is_expiring
):
# Grab the detail page
detail_page = self.client.get(
reverse("domain", kwargs={"pk": self.domaintorenew.id}),
)
# Make sure we see the link as a domain manager
self.assertContains(detail_page, "Renew to maintain access")
# Make sure we can see Renewal form on the sidebar since it's expiring
self.assertContains(detail_page, "Renewal form")
# Grab link to the renewal page
renewal_form_url = reverse("domain-renewal", kwargs={"pk": self.domaintorenew.id})
self.assertContains(detail_page, f'href="{renewal_form_url}"')
# Simulate clicking the link
response = self.client.get(renewal_form_url)
self.assertEqual(response.status_code, 200)
self.assertContains(response, f"Renew {self.domaintorenew.name}")
@override_flag("domain_renewal", active=True)
def test_domain_renewal_form_and_sidebar_expired(self):
self.client.force_login(self.user)
with patch.object(Domain, "is_expired", self.custom_is_expired_true), patch.object(
Domain, "is_expired", self.custom_is_expired_true
):
# Grab the detail page
detail_page = self.client.get(
reverse("domain", kwargs={"pk": self.domaintorenew.id}),
)
print("puglesss", self.domaintorenew.is_expired)
# Make sure we see the link as a domain manager
self.assertContains(detail_page, "Renew to maintain access")
# Make sure we can see Renewal form on the sidebar since it's expired
self.assertContains(detail_page, "Renewal form")
# Grab link to the renewal page
renewal_form_url = reverse("domain-renewal", kwargs={"pk": self.domaintorenew.id})
self.assertContains(detail_page, f'href="{renewal_form_url}"')
# Simulate clicking the link
response = self.client.get(renewal_form_url)
self.assertEqual(response.status_code, 200)
self.assertContains(response, f"Renew {self.domaintorenew.name}")
@override_flag("domain_renewal", active=True)
def test_domain_renewal_form_your_contact_info_edit(self):
with less_console_noise():
# Start on the Renewal page for the domain
renewal_page = self.app.get(reverse("domain-renewal", kwargs={"pk": self.domain_with_ip.id}))
# Verify we see "Your contact information" on the renewal form
self.assertContains(renewal_page, "Your contact information")
# Verify that the "Edit" button for Your contact is there and links to correct URL
edit_button_url = reverse("user-profile")
self.assertContains(renewal_page, f'href="{edit_button_url}"')
# Simulate clicking on edit button
edit_page = renewal_page.click(href=edit_button_url, index=1)
self.assertEqual(edit_page.status_code, 200)
self.assertContains(edit_page, "Review the details below and update any required information")
@override_flag("domain_renewal", active=True)
def test_domain_renewal_form_security_email_edit(self):
with less_console_noise():
# Start on the Renewal page for the domain
renewal_page = self.app.get(reverse("domain-renewal", kwargs={"pk": self.domain_with_ip.id}))
# Verify we see "Security email" on the renewal form
self.assertContains(renewal_page, "Security email")
# Verify we see "strong recommend" blurb
self.assertContains(renewal_page, "We strongly recommend that you provide a security email.")
# Verify that the "Edit" button for Security email is there and links to correct URL
edit_button_url = reverse("domain-security-email", kwargs={"pk": self.domain_with_ip.id})
self.assertContains(renewal_page, f'href="{edit_button_url}"')
# Simulate clicking on edit button
edit_page = renewal_page.click(href=edit_button_url, index=1)
self.assertEqual(edit_page.status_code, 200)
self.assertContains(edit_page, "A security contact should be capable of evaluating")
@override_flag("domain_renewal", active=True)
def test_domain_renewal_form_domain_manager_edit(self):
with less_console_noise():
# Start on the Renewal page for the domain
renewal_page = self.app.get(reverse("domain-renewal", kwargs={"pk": self.domain_with_ip.id}))
# Verify we see "Domain managers" on the renewal form
self.assertContains(renewal_page, "Domain managers")
# Verify that the "Edit" button for Domain managers is there and links to correct URL
edit_button_url = reverse("domain-users", kwargs={"pk": self.domain_with_ip.id})
self.assertContains(renewal_page, f'href="{edit_button_url}"')
# Simulate clicking on edit button
edit_page = renewal_page.click(href=edit_button_url, index=1)
self.assertEqual(edit_page.status_code, 200)
self.assertContains(edit_page, "Domain managers can update all information related to a domain")
@override_flag("domain_renewal", active=True)
def test_ack_checkbox_not_checked(self):
# Grab the renewal URL
renewal_url = reverse("domain-renewal", kwargs={"pk": self.domain_with_ip.id})
# Test that the checkbox is not checked
response = self.client.post(renewal_url, data={"submit_button": "next"})
error_message = "Check the box if you read and agree to the requirements for operating a .gov domain."
self.assertContains(response, error_message)
@override_flag("domain_renewal", active=True)
def test_ack_checkbox_checked(self):
# Grab the renewal URL
with patch.object(Domain, "renew_domain", self.custom_renew_domain):
renewal_url = reverse("domain-renewal", kwargs={"pk": self.domain_with_ip.id})
# Click the check, and submit
response = self.client.post(renewal_url, data={"is_policy_acknowledged": "on", "submit_button": "next"})
# Check that it redirects after a successfully submits
self.assertRedirects(response, reverse("domain", kwargs={"pk": self.domain_with_ip.id}))
# Check for the updated expiration
formatted_new_expiration_date = self.expiration_date_one_year_out().strftime("%b. %-d, %Y")
redirect_response = self.client.get(reverse("domain", kwargs={"pk": self.domain_with_ip.id}), follow=True)
self.assertContains(redirect_response, formatted_new_expiration_date)
class TestDomainManagers(TestDomainOverview):
@classmethod
@ -2660,7 +2816,6 @@ class TestDomainRenewal(TestWithUser):
UserDomainRole.objects.filter(user=self.user, domain=self.domain_with_expiring_soon_date).delete()
self.client.force_login(self.user)
domains_page = self.client.get("/")
self.assertNotContains(domains_page, "Expiring soon")
self.assertNotContains(domains_page, "will expire soon")
@less_console_noise_decorator
@ -2698,5 +2853,4 @@ class TestDomainRenewal(TestWithUser):
UserDomainRole.objects.filter(user=self.user, domain=self.domain_with_expiring_soon_date).delete()
self.client.force_login(self.user)
domains_page = self.client.get("/")
self.assertNotContains(domains_page, "Expiring soon")
self.assertNotContains(domains_page, "will expire soon")

View file

@ -14,6 +14,7 @@ from .domain import (
DomainInvitationCancelView,
DomainDeleteUserView,
PrototypeDomainDNSRecordView,
DomainRenewalView,
)
from .user_profile import UserProfileView, FinishProfileSetupView
from .health import *

View file

@ -12,11 +12,11 @@ from django.contrib import messages
from django.contrib.messages.views import SuccessMessageMixin
from django.db import IntegrityError
from django.http import HttpResponseRedirect
from django.shortcuts import redirect
from django.shortcuts import redirect, render, get_object_or_404
from django.urls import reverse
from django.views.generic.edit import FormMixin
from django.conf import settings
from registrar.forms.domain import DomainSuborganizationForm
from registrar.forms.domain import DomainSuborganizationForm, DomainRenewalForm
from registrar.models import (
Domain,
DomainRequest,
@ -311,6 +311,47 @@ class DomainView(DomainBaseView):
self._update_session_with_domain()
class DomainRenewalView(DomainView):
"""Domain detail overview page."""
template_name = "domain_renewal.html"
def post(self, request, pk):
domain = get_object_or_404(Domain, id=pk)
form = DomainRenewalForm(request.POST)
if form.is_valid():
# check for key in the post request data
if "submit_button" in request.POST:
try:
domain.renew_domain()
messages.success(request, "This domain has been renewed for one year.")
except Exception:
messages.error(
request,
"This domain has not been renewed for one year, "
"please email help@get.gov if this problem persists.",
)
return HttpResponseRedirect(reverse("domain", kwargs={"pk": pk}))
# if not valid, render the template with error messages
# passing editable, has_domain_renewal_flag, and is_editable for re-render
return render(
request,
"domain_renewal.html",
{
"domain": domain,
"form": form,
"is_editable": True,
"has_domain_renewal_flag": True,
"is_domain_manager": True,
},
)
class DomainOrgNameAddressView(DomainFormBaseView):
"""Organization view"""