-
Notifications
You must be signed in to change notification settings - Fork 49
Commit
This commit does not belong to any branch on this repository, and may belong to a fork outside of the repository.
feat(project, handlers): refactor project singal handlers for views a…
…nd add for tasks Signed-off-by: David Wallace <[email protected]>
- Loading branch information
Showing
8 changed files
with
165 additions
and
101 deletions.
There are no files selected for viewing
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Empty file.
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,78 @@ | ||
import logging | ||
|
||
from django.contrib.auth.models import User | ||
from django.contrib.sites.models import Site | ||
from django.db.models.signals import m2m_changed | ||
from django.dispatch import receiver | ||
|
||
from rdmo.projects.models import Membership, Project | ||
from rdmo.questions.models import Catalog | ||
from rdmo.tasks.models import Task | ||
|
||
logger = logging.getLogger(__name__) | ||
|
||
|
||
@receiver(m2m_changed, sender=Task.catalogs.through) | ||
def m2m_changed_task_catalog_signal(sender, instance, action, model, **kwargs): | ||
|
||
task = instance | ||
# catalogs that were changed | ||
catalogs = model.objects.filter(pk__in=kwargs['pk_set']) | ||
if action in ('post_remove', 'post_clear'): | ||
# Remove the task from projects whose catalog is no longer linked to this task | ||
projects_to_change = Project.objects.filter(catalog__in=catalogs, tasks=task) | ||
for project in projects_to_change: | ||
project.tasks.remove(task) | ||
|
||
elif action == 'post_add': | ||
# Add the task to projects whose catalog is now linked to this task | ||
projects_to_change = Project.objects.filter(catalog__in=task.catalogs.all()).exclude(tasks=task) | ||
for project in projects_to_change: | ||
project.tasks.add(task) | ||
|
||
|
||
@receiver(m2m_changed, sender=Task.sites.through) | ||
def m2m_changed_task_sites_signal(sender, instance, action, model, **kwargs): | ||
|
||
task = instance | ||
sites = model.objects.filter(pk__in=kwargs['pk_set']) | ||
catalogs = task.catalogs.all() or Catalog.objects.all() # If no catalogs, consider all | ||
|
||
if action in ('post_remove', 'post_clear'): | ||
# Remove the task from projects whose site is no longer linked to this task | ||
site_candidates = Site.objects.exclude(id__in=sites.values_list('id', flat=True)) | ||
projects_to_change = Project.objects.filter(site__in=site_candidates, catalog__in=catalogs, tasks=task) | ||
for project in projects_to_change: | ||
project.tasks.remove(task) | ||
|
||
elif action == 'post_add': | ||
# Add the task to projects whose site is now linked to this task | ||
site_candidates = sites | ||
projects_to_change = Project.objects.filter(site__in=site_candidates, catalog__in=catalogs).exclude(tasks=task) | ||
for project in projects_to_change: | ||
project.tasks.add(task) | ||
|
||
|
||
@receiver(m2m_changed, sender=Task.groups.through) | ||
def m2m_changed_task_groups_signal(sender, instance, action=None, **kwargs): | ||
|
||
task = instance | ||
groups = task.groups.all() | ||
catalogs = task.catalogs.all() or Catalog.objects.all() # If no catalogs, consider all | ||
|
||
if action in ('post_remove', 'post_clear'): | ||
# Remove the task from projects whose group is no longer linked to this task | ||
users = User.objects.exclude(groups__in=groups) | ||
memberships = Membership.objects.filter(role='owner', user__in=users).values_list('id', flat=True) | ||
projects_to_change = Project.objects.filter(memberships__in=memberships, catalog__in=catalogs, tasks=task) | ||
for project in projects_to_change: | ||
project.tasks.remove(task) | ||
|
||
elif action == 'post_add': | ||
# Add the task to projects whose group is now linked to this task | ||
users = User.objects.filter(groups__in=groups) | ||
memberships = Membership.objects.filter(role='owner', user__in=users).values_list('id', flat=True) | ||
projects_to_change = Project.objects.filter( | ||
memberships__in=memberships, catalog__in=catalogs).exclude(tasks=task) | ||
for project in projects_to_change: | ||
project.tasks.add(task) |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file was deleted.
Oops, something went wrong.
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,30 @@ | ||
|
||
|
||
from rdmo.projects.models import Project | ||
from rdmo.questions.models import Catalog | ||
from rdmo.tasks.models import Task | ||
|
||
task_id = 1 | ||
|
||
|
||
def test_project_views_sync_when_adding_or_removing_a_catalog_to_or_from_a_task(db, settings): | ||
assert settings.PROJECT_TASKS_SYNC | ||
|
||
# Setup: Create a catalog, a task, and a project using the catalog | ||
catalog = Catalog.objects.first() | ||
task = Task.objects.get(pk=task_id) | ||
task.catalogs.set([]) | ||
project = Project.objects.create(title="Test Project", catalog=catalog) | ||
|
||
# Initially, the project should not have the task | ||
assert task not in project.tasks.all() | ||
|
||
# Add the catalog to the task | ||
task.catalogs.add(catalog) | ||
# After adding the catalog, the project should now include the task | ||
assert task in project.tasks.all() | ||
|
||
# Remove the catalog from the task | ||
task.catalogs.remove(catalog) | ||
# After removing the catalog, the project should no longer include the task | ||
assert task not in project.tasks.all() |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,41 @@ | ||
|
||
|
||
|
||
from rdmo.projects.models import Project | ||
from rdmo.questions.models import Catalog | ||
from rdmo.views.models import View | ||
|
||
|
||
def test_project_views_sync_when_adding_or_removing_a_catalog_to_or_from_a_view(db, settings): | ||
assert settings.PROJECT_VIEWS_SYNC | ||
|
||
# Setup: Create a catalog, a view, and a project using the catalog | ||
catalog = Catalog.objects.first() | ||
view = View.objects.get(pk=3) | ||
# view.catalogs.clear() | ||
project = Project.objects.create(title="Test Project", catalog=catalog) | ||
pr10 = Project.objects.get(pk=10) | ||
|
||
# # Initially, the project should not have the view | ||
# assert view not in project.views.all() | ||
# assert view not in pr10.views.all() | ||
|
||
## Tests for .add and .remove | ||
# Add the catalog to the view and assert that the project now includes the view | ||
view.catalogs.add(catalog) | ||
assert view in project.views.all() | ||
|
||
# Remove the catalog from the view and assert that the project should no longer include the view | ||
view.catalogs.remove(catalog) | ||
assert view not in project.views.all() | ||
assert view not in pr10.views.all() | ||
|
||
## Tests for .set and .clear | ||
# Add the catalog to the view and assert that the project now includes the view | ||
view.catalogs.set([catalog]) | ||
assert view in project.views.all() | ||
|
||
# Remove the catalog from the view and assert that the project should no longer include the view | ||
view.catalogs.clear() | ||
assert view not in project.views.all() | ||
assert view not in pr10.views.all() |