mirror of
https://github.com/cisagov/manage.get.gov.git
synced 2025-07-22 02:36:02 +02:00
Unit tests, get domains for invited member
This commit is contained in:
parent
c5de4b3a1d
commit
3d6417bb99
3 changed files with 328 additions and 62 deletions
|
@ -2043,11 +2043,11 @@ class MembersTable extends LoadTableBase {
|
|||
if (member_permissions.includes(UserPortfolioPermissionChoices.EDIT_MEMBERS)) {
|
||||
permissionsHTML += "<p class='margin-top-1 p--blockquote'><strong class='text-base-dark'>Members:</strong> Can manage members including inviting new members, removing current members, and assigning domains to members.";
|
||||
} else if (member_permissions.includes(UserPortfolioPermissionChoices.VIEW_MEMBERS)) {
|
||||
permissionsHTML += "<p> class='margin-top-1 p--blockquote'><strong class='text-base-dark'>Members (view-only):</strong> Can view all organizational members. Can't manage any members.";
|
||||
permissionsHTML += "<p class='margin-top-1 p--blockquote'><strong class='text-base-dark'>Members (view-only):</strong> Can view all organizational members. Can't manage any members.";
|
||||
}
|
||||
// if there are no additional permissions, display a no additional permissions message
|
||||
if (!permissionsHTML) {
|
||||
permissionsHTML += "<p><b>No additional permissions:</b> There are no additional permissions for this member.</p>";
|
||||
permissionsHTML += "<p class='margin-top-1 p--blockquote'><b>No additional permissions:</b> There are no additional permissions for this member.</p>";
|
||||
}
|
||||
// add permissions header in all cases
|
||||
permissionsHTML = "<div class='desktop:grid-col-7'><h4 class='margin-y-0 text-primary'>Additional permissions for this member</h4>" + permissionsHTML + "</div>";
|
||||
|
@ -2058,7 +2058,7 @@ class MembersTable extends LoadTableBase {
|
|||
showMoreButton = `
|
||||
<button
|
||||
type="button"
|
||||
class="usa-button--show-more-button usa-button usa-button--unstyled display-block margin-top-2"
|
||||
class="usa-button--show-more-button usa-button usa-button--unstyled display-block margin-top-1"
|
||||
data-for=${member_id}
|
||||
>
|
||||
<span>Expand</span>
|
||||
|
|
|
@ -1,21 +1,25 @@
|
|||
from django.urls import reverse
|
||||
|
||||
from registrar.models.domain import Domain
|
||||
from registrar.models.domain_information import DomainInformation
|
||||
from registrar.models.domain_invitation import DomainInvitation
|
||||
from registrar.models.portfolio import Portfolio
|
||||
from registrar.models.portfolio_invitation import PortfolioInvitation
|
||||
from registrar.models.user import User
|
||||
from registrar.models.user_domain_role import UserDomainRole
|
||||
from registrar.models.user_portfolio_permission import UserPortfolioPermission
|
||||
from registrar.models.utility.portfolio_helper import UserPortfolioPermissionChoices, UserPortfolioRoleChoices
|
||||
from .test_views import TestWithUser
|
||||
from registrar.tests.common import MockEppLib, create_test_user
|
||||
from django_webtest import WebTest # type: ignore
|
||||
|
||||
|
||||
class GetPortfolioMembersJsonTest(TestWithUser, WebTest):
|
||||
@classmethod
|
||||
def setUpClass(cls):
|
||||
super().setUpClass()
|
||||
class GetPortfolioMembersJsonTest(MockEppLib, WebTest):
|
||||
def setUp(self):
|
||||
super().setUp()
|
||||
self.user = create_test_user()
|
||||
|
||||
# Create additional users
|
||||
cls.user2 = User.objects.create(
|
||||
self.user2 = User.objects.create(
|
||||
username="test_user2",
|
||||
first_name="Second",
|
||||
last_name="User",
|
||||
|
@ -23,7 +27,7 @@ class GetPortfolioMembersJsonTest(TestWithUser, WebTest):
|
|||
phone="8003112345",
|
||||
title="Member",
|
||||
)
|
||||
cls.user3 = User.objects.create(
|
||||
self.user3 = User.objects.create(
|
||||
username="test_user3",
|
||||
first_name="Third",
|
||||
last_name="User",
|
||||
|
@ -31,7 +35,7 @@ class GetPortfolioMembersJsonTest(TestWithUser, WebTest):
|
|||
phone="8003113456",
|
||||
title="Member",
|
||||
)
|
||||
cls.user4 = User.objects.create(
|
||||
self.user4 = User.objects.create(
|
||||
username="test_user4",
|
||||
first_name="Fourth",
|
||||
last_name="User",
|
||||
|
@ -39,60 +43,66 @@ class GetPortfolioMembersJsonTest(TestWithUser, WebTest):
|
|||
phone="8003114567",
|
||||
title="Admin",
|
||||
)
|
||||
cls.email5 = "fifth@example.com"
|
||||
self.user5 = User.objects.create(
|
||||
username="test_user5",
|
||||
first_name="Fifth",
|
||||
last_name="User",
|
||||
email="fifth@example.com",
|
||||
phone="8003114568",
|
||||
title="Admin",
|
||||
)
|
||||
self.email6 = "fifth@example.com"
|
||||
|
||||
# Create Portfolio
|
||||
cls.portfolio = Portfolio.objects.create(creator=cls.user, organization_name="Test Portfolio")
|
||||
self.portfolio = Portfolio.objects.create(creator=self.user, organization_name="Test Portfolio")
|
||||
|
||||
# Assign permissions
|
||||
UserPortfolioPermission.objects.create(
|
||||
user=cls.user,
|
||||
portfolio=cls.portfolio,
|
||||
roles=[UserPortfolioRoleChoices.ORGANIZATION_ADMIN],
|
||||
additional_permissions=[
|
||||
UserPortfolioPermissionChoices.VIEW_MEMBERS,
|
||||
UserPortfolioPermissionChoices.EDIT_MEMBERS,
|
||||
],
|
||||
)
|
||||
UserPortfolioPermission.objects.create(
|
||||
user=cls.user2,
|
||||
portfolio=cls.portfolio,
|
||||
roles=[UserPortfolioRoleChoices.ORGANIZATION_MEMBER],
|
||||
)
|
||||
UserPortfolioPermission.objects.create(
|
||||
user=cls.user3,
|
||||
portfolio=cls.portfolio,
|
||||
roles=[UserPortfolioRoleChoices.ORGANIZATION_MEMBER],
|
||||
)
|
||||
UserPortfolioPermission.objects.create(
|
||||
user=cls.user4,
|
||||
portfolio=cls.portfolio,
|
||||
roles=[UserPortfolioRoleChoices.ORGANIZATION_ADMIN],
|
||||
)
|
||||
PortfolioInvitation.objects.create(
|
||||
email=cls.email5,
|
||||
portfolio=cls.portfolio,
|
||||
roles=[UserPortfolioRoleChoices.ORGANIZATION_ADMIN],
|
||||
additional_permissions=[
|
||||
UserPortfolioPermissionChoices.VIEW_MEMBERS,
|
||||
UserPortfolioPermissionChoices.EDIT_MEMBERS,
|
||||
],
|
||||
)
|
||||
|
||||
@classmethod
|
||||
def tearDownClass(cls):
|
||||
self.app.set_user(self.user.username)
|
||||
|
||||
def tearDown(self):
|
||||
UserDomainRole.objects.all().delete()
|
||||
DomainInformation.objects.all().delete()
|
||||
Domain.objects.all().delete()
|
||||
PortfolioInvitation.objects.all().delete()
|
||||
UserPortfolioPermission.objects.all().delete()
|
||||
Portfolio.objects.all().delete()
|
||||
User.objects.all().delete()
|
||||
super().tearDownClass()
|
||||
|
||||
def setUp(self):
|
||||
super().setUp()
|
||||
self.app.set_user(self.user.username)
|
||||
super().tearDown()
|
||||
|
||||
def test_get_portfolio_members_json_authenticated(self):
|
||||
"""Test that portfolio members are returned properly for an authenticated user."""
|
||||
"""Also tests that reposnse is 200 when no domains"""
|
||||
UserPortfolioPermission.objects.create(
|
||||
user=self.user,
|
||||
portfolio=self.portfolio,
|
||||
roles=[UserPortfolioRoleChoices.ORGANIZATION_ADMIN],
|
||||
additional_permissions=[
|
||||
UserPortfolioPermissionChoices.VIEW_MEMBERS,
|
||||
UserPortfolioPermissionChoices.EDIT_MEMBERS,
|
||||
],
|
||||
)
|
||||
UserPortfolioPermission.objects.create(
|
||||
user=self.user2,
|
||||
portfolio=self.portfolio,
|
||||
roles=[UserPortfolioRoleChoices.ORGANIZATION_MEMBER],
|
||||
)
|
||||
UserPortfolioPermission.objects.create(
|
||||
user=self.user3,
|
||||
portfolio=self.portfolio,
|
||||
roles=[UserPortfolioRoleChoices.ORGANIZATION_MEMBER],
|
||||
)
|
||||
UserPortfolioPermission.objects.create(
|
||||
user=self.user4,
|
||||
portfolio=self.portfolio,
|
||||
roles=[UserPortfolioRoleChoices.ORGANIZATION_ADMIN],
|
||||
)
|
||||
UserPortfolioPermission.objects.create(
|
||||
user=self.user5,
|
||||
portfolio=self.portfolio,
|
||||
roles=[UserPortfolioRoleChoices.ORGANIZATION_ADMIN],
|
||||
)
|
||||
|
||||
response = self.app.get(reverse("get_portfolio_members_json"), params={"portfolio": self.portfolio.id})
|
||||
self.assertEqual(response.status_code, 200)
|
||||
data = response.json
|
||||
|
@ -115,15 +125,207 @@ class GetPortfolioMembersJsonTest(TestWithUser, WebTest):
|
|||
self.user3.email,
|
||||
self.user4.email,
|
||||
self.user4.email,
|
||||
self.email5,
|
||||
self.user5.email,
|
||||
}
|
||||
actual_emails = {member["email"] for member in data["members"]}
|
||||
self.assertEqual(expected_emails, actual_emails)
|
||||
|
||||
expected_roles = {
|
||||
UserPortfolioRoleChoices.ORGANIZATION_MEMBER,
|
||||
UserPortfolioRoleChoices.ORGANIZATION_ADMIN,
|
||||
}
|
||||
# Convert each member's roles list to a frozenset
|
||||
actual_roles = {role for member in data["members"] for role in member["roles"]}
|
||||
self.assertEqual(expected_roles, actual_roles)
|
||||
|
||||
expected_additional_permissions = {
|
||||
UserPortfolioPermissionChoices.VIEW_MEMBERS,
|
||||
UserPortfolioPermissionChoices.EDIT_MEMBERS,
|
||||
}
|
||||
actual_additional_permissions = {permission for member in data["members"] for permission in member["permissions"]}
|
||||
self.assertTrue(expected_additional_permissions.issubset(actual_additional_permissions))
|
||||
|
||||
def test_get_portfolio_invited_json_authenticated(self):
|
||||
"""Test that portfolio invitees are returned properly for an authenticated user."""
|
||||
"""Also tests that reposnse is 200 when no domains"""
|
||||
PortfolioInvitation.objects.create(
|
||||
email=self.email6,
|
||||
portfolio=self.portfolio,
|
||||
roles=[UserPortfolioRoleChoices.ORGANIZATION_ADMIN],
|
||||
additional_permissions=[
|
||||
UserPortfolioPermissionChoices.VIEW_MEMBERS,
|
||||
UserPortfolioPermissionChoices.EDIT_MEMBERS,
|
||||
],
|
||||
)
|
||||
|
||||
response = self.app.get(reverse("get_portfolio_members_json"), params={"portfolio": self.portfolio.id})
|
||||
self.assertEqual(response.status_code, 200)
|
||||
data = response.json
|
||||
|
||||
# Check pagination info
|
||||
self.assertEqual(data["page"], 1)
|
||||
self.assertEqual(data["num_pages"], 1)
|
||||
self.assertEqual(data["total"], 1)
|
||||
self.assertEqual(data["unfiltered_total"], 1)
|
||||
|
||||
# Check the number of members
|
||||
self.assertEqual(len(data["members"]), 1)
|
||||
|
||||
# Check member fields
|
||||
expected_emails = {
|
||||
self.email6
|
||||
}
|
||||
actual_emails = {member["email"] for member in data["members"]}
|
||||
self.assertEqual(expected_emails, actual_emails)
|
||||
|
||||
expected_roles = {
|
||||
UserPortfolioRoleChoices.ORGANIZATION_ADMIN,
|
||||
}
|
||||
# Convert each member's roles list to a frozenset
|
||||
actual_roles = {role for member in data["members"] for role in member["roles"]}
|
||||
self.assertEqual(expected_roles, actual_roles)
|
||||
|
||||
expected_additional_permissions = {
|
||||
UserPortfolioPermissionChoices.VIEW_MEMBERS,
|
||||
UserPortfolioPermissionChoices.EDIT_MEMBERS,
|
||||
}
|
||||
actual_additional_permissions = {permission for member in data["members"] for permission in member["permissions"]}
|
||||
self.assertTrue(expected_additional_permissions.issubset(actual_additional_permissions))
|
||||
|
||||
def test_get_portfolio_members_json_with_domains(self):
|
||||
"""Test that portfolio members are returned properly for an authenticated user and the response includes
|
||||
the domains that the member manages.."""
|
||||
UserPortfolioPermission.objects.create(
|
||||
user=self.user,
|
||||
portfolio=self.portfolio,
|
||||
roles=[UserPortfolioRoleChoices.ORGANIZATION_ADMIN],
|
||||
additional_permissions=[
|
||||
UserPortfolioPermissionChoices.VIEW_MEMBERS,
|
||||
UserPortfolioPermissionChoices.EDIT_MEMBERS,
|
||||
],
|
||||
)
|
||||
UserPortfolioPermission.objects.create(
|
||||
user=self.user2,
|
||||
portfolio=self.portfolio,
|
||||
roles=[UserPortfolioRoleChoices.ORGANIZATION_MEMBER],
|
||||
)
|
||||
UserPortfolioPermission.objects.create(
|
||||
user=self.user3,
|
||||
portfolio=self.portfolio,
|
||||
roles=[UserPortfolioRoleChoices.ORGANIZATION_MEMBER],
|
||||
)
|
||||
UserPortfolioPermission.objects.create(
|
||||
user=self.user4,
|
||||
portfolio=self.portfolio,
|
||||
roles=[UserPortfolioRoleChoices.ORGANIZATION_ADMIN],
|
||||
)
|
||||
|
||||
domain = Domain.objects.create(
|
||||
name="somedomain1.com",
|
||||
)
|
||||
|
||||
DomainInformation.objects.create(
|
||||
creator=self.user,
|
||||
domain=domain,
|
||||
portfolio=self.portfolio,
|
||||
)
|
||||
|
||||
UserDomainRole.objects.create(
|
||||
user=self.user,
|
||||
domain=domain,
|
||||
role=UserDomainRole.Roles.MANAGER,
|
||||
)
|
||||
|
||||
response = self.app.get(reverse("get_portfolio_members_json"), params={"portfolio": self.portfolio.id})
|
||||
self.assertEqual(response.status_code, 200)
|
||||
data = response.json
|
||||
|
||||
# Check if the domain appears in the response JSON
|
||||
domain_names = [
|
||||
domain_name
|
||||
for member in data["members"]
|
||||
for domain_name in member.get("domain_names", [])
|
||||
]
|
||||
self.assertIn("somedomain1.com", domain_names)
|
||||
|
||||
def test_get_portfolio_invited_json_with_domains(self):
|
||||
"""Test that portfolio invited members are returned properly for an authenticated user and the response includes
|
||||
the domains that the member manages.."""
|
||||
PortfolioInvitation.objects.create(
|
||||
email=self.email6,
|
||||
portfolio=self.portfolio,
|
||||
roles=[UserPortfolioRoleChoices.ORGANIZATION_ADMIN],
|
||||
additional_permissions=[
|
||||
UserPortfolioPermissionChoices.VIEW_MEMBERS,
|
||||
UserPortfolioPermissionChoices.EDIT_MEMBERS,
|
||||
],
|
||||
)
|
||||
|
||||
domain = Domain.objects.create(
|
||||
name="somedomain1.com",
|
||||
)
|
||||
|
||||
DomainInformation.objects.create(
|
||||
creator=self.user,
|
||||
domain=domain,
|
||||
portfolio=self.portfolio,
|
||||
)
|
||||
|
||||
DomainInvitation.objects.create(
|
||||
email=self.email6,
|
||||
domain=domain,
|
||||
)
|
||||
|
||||
response = self.app.get(reverse("get_portfolio_members_json"), params={"portfolio": self.portfolio.id})
|
||||
self.assertEqual(response.status_code, 200)
|
||||
data = response.json
|
||||
|
||||
# Check if the domain appears in the response JSON
|
||||
domain_names = [
|
||||
domain_name
|
||||
for member in data["members"]
|
||||
for domain_name in member.get("domain_names", [])
|
||||
]
|
||||
self.assertIn("somedomain1.com", domain_names)
|
||||
|
||||
def test_pagination(self):
|
||||
"""Test that pagination works properly when there are more members than page size."""
|
||||
UserPortfolioPermission.objects.create(
|
||||
user=self.user,
|
||||
portfolio=self.portfolio,
|
||||
roles=[UserPortfolioRoleChoices.ORGANIZATION_ADMIN],
|
||||
additional_permissions=[
|
||||
UserPortfolioPermissionChoices.VIEW_MEMBERS,
|
||||
UserPortfolioPermissionChoices.EDIT_MEMBERS,
|
||||
],
|
||||
)
|
||||
UserPortfolioPermission.objects.create(
|
||||
user=self.user2,
|
||||
portfolio=self.portfolio,
|
||||
roles=[UserPortfolioRoleChoices.ORGANIZATION_MEMBER],
|
||||
)
|
||||
UserPortfolioPermission.objects.create(
|
||||
user=self.user3,
|
||||
portfolio=self.portfolio,
|
||||
roles=[UserPortfolioRoleChoices.ORGANIZATION_MEMBER],
|
||||
)
|
||||
UserPortfolioPermission.objects.create(
|
||||
user=self.user4,
|
||||
portfolio=self.portfolio,
|
||||
roles=[UserPortfolioRoleChoices.ORGANIZATION_ADMIN],
|
||||
)
|
||||
PortfolioInvitation.objects.create(
|
||||
email=self.email6,
|
||||
portfolio=self.portfolio,
|
||||
roles=[UserPortfolioRoleChoices.ORGANIZATION_ADMIN],
|
||||
additional_permissions=[
|
||||
UserPortfolioPermissionChoices.VIEW_MEMBERS,
|
||||
UserPortfolioPermissionChoices.EDIT_MEMBERS,
|
||||
],
|
||||
)
|
||||
|
||||
# Create additional members to exceed page size of 10
|
||||
for i in range(5, 15):
|
||||
for i in range(6, 16):
|
||||
user, _ = User.objects.get_or_create(
|
||||
username=f"test_user{i}",
|
||||
first_name=f"User{i}",
|
||||
|
@ -172,6 +374,40 @@ class GetPortfolioMembersJsonTest(TestWithUser, WebTest):
|
|||
|
||||
def test_search(self):
|
||||
"""Test search functionality for portfolio members."""
|
||||
UserPortfolioPermission.objects.create(
|
||||
user=self.user,
|
||||
portfolio=self.portfolio,
|
||||
roles=[UserPortfolioRoleChoices.ORGANIZATION_ADMIN],
|
||||
additional_permissions=[
|
||||
UserPortfolioPermissionChoices.VIEW_MEMBERS,
|
||||
UserPortfolioPermissionChoices.EDIT_MEMBERS,
|
||||
],
|
||||
)
|
||||
UserPortfolioPermission.objects.create(
|
||||
user=self.user2,
|
||||
portfolio=self.portfolio,
|
||||
roles=[UserPortfolioRoleChoices.ORGANIZATION_MEMBER],
|
||||
)
|
||||
UserPortfolioPermission.objects.create(
|
||||
user=self.user3,
|
||||
portfolio=self.portfolio,
|
||||
roles=[UserPortfolioRoleChoices.ORGANIZATION_MEMBER],
|
||||
)
|
||||
UserPortfolioPermission.objects.create(
|
||||
user=self.user4,
|
||||
portfolio=self.portfolio,
|
||||
roles=[UserPortfolioRoleChoices.ORGANIZATION_ADMIN],
|
||||
)
|
||||
PortfolioInvitation.objects.create(
|
||||
email=self.email6,
|
||||
portfolio=self.portfolio,
|
||||
roles=[UserPortfolioRoleChoices.ORGANIZATION_ADMIN],
|
||||
additional_permissions=[
|
||||
UserPortfolioPermissionChoices.VIEW_MEMBERS,
|
||||
UserPortfolioPermissionChoices.EDIT_MEMBERS,
|
||||
],
|
||||
)
|
||||
|
||||
# Search by name
|
||||
response = self.app.get(
|
||||
reverse("get_portfolio_members_json"), params={"portfolio": self.portfolio.id, "search_term": "Second"}
|
||||
|
|
|
@ -1,13 +1,14 @@
|
|||
from django.http import JsonResponse
|
||||
from django.core.paginator import Paginator
|
||||
from django.contrib.auth.decorators import login_required
|
||||
from django.db.models import Value, F, CharField, TextField, Q, Case, When
|
||||
from django.db.models import Value, F, CharField, TextField, Q, Case, When, OuterRef, Subquery
|
||||
from django.db.models.functions import Concat, Coalesce
|
||||
from django.contrib.postgres.fields import ArrayField
|
||||
from django.contrib.postgres.aggregates import ArrayAgg
|
||||
from django.urls import reverse
|
||||
from django.db.models.functions import Cast
|
||||
|
||||
from registrar.models.domain_invitation import DomainInvitation
|
||||
from registrar.models.portfolio_invitation import PortfolioInvitation
|
||||
from registrar.models.user_domain_role import UserDomainRole
|
||||
from registrar.models.user_portfolio_permission import UserPortfolioPermission
|
||||
|
@ -89,7 +90,8 @@ def initial_permissions_search(portfolio):
|
|||
# specify the output_field to ensure union has same column types
|
||||
output_field=CharField()
|
||||
),
|
||||
distinct=True
|
||||
distinct=True,
|
||||
filter=Q(user__permissions__domain__isnull=False)
|
||||
),
|
||||
source=Value("permission", output_field=CharField()),
|
||||
)
|
||||
|
@ -110,7 +112,22 @@ def initial_permissions_search(portfolio):
|
|||
|
||||
|
||||
def initial_invitations_search(portfolio):
|
||||
"""Perform initial invitations search before applying any filters."""
|
||||
"""Perform initial invitations search and get related DomainInvitation data based on the email."""
|
||||
|
||||
|
||||
# Get DomainInvitation query for matching email
|
||||
domain_invitations = DomainInvitation.objects.filter(
|
||||
email=OuterRef('email'),
|
||||
domain__isnull=False
|
||||
).annotate(
|
||||
domain_info=Concat(
|
||||
F('domain__id'),
|
||||
Value(':'),
|
||||
F('domain__name'),
|
||||
output_field=CharField()
|
||||
)
|
||||
)
|
||||
|
||||
invitations = PortfolioInvitation.objects.filter(portfolio=portfolio)
|
||||
invitations = invitations.annotate(
|
||||
first_name=Value(None, output_field=CharField()),
|
||||
|
@ -118,7 +135,14 @@ def initial_invitations_search(portfolio):
|
|||
email_display=F("email"),
|
||||
last_active=Value("Invited", output_field=TextField()),
|
||||
member_display=F("email"),
|
||||
domain_info=Value([], output_field=ArrayField(TextField())),
|
||||
# ArrayAgg for multiple domain_invitations matched by email, filtered to exclude nulls
|
||||
domain_info=Coalesce( # Use Coalesce to return an empty list if no domain invitations exist
|
||||
ArrayAgg(
|
||||
Subquery(domain_invitations.values('domain_info')),
|
||||
distinct=True,
|
||||
),
|
||||
Value([], output_field=ArrayField(CharField())) # Ensure we return an empty list
|
||||
),
|
||||
source=Value("invitation", output_field=CharField()),
|
||||
).values(
|
||||
"id",
|
||||
|
@ -181,9 +205,15 @@ def serialize_members(request, portfolio, item, user):
|
|||
"member_display": item.get("member_display", ""),
|
||||
"roles": (item.get("roles") or []),
|
||||
"permissions": UserPortfolioPermission.get_portfolio_permissions(item.get("roles"), item.get("additional_permissions")),
|
||||
# split domain_info array values into ids to form urls, and names
|
||||
"domain_urls": [reverse("domain", kwargs={"pk": domain_info.split(":")[0]}) for domain_info in item.get("domain_info")],
|
||||
"domain_names": [domain_info.split(":")[1] for domain_info in item.get("domain_info")],
|
||||
"domain_names": [
|
||||
domain_info.split(":")[1] for domain_info in (item.get("domain_info") or [])
|
||||
if domain_info is not None # Prevent splitting None
|
||||
],
|
||||
"domain_urls": [
|
||||
reverse("domain", kwargs={"pk": domain_info.split(":")[0]})
|
||||
for domain_info in (item.get("domain_info") or [])
|
||||
if domain_info is not None # Prevent splitting None
|
||||
],
|
||||
"is_admin": is_admin,
|
||||
"last_active": item.get("last_active", ""),
|
||||
"action_url": action_url,
|
||||
|
|
Loading…
Add table
Add a link
Reference in a new issue