Skip to content

Commit

Permalink
Merge pull request #2491 from cisagov/gd/2354-handle-portfolio-edit-mode
Browse files Browse the repository at this point in the history
Ticket #2354: Read-only suborganization view
  • Loading branch information
zandercymatics authored Aug 8, 2024
2 parents e573b23 + 2fd9611 commit 25d3a54
Show file tree
Hide file tree
Showing 5 changed files with 127 additions and 60 deletions.
16 changes: 12 additions & 4 deletions src/registrar/templates/domain_detail.html
Original file line number Diff line number Diff line change
Expand Up @@ -64,11 +64,19 @@ <h2 class="margin-top-3"> DNS name servers </h2>
{% endif %}
{% endif %}

{% url 'domain-org-name-address' pk=domain.id as url %}
{% include "includes/summary_item.html" with title='Organization name and mailing address' value=domain.domain_info address='true' edit_link=url editable=is_editable %}
{% if portfolio %}
{% comment %} TODO - uncomment in #2352 and add to edit_link
{% url 'domain-suborganization' pk=domain.id as url %}
{% endcomment %}
{% include "includes/summary_item.html" with title='Suborganization' value=domain.domain_info.sub_organization edit_link="#" editable=is_editable %}
{% else %}
{% url 'domain-org-name-address' pk=domain.id as url %}
{% include "includes/summary_item.html" with title='Organization name and mailing address' value=domain.domain_info address='true' edit_link=url editable=is_editable %}

{% url 'domain-senior-official' pk=domain.id as url %}
{% include "includes/summary_item.html" with title='Senior official' value=domain.domain_info.senior_official contact='true' edit_link=url editable=is_editable %}
{% endif %}

{% url 'domain-senior-official' pk=domain.id as url %}
{% include "includes/summary_item.html" with title='Senior official' value=domain.domain_info.senior_official contact='true' edit_link=url editable=is_editable %}

{# Conditionally display profile #}
{% if not has_profile_feature_flag %}
Expand Down
80 changes: 31 additions & 49 deletions src/registrar/templates/domain_sidebar.html
Original file line number Diff line number Diff line change
Expand Up @@ -3,16 +3,19 @@
<div class="margin-bottom-4 tablet:margin-bottom-0">
<nav aria-label="Domain sections">
<ul class="usa-sidenav">
<li class="usa-sidenav__item">
{% url 'domain' pk=domain.id as url %}
<a href="{{ url }}"
{% if request.path == url %}class="usa-current"{% endif %}
>
Domain overview
</a>
</li>

{% with url_name="domain" %}
{% include "includes/domain_sidenav_item.html" with item_text="Domain overview" %}
{% endwith %}

{% if is_editable %}

{% if not portfolio %}
{% with url_name="domain-org-name-address" %}
{% include "includes/domain_sidenav_item.html" with item_text="Organization name and mailing address" %}
{% endwith %}
{% endif %}

<li class="usa-sidenav__item">
{% url 'domain-dns' pk=domain.id as url %}
<a href="{{ url }}" {% if request.path|startswith:url %}class="usa-current"{% endif %}>
Expand Down Expand Up @@ -55,53 +58,32 @@
{% endif %}
</li>

<li class="usa-sidenav__item">
{% url 'domain-org-name-address' pk=domain.id as url %}
<a href="{{ url }}"
{% if request.path == url %}class="usa-current"{% endif %}
>
Organization name and mailing address
</a>
</li>

<li class="usa-sidenav__item">
{% url 'domain-senior-official' pk=domain.id as url %}
<a href="{{ url }}"
{% if request.path == url %}class="usa-current"{% endif %}
>
Senior official
</a>
</li>

{% if portfolio %}
{% with url="#" %}
{% include "includes/domain_sidenav_item.html" with item_text="Suborganization" %}
{% endwith %}
{% else %}
{% with url_name="domain-senior-official" %}
{% include "includes/domain_sidenav_item.html" with item_text="Senior official" %}
{% endwith %}
{% endif %}

{% if not has_profile_feature_flag %}
{# Conditionally display profile link in main nav #}
<li class="usa-sidenav__item">
{% url 'domain-your-contact-information' pk=domain.id as url %}
<a href="{{ url }}"
{% if request.path == url %}class="usa-current"{% endif %}
>
Your contact information
</a>
</li>
{% with url_name="domain-your-contact-information" %}
{% include "includes/domain_sidenav_item.html" with item_text="Your contact information" %}
{% endwith %}
{% endif %}

<li class="usa-sidenav__item">
{% url 'domain-security-email' pk=domain.id as url %}
<a href="{{ url }}"
{% if request.path == url %}class="usa-current"{% endif %}
>
Security email
</a>
</li>
{% with url_name="domain-security-email" %}
{% include "includes/domain_sidenav_item.html" with item_text="Security email" %}
{% endwith %}

{% with url_name="domain-users" %}
{% include "includes/domain_sidenav_item.html" with item_text="Domain managers" %}
{% endwith %}

<li class="usa-sidenav__item">
{% url 'domain-users' pk=domain.id as url %}
<a href="{{ url }}"
{% if request.path|startswith:url %}class="usa-current"{% endif %}
>
Domain managers
</a>
</li>
{% endif %}
</ul>
</nav>
Expand Down
10 changes: 10 additions & 0 deletions src/registrar/templates/includes/domain_sidenav_item.html
Original file line number Diff line number Diff line change
@@ -0,0 +1,10 @@
<li class="usa-sidenav__item">
{% if url_name %}
{% url url_name pk=domain.id as url %}
{% endif %}
<a href="{{ url }}"
{% if request.path == url %}class="usa-current"{% endif %}
>
{{ item_text }}
</a>
</li>
58 changes: 53 additions & 5 deletions src/registrar/tests/test_views_domain.py
Original file line number Diff line number Diff line change
Expand Up @@ -4,10 +4,9 @@
from django.conf import settings
from django.urls import reverse
from django.contrib.auth import get_user_model

from waffle.testutils import override_flag
from api.tests.common import less_console_noise_decorator
from registrar.models.portfolio import Portfolio
from registrar.models.utility.portfolio_helper import UserPortfolioRoleChoices
from registrar.models.utility.portfolio_helper import UserPortfolioPermissionChoices, UserPortfolioRoleChoices
from .common import MockEppLib, MockSESClient, create_user # type: ignore
from django_webtest import WebTest # type: ignore
import boto3_mocking # type: ignore
Expand Down Expand Up @@ -35,6 +34,8 @@
UserDomainRole,
User,
FederalAgency,
Portfolio,
Suborganization,
)
from datetime import date, datetime, timedelta
from django.utils import timezone
Expand Down Expand Up @@ -140,6 +141,7 @@ def tearDown(self):
Host.objects.all().delete()
Domain.objects.all().delete()
UserDomainRole.objects.all().delete()
Suborganization.objects.all().delete()
Portfolio.objects.all().delete()
except ValueError: # pass if already deleted
pass
Expand Down Expand Up @@ -1126,7 +1128,7 @@ class TestDomainSeniorOfficial(TestDomainOverview):
def test_domain_senior_official(self):
"""Can load domain's senior official page."""
page = self.client.get(reverse("domain-senior-official", kwargs={"pk": self.domain.id}))
self.assertContains(page, "Senior official", count=13)
self.assertContains(page, "Senior official", count=14)

@less_console_noise_decorator
def test_domain_senior_official_content(self):
Expand Down Expand Up @@ -1346,7 +1348,7 @@ def test_domain_org_name_address(self):
"""Can load domain's org name and mailing address page."""
page = self.client.get(reverse("domain-org-name-address", kwargs={"pk": self.domain.id}))
# once on the sidebar, once in the page title, once as H1
self.assertContains(page, "Organization name and mailing address", count=3)
self.assertContains(page, "Organization name and mailing address", count=4)

@less_console_noise_decorator
def test_domain_org_name_address_content(self):
Expand Down Expand Up @@ -1521,6 +1523,52 @@ def test_federal_agency_submit_blocked(self):
self.assertNotEqual(self.domain_information.federal_agency, new_value)


class TestDomainSuborganization(TestDomainOverview):
"""Tests the Suborganization page for portfolio users"""

@less_console_noise_decorator
@override_flag("organization_feature", active=True)
def test_has_suborganization_field_on_overview_with_flag(self):
"""Ensures that the suborganization field is visible
and displays correctly on the domain overview page"""

# Create a portfolio
portfolio = Portfolio.objects.create(creator=self.user, organization_name="Ice Cream")
suborg = Suborganization.objects.create(portfolio=portfolio, name="Vanilla")

# Add the portfolio to the domain_information object
self.domain_information.portfolio = portfolio

# Add a organization_name to test if the old value still displays
self.domain_information.organization_name = "Broccoli"
self.domain_information.save()
self.domain_information.refresh_from_db()

# Add portfolio perms to the user object
self.user.portfolio = portfolio
self.user.portfolio_additional_permissions = [UserPortfolioPermissionChoices.VIEW_PORTFOLIO]
self.user.save()
self.user.refresh_from_db()

# Navigate to the domain overview page
page = self.app.get(reverse("domain", kwargs={"pk": self.domain.id}))

# Test for the title change
self.assertContains(page, "Suborganization")
self.assertNotContains(page, "Organization name")

# Test for the good value
self.assertContains(page, "Ice Cream")

# Test for the bad value
self.assertNotContains(page, "Broccoli")

# Cleanup
self.domain_information.delete()
suborg.delete()
portfolio.delete()


class TestDomainContactInformation(TestDomainOverview):
@less_console_noise_decorator
def test_domain_your_contact_information(self):
Expand Down
23 changes: 21 additions & 2 deletions src/registrar/views/domain.py
Original file line number Diff line number Diff line change
Expand Up @@ -23,8 +23,8 @@
DomainInvitation,
User,
UserDomainRole,
PublicContact,
)
from registrar.models.public_contact import PublicContact
from registrar.utility.enums import DefaultEmail
from registrar.utility.errors import (
GenericError,
Expand Down Expand Up @@ -231,6 +231,16 @@ def form_valid(self, form):
# superclass has the redirect
return super().form_valid(form)

def has_permission(self):
"""Override for the has_permission class to exclude portfolio users"""

# Org users shouldn't have access to this page
is_org_user = self.request.user.is_org_user(self.request)
if self.request.user.portfolio and is_org_user:
return False
else:
return super().has_permission()


class DomainSeniorOfficialView(DomainFormBaseView):
"""Domain senior official editing view."""
Expand All @@ -248,7 +258,6 @@ def get_form_kwargs(self, *args, **kwargs):
domain_info = self.get_domain_info_from_domain()
invalid_fields = [DomainRequest.OrganizationChoices.FEDERAL, DomainRequest.OrganizationChoices.TRIBAL]
is_federal_or_tribal = domain_info and (domain_info.generic_org_type in invalid_fields)

form_kwargs["disable_fields"] = is_federal_or_tribal
return form_kwargs

Expand Down Expand Up @@ -276,6 +285,16 @@ def form_valid(self, form):
# superclass has the redirect
return super().form_valid(form)

def has_permission(self):
"""Override for the has_permission class to exclude portfolio users"""

# Org users shouldn't have access to this page
is_org_user = self.request.user.is_org_user(self.request)
if self.request.user.portfolio and is_org_user:
return False
else:
return super().has_permission()


class DomainDNSView(DomainBaseView):
"""DNS Information View."""
Expand Down

0 comments on commit 25d3a54

Please sign in to comment.