No Description

views.py 4.3KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115
  1. from rest_framework import viewsets
  2. from rest_framework.permissions import IsAuthenticated, AllowAny
  3. from rest_framework.decorators import action
  4. from rest_framework.response import Response
  5. from django_filters.rest_framework import DjangoFilterBackend
  6. from django.db.models import Q
  7. from .models import Profile, Opportunity, IntroductionRequest
  8. from .serializers import ProfileSerializer, OpportunitySerializer, IntroductionRequestSerializer, LeaderRowSerializer
  9. from .services.matching import rank_users_for, rank_opportunities_for
  10. from .services.benefit import build_leaderboard_queryset
  11. class ProfileViewSet(viewsets.ModelViewSet):
  12. queryset = Profile.objects.all()
  13. serializer_class = ProfileSerializer
  14. permission_classes = [IsAuthenticated]
  15. filter_backends = [DjangoFilterBackend]
  16. filterset_fields = {
  17. 'user__username': ['exact', 'icontains'],
  18. 'is_verified': ['exact'],
  19. 'industry': ['exact', 'icontains'],
  20. 'interests': ['icontains'],
  21. 'tags__name': ['exact', 'icontains'],
  22. }
  23. @action(detail=False, methods=['get'], permission_classes=[IsAuthenticated])
  24. def match(self, request):
  25. """Return top user matches for the authenticated user."""
  26. ranked = rank_users_for(request.user, k=int(request.query_params.get('k', 20)))
  27. payload = [
  28. {
  29. 'score': round(item.score, 4),
  30. 'profile': ProfileSerializer(item.profile, context={'request': request}).data,
  31. }
  32. for item in ranked
  33. ]
  34. return Response(payload)
  35. class OpportunityViewSet(viewsets.ModelViewSet):
  36. queryset = Opportunity.objects.all()
  37. serializer_class = OpportunitySerializer
  38. permission_classes = [IsAuthenticated]
  39. filter_backends = [DjangoFilterBackend]
  40. filterset_fields = {
  41. 'title': ['exact', 'icontains'],
  42. 'created_at': ['gte', 'lte'],
  43. }
  44. @action(detail=False, methods=['get'], permission_classes=[IsAuthenticated])
  45. def recommend(self, request):
  46. """Return top opportunity recommendations for the authenticated user."""
  47. ranked = rank_opportunities_for(request.user, k=int(request.query_params.get('k', 20)))
  48. payload = [
  49. {
  50. 'score': round(item.score, 4),
  51. 'opportunity': OpportunitySerializer(item.opportunity, context={'request': request}).data,
  52. }
  53. for item in ranked
  54. ]
  55. return Response(payload)
  56. class IntroductionRequestViewSet(viewsets.ModelViewSet):
  57. queryset = IntroductionRequest.objects.all()
  58. serializer_class = IntroductionRequestSerializer
  59. permission_classes = [IsAuthenticated]
  60. filter_backends = [DjangoFilterBackend]
  61. filterset_fields = {
  62. 'from_user__username': ['exact', 'icontains'],
  63. 'to_user__username': ['exact', 'icontains'],
  64. 'is_accepted': ['exact'],
  65. 'message': ['icontains'],
  66. }
  67. def get_queryset(self):
  68. return IntroductionRequest.objects.filter(
  69. Q(from_user=self.request.user) | Q(to_user=self.request.user)
  70. )
  71. def perform_create(self, serializer):
  72. serializer.save(from_user=self.request.user)
  73. class LeaderboardView(viewsets.ViewSet):
  74. permission_classes = [AllowAny]
  75. def list(self, request):
  76. period = request.query_params.get('period', 'weekly')
  77. try:
  78. limit = min(int(request.query_params.get('limit', 100)), 500)
  79. except Exception:
  80. limit = 100
  81. try:
  82. offset = int(request.query_params.get('offset', 0))
  83. except Exception:
  84. offset = 0
  85. qs = build_leaderboard_queryset(period)
  86. page = qs[offset:offset+limit]
  87. data = LeaderRowSerializer(page, many=True).data
  88. return Response({"period": period, "offset": offset, "limit": limit, "results": data})
  89. class LeaderboardMeView(viewsets.ViewSet):
  90. permission_classes = [IsAuthenticated]
  91. def list(self, request):
  92. period = request.query_params.get('period', 'weekly')
  93. qs = build_leaderboard_queryset(period)
  94. me = qs.filter(id=request.user.id).first()
  95. if not me:
  96. return Response({
  97. "period": period,
  98. "result": None,
  99. "detail": "No rank for current user in this period.",
  100. })
  101. return Response({"period": period, "result": LeaderRowSerializer(me).data})