Skip to main content
Glama
SpasticPalate

Proton MCP Server

proton_list_emails

Retrieve emails from a Proton Mail folder with pagination. View sender, subject, date, and read status for organized email management.

Instructions

List emails in a specific folder with pagination. Shows sender, subject, date, and read status. Results are newest first.

Input Schema

TableJSON Schema
NameRequiredDescriptionDefault
folderNoINBOX
limitNo
offsetNo

Implementation Reference

  • Registration of the proton_list_emails tool, which uses the listMessages service to fetch data.
    export function registerListEmailsTool(server: McpServer) {
      server.registerTool(
        'proton_list_emails',
        {
          title: 'List Emails in Folder',
          description: 'List emails in a specific folder with pagination. Shows sender, subject, date, and read status. Results are newest first.',
          inputSchema: ListEmailsSchema,
          annotations: {
            readOnlyHint: true,
            destructiveHint: false,
            idempotentHint: true,
            openWorldHint: false,
          },
        },
        async (params: z.infer<typeof ListEmailsSchema>) => {
          try {
            const messages = await listMessages(params.folder, params.limit, params.offset);
    
            if (messages.length === 0) {
              return {
                content: [
                  {
                    type: 'text',
                    text: 'No messages found in this folder.',
                  },
                ],
              };
            }
    
            // Format as markdown table
            let result = `**Folder:** ${params.folder}\n`;
            result += `**Page:** offset=${params.offset}, limit=${params.limit}\n\n`;
            result += '| UID | From | Subject | Date | Read |\n';
            result += '|-----|------|---------|------|------|\n';
    
            for (const msg of messages) {
              const fromName = msg.from.name || msg.from.email;
              const subject = msg.subject.substring(0, 40);
              const date = msg.date.toISOString().split('T')[0];
              const readStatus = msg.seen ? '✓' : '✗';
    
              result += `| ${msg.uid} | ${fromName} | ${subject} | ${date} | ${readStatus} |\n`;
            }
    
            return {
              content: [
                {
                  type: 'text',
                  text: result,
                },
              ],
            };
          } catch (error) {
            return {
              content: [
                {
                  type: 'text',
                  text: `Error listing emails: ${error instanceof Error ? error.message : String(error)}`,
                },
              ],
            };
          }
        }
      );
    }
  • The handler logic for listing messages, which fetches and paginates emails via IMAP.
    export async function listMessages(
      folder: string,
      limit: number,
      offset: number
    ): Promise<MessageEnvelope[]> {
      const client = await getImapClient();
      try {
        const lock = await client.getMailboxLock(folder);
        try {
          // Get total message count
          const mailbox = await client.mailboxOpen(folder);
          const totalMessages = mailbox.exists || 0;
    
          // Calculate range for pagination
          const start = Math.max(1, totalMessages - offset - limit + 1);
          const end = Math.max(1, totalMessages - offset);
    
          if (start > end) {
            return [];
          }
    
          const messages: MessageEnvelope[] = [];
          const fetchQuery = await client.fetch(`${start}:${end}`, {
            envelope: true,
            uid: true,
            flags: true,
          });
    
          for await (const msg of fetchQuery) {
            if (msg.envelope) {
              const from = msg.envelope.from?.[0];
              const to = msg.envelope.to;
    
              messages.push({
                uid: msg.uid as number,
                from: {
                  name: from?.name || undefined,
                  email: from?.address || '',
                },
                to: to?.map(t => ({
                  name: t.name || undefined,
                  email: t.address || '',
                })),
                subject: msg.envelope.subject || '(no subject)',
                date: msg.envelope.date || new Date(),
                flags: Array.from(msg.flags || []).map(f => String(f)),
                seen: msg.flags.has('\\Seen'),
              });
            }
          }
    
          // Reverse to show newest first
          return messages.reverse();
        } finally {
          lock.release();
        }
      } finally {
        await client.logout();
      }
    }

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/SpasticPalate/proton-mcp-server'

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