Koa XML Body Parser Middleware

raw JSON →
3.0.0 verified Thu Apr 23 auth: no javascript maintenance

koa-xml-body is a Koa middleware designed to parse XML request bodies, making the parsed data available on `ctx.request.body`. The current stable version is 3.0.0, published approximately 3 years ago, which is compatible with Koa 2.x and 3.x, while Koa 1.x users should opt for `koa-xml-body@1.x`. It internally uses `xml2js` for the actual XML parsing, exposing its configuration options via the `xmlOptions` property. Key differentiators include its explicit focus on XML content types (e.g., `application/xml`, `text/xml`), robust error handling customization through an `onerror` callback, and seamless integration with other body parsers by carefully managing `ctx.request.body`. Its release cadence is generally tied to bug fixes or Koa compatibility updates rather than rapid feature additions, suggesting a maintenance-oriented status.

error HTTP Status 413: Payload Too Large
cause The incoming XML request body size exceeds the configured `limit` option in `koa-xml-body` (defaulting to 1MB).
fix
Increase the limit option when initializing the middleware: app.use(xmlParser({ limit: '5mb' })) to accommodate larger XML payloads.
error Error: Non-whitespace before first tag.
cause The request body is not valid XML or contains characters before the XML declaration/root element. This error originates from the underlying `xml2js` parser.
fix
Ensure the client sends well-formed XML without any leading non-whitespace characters. If the issue persists, review the content-type header to confirm it is application/xml or text/xml.
error TypeError: Cannot read properties of undefined (reading 'body')
cause This error typically occurs if `ctx.request.body` is accessed, but `koa-xml-body` either didn't parse a body (e.g., wrong `Content-Type`), or another middleware overwrote it, or parsing failed without a custom `onerror`.
fix
Verify that the request's Content-Type header is set to application/xml or text/xml. Check for preceding body parsing middleware that might have already consumed or processed the request stream. Add a console.log(ctx.request.body) to debug when it becomes undefined.
breaking Version 3.x of `koa-xml-body` is designed for Koa 2.x and newer. Users on Koa 1.x must use `koa-xml-body@1.x` to maintain compatibility and avoid runtime errors.
fix Upgrade Koa to version 2.x or 3.x, or explicitly install `koa-xml-body@1.x` if tied to Koa 1.x.
gotcha By default, `koa-xml-body` will throw an error if XML parsing fails and no `onerror` option is provided. This can lead to unhandled exceptions and server crashes in production environments.
fix Always provide a custom `onerror` function in the middleware options to gracefully handle parsing errors, e.g., `onerror: (err, ctx) => { ctx.status = 400; ctx.body = 'Bad Request: Invalid XML'; }`.
gotcha The default `limit` for the XML body size is 1MB. Requests exceeding this limit will result in a `413 Payload Too Large` error, which might be insufficient for applications handling large XML documents.
fix Configure the `limit` option in the middleware to a higher value if needed, e.g., `app.use(xmlParser({ limit: '5mb' }))`. Ensure your server resources can handle the increased payload size.
gotcha When integrating `koa-xml-body` with other generic body parsers (like `koa-bodyparser` or `koa-body`), the order of middleware matters. `koa-xml-body` should generally be placed before other body parsers if you specifically want it to handle XML, but it is designed to integrate well, carefully checking `ctx.request.body`.
fix Place `koa-xml-body` before other generic body parsers if it's meant to be the primary handler for XML. The library is designed to co-exist, so ensure the content-type allows `koa-xml-body` to process first.
npm install koa-xml-body
yarn add koa-xml-body
pnpm add koa-xml-body

This quickstart demonstrates setting up a Koa server with `koa-xml-body` to parse incoming XML requests. It includes custom options for body size limit, XML parsing behavior (e.g., `explicitArray`, `ignoreAttrs`), a custom request key, and an error handler for invalid XML, making it robust for production use.

import Koa from 'koa';
import koaXmlBody from 'koa-xml-body';

const app = new Koa();

// Apply the XML body parser middleware with custom options
app.use(koaXmlBody({
  limit: '2mb', // Set a higher limit if expecting larger XML payloads
  encoding: 'utf8', // Ensure correct encoding is used
  xmlOptions: {
    explicitArray: false, // Prevents single child elements from being wrapped in arrays
    ignoreAttrs: true, // Ignores XML attributes and only parses element values
  },
  key: 'parsedXml', // Store parsed XML in ctx.request.parsedXml instead of ctx.request.body
  onerror: (err, ctx) => {
    console.error('XML parsing error:', err.message);
    ctx.status = 400;
    ctx.body = 'Invalid XML format.';
  },
}));

app.use(async (ctx) => {
  if (ctx.method === 'POST' && ctx.is('application/xml')) {
    // Access the parsed XML body based on the 'key' option
    const xmlData = ctx.request.parsedXml;
    if (xmlData) {
      console.log('Received XML:', JSON.stringify(xmlData, null, 2));
      ctx.body = { status: 'success', received: xmlData };
    } else {
      ctx.status = 400;
      ctx.body = { status: 'error', message: 'No XML body received or parsed.' };
    }
  } else {
    ctx.body = 'Send an XML POST request to this endpoint.';
  }
});

const port = 3000;
app.listen(port, () => {
  console.log(`Koa server listening on http://localhost:${port}`);
});

// Example usage with curl:
// curl -X POST -H "Content-Type: application/xml" -d '<root><item id="1">Value1</item><item id="2">Value2</item></root>' http://localhost:3000