RSS Feeds

Purpose and Scope

Astro projects generate RSS feeds through the separate @astrojs/rss package. The package is designed for blogs and other content sites that need a machine-readable subscription feed while still using Astro’s file-based endpoint model. In practice, you create an endpoint such as src/pages/rss.xml.js, import the default rss() helper, and return the response from a GET handler. This keeps feed generation close to the rest of the site, so feeds can be built statically or generated on demand when the project uses an SSR adapter.

Sources: packages/astro-rss/README.md, packages/astro-rss/src/index.ts

The package README positions @astrojs/rss as fast RSS feed generation for content-oriented Astro sites and delegates installation and usage walkthroughs to the official Astro docs. The implementation then turns that reader-facing helper into a concrete web response: the default export accepts typed RSS options, renders an RSS XML string, and returns a Response with the Content-Type header set to application/xml. That means application code should treat the helper as an endpoint response factory rather than a low-level XML builder in normal usage.

Sources: packages/astro-rss/README.md, packages/astro-rss/src/index.ts

Relevant Source Files

  • packages/astro-rss/README.md - Documents the package purpose, reader-facing rss() configuration options, item fields, and examples for required and optional feed metadata.
  • packages/astro-rss/package.json - Defines the published package name, module export, type entry, runtime dependencies, package scripts, and repository directory for @astrojs/rss.
  • packages/astro-rss/src/index.ts - Implements the public rss() default export, getRssString(), RSSOptions, RSSFeedItem, validation, deprecated glob handling, and XML response behavior.
  • packages/astro-rss/src/schema.ts - Defines the Zod schema for individual RSS feed items, including date normalization, optional fields, and nested media/source objects.

Endpoint Workflow

The common workflow starts by installing @astrojs/rss, then adding an XML endpoint under src/pages/. Astro maps that endpoint filename to a URL, so src/pages/rss.xml.js becomes a feed URL such as /rss.xml. The endpoint should export a GET function and return rss({ ... }). The options include required channel-level metadata, the site URL, and an array of items. The official docs recommend passing context.site from the endpoint context so the feed uses the site configured in astro.config.*, and the package README repeats that recommendation for the site option.

Sources: packages/astro-rss/README.md, packages/astro-rss/src/index.ts

import rss from '@astrojs/rss';
 
export function GET(context) {
  return rss({
    title: 'Buzz’s Blog',
    description: 'A humble Astronaut’s guide to the stars',
    site: context.site,
    items: [],
    customData: '<language>en-us</language>',
  });
}

Because rss() returns a Response, the endpoint stays small and declarative. The implementation exposes getRssString() separately for callers that need the XML string instead of a Response, but the default export is the ergonomic path for Astro routes. Internally, options are validated before XML generation. The site value is accepted as either a string URL or a URL object through preprocessing, while items can be an array of validated RSS feed item objects. This validation boundary is important: it catches malformed feed metadata before the endpoint publishes invalid XML.

Sources: packages/astro-rss/src/index.ts, packages/astro-rss/src/schema.ts

Core Primitives

An RSS feed has two layers in this package: channel options and item options. Channel options describe the feed itself: title, description, site, items, and optional XML customization fields. Item options describe each entry in the feed: title, link, pubDate, description, content, categories, author, commentsUrl, source, enclosure, and customData. The README makes title, description, site, and items required at the feed level, while the schema makes many item fields optional so different feed styles can be represented.

Sources: packages/astro-rss/README.md, packages/astro-rss/src/index.ts, packages/astro-rss/src/schema.ts

The item schema is intentionally permissive where RSS feeds vary, but strict where incorrect data would break consumers. pubDate can be supplied as a string, number, or Date, and is transformed into a Date only if it represents a valid time. source must contain both a URL and title, which supports proper attribution when republishing from another feed. enclosure requires a media URL, MIME type, and a nonnegative integer length, matching the needs of podcast or other media-oriented feeds. Categories are represented as an array of strings and become multiple feed category entries.

Sources: packages/astro-rss/README.md, packages/astro-rss/src/schema.ts

API Reference

Entry pointPurposeSource contract
default async function getRssResponse(rssOptions: RSSOptions): Promise<Response>Main endpoint helper, normally imported as rss from @astrojs/rss.Validates options, generates XML, and returns an application/xml response.
getRssString(rssOptions: RSSOptions): Promise<string>Lower-level helper for callers that need the XML string.Validates the same options and returns generated RSS XML.
rssSchemaExported schema for RSS feed items.Defined in schema.ts and re-exported from index.ts.
RSSOptionsType for feed-level configuration.Includes required title, description, site, and items; optional xmlns, stylesheet, customData, and trailingSlash.
RSSFeedItemType for item-level feed entries.Mirrors fields validated by rssSchema, including source and enclosure.

The published package metadata confirms that consumers import from the root package name. packages/astro-rss/package.json names the package @astrojs/rss, marks it as an ES module package, points TypeScript declarations at ./dist/index.d.ts, and exports . as ./dist/index.js. It also lists fast-xml-parser, zod, and piccolore as runtime dependencies. Those dependencies line up with the source: Zod validates options and item schema, fast-xml-parser supplies XML parsing/building primitives, and piccolore colors the deprecation warning printed for direct glob result input.

Sources: packages/astro-rss/package.json, packages/astro-rss/src/index.ts

Implementation Details

The implementation accepts two shapes for items: a normal array of feed items, or a glob result object whose values are async loader functions. Directly passing a glob result still works through a transform, but the package emits a warning that this pattern is deprecated and points users toward the pagesGlobToRssItems() helper in the RSS recipe. That detail matters during migrations from older examples: a feed may keep building, but new code should normalize glob output before passing it to rss() so endpoint code remains explicit and future-compatible.

Sources: packages/astro-rss/src/index.ts

Customization is handled at both feed and item levels. Feed-level customData can inject additional XML near the top of the file, and xmlns allows arbitrary namespace metadata on the opening XML element. The stylesheet option can be a string or boolean, which lets feed authors opt into or point at an XSL stylesheet. Item-level customData supports XML-valid additions per entry. These extension points are powerful, but they should be used carefully because the package validates known fields while custom XML remains the author’s responsibility.

Sources: packages/astro-rss/README.md, packages/astro-rss/src/index.ts, packages/astro-rss/src/schema.ts

Testing and Maintenance Signals

The package is maintained as its own workspace package inside the Astro monorepo. Its package scripts build TypeScript source with astro-scripts, run TypeScript project builds, start a development watcher for source files, and execute tests that match test/**/*.test.ts. The root monorepo test flow includes @astrojs/* packages in integration test filters, so changes to @astrojs/rss participate in the broader package quality workflow. For a documentation reader, the key signal is that feed behavior is packaged, typed, validated, and published independently from the core astro package.

Sources: packages/astro-rss/package.json

Next Steps

To add a feed, install @astrojs/rss, create an XML endpoint under src/pages/, and pass site metadata plus items from your pages, content collections, or other data source. Prefer explicit item arrays and use the documented conversion helpers when starting from glob imports. If your feed needs full article HTML, include content and keep description as a short summary. If your project is server-rendered, the same endpoint pattern can generate feeds on demand. For adjacent topics, read the pages on content collections, Markdown and MDX content, endpoints, and deployment behavior.