Skip to main content
Glama

timecard_save

Save timesheet data for a specific week by applying project entries, hours, and notes in one atomic operation. This tool fetches the target week, reconstructs form state, and submits changes without prior setup.

Instructions

Atomic save: apply entries, hours, and notes to a specific week in one operation.

This tool fetches the target week's page, reconstructs the full form state, applies your changes on top, and POSTs to the server — all in a single call. No prior setup needed other than authentication (handled automatically).

Parameters:

  • date (REQUIRED): YYYY-MM-DD — any date in the target week. Determines which week to save to.

  • entries: Set project/activity for row slots. Get activity_value from timecard_get_activities.

  • hours: Set hours for specific days. Use date in YYYY-MM-DD format.

  • notes: Set notes for specific days. Use date in YYYY-MM-DD format.

All dates in hours/notes must fall within the same week as the top-level date.

⚠️ WORKFLOW:

  1. timecard_get_timesheet(date) — view current data

  2. timecard_get_activities(project_id) — get activity_value for entries

  3. timecard_save({ — atomic save date: "2026-03-02", entries: [{ entry_index: 0, project_id: "17647", activity_value: "true$9$17647$100" }], hours: [ { entry_index: 0, date: "2026-03-02", hours: 8.0 }, { entry_index: 0, date: "2026-03-03", hours: 8.0 } ], notes: [ { entry_index: 0, date: "2026-03-02", note: "Development" } ] })

NOTE: Only 'save' (draft) is supported. 'submit' (for approval) is strictly prohibited. WARNING: Notes cannot contain special characters: #$%^&*=+{}[]|?'"

Input Schema

TableJSON Schema
NameRequiredDescriptionDefault
dateYesTarget date in YYYY-MM-DD format (any date in the target week)
entriesNoProject/activity configurations to set
hoursNoHour values to set
notesNoNote values to set

Implementation Reference

  • The handler function for 'timecard_save' tool. It validates the input date and calls the 'session.saveTimesheet' method.
    handler: async (args: Record<string, any>, session: TimeCardSession) => {
      const { date, entries, hours, notes } = args;
    
      if (!date || !/^\d{4}-\d{2}-\d{2}$/.test(date)) {
        throw new Error('date is required and must be in YYYY-MM-DD format');
      }
    
      const result = await session.saveTimesheet({ date, entries, hours, notes });
    
      return {
        success: result.success,
        message: result.message,
      };
    },
  • The input schema for the 'timecard_save' tool, defining the required date parameter and optional entries, hours, and notes arrays.
    inputSchema: {
      type: 'object',
      properties: {
        date: {
          type: 'string',
          description: 'Target date in YYYY-MM-DD format (any date in the target week)',
        },
        entries: {
          type: 'array',
          description: 'Project/activity configurations to set',
          items: {
            type: 'object',
            properties: {
              entry_index: {
                type: 'integer',
                description: 'Entry index (0-9)',
                minimum: 0,
                maximum: 9,
              },
              project_id: {
                type: 'string',
                description: 'Project ID',
              },
              activity_value: {
                type: 'string',
                description: 'Activity value from get_activities (format: bottom$uid$pid$progress)',
              },
            },
            required: ['entry_index', 'project_id', 'activity_value'],
          },
        },
        hours: {
          type: 'array',
          description: 'Hour values to set',
          items: {
            type: 'object',
            properties: {
              entry_index: {
                type: 'integer',
                description: 'Entry index (0-9)',
                minimum: 0,
                maximum: 9,
              },
              date: {
                type: 'string',
                description: 'Target date in YYYY-MM-DD format (must be in same week)',
              },
              hours: {
                type: 'number',
                description: 'Hours to set (0 to clear)',
              },
            },
            required: ['entry_index', 'date', 'hours'],
          },
        },
        notes: {
          type: 'array',
          description: 'Note values to set',
          items: {
            type: 'object',
            properties: {
              entry_index: {
                type: 'integer',
                description: 'Entry index (0-9)',
                minimum: 0,
                maximum: 9,
              },
              date: {
                type: 'string',
                description: 'Target date in YYYY-MM-DD format (must be in same week)',
              },
              note: {
                type: 'string',
                description: 'Note content (cannot contain: #$%^&*=+{}[]|?\'")',
              },
            },
            required: ['entry_index', 'date', 'note'],
          },
        },
      },
      required: ['date'],
    },
  • The registration of the 'timecard_save' tool within the 'saveTools' array.
    export const saveTools: MCPTool[] = [
      timecardSave,
    ];

Latest Blog Posts

MCP directory API

We provide all the information about MCP servers via our MCP API.

curl -X GET 'https://glama.ai/api/mcp/v1/servers/keith-hung/timecard-mcp'

If you have feedback or need assistance with the MCP directory API, please join our Discord server