What Causes This Error?
This error occurs when you try to call an Astro component as a function instead of using it in the template markup. Astro components must be rendered using JSX-like syntax, not function calls.
The Problem
---
import Card from '../components/Card.astro';
// ❌ Can't call component as function
const result = Card({ title: 'Hello' });
// ❌ Can't use component in expressions this way
const cards = items.map(item => Card({ title: item.title }));
---
The Fix
Use Component in Template
---
import Card from '../components/Card.astro';
---
<!-- ✅ Use in template markup -->
<Card title="Hello" />
Map Over Items in Template
---
import Card from '../components/Card.astro';
const items = [
{ title: 'First' },
{ title: 'Second' },
{ title: 'Third' },
];
---
<!-- ✅ Map in template -->
{items.map((item) => (
<Card title={item.title} />
))}
Common Scenarios
Dynamic Component Rendering
---
import Card from '../components/Card.astro';
import Banner from '../components/Banner.astro';
const showBanner = true;
---
<!-- ✅ Conditional rendering in template -->
{showBanner && <Banner />}
<Card title="Content" />
Slots and Children
---
import Wrapper from '../components/Wrapper.astro';
---
<!-- ✅ Pass children via slots -->
<Wrapper>
<p>This is the content</p>
</Wrapper>
Props Spreading
---
import Button from '../components/Button.astro';
const buttonProps = {
label: 'Click me',
variant: 'primary',
disabled: false,
};
---
<!-- ✅ Spread props in template -->
<Button {...buttonProps} />
Repeated Components
---
import ListItem from '../components/ListItem.astro';
const todos = [
{ id: 1, text: 'Learn Astro', done: true },
{ id: 2, text: 'Build site', done: false },
];
---
<ul>
{todos.map((todo) => (
<ListItem key={todo.id} text={todo.text} done={todo.done} />
))}
</ul>
Nested Components
---
import Layout from '../layouts/Layout.astro';
import Header from '../components/Header.astro';
import Footer from '../components/Footer.astro';
---
<Layout>
<Header />
<main>
<slot />
</main>
<Footer />
</Layout>
Named Slots
---
import Card from '../components/Card.astro';
---
<Card>
<span slot="header">Card Title</span>
<p>Card content goes here</p>
<span slot="footer">Card footer</span>
</Card>
Dynamic Component Selection
---
import CardA from '../components/CardA.astro';
import CardB from '../components/CardB.astro';
const useAlternate = true;
const CardComponent = useAlternate ? CardB : CardA;
---
<!-- ✅ Can use dynamic component reference -->
<CardComponent title="Dynamic" />
Quick Checklist
- Components must be used in template, not called as functions
- Use
{items.map(...)}for lists in template - Use
{condition && <Component />}for conditionals - Spread props with
{...props}syntax - Pass children via default slot or named slots