Skip to content
Open
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
11 changes: 11 additions & 0 deletions osf/models/mixins.py
Original file line number Diff line number Diff line change
Expand Up @@ -30,6 +30,7 @@
)
from osf.models.notification_type import NotificationTypeEnum
from osf.models.notification_subscription import NotificationSubscription
from .base import VersionedGuidMixin
from .node_relation import NodeRelation
from .nodelog import NodeLog
from .subject import Subject
Expand Down Expand Up @@ -1908,6 +1909,16 @@ def remove_contributor(self, contributor, auth, log=True, _force=False):
save=False,
)

if isinstance(self, VersionedGuidMixin) and not self._id:
# Legacy/un-migrated versioned resources can't be saved -- Preprint.save() requires a
# valid _id. The contributor row is already removed above; there's
# nothing else to persist, so skip save + downstream signals.
logger.info(
f'Skipping save on {self.__class__.__name__} (pk={self.pk}) in remove_contributor: '
'resource has no valid _id.'
)
return True

self.save()
# send signal to remove this user from project subscriptions
project_signals.contributor_removed.send(self, user=contributor)
Expand Down
19 changes: 19 additions & 0 deletions osf_tests/test_user.py
Original file line number Diff line number Diff line change
Expand Up @@ -27,6 +27,7 @@
from osf.models import (
AbstractNode,
OSFUser,
Preprint,
Tag,
Contributor,
NotableDomain,
Expand Down Expand Up @@ -2135,6 +2136,14 @@ def project_with_two_admins(self, user):
project.save()
return project

@pytest.fixture()
def preprint_with_two_admins(self, user):
second_admin_contrib = UserFactory()
preprint = PreprintFactory(creator=user)
preprint.add_contributor(second_admin_contrib, permissions=permissions.ADMIN)
preprint.save()
return preprint

@pytest.fixture()
def project_with_two_admins_and_addon_credentials(self, user):
second_admin_contrib = UserFactory()
Expand Down Expand Up @@ -2338,6 +2347,16 @@ def test_can_gdpr_delete_shared_node_without_guid(self, user, project_with_two_a

assert user.nodes.all().count() == 0

def test_can_gdpr_delete_shared_preprint_without_guid(self, user, preprint_with_two_admins):
preprint_with_two_admins.versioned_guids.all().delete()
preprint = Preprint.objects.get(pk=preprint_with_two_admins.pk)
assert preprint._id is None

with override_flag(ENABLE_GV, active=True):
user.gdpr_delete()

assert user.preprints.all().count() == 0

def test_cant_gdpr_delete_with_addon_credentials(self, user, project_with_two_admins_and_addon_credentials):

with pytest.raises(UserStateError) as exc_info:
Expand Down
Loading