Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

feat(organizations): add owner_label field to AssetSerializer TASK-1181 #5312

Merged

Conversation

rajpatel24
Copy link
Contributor

🗒️ Checklist

  1. run linter locally
  2. update all related docs (API, README, inline, etc.), if any
  3. draft PR with a title <type>(<scope>)<!>: <title> TASK-1234
  4. tag PR: at least frontend or backend unless it's global
  5. fill in the template below and delete template comments
  6. review thyself: read the diff and repro the preview as written
  7. open PR & confirm that CI passes
  8. request reviewers, if needed
  9. delete this section before merging

📣 Summary

Added owner_label field to the Asset API to clarify ownership information, dynamically reflecting either the owner's username or the organization's name.

📖 Description

The owner_label field in the Asset API now dynamically displays:

  • The username of the asset owner if the organization is not a multi-member organization (MMO).
  • The name of the organization if the organization is a multi-member organization (MMO) and the user is the organization owner.
    This enhancement improves clarity by providing contextual ownership details directly in the API response.

👷 Description for instance maintainers

This update introduces a new owner_label field in the Asset serializer:

  • The field logic dynamically evaluates the organization's multi-member status (is_mmo) and ownership (is_owner).
  • Efficient database queries and optimizations ensure minimal impact on performance.

👀 Preview steps

  1. ℹ️ Have an account and at least one asset in a project.
  2. Ensure the asset belongs to a user who is also an organization owner.
  3. 🟢 Verify that the API response for the asset includes owner_label reflecting the username of the owner.
  4. Change the organization's status to a multi-member organization (enable is_mmo).
  5. 🟢 Verify that the owner_label in the API response now reflects the organization's name.
  6. Transfer ownership of the organization to a different user.
  7. 🟢 Verify that the owner_label reverts to the original owner's username.

💭 Notes

  • Testing: Unit tests were added to validate the owner_label behavior under various conditions, including ownership changes and multi-member organization scenarios.
  • Performance: The implementation minimizes additional queries by prefetching related data and leveraging efficient annotations.
  • Scalability: The logic is designed to handle a large number of assets and organizations without introducing significant overhead.

@rajpatel24 rajpatel24 removed the request for review from jnm December 2, 2024 08:57
@rajpatel24 rajpatel24 force-pushed the task-1181-add-owner_label-field-to-asset-serializer branch from 916e01c to aa796c9 Compare December 2, 2024 11:53
@@ -1,5 +1,6 @@
import copy
import json
import mock
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

This is deprecated, please use from unitest import mock instead

Comment on lines 112 to 140
# Fetch the assets list and verify the initial owner_label
list_response = self.client.get(self.list_url)
self.assertEqual(
list_response.data['results'][0]['owner_label'],
asset_owner_username
)

# Mock the is_mmo property to simulate a multi-member organization
with mock.patch.object(Organization, 'is_mmo', return_value=True):
list_response = self.client.get(self.list_url)

# Verify the owner_label now reflects the organization's name
self.assertEqual(
list_response.data['results'][0]['owner_label'],
asset_owner.organization.name
)

# Assign a new user as the organization owner
another_user = User.objects.get(username='anotheruser')
another_org_user = OrganizationUser.objects.create(
organization=asset_owner.organization,
user=another_user,
is_admin=True
)
org_owner = OrganizationOwner.objects.get(
organization=asset_owner.organization
)
org_owner.organization_user = another_org_user
org_owner.save()
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I think the test should be different.

  • Make asset_owner organization a MMO (set mmo_override to True)
  • Add another user (anotheruser) to asset_owner organization (asset_owner.organization.add_user(another_user))
  • Share asset with anotheruser (assign_perm(anotheruser, PERM_VIEW_ASSET) )
  • Create another asset with an external user and share it with anotheruser.
  • Test the endpoint (with anotheruser logged in) that returns the org' name for first asset and external username for the second asset.
  • Test the endpoint (with external user logged in) that returns external user's username

Comment on lines +725 to +735
# 5) Get organization per asset
assets = (
Asset.objects.filter(id__in=asset_ids)
.prefetch_related('owner__organizations_organization')
)
organization_by_asset = defaultdict(dict)
for asset in assets:
organization = getattr(asset.owner, 'organization', None)
organization_by_asset[asset.id] = organization
context_['organization_by_asset'] = organization_by_asset

Copy link
Contributor

@noliveleger noliveleger Dec 2, 2024

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Do we have the same optimization for /api/v2/organizations/<organization_id>/assets/?.
Nevermind, the (asset org) endpoint is always showing the same org. @cache_for_request should help to avoid making multiple queries.

@rajpatel24 rajpatel24 force-pushed the task-1181-add-owner_label-field-to-asset-serializer branch from e6b5d52 to d4e6c47 Compare December 3, 2024 16:34
@rajpatel24 rajpatel24 force-pushed the task-1181-add-owner_label-field-to-asset-serializer branch from d4e6c47 to 0fe5035 Compare December 3, 2024 16:38
@rajpatel24 rajpatel24 self-assigned this Dec 3, 2024
Copy link
Contributor

@noliveleger noliveleger left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

LGTM

@noliveleger
Copy link
Contributor

#5324 will be add more optimization to this PR.

… github.com:kobotoolbox/kpi into task-1181-add-owner_label-field-to-asset-serializer
@rajpatel24 rajpatel24 merged commit f5e9183 into main Dec 4, 2024
4 checks passed
@rajpatel24 rajpatel24 deleted the task-1181-add-owner_label-field-to-asset-serializer branch December 4, 2024 15:38
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
Projects
None yet
Development

Successfully merging this pull request may close these issues.

2 participants