const express = require("express");
const Task = require("../models/Task");
const User = require("../models/User");
const couchdbService = require("../services/couchdbService");
const auth = require("../middleware/auth");
const { asyncHandler } = require("../middleware/errorHandler");
const {
  createTaskValidation,
  taskIdValidation,
} = require("../middleware/validators/taskValidator");

const router = express.Router();

// Get all tasks for user (with pagination)
router.get(
  "/",
  auth,
  asyncHandler(async (req, res) => {
    const { buildPaginatedResponse } = require("../middleware/pagination");

    // Parse pagination params
    const page = parseInt(req.query.page) || 1;
    const limit = Math.min(parseInt(req.query.limit) || 10, 100);
    const skip = (page - 1) * limit;

    const tasks = await Task.find({ completedBy: req.user.id })
      .sort([{ createdAt: "desc" }])
      .skip(skip)
      .limit(limit);

    // Populate street and completedBy information
    for (const task of tasks) {
      if (task.street && task.street.streetId) {
        await task.populate("street");
      }
      if (task.completedBy && task.completedBy.userId) {
        await task.populate("completedBy");
      }
    }

    const totalCount = await Task.countDocuments({ completedBy: req.user.id });

    res.json(buildPaginatedResponse(tasks, totalCount, page, limit));
  }),
);

// Create a task
router.post(
  "/",
  auth,
  createTaskValidation,
  asyncHandler(async (req, res) => {
    const { street, description } = req.body;

    // Get street details for embedding
    const Street = require("../models/Street");
    const streetDoc = await Street.findById(street);
    
    if (!streetDoc) {
      return res.status(404).json({ msg: "Street not found" });
    }

    const streetData = {
      streetId: streetDoc._id,
      name: streetDoc.name,
      location: streetDoc.location
    };

    const task = await Task.create({
      street: streetData,
      description,
    });

    // Emit SSE event for new task
    const sse = req.app.get("sse");
    if (sse) {
      sse.broadcastToTopic("tasks", "taskUpdate", {
        type: "new_task",
        task,
      });
    }

    res.json(task);
  }),
);

// Complete a task
router.put(
  "/:id",
  auth,
  taskIdValidation,
  asyncHandler(async (req, res) => {
    try {
      await couchdbService.initialize();
      
      const task = await Task.findById(req.params.id);
      if (!task) {
        return res.status(404).json({ msg: "Task not found" });
      }

      // Check if task is already completed
      if (task.status === "completed") {
        return res.status(400).json({ msg: "Task already completed" });
      }

      // Get user details for embedding
      const user = await User.findById(req.user.id);
      const userDetails = {
        userId: user._id,
        name: user.name,
        profilePicture: user.profilePicture || ''
      };

      // Update task
      task.completedBy = userDetails;
      task.status = "completed";
      task.completedAt = new Date().toISOString();
      await task.save();

      // Award points for task completion using CouchDB service
      const updatedUser = await couchdbService.updateUserPoints(
        req.user.id,
        task.pointsAwarded || 10,
        `Completed task: ${task.description}`,
        {
          entityType: 'Task',
          entityId: task._id,
          entityName: task.description
        }
      );

      // Emit SSE event for task completion
      const sse = req.app.get("sse");
      if (sse) {
        sse.broadcastToTopic("tasks", "taskUpdate", {
          type: "task_completed",
          task,
        });
      }

      res.json({
        task,
        pointsAwarded: task.pointsAwarded || 10,
        newBalance: updatedUser.points,
        badgesEarned: [], // Badges are handled automatically in CouchDB service
      });
    } catch (err) {
      console.error("Error completing task:", err.message);
      throw err;
    }
  }),
);

module.exports = router;
