Skip to main content
Glama

vote_on_poll

Submit availability votes for poll time slots by mapping each option to yes, maybe, or no. Updates previous votes on resubmission with same voter name.

Instructions

Submit votes on a Timergy poll. First call get_poll to retrieve the available optionId values. Each vote maps an optionId to an availability: 'yes' (available), 'maybe' (might work), or 'no' (unavailable). A unique voter token is auto-generated per voter name. Resubmitting with the same voter name updates previous votes.

Input Schema

TableJSON Schema
NameRequiredDescriptionDefault
pollIdYesPoll UUID
voterNameYesName of the voter
voterEmailNoOptional voter email for finalization notification
votesYesOne vote per time slot

Implementation Reference

  • src/index.ts:77-97 (registration)
    MCP server registration of the 'vote_on_poll' tool with Zod input schema (pollId, voterName, voterEmail, votes array) and a handler that delegates to handleToolCall.
    server.tool(
      "vote_on_poll",
      TOOL_DESCRIPTIONS.vote_on_poll,
      {
        pollId: z.string().describe("Poll UUID"),
        voterName: z.string().describe("Name of the voter"),
        voterEmail: z.string().optional().describe("Optional voter email for finalization notification"),
        votes: z.array(z.object({
          optionId: z.string().describe("Time slot option UUID (from get_poll)"),
          availability: z.enum(["yes", "maybe", "no"]).describe("yes = available, maybe = might work, no = unavailable"),
        })).describe("One vote per time slot"),
      },
      async (args) => {
        try {
          const text = await handleToolCall("vote_on_poll", args, client, stdioSession());
          return { content: [{ type: "text", text }] };
        } catch (e) {
          return { content: [{ type: "text", text: `Error: ${e instanceof Error ? e.message : String(e)}` }], isError: true };
        }
      },
    );
  • Core handler for 'vote_on_poll'. Parses args with Zod, retrieves/generates a voterToken per voter name via session state, calls client.vote() via HTTP, and returns success JSON.
    case "vote_on_poll": {
      const input = z.object({
        pollId: z.string(),
        voterName: z.string(),
        voterEmail: z.string().optional(),
        votes: z.array(z.object({
          optionId: z.string(),
          availability: z.enum(["yes", "maybe", "no"]),
        })),
      }).parse(args);
    
      // Reuse or generate voterToken per voter name
      const tokenKey = `${input.pollId}:${input.voterName}`;
      let voterToken = voterTokenMap.get(tokenKey);
      if (!voterToken) {
        voterToken = randomUUID();
        voterTokenMap.set(tokenKey, voterToken);
      }
    
      await client.vote(input.pollId, {
        voterName: input.voterName,
        voterToken,
        voterEmail: input.voterEmail,
        votes: input.votes,
      });
    
      return JSON.stringify({
        success: true,
        voterName: input.voterName,
        votesSubmitted: input.votes.length,
      }, null, 2);
    }
  • Descriptive text for the 'vote_on_poll' tool explaining usage: map optionId to yes/maybe/no, auto-generates voter token, resubmitting updates votes.
    vote_on_poll:
      "Submit votes on a Timergy poll. First call get_poll to retrieve the available optionId values. " +
      "Each vote maps an optionId to an availability: 'yes' (available), 'maybe' (might work), or 'no' (unavailable). " +
      "A unique voter token is auto-generated per voter name. Resubmitting with the same voter name updates previous votes.",
  • Zod schema for vote_on_poll input: pollId (string), voterName (string), voterEmail (optional string), votes (array of {optionId, availability: yes|maybe|no}).
    {
      pollId: z.string().describe("Poll UUID"),
      voterName: z.string().describe("Name of the voter"),
      voterEmail: z.string().optional().describe("Optional voter email for finalization notification"),
      votes: z.array(z.object({
        optionId: z.string().describe("Time slot option UUID (from get_poll)"),
        availability: z.enum(["yes", "maybe", "no"]).describe("yes = available, maybe = might work, no = unavailable"),
      })).describe("One vote per time slot"),
  • VoteInput interface used by client.vote() – defines the structure sent to the API: voterName, voterToken, voterEmail?, votes array.
    export interface VoteInput {
      voterName: string;
      voterToken: string;
      voterEmail?: string;
      votes: Array<{ optionId: string; availability: "yes" | "maybe" | "no" }>;
    }
Behavior4/5

Does the description disclose side effects, auth requirements, rate limits, or destructive behavior?

Description discloses that a unique voter token is auto-generated per voter name and that resubmission updates previous votes. With no annotations provided, this adds valuable behavioral context about idempotency and auto-generation.

Agents need to know what a tool does to the world before calling it. Descriptions should go beyond structured annotations to explain consequences.

Conciseness5/5

Is the description appropriately sized, front-loaded, and free of redundancy?

Five sentences packed with essential information: purpose, prerequisite, mapping, behavior. No redundant words; well-structured and efficient.

Shorter descriptions cost fewer tokens and are easier for agents to parse. Every sentence should earn its place.

Completeness4/5

Given the tool's complexity, does the description cover enough for an agent to succeed on first attempt?

Covers prerequisite, vote mapping, and update behavior. Lacks mention of return values (no output schema), but for a voting submit tool the description is sufficiently complete.

Complex tools with many parameters or behaviors need more documentation. Simple tools need less. This dimension scales expectations accordingly.

Parameters4/5

Does the description clarify parameter syntax, constraints, interactions, or defaults beyond what the schema provides?

Schema already covers all parameters with descriptions (100% coverage). Description adds context that optionIds come from get_poll and explains the availability enum values, enriching meaning beyond the schema.

Input schemas describe structure but not intent. Descriptions should explain non-obvious parameter relationships and valid value ranges.

Purpose5/5

Does the description clearly state what the tool does and how it differs from similar tools?

Clearly states 'Submit votes on a Timergy poll' as the main action. Differentiates from siblings by mentioning prerequisite get_poll to retrieve optionIds, and explains the vote mapping.

Agents choose between tools based on descriptions. A clear purpose with a specific verb and resource helps agents select the right tool.

Usage Guidelines4/5

Does the description explain when to use this tool, when not to, or what alternatives exist?

Explicitly instructs to call get_poll first to get optionIds, and notes that resubmitting with same voter name updates votes. Does not explicitly mention when not to use this tool versus finalize_poll, but the guidance is clear enough.

Agents often have multiple tools that could apply. Explicit usage guidance like "use X instead of Y when Z" prevents misuse.

Install Server

Other Tools

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/timergy-app/timergy'

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