mirror of
https://github.com/cisagov/manage.get.gov.git
synced 2025-08-15 05:54:11 +02:00
Merge branch 'main' into dk/902-epp-dnssec
This commit is contained in:
commit
59d68dee14
25 changed files with 184 additions and 82 deletions
|
@ -11,6 +11,7 @@ applications:
|
||||||
command: ./run.sh
|
command: ./run.sh
|
||||||
health-check-type: http
|
health-check-type: http
|
||||||
health-check-http-endpoint: /health
|
health-check-http-endpoint: /health
|
||||||
|
health-check-invocation-timeout: 40
|
||||||
env:
|
env:
|
||||||
# Send stdout and stderr straight to the terminal without buffering
|
# Send stdout and stderr straight to the terminal without buffering
|
||||||
PYTHONUNBUFFERED: yup
|
PYTHONUNBUFFERED: yup
|
||||||
|
|
|
@ -11,6 +11,7 @@ applications:
|
||||||
command: ./run.sh
|
command: ./run.sh
|
||||||
health-check-type: http
|
health-check-type: http
|
||||||
health-check-http-endpoint: /health
|
health-check-http-endpoint: /health
|
||||||
|
health-check-invocation-timeout: 40
|
||||||
env:
|
env:
|
||||||
# Send stdout and stderr straight to the terminal without buffering
|
# Send stdout and stderr straight to the terminal without buffering
|
||||||
PYTHONUNBUFFERED: yup
|
PYTHONUNBUFFERED: yup
|
||||||
|
|
|
@ -11,6 +11,7 @@ applications:
|
||||||
command: ./run.sh
|
command: ./run.sh
|
||||||
health-check-type: http
|
health-check-type: http
|
||||||
health-check-http-endpoint: /health
|
health-check-http-endpoint: /health
|
||||||
|
health-check-invocation-timeout: 40
|
||||||
env:
|
env:
|
||||||
# Send stdout and stderr straight to the terminal without buffering
|
# Send stdout and stderr straight to the terminal without buffering
|
||||||
PYTHONUNBUFFERED: yup
|
PYTHONUNBUFFERED: yup
|
||||||
|
|
|
@ -11,6 +11,7 @@ applications:
|
||||||
command: ./run.sh
|
command: ./run.sh
|
||||||
health-check-type: http
|
health-check-type: http
|
||||||
health-check-http-endpoint: /health
|
health-check-http-endpoint: /health
|
||||||
|
health-check-invocation-timeout: 40
|
||||||
env:
|
env:
|
||||||
# Send stdout and stderr straight to the terminal without buffering
|
# Send stdout and stderr straight to the terminal without buffering
|
||||||
PYTHONUNBUFFERED: yup
|
PYTHONUNBUFFERED: yup
|
||||||
|
|
|
@ -11,6 +11,7 @@ applications:
|
||||||
command: ./run.sh
|
command: ./run.sh
|
||||||
health-check-type: http
|
health-check-type: http
|
||||||
health-check-http-endpoint: /health
|
health-check-http-endpoint: /health
|
||||||
|
health-check-invocation-timeout: 40
|
||||||
env:
|
env:
|
||||||
# Send stdout and stderr straight to the terminal without buffering
|
# Send stdout and stderr straight to the terminal without buffering
|
||||||
PYTHONUNBUFFERED: yup
|
PYTHONUNBUFFERED: yup
|
||||||
|
|
|
@ -11,6 +11,7 @@ applications:
|
||||||
command: ./run.sh
|
command: ./run.sh
|
||||||
health-check-type: http
|
health-check-type: http
|
||||||
health-check-http-endpoint: /health
|
health-check-http-endpoint: /health
|
||||||
|
health-check-invocation-timeout: 40
|
||||||
env:
|
env:
|
||||||
# Send stdout and stderr straight to the terminal without buffering
|
# Send stdout and stderr straight to the terminal without buffering
|
||||||
PYTHONUNBUFFERED: yup
|
PYTHONUNBUFFERED: yup
|
||||||
|
|
|
@ -11,6 +11,7 @@ applications:
|
||||||
command: ./run.sh
|
command: ./run.sh
|
||||||
health-check-type: http
|
health-check-type: http
|
||||||
health-check-http-endpoint: /health
|
health-check-http-endpoint: /health
|
||||||
|
health-check-invocation-timeout: 40
|
||||||
env:
|
env:
|
||||||
# Send stdout and stderr straight to the terminal without buffering
|
# Send stdout and stderr straight to the terminal without buffering
|
||||||
PYTHONUNBUFFERED: yup
|
PYTHONUNBUFFERED: yup
|
||||||
|
|
|
@ -11,6 +11,7 @@ applications:
|
||||||
command: ./run.sh
|
command: ./run.sh
|
||||||
health-check-type: http
|
health-check-type: http
|
||||||
health-check-http-endpoint: /health
|
health-check-http-endpoint: /health
|
||||||
|
health-check-invocation-timeout: 40
|
||||||
env:
|
env:
|
||||||
# Send stdout and stderr straight to the terminal without buffering
|
# Send stdout and stderr straight to the terminal without buffering
|
||||||
PYTHONUNBUFFERED: yup
|
PYTHONUNBUFFERED: yup
|
||||||
|
|
|
@ -11,6 +11,7 @@ applications:
|
||||||
command: ./run.sh
|
command: ./run.sh
|
||||||
health-check-type: http
|
health-check-type: http
|
||||||
health-check-http-endpoint: /health
|
health-check-http-endpoint: /health
|
||||||
|
health-check-invocation-timeout: 40
|
||||||
env:
|
env:
|
||||||
# Send stdout and stderr straight to the terminal without buffering
|
# Send stdout and stderr straight to the terminal without buffering
|
||||||
PYTHONUNBUFFERED: yup
|
PYTHONUNBUFFERED: yup
|
||||||
|
|
|
@ -11,6 +11,7 @@ applications:
|
||||||
command: ./run.sh
|
command: ./run.sh
|
||||||
health-check-type: http
|
health-check-type: http
|
||||||
health-check-http-endpoint: /health
|
health-check-http-endpoint: /health
|
||||||
|
health-check-invocation-timeout: 40
|
||||||
env:
|
env:
|
||||||
# Send stdout and stderr straight to the terminal without buffering
|
# Send stdout and stderr straight to the terminal without buffering
|
||||||
PYTHONUNBUFFERED: yup
|
PYTHONUNBUFFERED: yup
|
||||||
|
|
|
@ -11,6 +11,7 @@ applications:
|
||||||
command: ./run.sh
|
command: ./run.sh
|
||||||
health-check-type: http
|
health-check-type: http
|
||||||
health-check-http-endpoint: /health
|
health-check-http-endpoint: /health
|
||||||
|
health-check-invocation-timeout: 40
|
||||||
env:
|
env:
|
||||||
# Send stdout and stderr straight to the terminal without buffering
|
# Send stdout and stderr straight to the terminal without buffering
|
||||||
PYTHONUNBUFFERED: yup
|
PYTHONUNBUFFERED: yup
|
||||||
|
|
|
@ -11,6 +11,7 @@ applications:
|
||||||
command: ./run.sh
|
command: ./run.sh
|
||||||
health-check-type: http
|
health-check-type: http
|
||||||
health-check-http-endpoint: /health
|
health-check-http-endpoint: /health
|
||||||
|
health-check-invocation-timeout: 40
|
||||||
env:
|
env:
|
||||||
# Send stdout and stderr straight to the terminal without buffering
|
# Send stdout and stderr straight to the terminal without buffering
|
||||||
PYTHONUNBUFFERED: yup
|
PYTHONUNBUFFERED: yup
|
||||||
|
|
|
@ -11,6 +11,7 @@ applications:
|
||||||
command: ./run.sh
|
command: ./run.sh
|
||||||
health-check-type: http
|
health-check-type: http
|
||||||
health-check-http-endpoint: /health
|
health-check-http-endpoint: /health
|
||||||
|
health-check-invocation-timeout: 40
|
||||||
env:
|
env:
|
||||||
# Send stdout and stderr straight to the terminal without buffering
|
# Send stdout and stderr straight to the terminal without buffering
|
||||||
PYTHONUNBUFFERED: yup
|
PYTHONUNBUFFERED: yup
|
||||||
|
|
|
@ -11,6 +11,7 @@ applications:
|
||||||
command: ./run.sh
|
command: ./run.sh
|
||||||
health-check-type: http
|
health-check-type: http
|
||||||
health-check-http-endpoint: /health
|
health-check-http-endpoint: /health
|
||||||
|
health-check-invocation-timeout: 40
|
||||||
env:
|
env:
|
||||||
# Send stdout and stderr straight to the terminal without buffering
|
# Send stdout and stderr straight to the terminal without buffering
|
||||||
PYTHONUNBUFFERED: yup
|
PYTHONUNBUFFERED: yup
|
||||||
|
|
|
@ -399,6 +399,11 @@ a.usa-button--unstyled:visited {
|
||||||
border-color: color('accent-cool-lighter');
|
border-color: color('accent-cool-lighter');
|
||||||
}
|
}
|
||||||
|
|
||||||
|
.dotgov-status-box--action-need {
|
||||||
|
background-color: color('warning-lighter');
|
||||||
|
border-color: color('warning');
|
||||||
|
}
|
||||||
|
|
||||||
#wrapper {
|
#wrapper {
|
||||||
padding-top: units(3);
|
padding-top: units(3);
|
||||||
padding-bottom: units(6) * 2 ; //Workaround because USWDS units jump from 10 to 15
|
padding-bottom: units(6) * 2 ; //Workaround because USWDS units jump from 10 to 15
|
||||||
|
|
|
@ -0,0 +1,24 @@
|
||||||
|
# Generated by Django 4.2.1 on 2023-09-27 00:18
|
||||||
|
|
||||||
|
from django.db import migrations, models
|
||||||
|
|
||||||
|
|
||||||
|
class Migration(migrations.Migration):
|
||||||
|
dependencies = [
|
||||||
|
("registrar", "0031_transitiondomain_and_more"),
|
||||||
|
]
|
||||||
|
|
||||||
|
operations = [
|
||||||
|
migrations.AlterField(
|
||||||
|
model_name="transitiondomain",
|
||||||
|
name="status",
|
||||||
|
field=models.CharField(
|
||||||
|
blank=True,
|
||||||
|
choices=[("ready", "Ready"), ("hold", "Hold")],
|
||||||
|
default="ready",
|
||||||
|
help_text="domain status during the transfer",
|
||||||
|
max_length=255,
|
||||||
|
verbose_name="Status",
|
||||||
|
),
|
||||||
|
),
|
||||||
|
]
|
|
@ -1006,28 +1006,50 @@ class Domain(TimeStampedModel, DomainHelper):
|
||||||
for extension in returned_extensions:
|
for extension in returned_extensions:
|
||||||
if isinstance(extension, extensions.DNSSECExtension):
|
if isinstance(extension, extensions.DNSSECExtension):
|
||||||
cleaned["dnssecdata"] = extension
|
cleaned["dnssecdata"] = extension
|
||||||
|
# Capture and store old hosts and contacts from cache if they exist
|
||||||
|
old_cache_hosts = self._cache.get("hosts")
|
||||||
|
old_cache_contacts = self._cache.get("contacts")
|
||||||
|
|
||||||
# get contact info, if there are any
|
# get contact info, if there are any
|
||||||
if (
|
if (
|
||||||
# fetch_contacts and
|
fetch_contacts
|
||||||
"_contacts" in cleaned
|
and "_contacts" in cleaned
|
||||||
and isinstance(cleaned["_contacts"], list)
|
and isinstance(cleaned["_contacts"], list)
|
||||||
and len(cleaned["_contacts"])
|
and len(cleaned["_contacts"])
|
||||||
):
|
):
|
||||||
cleaned["contacts"] = []
|
cleaned["contacts"] = self._fetch_contacts(cleaned["_contacts"])
|
||||||
for domainContact in cleaned["_contacts"]:
|
# We're only getting contacts, so retain the old
|
||||||
# we do not use _get_or_create_* because we expect the object we
|
# hosts that existed in cache (if they existed)
|
||||||
# just asked the registry for still exists --
|
# and pass them along.
|
||||||
# if not, that's a problem
|
if old_cache_hosts is not None:
|
||||||
|
cleaned["hosts"] = old_cache_hosts
|
||||||
|
|
||||||
# TODO- discuss-should we check if contact is in public contacts
|
# get nameserver info, if there are any
|
||||||
# and add it if not- this is really to keep in mine the transisiton
|
if (
|
||||||
|
fetch_hosts
|
||||||
|
and "_hosts" in cleaned
|
||||||
|
and isinstance(cleaned["_hosts"], list)
|
||||||
|
and len(cleaned["_hosts"])
|
||||||
|
):
|
||||||
|
cleaned["hosts"] = self._fetch_hosts(cleaned["_hosts"])
|
||||||
|
# We're only getting hosts, so retain the old
|
||||||
|
# contacts that existed in cache (if they existed)
|
||||||
|
# and pass them along.
|
||||||
|
if old_cache_contacts is not None:
|
||||||
|
cleaned["contacts"] = old_cache_contacts
|
||||||
|
|
||||||
|
# replace the prior cache with new data
|
||||||
|
self._cache = cleaned
|
||||||
|
|
||||||
|
except RegistryError as e:
|
||||||
|
logger.error(e)
|
||||||
|
|
||||||
|
def _fetch_contacts(self, contact_data):
|
||||||
|
"""Fetch contact info."""
|
||||||
|
contacts = []
|
||||||
|
for domainContact in contact_data:
|
||||||
req = commands.InfoContact(id=domainContact.contact)
|
req = commands.InfoContact(id=domainContact.contact)
|
||||||
data = registry.send(req, cleaned=True).res_data[0]
|
data = registry.send(req, cleaned=True).res_data[0]
|
||||||
|
|
||||||
# extract properties from response
|
|
||||||
# (Ellipsis is used to mean "null")
|
|
||||||
# convert this to use PublicContactInstead
|
|
||||||
contact = {
|
contact = {
|
||||||
"id": domainContact.contact,
|
"id": domainContact.contact,
|
||||||
"type": domainContact.type,
|
"type": domainContact.type,
|
||||||
|
@ -1042,29 +1064,15 @@ class Domain(TimeStampedModel, DomainHelper):
|
||||||
"up_date": getattr(data, "up_date", ...),
|
"up_date": getattr(data, "up_date", ...),
|
||||||
"voice": getattr(data, "voice", ...),
|
"voice": getattr(data, "voice", ...),
|
||||||
}
|
}
|
||||||
|
contacts.append({k: v for k, v in contact.items() if v is not ...})
|
||||||
|
return contacts
|
||||||
|
|
||||||
cleaned["contacts"].append(
|
def _fetch_hosts(self, host_data):
|
||||||
{k: v for k, v in contact.items() if v is not ...}
|
"""Fetch host info."""
|
||||||
)
|
hosts = []
|
||||||
|
for name in host_data:
|
||||||
# get nameserver info, if there are any
|
|
||||||
if (
|
|
||||||
# fetch_hosts and
|
|
||||||
"_hosts" in cleaned
|
|
||||||
and isinstance(cleaned["_hosts"], list)
|
|
||||||
and len(cleaned["_hosts"])
|
|
||||||
):
|
|
||||||
# TODO- add elif in cache set it to be the old cache value
|
|
||||||
# no point in removing
|
|
||||||
cleaned["hosts"] = []
|
|
||||||
for name in cleaned["_hosts"]:
|
|
||||||
# we do not use _get_or_create_* because we expect the object we
|
|
||||||
# just asked the registry for still exists --
|
|
||||||
# if not, that's a problem
|
|
||||||
req = commands.InfoHost(name=name)
|
req = commands.InfoHost(name=name)
|
||||||
data = registry.send(req, cleaned=True).res_data[0]
|
data = registry.send(req, cleaned=True).res_data[0]
|
||||||
# extract properties from response
|
|
||||||
# (Ellipsis is used to mean "null")
|
|
||||||
host = {
|
host = {
|
||||||
"name": name,
|
"name": name,
|
||||||
"addrs": getattr(data, "addrs", ...),
|
"addrs": getattr(data, "addrs", ...),
|
||||||
|
@ -1073,15 +1081,8 @@ class Domain(TimeStampedModel, DomainHelper):
|
||||||
"tr_date": getattr(data, "tr_date", ...),
|
"tr_date": getattr(data, "tr_date", ...),
|
||||||
"up_date": getattr(data, "up_date", ...),
|
"up_date": getattr(data, "up_date", ...),
|
||||||
}
|
}
|
||||||
cleaned["hosts"].append(
|
hosts.append({k: v for k, v in host.items() if v is not ...})
|
||||||
{k: v for k, v in host.items() if v is not ...}
|
return hosts
|
||||||
)
|
|
||||||
|
|
||||||
# replace the prior cache with new data
|
|
||||||
self._cache = cleaned
|
|
||||||
|
|
||||||
except RegistryError as e:
|
|
||||||
logger.error(e)
|
|
||||||
|
|
||||||
def _invalidate_cache(self):
|
def _invalidate_cache(self):
|
||||||
"""Remove cache data when updates are made."""
|
"""Remove cache data when updates are made."""
|
||||||
|
|
|
@ -3,15 +3,16 @@ from django.db import models
|
||||||
from .utility.time_stamped_model import TimeStampedModel
|
from .utility.time_stamped_model import TimeStampedModel
|
||||||
|
|
||||||
|
|
||||||
|
class StatusChoices(models.TextChoices):
|
||||||
|
READY = "ready", "Ready"
|
||||||
|
HOLD = "hold", "Hold"
|
||||||
|
|
||||||
|
|
||||||
class TransitionDomain(TimeStampedModel):
|
class TransitionDomain(TimeStampedModel):
|
||||||
"""Transition Domain model stores information about the
|
"""Transition Domain model stores information about the
|
||||||
state of a domain upon transition between registry
|
state of a domain upon transition between registry
|
||||||
providers"""
|
providers"""
|
||||||
|
|
||||||
class StatusChoices(models.TextChoices):
|
|
||||||
CREATED = "created", "Created"
|
|
||||||
HOLD = "hold", "Hold"
|
|
||||||
|
|
||||||
username = models.TextField(
|
username = models.TextField(
|
||||||
null=False,
|
null=False,
|
||||||
blank=False,
|
blank=False,
|
||||||
|
@ -27,6 +28,7 @@ class TransitionDomain(TimeStampedModel):
|
||||||
max_length=255,
|
max_length=255,
|
||||||
null=False,
|
null=False,
|
||||||
blank=True,
|
blank=True,
|
||||||
|
default=StatusChoices.READY,
|
||||||
choices=StatusChoices.choices,
|
choices=StatusChoices.choices,
|
||||||
verbose_name="Status",
|
verbose_name="Status",
|
||||||
help_text="domain status during the transfer",
|
help_text="domain status during the transfer",
|
||||||
|
@ -39,4 +41,9 @@ class TransitionDomain(TimeStampedModel):
|
||||||
)
|
)
|
||||||
|
|
||||||
def __str__(self):
|
def __str__(self):
|
||||||
return self.username
|
return (
|
||||||
|
f"username: {self.username} "
|
||||||
|
f"domainName: {self.domain_name} "
|
||||||
|
f"status: {self.status} "
|
||||||
|
f"email sent: {self.email_sent} "
|
||||||
|
)
|
||||||
|
|
|
@ -5,6 +5,28 @@
|
||||||
{{ block.super }}
|
{{ block.super }}
|
||||||
<div class="margin-top-4 tablet:grid-col-10">
|
<div class="margin-top-4 tablet:grid-col-10">
|
||||||
|
|
||||||
|
<div
|
||||||
|
class="usa-summary-box dotgov-status-box margin-top-3 padding-left-2{% if domain.state == domain.State.UNKNOWN or domain.state == domain.State.DNS_NEEDED%} dotgov-status-box--action-need{% endif %}"
|
||||||
|
role="region"
|
||||||
|
aria-labelledby="summary-box-key-information"
|
||||||
|
>
|
||||||
|
<div class="usa-summary-box__body">
|
||||||
|
<p class="usa-summary-box__heading font-sans-md margin-bottom-0"
|
||||||
|
id="summary-box-key-information"
|
||||||
|
>
|
||||||
|
<span class="text-bold text-primary-darker">
|
||||||
|
Status:
|
||||||
|
</span>
|
||||||
|
{% if domain.state == domain.State.UNKNOWN or domain.state == domain.State.DNS_NEEDED%}
|
||||||
|
DNS Needed
|
||||||
|
{% else %}
|
||||||
|
{{ domain.state|title }}
|
||||||
|
{% endif %}
|
||||||
|
</p>
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
<br>
|
||||||
|
|
||||||
{% url 'domain-nameservers' pk=domain.id as url %}
|
{% url 'domain-nameservers' pk=domain.id as url %}
|
||||||
{% if domain.nameservers|length > 0 %}
|
{% if domain.nameservers|length > 0 %}
|
||||||
{% include "includes/summary_item.html" with title='DNS name servers' value=domain.nameservers list='true' edit_link=url %}
|
{% include "includes/summary_item.html" with title='DNS name servers' value=domain.nameservers list='true' edit_link=url %}
|
||||||
|
|
|
@ -40,11 +40,11 @@
|
||||||
</svg><span class="margin-left-05">Add another name server</span>
|
</svg><span class="margin-left-05">Add another name server</span>
|
||||||
</button>
|
</button>
|
||||||
|
|
||||||
|
|
||||||
<button
|
<button
|
||||||
type="submit"
|
type="submit"
|
||||||
class="usa-button"
|
class="usa-button"
|
||||||
>Save</button>
|
>Save
|
||||||
|
</button>
|
||||||
</form>
|
</form>
|
||||||
|
|
||||||
{% endblock %} {# domain_content #}
|
{% endblock %} {# domain_content #}
|
||||||
|
|
|
@ -33,14 +33,18 @@
|
||||||
</thead>
|
</thead>
|
||||||
<tbody>
|
<tbody>
|
||||||
{% for domain in domains %}
|
{% for domain in domains %}
|
||||||
{% comment %} ticket 796
|
|
||||||
{% if domain.application_status == "approved" or (domain.application does not exist) %} {% endcomment %}
|
|
||||||
<tr>
|
<tr>
|
||||||
<th th scope="row" role="rowheader" data-label="Domain name">
|
<th th scope="row" role="rowheader" data-label="Domain name">
|
||||||
{{ domain.name }}
|
{{ domain.name }}
|
||||||
</th>
|
</th>
|
||||||
<td data-sort-value="{{ domain.created_time|date:"U" }}" data-label="Date created">{{ domain.created_time|date }}</td>
|
<td data-sort-value="{{ domain.created_time|date:"U" }}" data-label="Date created">{{ domain.created_time|date }}</td>
|
||||||
<td data-label="Status">{{ domain.application_status|title }}</td>
|
<td data-label="Status">
|
||||||
|
{% if domain.state == "unknown" or domain.state == "dns needed"%}
|
||||||
|
DNS Needed
|
||||||
|
{% else %}
|
||||||
|
{{ domain.state|title }}
|
||||||
|
{% endif %}
|
||||||
|
</td>
|
||||||
<td>
|
<td>
|
||||||
<a href="{% url "domain" pk=domain.pk %}">
|
<a href="{% url "domain" pk=domain.pk %}">
|
||||||
<svg
|
<svg
|
||||||
|
@ -50,9 +54,15 @@
|
||||||
role="img"
|
role="img"
|
||||||
width="24"
|
width="24"
|
||||||
>
|
>
|
||||||
|
{% if domain.state == "deleted" or domain.state == "on hold" %}
|
||||||
|
<use xlink:href="{%static 'img/sprite.svg'%}#visibility"></use>
|
||||||
|
</svg>
|
||||||
|
View <span class="usa-sr-only">{{ domain.name }}</span>
|
||||||
|
{% else %}
|
||||||
<use xlink:href="{%static 'img/sprite.svg'%}#settings"></use>
|
<use xlink:href="{%static 'img/sprite.svg'%}#settings"></use>
|
||||||
</svg>
|
</svg>
|
||||||
Manage <span class="usa-sr-only">{{ domain.name }}</span>
|
Manage <span class="usa-sr-only">{{ domain.name }}</span>
|
||||||
|
{% endif %}
|
||||||
</a>
|
</a>
|
||||||
</td>
|
</td>
|
||||||
</tr>
|
</tr>
|
||||||
|
|
|
@ -53,8 +53,6 @@ class TestDomainCache(MockEppLib):
|
||||||
commands.InfoDomain(name="igorville.gov", auth_info=None),
|
commands.InfoDomain(name="igorville.gov", auth_info=None),
|
||||||
cleaned=True,
|
cleaned=True,
|
||||||
),
|
),
|
||||||
call(commands.InfoContact(id="123", auth_info=None), cleaned=True),
|
|
||||||
call(commands.InfoHost(name="fake.host.com"), cleaned=True),
|
|
||||||
],
|
],
|
||||||
any_order=False, # Ensure calls are in the specified order
|
any_order=False, # Ensure calls are in the specified order
|
||||||
)
|
)
|
||||||
|
@ -76,8 +74,6 @@ class TestDomainCache(MockEppLib):
|
||||||
call(
|
call(
|
||||||
commands.InfoDomain(name="igorville.gov", auth_info=None), cleaned=True
|
commands.InfoDomain(name="igorville.gov", auth_info=None), cleaned=True
|
||||||
),
|
),
|
||||||
call(commands.InfoContact(id="123", auth_info=None), cleaned=True),
|
|
||||||
call(commands.InfoHost(name="fake.host.com"), cleaned=True),
|
|
||||||
]
|
]
|
||||||
|
|
||||||
self.mockedSendFunction.assert_has_calls(expectedCalls)
|
self.mockedSendFunction.assert_has_calls(expectedCalls)
|
||||||
|
@ -112,6 +108,19 @@ class TestDomainCache(MockEppLib):
|
||||||
# get and check hosts is set correctly
|
# get and check hosts is set correctly
|
||||||
domain._get_property("hosts")
|
domain._get_property("hosts")
|
||||||
self.assertEqual(domain._cache["hosts"], [expectedHostsDict])
|
self.assertEqual(domain._cache["hosts"], [expectedHostsDict])
|
||||||
|
self.assertEqual(domain._cache["contacts"], [expectedContactsDict])
|
||||||
|
|
||||||
|
# invalidate cache
|
||||||
|
domain._cache = {}
|
||||||
|
|
||||||
|
# get host
|
||||||
|
domain._get_property("hosts")
|
||||||
|
self.assertEqual(domain._cache["hosts"], [expectedHostsDict])
|
||||||
|
|
||||||
|
# get contacts
|
||||||
|
domain._get_property("contacts")
|
||||||
|
self.assertEqual(domain._cache["hosts"], [expectedHostsDict])
|
||||||
|
self.assertEqual(domain._cache["contacts"], [expectedContactsDict])
|
||||||
|
|
||||||
def tearDown(self) -> None:
|
def tearDown(self) -> None:
|
||||||
Domain.objects.all().delete()
|
Domain.objects.all().delete()
|
||||||
|
@ -172,8 +181,6 @@ class TestDomainCreation(MockEppLib):
|
||||||
commands.InfoDomain(name="beef-tongue.gov", auth_info=None),
|
commands.InfoDomain(name="beef-tongue.gov", auth_info=None),
|
||||||
cleaned=True,
|
cleaned=True,
|
||||||
),
|
),
|
||||||
call(commands.InfoContact(id="123", auth_info=None), cleaned=True),
|
|
||||||
call(commands.InfoHost(name="fake.host.com"), cleaned=True),
|
|
||||||
],
|
],
|
||||||
any_order=False, # Ensure calls are in the specified order
|
any_order=False, # Ensure calls are in the specified order
|
||||||
)
|
)
|
||||||
|
@ -223,8 +230,6 @@ class TestDomainStatuses(MockEppLib):
|
||||||
commands.InfoDomain(name="chicken-liver.gov", auth_info=None),
|
commands.InfoDomain(name="chicken-liver.gov", auth_info=None),
|
||||||
cleaned=True,
|
cleaned=True,
|
||||||
),
|
),
|
||||||
call(commands.InfoContact(id="123", auth_info=None), cleaned=True),
|
|
||||||
call(commands.InfoHost(name="fake.host.com"), cleaned=True),
|
|
||||||
],
|
],
|
||||||
any_order=False, # Ensure calls are in the specified order
|
any_order=False, # Ensure calls are in the specified order
|
||||||
)
|
)
|
||||||
|
|
|
@ -25,6 +25,7 @@ from registrar.models import (
|
||||||
from registrar.views.application import ApplicationWizard, Step
|
from registrar.views.application import ApplicationWizard, Step
|
||||||
|
|
||||||
from .common import less_console_noise
|
from .common import less_console_noise
|
||||||
|
from .common import MockEppLib
|
||||||
|
|
||||||
|
|
||||||
class TestViews(TestCase):
|
class TestViews(TestCase):
|
||||||
|
@ -47,8 +48,9 @@ class TestViews(TestCase):
|
||||||
self.assertIn("/login?next=/register/", response.headers["Location"])
|
self.assertIn("/login?next=/register/", response.headers["Location"])
|
||||||
|
|
||||||
|
|
||||||
class TestWithUser(TestCase):
|
class TestWithUser(MockEppLib):
|
||||||
def setUp(self):
|
def setUp(self):
|
||||||
|
super().setUp()
|
||||||
username = "test_user"
|
username = "test_user"
|
||||||
first_name = "First"
|
first_name = "First"
|
||||||
last_name = "Last"
|
last_name = "Last"
|
||||||
|
@ -59,6 +61,7 @@ class TestWithUser(TestCase):
|
||||||
|
|
||||||
def tearDown(self):
|
def tearDown(self):
|
||||||
# delete any applications too
|
# delete any applications too
|
||||||
|
super().tearDown()
|
||||||
DomainApplication.objects.all().delete()
|
DomainApplication.objects.all().delete()
|
||||||
self.user.delete()
|
self.user.delete()
|
||||||
|
|
||||||
|
@ -91,6 +94,7 @@ class LoggedInTests(TestWithUser):
|
||||||
response = self.client.get("/")
|
response = self.client.get("/")
|
||||||
# count = 2 because it is also in screenreader content
|
# count = 2 because it is also in screenreader content
|
||||||
self.assertContains(response, "igorville.gov", count=2)
|
self.assertContains(response, "igorville.gov", count=2)
|
||||||
|
self.assertContains(response, "DNS Needed")
|
||||||
# clean up
|
# clean up
|
||||||
role.delete()
|
role.delete()
|
||||||
|
|
||||||
|
@ -1141,6 +1145,7 @@ class TestDomainDetail(TestWithDomainPermissions, WebTest):
|
||||||
# click the "Edit" link
|
# click the "Edit" link
|
||||||
detail_page = home_page.click("Manage")
|
detail_page = home_page.click("Manage")
|
||||||
self.assertContains(detail_page, "igorville.gov")
|
self.assertContains(detail_page, "igorville.gov")
|
||||||
|
self.assertContains(detail_page, "Status")
|
||||||
|
|
||||||
def test_domain_user_management(self):
|
def test_domain_user_management(self):
|
||||||
response = self.client.get(
|
response = self.client.get(
|
||||||
|
@ -1307,6 +1312,7 @@ class TestDomainDetail(TestWithDomainPermissions, WebTest):
|
||||||
)
|
)
|
||||||
self.assertContains(page, "Domain name servers")
|
self.assertContains(page, "Domain name servers")
|
||||||
|
|
||||||
|
@skip("Broken by adding registry connection fix in ticket 848")
|
||||||
def test_domain_nameservers_form(self):
|
def test_domain_nameservers_form(self):
|
||||||
"""Can change domain's nameservers.
|
"""Can change domain's nameservers.
|
||||||
|
|
||||||
|
|
|
@ -139,10 +139,17 @@ class DomainNameserversView(DomainPermissionView, FormMixin):
|
||||||
"""The initial value for the form (which is a formset here)."""
|
"""The initial value for the form (which is a formset here)."""
|
||||||
domain = self.get_object()
|
domain = self.get_object()
|
||||||
nameservers = domain.nameservers
|
nameservers = domain.nameservers
|
||||||
if nameservers is None:
|
initial_data = []
|
||||||
return []
|
|
||||||
|
|
||||||
return [{"server": name} for name, *ip in domain.nameservers]
|
if nameservers is not None:
|
||||||
|
# Add existing nameservers as initial data
|
||||||
|
initial_data.extend({"server": name} for name, *ip in nameservers)
|
||||||
|
|
||||||
|
# Ensure at least 3 fields, filled or empty
|
||||||
|
while len(initial_data) < 2:
|
||||||
|
initial_data.append({})
|
||||||
|
|
||||||
|
return initial_data
|
||||||
|
|
||||||
def get_success_url(self):
|
def get_success_url(self):
|
||||||
"""Redirect to the nameservers page for the domain."""
|
"""Redirect to the nameservers page for the domain."""
|
||||||
|
@ -158,6 +165,7 @@ class DomainNameserversView(DomainPermissionView, FormMixin):
|
||||||
def get_form(self, **kwargs):
|
def get_form(self, **kwargs):
|
||||||
"""Override the labels and required fields every time we get a formset."""
|
"""Override the labels and required fields every time we get a formset."""
|
||||||
formset = super().get_form(**kwargs)
|
formset = super().get_form(**kwargs)
|
||||||
|
|
||||||
for i, form in enumerate(formset):
|
for i, form in enumerate(formset):
|
||||||
form.fields["server"].label += f" {i+1}"
|
form.fields["server"].label += f" {i+1}"
|
||||||
if i < 2:
|
if i < 2:
|
||||||
|
|
|
@ -19,7 +19,7 @@ def index(request):
|
||||||
pk=F("domain__id"),
|
pk=F("domain__id"),
|
||||||
name=F("domain__name"),
|
name=F("domain__name"),
|
||||||
created_time=F("domain__created_at"),
|
created_time=F("domain__created_at"),
|
||||||
application_status=F("domain__domain_application__status"),
|
state=F("domain__state"),
|
||||||
)
|
)
|
||||||
context["domains"] = domains
|
context["domains"] = domains
|
||||||
return render(request, "home.html", context)
|
return render(request, "home.html", context)
|
||||||
|
|
Loading…
Add table
Add a link
Reference in a new issue