package task

import (
	"net/http"
	"strings"

	"github.com/tidbcloud/AgentTeam/internal/api"
	"github.com/tidbcloud/AgentTeam/internal/api/dto"
	"github.com/tidbcloud/AgentTeam/internal/api/dto/converter"
)

// Claim handles PATCH /api/tasks/:taskId/claim.
// It claims a task for the authenticated user.
func (handler *LifecycleHandler) Claim(r api.WorkspaceScopedRequest) (api.Response, error) {
	authenticated := r.User
	workspaceID := r.WorkspaceID()

	taskID := strings.TrimSpace(r.Gin.Param("taskId"))
	if taskID == "" {
		return api.Response{}, api.NewHTTPError(http.StatusBadRequest, "taskId is required")
	}

	response, err := handler.taskBoard.ClaimTasks(r.Context(), ClaimTasksRequest{
		Context: NewUserServiceContext(workspaceID, authenticated.User.ID, authenticated.User.Name),
		Tasks:   []TaskRef{{TaskID: taskID}},
	})
	if err != nil {
		return api.Response{}, err
	}

	return api.OK(converter.ToTaskResponse(taskboardTaskForDTO(response.Task))), nil
}

// Unclaim handles PATCH /api/tasks/:taskId/unclaim.
// It releases the claim on a task.
func (handler *LifecycleHandler) Unclaim(r api.WorkspaceScopedRequest) (api.Response, error) {
	authenticated := r.User
	workspaceID := r.WorkspaceID()

	taskID := strings.TrimSpace(r.Gin.Param("taskId"))
	if taskID == "" {
		return api.Response{}, api.NewHTTPError(http.StatusBadRequest, "taskId is required")
	}

	response, err := handler.taskBoard.UnclaimTask(r.Context(), UnclaimTaskRequest{
		Context: NewUserServiceContext(workspaceID, authenticated.User.ID, authenticated.User.Name),
		Task:    TaskRef{TaskID: taskID},
	})
	if err != nil {
		return api.Response{}, err
	}

	return api.OK(converter.ToTaskResponse(taskboardTaskForDTO(response.Task))), nil
}

// Block handles PATCH /api/tasks/:taskId/block.
// It marks a task as blocked with a specified reason.
func (handler *LifecycleHandler) Block(r api.WorkspaceScopedJSON[dto.TaskBlockRequest]) (api.Response, error) {
	request := r.Body
	authenticated := r.User
	workspaceID := r.WorkspaceID()

	taskID := strings.TrimSpace(r.Gin.Param("taskId"))
	if taskID == "" {
		return api.Response{}, api.NewHTTPError(http.StatusBadRequest, "taskId is required")
	}

	response, err := handler.taskBoard.BlockTask(r.Context(), BlockTaskRequest{
		Context: NewUserServiceContext(workspaceID, authenticated.User.ID, authenticated.User.Name),
		Task:    TaskRef{TaskID: taskID},
		Block: TaskBlockInput{
			Reason: request.Reason,
		},
	})
	if err != nil {
		return api.Response{}, err
	}

	return api.OK(converter.ToTaskResponse(taskboardTaskForDTO(response.Task))), nil
}

// Unblock handles PATCH /api/tasks/:taskId/unblock.
// It removes the blocked status from a task.
func (handler *LifecycleHandler) Unblock(r api.WorkspaceScopedRequest) (api.Response, error) {
	authenticated := r.User
	workspaceID := r.WorkspaceID()

	taskID := strings.TrimSpace(r.Gin.Param("taskId"))
	if taskID == "" {
		return api.Response{}, api.NewHTTPError(http.StatusBadRequest, "taskId is required")
	}

	response, err := handler.taskBoard.UnblockTask(r.Context(), UnblockTaskRequest{
		Context: NewUserServiceContext(workspaceID, authenticated.User.ID, authenticated.User.Name),
		Task:    TaskRef{TaskID: taskID},
	})
	if err != nil {
		return api.Response{}, err
	}

	return api.OK(converter.ToTaskResponse(taskboardTaskForDTO(response.Task))), nil
}
