1// SPDX-FileCopyrightText: Amolith <amolith@secluded.site>
2//
3// SPDX-License-Identifier: AGPL-3.0-or-later
4
5// Package timestamp provides the get_timestamp MCP tool for parsing natural
6// language dates into formatted timestamps.
7package timestamp
8
9import (
10 "context"
11 "fmt"
12 "time"
13
14 "github.com/ijt/go-anytime"
15 "github.com/mark3labs/mcp-go/mcp"
16
17 "git.sr.ht/~amolith/lunatask-mcp-server/tools/shared"
18)
19
20// Handler handles timestamp-related MCP tool calls.
21type Handler struct {
22 timezone string
23}
24
25// NewHandler creates a new timestamp Handler.
26func NewHandler(timezone string) *Handler {
27 return &Handler{timezone: timezone}
28}
29
30// Handle handles the get_timestamp tool call.
31//
32//nolint:wrapcheck // ReportError returns nil for error
33func (h *Handler) Handle(
34 _ context.Context,
35 request mcp.CallToolRequest,
36) (*mcp.CallToolResult, error) {
37 natLangDate, ok := request.Params.Arguments["natural_language_date"].(string)
38 if !ok || natLangDate == "" {
39 return shared.ReportError(
40 "Missing or invalid required argument: natural_language_date",
41 )
42 }
43
44 loc, err := shared.LoadLocation(h.timezone)
45 if err != nil {
46 return shared.ReportError(err.Error())
47 }
48
49 parsedTime, err := anytime.Parse(natLangDate, time.Now().In(loc))
50 if err != nil {
51 return shared.ReportError(
52 fmt.Sprintf("Could not parse natural language date: %v", err),
53 )
54 }
55
56 return &mcp.CallToolResult{
57 Content: []mcp.Content{
58 mcp.TextContent{
59 Type: "text",
60 Text: parsedTime.Format(time.RFC3339),
61 },
62 },
63 }, nil
64}