Skip to content
Snippets Groups Projects
serializers.py 6.62 KiB
Newer Older
  • Learn to ignore specific revisions
  • from django.db import transaction
    
    from django.utils import timezone
    
    from rest_framework import serializers
    
    from funkwhale_api.common import serializers as common_serializers
    from funkwhale_api.music import models as music_models
    
    from funkwhale_api.requests import models as requests_models
    
    Eliot Berriot's avatar
    Eliot Berriot committed
    from funkwhale_api.users import models as users_models
    
    
    from . import filters
    
    
    class ManageTrackFileArtistSerializer(serializers.ModelSerializer):
        class Meta:
            model = music_models.Artist
    
    Eliot Berriot's avatar
    Eliot Berriot committed
            fields = ["id", "mbid", "creation_date", "name"]
    
    
    
    class ManageTrackFileAlbumSerializer(serializers.ModelSerializer):
        artist = ManageTrackFileArtistSerializer()
    
        class Meta:
            model = music_models.Album
            fields = (
    
    Eliot Berriot's avatar
    Eliot Berriot committed
                "id",
                "mbid",
                "title",
                "artist",
                "release_date",
                "cover",
                "creation_date",
    
            )
    
    
    class ManageTrackFileTrackSerializer(serializers.ModelSerializer):
        artist = ManageTrackFileArtistSerializer()
        album = ManageTrackFileAlbumSerializer()
    
        class Meta:
            model = music_models.Track
    
    Eliot Berriot's avatar
    Eliot Berriot committed
            fields = ("id", "mbid", "title", "album", "artist", "creation_date", "position")
    
    
    
    class ManageTrackFileSerializer(serializers.ModelSerializer):
        track = ManageTrackFileTrackSerializer()
    
        class Meta:
            model = music_models.TrackFile
            fields = (
    
    Eliot Berriot's avatar
    Eliot Berriot committed
                "id",
                "path",
                "source",
                "filename",
                "mimetype",
                "track",
                "duration",
                "mimetype",
                "bitrate",
                "size",
                "path",
                "library_track",
    
            )
    
    
    class ManageTrackFileActionSerializer(common_serializers.ActionSerializer):
    
        actions = [common_serializers.Action("delete", allow_all=False)]
    
        filterset_class = filters.ManageTrackFileFilterSet
    
        @transaction.atomic
        def handle_delete(self, objects):
            return objects.delete()
    
    class PermissionsSerializer(serializers.Serializer):
        def to_representation(self, o):
            return o.get_permissions(defaults=self.context.get("default_permissions"))
    
        def to_internal_value(self, o):
            return {"permissions": o}
    
    
    
    class ManageUserSimpleSerializer(serializers.ModelSerializer):
        class Meta:
            model = users_models.User
            fields = (
                "id",
                "username",
                "email",
                "name",
                "is_active",
                "is_staff",
                "is_superuser",
                "date_joined",
                "last_activity",
                "privacy_level",
            )
    
    
    
    Eliot Berriot's avatar
    Eliot Berriot committed
    class ManageUserSerializer(serializers.ModelSerializer):
    
        permissions = PermissionsSerializer(source="*")
    
    Eliot Berriot's avatar
    Eliot Berriot committed
    
        class Meta:
            model = users_models.User
            fields = (
                "id",
                "username",
                "email",
                "name",
                "is_active",
                "is_staff",
                "is_superuser",
                "date_joined",
                "last_activity",
                "permissions",
                "privacy_level",
            )
            read_only_fields = [
                "id",
                "email",
                "privacy_level",
                "username",
                "date_joined",
                "last_activity",
            ]
    
    
        def update(self, instance, validated_data):
            instance = super().update(instance, validated_data)
            permissions = validated_data.pop("permissions", {})
            if permissions:
                for p, value in permissions.items():
                    setattr(instance, "permission_{}".format(p), value)
                instance.save(
                    update_fields=["permission_{}".format(p) for p in permissions.keys()]
                )
            return instance
    
    
    
    class ManageInvitationSerializer(serializers.ModelSerializer):
        users = ManageUserSimpleSerializer(many=True, required=False)
        owner = ManageUserSimpleSerializer(required=False)
        code = serializers.CharField(required=False, allow_null=True)
    
        class Meta:
            model = users_models.Invitation
            fields = ("id", "owner", "code", "expiration_date", "creation_date", "users")
            read_only_fields = ["id", "expiration_date", "owner", "creation_date", "users"]
    
        def validate_code(self, value):
            if not value:
                return value
    
            if users_models.Invitation.objects.filter(code__iexact=value).exists():
    
                raise serializers.ValidationError(
                    "An invitation with this code already exists"
                )
            return value
    
    
    
    class ManageInvitationActionSerializer(common_serializers.ActionSerializer):
    
        actions = [
            common_serializers.Action(
                "delete", allow_all=False, qs_filter=lambda qs: qs.open()
            )
        ]
    
        filterset_class = filters.ManageInvitationFilterSet
    
        @transaction.atomic
        def handle_delete(self, objects):
            return objects.delete()
    
    
    
    class ManageImportRequestSerializer(serializers.ModelSerializer):
        user = ManageUserSimpleSerializer(required=False)
    
        class Meta:
            model = requests_models.ImportRequest
            fields = [
                "id",
                "status",
                "creation_date",
                "imported_date",
                "user",
                "albums",
                "artist_name",
                "comment",
            ]
            read_only_fields = [
                "id",
                "status",
                "creation_date",
                "imported_date",
                "user",
                "albums",
                "artist_name",
                "comment",
            ]
    
        def validate_code(self, value):
            if not value:
                return value
            if users_models.Invitation.objects.filter(code__iexact=value).exists():
                raise serializers.ValidationError(
                    "An invitation with this code already exists"
                )
            return value
    
    
    class ManageImportRequestActionSerializer(common_serializers.ActionSerializer):
        actions = [
            common_serializers.Action(
                "mark_closed",
                allow_all=True,
                qs_filter=lambda qs: qs.filter(status__in=["pending", "accepted"]),
            ),
            common_serializers.Action(
                "mark_imported",
                allow_all=True,
                qs_filter=lambda qs: qs.filter(status__in=["pending", "accepted"]),
            ),
            common_serializers.Action("delete", allow_all=False),
        ]
        filterset_class = filters.ManageImportRequestFilterSet
    
        @transaction.atomic
        def handle_delete(self, objects):
            return objects.delete()
    
        @transaction.atomic
        def handle_mark_closed(self, objects):
            return objects.update(status="closed")
    
        @transaction.atomic
        def handle_mark_imported(self, objects):
            now = timezone.now()
            return objects.update(status="imported", imported_date=now)