add DELETE endpoints for /friends and /friendrequests
All checks were successful
continuous-integration/drone/push Build is passing

This commit is contained in:
j3d1 2023-10-25 23:50:19 +02:00
parent 41251b64b7
commit a461807edd
3 changed files with 49 additions and 6 deletions

View file

@ -2,7 +2,7 @@ import secrets
from django.urls import path from django.urls import path
from rest_framework import status from rest_framework import status
from rest_framework.decorators import api_view from rest_framework.decorators import api_view, authentication_classes, permission_classes
from rest_framework.generics import get_object_or_404 from rest_framework.generics import get_object_or_404
from rest_framework.permissions import IsAuthenticated from rest_framework.permissions import IsAuthenticated
from rest_framework.response import Response from rest_framework.response import Response
@ -11,7 +11,7 @@ from rest_framework.viewsets import ViewSetMixin
from authentication.models import KnownIdentity, FriendRequestIncoming, FriendRequestOutgoing, ToolshedUser from authentication.models import KnownIdentity, FriendRequestIncoming, FriendRequestOutgoing, ToolshedUser
from authentication.signature_auth import verify_incoming_friend_request, split_userhandle_or_throw, \ from authentication.signature_auth import verify_incoming_friend_request, split_userhandle_or_throw, \
authenticate_request_against_local_users, SignatureAuthentication authenticate_request_against_local_users, SignatureAuthenticationLocal, SignatureAuthentication
from toolshed.serializers import FriendSerializer, FriendRequestSerializer from toolshed.serializers import FriendSerializer, FriendRequestSerializer
@ -120,7 +120,30 @@ class FriendsRequests(APIView, ViewSetMixin):
return Response(status=status.HTTP_400_BAD_REQUEST) return Response(status=status.HTTP_400_BAD_REQUEST)
@api_view(['DELETE'])
@authentication_classes([SignatureAuthenticationLocal])
@permission_classes([IsAuthenticated])
def dropFriend(request, pk, format=None): # /api/friends/<id>/
user = request.user
friend = get_object_or_404(user.friends, pk=pk)
user.friends.remove(friend)
user.save()
return Response(status=status.HTTP_204_NO_CONTENT)
@api_view(['DELETE'])
@authentication_classes([SignatureAuthenticationLocal])
@permission_classes([IsAuthenticated])
def deleteFriendRequest(request, pk, format=None): # /api/friendrequests/<id>/
user = request.user
get_object_or_404(user.friend_requests_incoming, pk=pk).delete()
user.save()
return Response(status=status.HTTP_204_NO_CONTENT)
urlpatterns = [ urlpatterns = [
path('friends/', Friends.as_view(), name='friends'), path('friends/', Friends.as_view(), name='friends'),
path('friends/<int:pk>/', dropFriend),
path('friendrequests/', FriendsRequests.as_view(), name='friendrequests'), path('friendrequests/', FriendsRequests.as_view(), name='friendrequests'),
path('friendrequests/<int:pk>/', deleteFriendRequest),
] ]

View file

@ -5,7 +5,7 @@ from rest_framework.decorators import authentication_classes, api_view, permissi
from rest_framework.permissions import IsAuthenticated from rest_framework.permissions import IsAuthenticated
from rest_framework.response import Response from rest_framework.response import Response
from authentication.models import ToolshedUser from authentication.models import ToolshedUser, KnownIdentity
from authentication.signature_auth import SignatureAuthentication from authentication.signature_auth import SignatureAuthentication
from toolshed.models import InventoryItem from toolshed.models import InventoryItem
from toolshed.serializers import InventoryItemSerializer from toolshed.serializers import InventoryItemSerializer
@ -33,7 +33,9 @@ class InventoryItemViewSet(viewsets.ModelViewSet):
permission_classes = [IsAuthenticated] permission_classes = [IsAuthenticated]
def get_queryset(self): def get_queryset(self):
if type(self.request.user) == KnownIdentity and self.request.user.user.exists():
return InventoryItem.objects.filter(owner=self.request.user.user.get()) return InventoryItem.objects.filter(owner=self.request.user.user.get())
return InventoryItem.objects.none()
def perform_create(self, serializer): def perform_create(self, serializer):
with transaction.atomic(): with transaction.atomic():

View file

@ -78,6 +78,12 @@ class FriendApiTestCase(UserTestMixin, ToolshedTestCase):
self.assertEqual(len(reply.json()), 1) self.assertEqual(len(reply.json()), 1)
self.assertEqual(reply.json()[0]['username'], str(self.f['local_user1'])) self.assertEqual(reply.json()[0]['username'], str(self.f['local_user1']))
def test_friend_delete(self):
reply = client.delete('/api/friends/{}/'.format(self.f['local_user2'].public_identity.id),
self.f['local_user1'])
self.assertEqual(reply.status_code, 204)
self.assertEqual(self.f['local_user1'].friends.count(), 1)
# what ~should~ happen: # what ~should~ happen:
# 1. user x@A sends a friend request to user y@B # 1. user x@A sends a friend request to user y@B
@ -100,10 +106,11 @@ class FriendRequestListTestCase(UserTestMixin, ToolshedTestCase):
def setUp(self): def setUp(self):
super().setUp() super().setUp()
self.prepare_users() self.prepare_users()
FriendRequestIncoming.objects.create( self.friendrequest1 = FriendRequestIncoming.objects.create(
befriender_username=self.f['ext_user2'].username, befriender_domain=self.f['ext_user2'].domain, befriender_username=self.f['ext_user2'].username, befriender_domain=self.f['ext_user2'].domain,
befriender_public_key=self.f['ext_user2'].public_key(), befriendee_user=self.f['local_user1'], befriender_public_key=self.f['ext_user2'].public_key(), befriendee_user=self.f['local_user1'],
secret='secret1').save() secret='secret1')
self.friendrequest1.save()
def test_friend_request_withouth_auth(self): def test_friend_request_withouth_auth(self):
reply = Client().get('/api/friendrequests/') reply = Client().get('/api/friendrequests/')
@ -121,6 +128,17 @@ class FriendRequestListTestCase(UserTestMixin, ToolshedTestCase):
self.assertEqual(reply.json()[0]['befriender'], str(self.f['ext_user2'])) self.assertEqual(reply.json()[0]['befriender'], str(self.f['ext_user2']))
self.assertEqual(reply.json()[0]['befriender_public_key'], self.f['ext_user2'].public_key()) self.assertEqual(reply.json()[0]['befriender_public_key'], self.f['ext_user2'].public_key())
def test_delete_friend_request(self):
reply = client.delete('/api/friendrequests/{}/'.format(self.friendrequest1.id),
self.f['local_user1'])
self.assertEqual(reply.status_code, 204)
self.assertEqual(FriendRequestIncoming.objects.count(), 0)
def test_delete_friend_request_not_found(self):
reply = client.delete('/api/friendrequests/999/', self.f['local_user1'])
self.assertEqual(reply.status_code, 404)
self.assertEqual(FriendRequestIncoming.objects.count(), 1)
class FriendRequestIncomingTestCase(UserTestMixin, ToolshedTestCase): class FriendRequestIncomingTestCase(UserTestMixin, ToolshedTestCase):
def setUp(self): def setUp(self):