import logging import re from rest_framework.mixins import CreateModelMixin from rest_framework.permissions import IsAuthenticated from rest_framework.authentication import TokenAuthentication from rest_framework.generics import GenericAPIView from rest_framework.response import Response from rest_framework import status from apps.account.models import LocationHistory from apps.account.serializers import LocationHistorySerializer from utils.ip_helper import get_client_ip logger = logging.getLogger(__name__) def detect_browser_from_user_agent(user_agent): if not user_agent: return None try: ua = user_agent.lower() patterns = [ (r'edg/', 'Edge'), (r'opr/', 'Opera'), (r'chrome/', 'Chrome'), (r'firefox/', 'Firefox'), (r'safari/', 'Safari'), ] for pattern, browser in patterns: if re.search(pattern, ua): return browser return 'Unknown' except Exception: return None class LocationHistoryView(GenericAPIView, CreateModelMixin): permission_classes = [IsAuthenticated] authentication_classes = [TokenAuthentication] serializer_class = LocationHistorySerializer def post(self, request, *args, **kwargs): ip = get_client_ip(request) data = request.data.copy() data['ip'] = ip serializer = self.get_serializer(data=data) if serializer.is_valid(): serializer.save(user=request.user) return Response(serializer.data, status=status.HTTP_201_CREATED) return Response(serializer.errors, status=status.HTTP_400_BAD_REQUEST) def get_queryset(self): return LocationHistory.objects.filter(user=self.request.user) class RegionInfoView(GenericAPIView): """ Returns basic client region, browser, and network info """ def get(self, request, *args, **kwargs): user_agent = request.META.get('HTTP_USER_AGENT', '') client_ip = get_client_ip(request) browser = detect_browser_from_user_agent(user_agent) return Response({ 'ip': client_ip, 'browser': browser, 'user_agent': user_agent, })