Skip to content

Container API: render components in isolation #533

@Princesseuh

Description

@Princesseuh

Body

Summary

Astro components are tightly coupled to astro (the metaframework). This proposal introduces a possible server-side API for rendering .astro files in isolation, outside of the full astro build pipeline.

Background & Motivation

Some of our own proposals, as well as many third-party tool integrations, are blocked until we expose a proper server-side rendering API for .astro components. Other frameworks have tools like preact-render-to-string or react-dom/server that make rendering components on the server straight-forward.

We've avoided doing this because... it's very hard! Part of the appeal of .astro components is that they have immediate access to a number of powerful APIs, context about your site, and a rich set of framework renderers. In the full astro build process, we are able to wire up all this context invisibly. Wiring up the context manually as a third-party is prohibitively complex.

Goals

  • Provide an API for rendering .astro components in isolation
  • Expose a familiar, user-friendly API
  • Surface enough control for full astro parity, but abstract away internal APIs
  • Enable third-party tools to consume .astro files on the server
  • Enable unit testing of .astro component output
  • Possibly unblock .mdx compiledContent/html output?
  • Support Astro framework renderers (@astrojs/*) if possible

Example

import { AstroContainer } from 'astro/container';
import Component from './components/Component.astro';

const astro = new AstroContainer();
console.log(await astro.renderToString(Component, { props, slots }))

The container can be optionally constructed with some settings that are typically reserved for Astro configuration.

const astro = new AstroContainer({
  mode?: 'development' | 'production';
  site?: string;
  renderers?: Renderer[]
});

The second argument to renderToString optionally provides render-specific data that may be exposed through the Astro global, like props, slots, request, and/or params.

await astro.renderToString(Component, { props, slots, request, params })

Metadata

Metadata

Assignees

No one assigned

    Labels

    No labels
    No labels

    Type

    No type

    Projects

    Status

    Stage 3: Accepted Proposals, Has RFC

    Milestone

    No milestone

    Relationships

    None yet

    Development

    No branches or pull requests

    Issue actions