Skip to content

Commit f2125c3

Browse files
committed
Use static subclasses instead of a subclass generating function
1 parent c42406a commit f2125c3

File tree

6 files changed

+62
-53
lines changed

6 files changed

+62
-53
lines changed

multinet/api/views/common.py

Lines changed: 55 additions & 46 deletions
Original file line numberDiff line numberDiff line change
@@ -41,64 +41,73 @@ def paginate_queryset(self, query: ArangoQuery, request: Request) -> List[Dict]:
4141
return list(cur)
4242

4343

44-
def WorkspaceChildMixin(prefix=None):
45-
class _WorkspaceChildMixin(NestedViewSetMixin):
46-
def my_lookup_field(self):
47-
field = 'workspace__name'
48-
if prefix is not None:
49-
field = f'{prefix}__{field}'
44+
class WorkspaceChildMixin(NestedViewSetMixin):
45+
prefix = None
5046

51-
return field
47+
@property
48+
def workspace_field(self):
49+
field = 'workspace__name'
50+
print(type(self))
51+
if self.prefix is not None:
52+
field = f'{self.prefix}__{field}'
5253

53-
def get_parents_query_dict(self):
54-
parents_query_dict = super().get_parents_query_dict()
54+
return field
5555

56-
print(parents_query_dict)
56+
def get_parents_query_dict(self):
57+
parents_query_dict = super().get_parents_query_dict()
5758

58-
# Replace the standard lookup field with one that (possibly) goes
59-
# through the session object's related network or table object.
60-
new_field = self.my_lookup_field()
61-
if not new_field in parents_query_dict:
62-
old_field = 'workspace__name'
63-
parents_query_dict[new_field] = parents_query_dict.pop(old_field)
59+
print(parents_query_dict)
6460

65-
return parents_query_dict
61+
# Replace the standard lookup field with one that (possibly) goes
62+
# through the session object's related network or table object.
63+
new_field = self.workspace_field
64+
if not new_field in parents_query_dict:
65+
old_field = 'workspace__name'
66+
parents_query_dict[new_field] = parents_query_dict.pop(old_field)
6667

67-
def get_queryset(self):
68-
"""
69-
Get the queryset for workspace child enpoints.
68+
return parents_query_dict
7069

71-
Check that the requeting user has appropriate permissions for the associated workspace.
72-
"""
73-
child_objects = super().get_queryset()
70+
def get_queryset(self):
71+
"""
72+
Get the queryset for workspace child enpoints.
7473
75-
# prevent warning for schema generation incompatibility
76-
if getattr(self, 'swagger_fake_view', False):
77-
return child_objects.none()
74+
Check that the requeting user has appropriate permissions for the associated workspace.
75+
"""
76+
child_objects = super().get_queryset()
7877

79-
parent_query_dict = self.get_parents_query_dict()
80-
workspace = get_object_or_404(
81-
Workspace.objects.select_related('owner'), name=parent_query_dict[self.my_lookup_field()]
82-
)
78+
# prevent warning for schema generation incompatibility
79+
if getattr(self, 'swagger_fake_view', False):
80+
return child_objects.none()
8381

84-
# No user or user permission required for public workspaces
85-
if workspace.public:
86-
return child_objects
82+
parent_query_dict = self.get_parents_query_dict()
83+
workspace = get_object_or_404(
84+
Workspace.objects.select_related('owner'), name=parent_query_dict[self.workspace_field]
85+
)
8786

88-
# Private workspace
89-
request_user = self.request.user
90-
if not request_user.is_authenticated: # anonymous user
91-
raise Http404
87+
# No user or user permission required for public workspaces
88+
if workspace.public:
89+
return child_objects
9290

93-
workspace_role = WorkspaceRole.objects.filter(
94-
workspace=workspace, user=request_user
95-
).first()
91+
# Private workspace
92+
request_user = self.request.user
93+
if not request_user.is_authenticated: # anonymous user
94+
raise Http404
9695

97-
# If the user is at least a reader or the owner, grant access
98-
if workspace_role is not None or workspace.owner == request_user:
99-
return child_objects
96+
workspace_role = WorkspaceRole.objects.filter(
97+
workspace=workspace, user=request_user
98+
).first()
99+
100+
# If the user is at least a reader or the owner, grant access
101+
if workspace_role is not None or workspace.owner == request_user:
102+
return child_objects
103+
104+
# Read access denied
105+
raise Http404
106+
107+
108+
class NetworkWorkspaceChildMixin(WorkspaceChildMixin):
109+
prefix = 'network'
100110

101-
# Read access denied
102-
raise Http404
103111

104-
return _WorkspaceChildMixin
112+
class TableWorkspaceChildMixin(WorkspaceChildMixin):
113+
prefix = 'table'

multinet/api/views/network.py

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -70,7 +70,7 @@ def validate_edge_table(
7070
return Response(serialized_resp.data, status=status.HTTP_400_BAD_REQUEST)
7171

7272

73-
class NetworkViewSet(WorkspaceChildMixin(), DetailSerializerMixin, ReadOnlyModelViewSet):
73+
class NetworkViewSet(WorkspaceChildMixin, DetailSerializerMixin, ReadOnlyModelViewSet):
7474
queryset = Network.objects.all().select_related('workspace')
7575
lookup_field = 'name'
7676

multinet/api/views/query.py

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -14,7 +14,7 @@
1414
from .serializers import AqlQueryResultsSerializer, AqlQuerySerializer, AqlQueryTaskSerializer
1515

1616

17-
class AqlQueryViewSet(WorkspaceChildMixin(), ReadOnlyModelViewSet):
17+
class AqlQueryViewSet(WorkspaceChildMixin, ReadOnlyModelViewSet):
1818
queryset = AqlQuery.objects.all().select_related('workspace')
1919
permission_classes = [IsAuthenticatedOrReadOnly]
2020
serializer_class = AqlQueryTaskSerializer

multinet/api/views/session.py

Lines changed: 3 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -14,7 +14,7 @@
1414
from ..models import NetworkSession, TableSession, Workspace, WorkspaceRoleChoice
1515
from ..auth.decorators import require_workspace_permission
1616
from .serializers import NetworkSessionSerializer, TableSessionSerializer
17-
from .common import WorkspaceChildMixin
17+
from .common import TableWorkspaceChildMixin, NetworkWorkspaceChildMixin
1818

1919

2020
class SessionCreateSerializer(serializers.Serializer):
@@ -62,11 +62,11 @@ def state(self, request, parent_lookup_workspace__name: str, pk=None):
6262
return Response(status=status.HTTP_204_NO_CONTENT)
6363

6464

65-
class NetworkSessionViewSet(WorkspaceChildMixin('network'), SessionViewSet):
65+
class NetworkSessionViewSet(NetworkWorkspaceChildMixin, SessionViewSet):
6666
queryset = NetworkSession.objects.all().select_related('network__workspace')
6767
serializer_class = NetworkSessionSerializer
6868

6969

70-
class TableSessionViewSet(WorkspaceChildMixin('table'), SessionViewSet):
70+
class TableSessionViewSet(TableWorkspaceChildMixin, SessionViewSet):
7171
queryset = TableSession.objects.all().select_related('table__workspace')
7272
serializer_class = TableSessionSerializer

multinet/api/views/table.py

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -36,7 +36,7 @@ class RowDeleteResponseSerializer(serializers.Serializer):
3636
errors = serializers.ListField(child=serializers.JSONField())
3737

3838

39-
class TableViewSet(WorkspaceChildMixin(), ReadOnlyModelViewSet):
39+
class TableViewSet(WorkspaceChildMixin, ReadOnlyModelViewSet):
4040
queryset = Table.objects.all().select_related('workspace')
4141
lookup_field = 'name'
4242

multinet/api/views/upload.py

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -38,7 +38,7 @@ def field_value_object_key(serializer: serializers.Serializer) -> Optional[str]:
3838
return object_key
3939

4040

41-
class UploadViewSet(WorkspaceChildMixin(), ReadOnlyModelViewSet):
41+
class UploadViewSet(WorkspaceChildMixin, ReadOnlyModelViewSet):
4242
queryset = Upload.objects.all().select_related('workspace')
4343

4444
permission_classes = [IsAuthenticatedOrReadOnly]

0 commit comments

Comments
 (0)