Skip to main content
Glama

search_monsters

Search D&D 5e SRD monsters by name, challenge rating, type, size, or alignment to retrieve complete stat blocks for encounter planning and game preparation.

Instructions

Search D&D 5e SRD monsters by name, CR, type, size, or alignment. Returns full stat blocks.

Input Schema

TableJSON Schema
NameRequiredDescriptionDefault
queryNoSearch term for monster name or description
crNoExact challenge rating (e.g. "1/4", "5")
cr_minNoMinimum challenge rating (numeric, e.g. 0.25 for 1/4)
cr_maxNoMaximum challenge rating (numeric)
typeNoMonster type (e.g. "beast", "undead", "dragon")
sizeNoSize category (Tiny, Small, Medium, Large, Huge, Gargantuan)
alignmentNoAlignment (e.g. "chaotic evil", "neutral")
limitNoResults per page (max 50)
offsetNoOffset for pagination

Implementation Reference

  • The tool handler function for `search_monsters` which processes the search request and formats the database results.
    async ({ query, cr, cr_min, cr_max, type, size, alignment, limit, offset }) => {
      const result = searchMonsters(db, {
        query,
        cr,
        cr_min,
        cr_max,
        type,
        size,
        alignment,
        limit,
        offset,
      });
    
      if (result.rows.length === 0) {
        return {
          content: [
            {
              type: 'text' as const,
              text: 'No monsters found matching your criteria. Try a broader search — for example, remove some filters or use a partial name.',
            },
          ],
          isError: true,
        };
      }
    
      const start = (offset ?? 0) + 1;
      const end = (offset ?? 0) + result.rows.length;
      const header = `Found ${result.total} monster${result.total === 1 ? '' : 's'} (showing ${start}-${end})\n`;
    
      const monsters = result.rows.map(formatMonster).join('\n\n---\n\n');
    
      return {
        content: [{ type: 'text' as const, text: header + '\n' + monsters }],
      };
    },
  • The registration function for the `search_monsters` tool, including its input schema and description.
    export function registerSearchMonsters(
      server: McpServer,
      db: Database.Database,
    ): void {
      server.registerTool(
        'search_monsters',
        {
          description:
            'Search D&D 5e SRD monsters by name, CR, type, size, or alignment. Returns full stat blocks.',
          inputSchema: {
            query: z.string().optional().describe('Search term for monster name or description'),
            cr: z.string().optional().describe('Exact challenge rating (e.g. "1/4", "5")'),
            cr_min: z.number().optional().describe('Minimum challenge rating (numeric, e.g. 0.25 for 1/4)'),
            cr_max: z.number().optional().describe('Maximum challenge rating (numeric)'),
            type: z.string().optional().describe('Monster type (e.g. "beast", "undead", "dragon")'),
            size: z.string().optional().describe('Size category (Tiny, Small, Medium, Large, Huge, Gargantuan)'),
            alignment: z.string().optional().describe('Alignment (e.g. "chaotic evil", "neutral")'),
            limit: z.number().min(1).max(50).default(10).describe('Results per page (max 50)'),
            offset: z.number().min(0).default(0).describe('Offset for pagination'),
          },
        },
        async ({ query, cr, cr_min, cr_max, type, size, alignment, limit, offset }) => {
          const result = searchMonsters(db, {
            query,
            cr,
            cr_min,
            cr_max,
            type,
            size,
            alignment,
            limit,
            offset,
          });
    
          if (result.rows.length === 0) {
            return {
              content: [
                {
                  type: 'text' as const,
                  text: 'No monsters found matching your criteria. Try a broader search — for example, remove some filters or use a partial name.',
                },
              ],
              isError: true,
            };
          }
    
          const start = (offset ?? 0) + 1;
          const end = (offset ?? 0) + result.rows.length;
          const header = `Found ${result.total} monster${result.total === 1 ? '' : 's'} (showing ${start}-${end})\n`;
    
          const monsters = result.rows.map(formatMonster).join('\n\n---\n\n');
    
          return {
            content: [{ type: 'text' as const, text: header + '\n' + monsters }],
          };
        },
      );
    }

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/gregario/dnd-oracle'

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