import { Router } from "express";
import { scrobbleService } from "../../scrobbleService.js";
import { listenBrainzService } from "../../listenBrainzService.js";
import { serverLogger } from "../../../utils/logger.js";
const router = Router();
// Submit a scrobble
router.post("/scrobble", async (req, res)=>{
    try {
        const { track_path, artist, album, title, timestamp, duration, duration_played, source, loved } = req.body;
        if (!track_path && (!artist || !title)) {
            return res.status(400).json({
                error: "Either track_path or artist+title required"
            });
        }
        const scrobbleId = await scrobbleService.scrobble({
            track_path,
            artist,
            album,
            title,
            timestamp: timestamp || Date.now(),
            duration,
            duration_played,
            source: source || "api",
            user_agent: req.headers["user-agent"],
            ip_address: req.ip,
            loved
        });
        res.json({
            success: true,
            scrobble_id: scrobbleId,
            message: "Scrobble recorded"
        });
    } catch (error) {
        const errorMessage = error instanceof Error ? error.message : String(error);
        serverLogger.error("Failed to record scrobble", {
            error: errorMessage
        });
        res.status(500).json({
            error: "Failed to record scrobble"
        });
    }
});
// Submit multiple scrobbles (batch)
router.post("/scrobble/batch", async (req, res)=>{
    try {
        const { scrobbles } = req.body;
        if (!Array.isArray(scrobbles)) {
            return res.status(400).json({
                error: "scrobbles must be an array"
            });
        }
        const results = [];
        for (const scrobble of scrobbles){
            try {
                const id = await scrobbleService.scrobble({
                    ...scrobble,
                    source: scrobble.source || "api",
                    user_agent: req.headers["user-agent"],
                    ip_address: req.ip
                });
                results.push({
                    success: true,
                    id
                });
            } catch (error) {
                const errorMessage = error instanceof Error ? error.message : String(error);
                results.push({
                    success: false,
                    error: errorMessage
                });
            }
        }
        res.json({
            success: true,
            processed: scrobbles.length,
            results
        });
    } catch (error) {
        const errorMessage = error instanceof Error ? error.message : String(error);
        serverLogger.error("Failed to process batch scrobbles", {
            error: errorMessage
        });
        res.status(500).json({
            error: "Failed to process batch scrobbles"
        });
    }
});
// Get scrobble history
router.get("/scrobbles", async (req, res)=>{
    try {
        const { limit = 50, offset = 0, artist, album, from, to, loved } = req.query;
        const scrobbles = await scrobbleService.getScrobbles({
            limit: parseInt(limit),
            offset: parseInt(offset),
            artist: artist,
            album: album,
            from: from ? parseInt(from) : undefined,
            to: to ? parseInt(to) : undefined,
            loved: loved === "true"
        });
        res.json({
            scrobbles
        });
    } catch (error) {
        const errorMessage = error instanceof Error ? error.message : String(error);
        serverLogger.error("Failed to get scrobbles", {
            error: errorMessage
        });
        res.status(500).json({
            error: "Failed to get scrobbles"
        });
    }
});
// Get top artists
router.get("/top/artists", async (req, res)=>{
    try {
        const { limit = 50, period = "all", from, to } = req.query;
        const artists = await scrobbleService.getTopArtists({
            limit: parseInt(limit),
            period: period,
            from: from ? parseInt(from) : undefined,
            to: to ? parseInt(to) : undefined
        });
        res.json({
            artists
        });
    } catch (error) {
        const errorMessage = error instanceof Error ? error.message : String(error);
        serverLogger.error("Failed to get top artists", {
            error: errorMessage
        });
        res.status(500).json({
            error: "Failed to get top artists"
        });
    }
});
// Get top tracks
router.get("/top/tracks", async (req, res)=>{
    try {
        const { limit = 50, period = "all", artist, from, to } = req.query;
        const tracks = await scrobbleService.getTopTracks({
            limit: parseInt(limit),
            period: period,
            artist: artist,
            from: from ? parseInt(from) : undefined,
            to: to ? parseInt(to) : undefined
        });
        res.json({
            tracks
        });
    } catch (error) {
        const errorMessage = error instanceof Error ? error.message : String(error);
        serverLogger.error("Failed to get top tracks", {
            error: errorMessage
        });
        res.status(500).json({
            error: "Failed to get top tracks"
        });
    }
});
// Get overall statistics
router.get("/stats", async (req, res)=>{
    try {
        const { period = "all" } = req.query;
        const stats = await scrobbleService.getStats(period);
        res.json(stats);
    } catch (error) {
        const errorMessage = error instanceof Error ? error.message : String(error);
        serverLogger.error("Failed to get stats", {
            error: errorMessage
        });
        res.status(500).json({
            error: "Failed to get stats"
        });
    }
});
// Get listening history (for charts)
router.get("/history", async (req, res)=>{
    try {
        const { days = 30 } = req.query;
        const history = await scrobbleService.getListeningHistory(parseInt(days));
        res.json({
            history
        });
    } catch (error) {
        const errorMessage = error instanceof Error ? error.message : String(error);
        serverLogger.error("Failed to get listening history", {
            error: errorMessage
        });
        res.status(500).json({
            error: "Failed to get listening history"
        });
    }
});
// Love/unlove a track
router.post("/love", async (req, res)=>{
    try {
        const { track_path, loved = true } = req.body;
        if (!track_path) {
            return res.status(400).json({
                error: "track_path required"
            });
        }
        await scrobbleService.loveTrack(track_path, loved);
        res.json({
            success: true,
            message: loved ? "Track loved" : "Track unloved"
        });
    } catch (error) {
        const errorMessage = error instanceof Error ? error.message : String(error);
        serverLogger.error("Failed to love track", {
            error: errorMessage
        });
        res.status(500).json({
            error: "Failed to love track"
        });
    }
});
// Get loved tracks
router.get("/loved", async (req, res)=>{
    try {
        const { limit = 50 } = req.query;
        const tracks = await scrobbleService.getLovedTracks(parseInt(limit));
        res.json({
            tracks
        });
    } catch (error) {
        const errorMessage = error instanceof Error ? error.message : String(error);
        serverLogger.error("Failed to get loved tracks", {
            error: errorMessage
        });
        res.status(500).json({
            error: "Failed to get loved tracks"
        });
    }
});
// Now Playing endpoint (for current track being played)
router.post("/nowplaying", async (req, res)=>{
    try {
        const { track_path, artist, album, title, duration } = req.body;
        // Store in memory or temporary table for "now playing" display
        // This doesn't create a scrobble yet, just shows what's currently playing
        // Submit to ListenBrainz as "now playing" (async, don't wait)
        listenBrainzService.submitNowPlaying(artist, title, album, duration ? duration * 1000 : undefined).catch((err)=>{
            serverLogger.error("Failed to submit now playing to ListenBrainz", {
                error: err
            });
        });
        serverLogger.info("Now playing", {
            artist,
            title,
            source: req.body.source || "api"
        });
        res.json({
            success: true,
            message: "Now playing updated"
        });
    } catch (error) {
        const errorMessage = error instanceof Error ? error.message : String(error);
        serverLogger.error("Failed to update now playing", {
            error: errorMessage
        });
        res.status(500).json({
            error: "Failed to update now playing"
        });
    }
});
// Export scrobbles in various formats
router.get("/export", async (req, res)=>{
    try {
        const { format = "json", from, to } = req.query;
        let query = `SELECT * FROM scrobbles WHERE 1=1`;
        const params = [];
        if (from) {
            query += ` AND timestamp >= ?`;
            params.push(parseInt(from));
        }
        if (to) {
            query += ` AND timestamp <= ?`;
            params.push(parseInt(to));
        }
        query += ` ORDER BY timestamp DESC`;
        const scrobbles = scrobbleService.getDatabase().db.prepare(query).all(...params);
        if (format === "csv") {
            // Generate CSV
            const csv = [
                "artist,album,title,timestamp,duration,loved",
                ...scrobbles.map((s)=>`"${s.artist}","${s.album || ""}","${s.title}",${s.timestamp},${s.duration || ""},${s.loved || 0}`)
            ].join("\n");
            res.setHeader("Content-Type", "text/csv");
            res.setHeader("Content-Disposition", `attachment; filename="scrobbles-${Date.now()}.csv"`);
            res.send(csv);
        } else if (format === "lastfm") {
            // Last.fm compatible format
            const lastfmData = scrobbles.map((s)=>({
                    artist: {
                        "#text": s.artist
                    },
                    album: {
                        "#text": s.album || ""
                    },
                    name: s.title,
                    date: {
                        uts: Math.floor(s.timestamp / 1000).toString()
                    }
                }));
            res.json({
                recenttracks: {
                    track: lastfmData
                }
            });
        } else if (format === "listenbrainz") {
            // ListenBrainz format
            const lbData = scrobbles.map((s)=>({
                    listened_at: Math.floor(s.timestamp / 1000),
                    track_metadata: {
                        artist_name: s.artist,
                        track_name: s.title,
                        release_name: s.album,
                        additional_info: {
                            duration_ms: s.duration ? s.duration * 1000 : undefined
                        }
                    }
                }));
            res.json({
                payload: lbData
            });
        } else {
            // Default JSON format
            res.json({
                scrobbles,
                count: scrobbles.length
            });
        }
    } catch (error) {
        const errorMessage = error instanceof Error ? error.message : String(error);
        serverLogger.error("Failed to export scrobbles", {
            error: errorMessage
        });
        res.status(500).json({
            error: "Failed to export scrobbles"
        });
    }
});
// Import scrobbles from file
router.post("/import", async (req, res)=>{
    try {
        const { content, format } = req.body;
        let imported = 0;
        let failed = 0;
        if (format === "csv") {
            // Parse CSV
            const lines = content.split("\n").slice(1); // Skip header
            for (const line of lines){
                if (!line.trim()) continue;
                const [artist, album, title, timestamp, duration, loved] = line.split(",").map((s)=>s.replace(/^"|"$/g, ""));
                try {
                    await scrobbleService.scrobble({
                        artist,
                        album: album || undefined,
                        title,
                        timestamp: parseInt(timestamp),
                        duration: duration ? parseInt(duration) : undefined,
                        loved: loved === "1",
                        source: "import",
                        track_path: `import://${artist}/${album}/${title}`
                    });
                    imported++;
                } catch (err) {
                    failed++;
                }
            }
        } else {
            // Parse JSON
            const data = typeof content === "string" ? JSON.parse(content) : content;
            const scrobbles = data.scrobbles || data.payload || data.recenttracks?.track || [];
            for (const item of scrobbles){
                try {
                    let scrobbleData = {};
                    if (item.track_metadata) {
                        // ListenBrainz format
                        scrobbleData = {
                            artist: item.track_metadata.artist_name,
                            title: item.track_metadata.track_name,
                            album: item.track_metadata.release_name,
                            timestamp: item.listened_at * 1000,
                            duration: item.track_metadata.additional_info?.duration_ms ? item.track_metadata.additional_info.duration_ms / 1000 : undefined
                        };
                    } else if (item.artist && typeof item.artist === "object") {
                        // Last.fm format
                        scrobbleData = {
                            artist: item.artist["#text"] || item.artist.name,
                            title: item.name,
                            album: item.album?.["#text"] || item.album?.name,
                            timestamp: item.date?.uts ? parseInt(item.date.uts) * 1000 : Date.now()
                        };
                    } else {
                        // Direct format
                        scrobbleData = item;
                    }
                    scrobbleData.source = "import";
                    scrobbleData.track_path = scrobbleData.track_path || `import://${scrobbleData.artist}/${scrobbleData.album}/${scrobbleData.title}`;
                    await scrobbleService.scrobble(scrobbleData);
                    imported++;
                } catch (err) {
                    failed++;
                }
            }
        }
        res.json({
            success: true,
            imported,
            failed,
            message: `Imported ${imported} scrobbles`
        });
    } catch (error) {
        const errorMessage = error instanceof Error ? error.message : String(error);
        serverLogger.error("Failed to import scrobbles", {
            error: errorMessage
        });
        res.status(500).json({
            error: "Failed to import scrobbles"
        });
    }
});
export default router;

//# sourceMappingURL=scrobbleRoutes.js.map