132 lines
4.9 KiB
Python
132 lines
4.9 KiB
Python
from django.contrib.auth.views import LoginView
|
|
from django.views.generic import CreateView
|
|
from django.contrib.auth import login
|
|
from django.urls import reverse_lazy
|
|
from django.db.models import Count, Sum, F, IntegerField
|
|
|
|
from rest_framework.viewsets import ModelViewSet, GenericViewSet
|
|
from rest_framework import mixins
|
|
from rest_framework.decorators import action
|
|
from rest_framework.response import Response
|
|
import shutil
|
|
|
|
from .models import User, FriendRequest, Invitation
|
|
from .forms import RegisterForm
|
|
from .serializers import UserSerializer, FriendRequestSerializer, InvitationSerializer
|
|
|
|
|
|
|
|
class UserLoginView(LoginView):
|
|
template_name = "user/login.html"
|
|
fields = "__all__"
|
|
redirect_authenticated_user = True
|
|
|
|
|
|
class RegisterView(CreateView):
|
|
template_name = "user/register.html"
|
|
form_class = RegisterForm
|
|
success_url = reverse_lazy("torrent:home")
|
|
|
|
invitation = None
|
|
|
|
def get_form(self, form_class=None):
|
|
self.invitation = Invitation.objects.get(token=self.kwargs.get("token"), user__isnull=True)
|
|
return super().get_form(form_class)
|
|
|
|
def form_valid(self, form):
|
|
r = super().form_valid(form)
|
|
self.invitation.user = self.object
|
|
self.invitation.save()
|
|
login(self.request, self.object)
|
|
return r
|
|
|
|
|
|
class UserViewSet(mixins.RetrieveModelMixin,
|
|
mixins.ListModelMixin,
|
|
GenericViewSet):
|
|
queryset = User.objects.all().annotate(
|
|
count_torrent=Count("torrents") + Count("torrents_shares")
|
|
)
|
|
serializer_class = UserSerializer
|
|
|
|
def get_queryset(self):
|
|
qs = super().get_queryset()
|
|
|
|
only_friends = self.request.query_params.get("only_friends", "false") == "true"
|
|
if only_friends:
|
|
qs = qs.filter(friends=self.request.user)
|
|
|
|
return qs
|
|
|
|
@action(methods=["get"], detail=True)
|
|
def add_friend_request(self, request, pk):
|
|
# receiver = User.objects.get(pk=pk)
|
|
if not User.objects.filter(username__iexact=pk).exists():
|
|
return Response({"success": False, "message": f"User '{pk}' doesn't exist"})
|
|
|
|
receiver = User.objects.get(username__iexact=pk)
|
|
user: User = self.request.user
|
|
if user.friends.filter(id=receiver.id).exists():
|
|
# déjà dans les amis
|
|
return Response({"success": False, "message": "Already friend"})
|
|
elif FriendRequest.objects.filter(sender=user, receiver=receiver).exists():
|
|
# déjà une demande en attente
|
|
return Response({"success": False, "message": "Friend request Already sent"})
|
|
elif FriendRequest.objects.filter(sender=receiver, receiver=user).exists():
|
|
# friend request en cours, on accepte
|
|
FriendRequest.objects.filter(sender=receiver, receiver=user).delete()
|
|
user.friends.add(receiver)
|
|
return Response({"success": True, "message": f"{receiver.username} added to your friend list"})
|
|
else:
|
|
# aucune demande en cours, on créer un friend request
|
|
FriendRequest.objects.create(
|
|
sender=user,
|
|
receiver=receiver
|
|
)
|
|
return Response({"success": True, "message": "Request sent"})
|
|
|
|
@action(methods=["get"], detail=True)
|
|
def remove_friend(self, request, pk):
|
|
friend = User.objects.get(pk=pk)
|
|
if self.request.user.friends.filter(pk=friend.pk).exists():
|
|
self.request.user.friends.remove(friend)
|
|
return Response({"success": True, "message": f"The friend {friend.username} successfully removed"})
|
|
return Response({"success": False, "message": f"error"})
|
|
|
|
@action(methods=["get"], detail=False)
|
|
def user_stats(self, request):
|
|
stats = User.objects.filter(id=request.user.id).aggregate(
|
|
total_size=Sum("torrents__size"),
|
|
total_torrent=Count("torrents"),
|
|
total_shared_torrent=Count("torrents_shares")
|
|
)
|
|
|
|
disk_usage = shutil.disk_usage("/")
|
|
|
|
return Response({
|
|
"torrents_size": stats["total_size"],
|
|
"torrents_len": stats["total_torrent"],
|
|
"torrent_len_shared": stats["total_shared_torrent"],
|
|
"torrents_total_len": stats["total_torrent"] + stats["total_shared_torrent"],
|
|
"user_max_size": request.user.max_size,
|
|
"user_usage_percent": (stats["total_size"] / request.user.max_size) * 100,
|
|
"disk_total": disk_usage.total,
|
|
"disk_used": disk_usage.used,
|
|
"disk_free": disk_usage.free,
|
|
"disk_usage_percent": (disk_usage.used / disk_usage.total) * 100,
|
|
})
|
|
|
|
|
|
class FriendRequestViewSet(mixins.ListModelMixin,
|
|
mixins.DestroyModelMixin,
|
|
GenericViewSet):
|
|
queryset = FriendRequest.objects.all()
|
|
serializer_class = FriendRequestSerializer
|
|
|
|
def get_queryset(self):
|
|
qs = super().get_queryset()
|
|
|
|
qs = qs.filter(receiver=self.request.user)
|
|
|
|
return qs
|