#How to reuse child component's type interface for props in parent components?

2 messages · Page 1 of 1 (latest)

bleak orchid
#

Hi, I just started tinkering with Astro and Typescript(and frontend in general...) and have a question stated in the title.

Code:

Head element with title(required) and description(not):

---
export interface HeadProps { (#1)
  title: string;
  description?: string;
}

const { title, description = "Default Page Description" } = Astro.props as HeadProps;
---

<head>
  ...
  <title>{title}</title>
  <meta name="description" content={description} />
</head>

Base layout that uses head element:

---
import type { HeadProps } from "@components/BaseHead.astro";
import BaseHead from "@components/BaseHead.astro";

export interface Props extends HeadProps {}; (#2)
const props = Astro.props as Props; (#3)
---

<html lang="en">
  <BaseHead {...props} />
  <slot>
    <p>Default Layout</p>
  </slot>
</html>

Index page that uses BaseLayout and passes title down:

---
import BaseLayout from "@layouts/BaseLayout.astro";
---

<BaseLayout title="Index Page">Index Page</BaseLayout> (#4)

(1/2)

#

(2/2)

  1. Is this code "acceptable" by typescript standards?
  2. Do I understand correctly that at this point there's two ways to give types to props: const props: Props = Astro.props and const props = Astro.props as Props, as well as implicit const props = Astro.props with defined interface/type?
    2.1) For some reason if I use custom name(like HeadProps at #1) instead of Props and try the first method(like : HeadProps) the error appears:
    Property 'title' is missing in type 'Record<string, any>' but required in type 'HeadProps'.
    While using Props doesn't produce same behavior(?implicit as -> const props: Props = Astro.props as Props?).
  3. Since the props that get passed aren't changing in BaseLayout I want to reuse already existing type interface from BaseHead(#2).
    However: if instead of extending the HeadProps to use it directly instead of Props at #3 - the error that should be present in case of missing title(#4) disappears, which I can't really explain.

My overall goals are: a) reuse interface; b) get an error when required field in props is missing; bonus) understand what's happening + confirm wether or not there's a better way to do this

Hope my explanation makes sense, thanks in advance.