Skip to main content
Glama
rawr-ai

Filesystem MCP Server

xml_structure

Analyze XML file structure quickly by extracting element counts, attribute usage, namespaces, and hierarchy details without full file processing. Configure depth and byte limits for efficient handling of large files.

Instructions

Analyze XML file structure without reading the entire file. Returns statistical information about element counts, attribute usage, namespaces, and hierarchical structure. Useful for understanding the structure of large XML files before performing detailed queries. Requires maxBytes (default 10KB) and maxDepth (default 2) parameters. The path must be within allowed directories.

Input Schema

TableJSON Schema
NameRequiredDescriptionDefault
includeAttributesNoWhether to include attribute information
maxBytesYesMaximum bytes to read from the file. Must be a positive integer. Handler default: 10KB.
maxDepthYesHow deep to analyze the hierarchy. Must be a positive integer. Handler default: 2.
pathYesPath to the XML file to analyze

Implementation Reference

  • Main handler function for the 'xml_structure' tool. Validates arguments, reads and parses the XML file, extracts structure using extractXmlStructure, handles response size limits, and returns the structure as JSON.
    export async function handleXmlStructure(
      args: unknown,
      allowedDirectories: string[],
      symlinksMap: Map<string, string>,
      noFollowSymlinks: boolean
    ): Promise<{ content: Array<{ type: string; text: string }> }> {
      const parsed = parseArgs(XmlStructureArgsSchema, args, 'xml_structure');
    
      const validPath = await validatePath(
        parsed.path,
        allowedDirectories,
        symlinksMap,
        noFollowSymlinks
      );
    
      try {
        const xmlContent = await fs.readFile(validPath, 'utf8');
    
        try {
          const parser = new XmldomDOMParser();
          const doc: any = parser.parseFromString(xmlContent, 'text/xml');
          const structure = extractXmlStructure(
            doc,
            parsed.maxDepth,
            parsed.includeAttributes
          );
    
          const responseLimit = (parsed as any).maxResponseBytes ?? parsed.maxBytes ?? 200 * 1024; // 200KB default
          let json = JSON.stringify(structure, null, 2);
    
          if (typeof responseLimit === 'number' && responseLimit > 0) {
            const size = Buffer.byteLength(json, 'utf8');
            if (size > responseLimit) {
              // Fallback to a summarized structure to respect response limit
              const summary = {
                rootElement: structure.rootElement,
                namespaces: structure.namespaces,
                elementTypeCount: Object.keys(structure.elements).length,
                attributeKeyCount: structure.attributes ? Object.keys(structure.attributes).length : 0,
                hierarchy: structure.hierarchy ? { name: structure.hierarchy.name, hasChildren: structure.hierarchy.hasChildren, childrenCount: structure.hierarchy.children?.length ?? 0 } : undefined,
                _meta: {
                  truncated: true,
                  note: `Full structure omitted to fit response limit of ${responseLimit} bytes`
                }
              };
              json = JSON.stringify(summary, null, 2);
            }
          }
    
          return {
            content: [{
              type: 'text',
              text: json
            }]
          };
        } catch (err) {
          const errorMessage = err instanceof Error ? err.message : String(err);
          throw new Error(`Failed to extract XML structure: ${errorMessage}`);
        }
      } catch (err) {
        const errorMessage = err instanceof Error ? err.message : String(err);
        throw new Error(`Failed to analyze XML structure: ${errorMessage}`);
      }
    }
  • Core helper function that extracts detailed XML structure: root element, element counts, attribute counts, namespaces, and hierarchy up to maxDepth.
    function extractXmlStructure(doc: any, maxDepth = 2, includeAttributes = true): XmlStructureInfo {
      const structure: XmlStructureInfo = {
        rootElement: doc.documentElement?.nodeName,
        elements: {},
        attributes: includeAttributes ? {} : undefined,
        namespaces: extractNamespaces(doc),
      };
    
      // Get all element names and counts
      const elementQuery = "//*";
      const elements = xpath.select(elementQuery, doc) as any[];
    
      elements.forEach((element) => {
        const el = element as any;
        const name = el.nodeName;
        structure.elements[name] = (structure.elements[name] || 0) + 1;
    
        if (includeAttributes && el.attributes && el.attributes.length > 0) {
          for (let i = 0; i < el.attributes.length; i++) {
            const attr = el.attributes[i];
            const attrKey = `${name}@${attr.nodeName}`;
            if (structure.attributes) {
              structure.attributes[attrKey] = (structure.attributes[attrKey] || 0) + 1;
            }
          }
        }
      });
    
      // Get child relationship structure up to maxDepth
      if (maxDepth > 0 && doc.documentElement) {
        structure.hierarchy = buildHierarchy(doc.documentElement, maxDepth);
      }
    
      return structure;
    }
  • TypeBox schema defining input parameters for the xml_structure tool: path, maxDepth, includeAttributes, size limits.
    export const XmlStructureArgsSchema = Type.Object({
      path: Type.String({ description: 'Path to the XML file to analyze' }),
      maxDepth: Type.Integer({
        minimum: 1,
        description: 'How deep to analyze the hierarchy. Must be a positive integer. Handler default: 2.'
      }),
      includeAttributes: Type.Optional(Type.Boolean({ default: true, description: 'Whether to include attribute information' })),
      maxBytes: Type.Optional(Type.Integer({
        minimum: 1,
        description: '[Deprecated semantics] Previously limited file bytes read; now treated as a response size cap in bytes.'
      })),
      maxResponseBytes: Type.Optional(Type.Integer({
        minimum: 1,
        description: 'Maximum size, in bytes, of the returned content. Parsing reads full file; response may be truncated to respect this limit.'
      }))
    });
    export type XmlStructureArgs = Static<typeof XmlStructureArgsSchema>;
  • index.ts:259-260 (registration)
    Registers the handleXmlStructure function as the executor for the 'xml_structure' tool in the toolHandlers object, which is used in server.addTool.
    xml_structure: (a: unknown) =>
      handleXmlStructure(a, allowedDirectories, symlinksMap, noFollowSymlinks),
  • index.ts:322-322 (registration)
    Includes 'xml_structure' in the allTools list with description, used to conditionally add the tool via server.addTool.
    { name: "xml_structure", description: "Analyze XML structure" },
Behavior3/5

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

With no annotations provided, the description carries the full burden of behavioral disclosure. It adds useful context beyond basic functionality, such as the constraint that 'The path must be within allowed directories' and that it analyzes 'without reading the entire file'. However, it lacks details on error handling, performance implications, or output format specifics, which are important for a tool with no output schema.

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?

The description is efficiently structured with four sentences that each add value: stating the purpose, output, usage context, and key parameters. It is front-loaded with the core functionality and avoids redundancy, making it easy to parse quickly.

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?

Given the tool's complexity (analyzing XML structure with constraints) and lack of annotations or output schema, the description does a good job covering purpose, usage, and key behavioral traits. However, it could be more complete by detailing the output format or error cases, which would help compensate for the missing structured data.

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

Parameters3/5

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

Schema description coverage is 100%, so the schema already documents all parameters thoroughly. The description adds minimal value by mentioning defaults for maxBytes and maxDepth, but does not provide additional semantic context beyond what the schema specifies. This meets the baseline for high schema coverage.

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?

The description clearly states the specific action ('Analyze XML file structure') and resource ('XML file'), distinguishing it from sibling tools like xml_query or xml_to_json_string. It explicitly mentions what it returns ('statistical information about element counts, attribute usage, namespaces, and hierarchical structure'), making the purpose distinct and well-defined.

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?

The description provides clear context for when to use this tool ('Useful for understanding the structure of large XML files before performing detailed queries'), which helps differentiate it from other XML tools. However, it does not explicitly state when not to use it or name specific alternatives among siblings, such as xml_query for detailed queries.

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

Related 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/rawr-ai/mcp-filesystem'

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