import SwiftUI
import SwiftData

// MARK: - SessionListView
/// The session archive screen showing all recorded sessions
/// in a searchable, card-style list with sync status indicators.
/// Redesigned with a minimalist wireframe business style.
struct SessionListView: View {
    @Environment(\.modelContext) private var modelContext
    @Query(sort: \CelestiaSession.startTime, order: .reverse) private var sessions: [CelestiaSession]

    var onStartRecording: () -> Void = {}

    @State private var searchText = ""
    @State private var showSyncAuthPrompt = false
    @State private var showAuthModal = false
    @State private var deletionError: String?
    @State private var sessionPendingDeletion: CelestiaSession?
    @State private var selectedSession: CelestiaSession?
    @State private var showSessionDetail = false
    @ObservedObject private var authManager: AuthManager = .shared
    @ObservedObject private var syncManager: SyncManager = .shared

    var body: some View {
        NavigationStack {
            ZStack {
                Color.spaceBlack.ignoresSafeArea()

                if filteredSessions.isEmpty {
                    emptyState
                } else {
                    sessionList
                }
            }
            .navigationTitle("历史记录")
            .navigationBarTitleDisplayMode(.inline)
            .toolbar {
                if !sessions.isEmpty {
                    ToolbarItem(placement: .topBarTrailing) {
                        Button {
                            guard let userID = authManager.currentUser?.id else {
                                showSyncAuthPrompt = true
                                return
                            }
                            Task {
                                _ = await syncManager.sync(sessions: sessions, modelContext: modelContext, userID: userID)
                            }
                        } label: {
                            HStack(spacing: 4) {
                                Image(systemName: "icloud.and.arrow.up")
                                    .font(.system(size: 13))
                                Text(syncManager.isSyncing ? "同步中" : "同步")
                                    .font(.system(size: 13, weight: .medium))
                            }
                            .foregroundStyle(Color.primary)
                        }
                        .disabled(syncManager.isSyncing)
                    }
                }
            }
            .modifier(SessionSearchModifier(isEnabled: !sessions.isEmpty, searchText: $searchText))
            .sheet(isPresented: $showSyncAuthPrompt) {
                SyncAuthPromptModal(onLoginClick: {
                    showAuthModal = true
                })
            }
            .sheet(isPresented: $showAuthModal) {
                AuthModalView()
            }
            .navigationDestination(isPresented: $showSessionDetail) {
                if let selectedSession {
                    SessionDetailView(session: selectedSession)
                }
            }
            .alert("删除失败", isPresented: Binding(
                get: { deletionError != nil },
                set: { if !$0 { deletionError = nil } }
            )) {
                Button("好", role: .cancel) {}
            } message: {
                Text(deletionError ?? "请稍后重试。")
            }
            .alert(
                "确认删除？",
                isPresented: Binding(
                    get: { sessionPendingDeletion != nil },
                    set: { if !$0 { sessionPendingDeletion = nil } }
                ),
                presenting: sessionPendingDeletion
            ) { session in
                Button("取消", role: .cancel) {}
                Button("删除", role: .destructive) {
                    deleteSession(session)
                    sessionPendingDeletion = nil
                }
            } message: { session in
                Text("删除「\(session.title)」后，相关录音和图片也会被删除，且无法恢复。")
            }
        }
    }

    // MARK: - Filtered Sessions

    private var filteredSessions: [CelestiaSession] {
        guard !searchText.isEmpty else { return sessions }
        let query = searchText.lowercased()
        return sessions.filter { session in
            if session.title.lowercased().contains(query) { return true }
            return session.events.contains { event in
                event.textContent?.lowercased().contains(query) == true
            }
        }
    }

    // MARK: - Session List

    private var sessionList: some View {
        List {
            ForEach(filteredSessions) { session in
                Button {
                    selectedSession = session
                    showSessionDetail = true
                } label: {
                    SessionRowCard(session: session)
                        .contentShape(Rectangle())
                }
                .buttonStyle(.plain)
                .listRowInsets(EdgeInsets(top: 6, leading: 16, bottom: 6, trailing: 16))
                .listRowBackground(Color.clear)
                .listRowSeparator(.hidden)
                .swipeActions(edge: .trailing, allowsFullSwipe: false) {
                    Button {
                        sessionPendingDeletion = session
                    } label: {
                        Label("删除", systemImage: "trash")
                    }
                    .tint(.red)
                }
            }
        }
        .listStyle(.plain)
        .scrollContentBackground(.hidden)
        .contentMargins(.bottom, 18, for: .scrollContent)
    }

    private func deleteSession(_ session: CelestiaSession) {
        let storedPaths =
            [session.localAudioPath].compactMap { $0 } +
            session.audioChunks.map(\.localFilePath) +
            session.events.compactMap(\.localFilePath)
        let fileURLs = Set(storedPaths.compactMap { AudioPathHelper.resolveURL(for: $0) })

        modelContext.delete(session)

        do {
            try modelContext.save()
            for fileURL in fileURLs {
                try? FileManager.default.removeItem(at: fileURL)
            }
        } catch {
            modelContext.rollback()
            deletionError = error.localizedDescription
        }
    }

    // MARK: - Empty State

    @ViewBuilder
    private var emptyState: some View {
        if sessions.isEmpty {
            Button(action: onStartRecording) {
                emptyStateContent
                    .contentShape(Rectangle())
            }
            .buttonStyle(.plain)
        } else {
            emptyStateContent
        }
    }

    private var emptyStateContent: some View {
        VStack(spacing: 16) {
            Image(systemName: "square.dashed")
                .font(.system(size: 36))
                .foregroundStyle(Color.secondary.opacity(0.4))

            Text("暂无记录")
                .font(.system(size: 14, weight: .medium))
                .foregroundStyle(Color.primary)

            if !searchText.isEmpty {
                Text("未找到与「\(searchText)」匹配的会话")
                    .font(.system(size: 12))
                    .foregroundStyle(Color.secondary)
            } else {
                Text("先试试去开始一次现场记录")
                    .font(.system(size: 12))
                    .foregroundStyle(Color.secondary.opacity(0.7))
            }
        }
        .frame(maxWidth: .infinity, maxHeight: .infinity)
        .padding(.bottom, 60)
    }
}

private struct SessionSearchModifier: ViewModifier {
    let isEnabled: Bool
    @Binding var searchText: String

    @ViewBuilder
    func body(content: Content) -> some View {
        if isEnabled {
            content.searchable(
                text: $searchText,
                placement: .navigationBarDrawer(displayMode: .always),
                prompt: "搜索会话或笔记..."
            )
        } else {
            content
        }
    }
}

// MARK: - Session Row Card

private struct SessionRowCard: View {
    let session: CelestiaSession

    var body: some View {
        HStack(spacing: 12) {
            // Sync status indicator (plain circular dot)
            Circle()
                .fill(session.isSynced ? Color.secondary.opacity(0.4) : Color.recordingRed.opacity(0.6))
                .frame(width: 6, height: 6)

            VStack(alignment: .leading, spacing: 4) {
                Text(session.title)
                    .font(.system(size: 14, weight: .medium))
                    .foregroundStyle(Color.primary)
                    .lineLimit(1)

                HStack(spacing: 6) {
                    Text(session.startTime.formatted(.dateTime.month().day().hour().minute()))
                        .font(.system(size: 11))
                        .foregroundStyle(Color.secondary)

                    Text("·")
                        .foregroundStyle(Color.secondary.opacity(0.4))

                    Text(session.durationFormatted)
                        .font(.system(size: 11, weight: .regular, design: .monospaced))
                        .foregroundStyle(Color.secondary)
                }
            }

            Spacer()

            // Count badges (plain line style)
            HStack(spacing: 8) {
                countBadge(icon: "camera", count: session.photoCount)
                countBadge(icon: "doc.text", count: session.noteCount)
            }
            .padding(.trailing, 4)

        }
        .padding(14)
        .background(Color.cardBackground.opacity(0.2))
        .businessBorder(cornerRadius: 8)
    }

    private func countBadge(icon: String, count: Int) -> some View {
        HStack(spacing: 3) {
            Image(systemName: icon)
                .font(.system(size: 10, weight: .light))
            Text("\(count)")
                .font(.system(size: 11, weight: .regular, design: .monospaced))
        }
        .foregroundStyle(Color.secondary)
        .padding(.horizontal, 6)
        .padding(.vertical, 2)
        .businessBorder(cornerRadius: 4)
    }
}

// MARK: - Preview

#Preview {
    SessionListView()
        .modelContainer(for: CelestiaSession.self, inMemory: true)
}
