# Generated by Django 4.2.9 on 2025-01-03 16:12

from django.db import migrations, models
from django.db import IntegrityError

from funkwhale_api.federation import utils as federation_utils
from django.urls import reverse
import uuid


def insert_tracks_to_playlist(apps, playlist, uploads):
    PlaylistTrack = apps.get_model("playlists", "PlaylistTrack")
    plts = [
        PlaylistTrack(
            creation_date=playlist.creation_date,
            playlist=playlist,
            track=upload.track,
            index=0 + i,
            uuid=(new_uuid := uuid.uuid4()),
            fid=federation_utils.full_url(
                reverse(
                    f"federation:music:playlists-detail",
                    kwargs={"uuid": new_uuid},
                )
            ),
        )
        for i, upload in enumerate(uploads)
        if upload.track
    ]

    return PlaylistTrack.objects.bulk_create(plts)


def migrate_libraries_to_playlist(apps, schema_editor):
    Playlist = apps.get_model("playlists", "Playlist")
    Library = apps.get_model("music", "Library")
    LibraryFollow = apps.get_model("federation", "LibraryFollow")
    Follow = apps.get_model("federation", "Follow")
    User = apps.get_model("users", "User")
    Actor = apps.get_model("federation", "Actor")

    # library to playlist
    for library in Library.objects.all():
        playlist = Playlist.objects.create(
            name=library.name,
            actor=library.actor,
            creation_date=library.creation_date,
            privacy_level=library.privacy_level,
            uuid=(new_uuid := uuid.uuid4()),
            fid=federation_utils.full_url(
                reverse(
                    f"federation:music:playlists-detail",
                    kwargs={"uuid": new_uuid},
                )
            ),
        )
        playlist.save()

        if library.uploads.all().exists():
            insert_tracks_to_playlist(apps, playlist, library.uploads.all())

        # library follows to user follow
        for lib_follow in LibraryFollow.objects.filter(target=library):
            try:
                Follow.objects.create(
                    uuid=lib_follow.uuid,
                    target=library.actor,
                    actor=lib_follow.actor,
                    approved=lib_follow.approved,
                    creation_date=lib_follow.creation_date,
                    modification_date=lib_follow.modification_date,
                )
            except IntegrityError:
                pass

        LibraryFollow.objects.all().delete()

    # migrate uploads to new library
    for actor in Actor.objects.all():
        privacy_levels = ["me", "instance", "everyone"]
        for privacy_level in privacy_levels:
            build_in_lib = Library.objects.create(
                actor=actor,
                privacy_level=privacy_level,
                name=privacy_level,
                uuid=(new_uuid := uuid.uuid4()),
                fid=federation_utils.full_url(
                    reverse(
                        f"federation:music:playlists-detail",
                        kwargs={"uuid": new_uuid},
                    )
                ),
            )
            for library in actor.libraries.filter(privacy_level=privacy_level):
                library.uploads.all().update(library=build_in_lib)
                if library.pk is not build_in_lib.pk:
                    library.delete()


class Migration(migrations.Migration):
    dependencies = [
        ("music", "0060_remove_library_description_and_more"),
    ]
    operations = [
        migrations.RunPython(
            migrate_libraries_to_playlist, reverse_code=migrations.RunPython.noop
        ),
    ]
