TypeScript
AstroにはTypeScriptのサポートが組み込まれています。Astroプロジェクト内で.tsや.tsxファイルをインポートしたり、Astroコンポーネントの中に直接TypeScriptコードを書いたり、お好みでAstroの設定にastro.config.tsファイルを使ったりできます。
TypeScriptを使うと、コード内のオブジェクトやコンポーネントの形を定義することで、実行時のエラーを未然に防げます。たとえば、TypeScriptでコンポーネントのpropsに型をつけると、そのコンポーネントが受け付けないpropを設定した際にエディタ上でエラーが表示されます。
TypeScriptの恩恵を受けるために、Astroプロジェクトで必ずしもTypeScriptコードを書く必要はありません。Astroは常にコンポーネントのコードをTypeScriptとして扱い、AstroのVS Code拡張機能が可能な限り型を推論して、エディタ上で自動補完やヒント、エラー表示を提供します。
Astroの開発サーバーは型チェックをおこないませんが、コマンドラインから型エラーをチェックするための別のスクリプトを利用できます。
セットアップ
Section titled “セットアップ”Astroのスタータープロジェクトには、tsconfig.jsonファイルが含まれています。TypeScriptコードを書かない場合でも、AstroやVS Codeといったツールがプロジェクトを正しく理解するために、このファイルは重要です。一部の機能(npmパッケージのインポートなど)は、tsconfig.jsonファイルがないとエディタで完全にはサポートされません。Astroを手動でインストールする場合は、このファイルを必ず自分で作成してください。
TSConfigのテンプレート
Section titled “TSConfigのテンプレート”Astroには、拡張可能な3つのtsconfig.jsonテンプレート、base、strict、strictestが含まれています。baseテンプレートはモダンなJavaScript機能のサポートを有効にし、他のテンプレートのベースとしても使われます。プロジェクトでTypeScriptを書く予定がある場合は、strictまたはstrictestの使用をおすすめします。3つのテンプレートの設定は、astro/tsconfigs/で確認・比較できます。
いずれかのテンプレートを継承するには、extends設定を使います。
{ "extends": "astro/tsconfigs/base"}さらに、Astroの型の恩恵を受けつつ、ビルド済みファイルのチェックを避けるために、includeとexcludeを次のように設定することをおすすめします。
{ "extends": "astro/tsconfigs/base", "include": [".astro/types.d.ts", "**/*"], "exclude": ["dist"]}TypeScriptエディタプラグイン
Section titled “TypeScriptエディタプラグイン”公式のAstro VS Code拡張機能を使っていない場合は、Astro TypeScriptプラグインを個別にインストールできます。このプラグインはVS Code拡張機能によって自動的にインストール・設定されるため、両方をインストールする必要はありません。
このプラグインはエディタ内でのみ動作します。ターミナルでtscを実行すると、.astroファイルは完全に無視されます。代わりに、astro checkCLIコマンド (EN)を使えば、.astroと.tsの両方のファイルをチェックできます。
このプラグインは、.tsファイルから.astroファイルをインポートすることもサポートしています(再エクスポートに便利です)。
npm install @astrojs/ts-pluginpnpm add @astrojs/ts-pluginyarn add @astrojs/ts-pluginそして、tsconfig.jsonに以下を追加します:
{ "compilerOptions": { "plugins": [ { "name": "@astrojs/ts-plugin" }, ], }}プラグインが動作していることを確認するには、.tsファイルを作成し、そこにAstroコンポーネントをインポートします。エディタから警告メッセージが表示されなければ問題ありません。
UIフレームワーク
Section titled “UIフレームワーク”プロジェクトでUIフレームワークを使っている場合は、フレームワークに応じた追加の設定が必要になることがあります。詳しくは、各フレームワークのTypeScriptドキュメントを参照してください。(Vue、React、Preact、Solid、Svelte)
型のインポート
Section titled “型のインポート”可能な限り、明示的な型のインポートとエクスポートを使ってください。
import { SomeType } from "./script";import type { SomeType } from "./script";こうすることで、Astroのバンドラーが、インポートした型をJavaScriptであるかのように誤ってバンドルしようとするエッジケースを回避できます。
tsconfig.jsonファイルで、TypeScriptに型のインポートを強制するように設定できます。verbatimModuleSyntaxをtrueに設定してください。TypeScriptがインポートをチェックし、import typeを使うべき箇所を教えてくれます。この設定は、Astroのすべてのプリセットでデフォルトで有効になっています。
{ "compilerOptions": { "verbatimModuleSyntax": true }}インポートエイリアス
Section titled “インポートエイリアス”Astroは、tsconfig.jsonのpaths設定で定義するインポートエイリアスをサポートしています。詳しくは、インポートガイド (EN)を参照してください。
---import HelloWorld from "@components/HelloWorld.astro";import Layout from "@layouts/Layout.astro";---{ "compilerOptions": { "paths": { "@components/*": ["./src/components/*"], "@layouts/*": ["./src/layouts/*"] } }}グローバル型の拡張
Section titled “グローバル型の拡張”カスタムの型宣言を追加するための慣習として、またはtsconfig.jsonがない場合にAstroの型の恩恵を受けるために、src/env.d.tsを作成できます。
// カスタムの型宣言declare var myString: string;
// Astroの型。すでに`tsconfig.json`がある場合は不要/// <reference path="../.astro/types.d.ts" />windowとglobalThis
Section titled “windowとglobalThis”グローバルオブジェクトにプロパティを追加したい場合があります。これは、env.d.tsファイルにdeclareキーワードを使ってトップレベルの宣言を追加することでおこなえます。
declare var myString: string;declare function myFunction(): boolean;これにより、window.myStringとwindow.myFunctionだけでなく、globalThis.myStringとglobalThis.myFunctionにも型が提供されます。
windowはクライアントサイドのコードでのみ利用できることに注意してください。globalThisはサーバーサイドとクライアントサイドの両方で利用できますが、サーバーサイドの値はクライアントと共有されません。
windowオブジェクトのプロパティにのみ型をつけたい場合は、代わりにWindowインターフェースを指定します。
interface Window { myFunction(): boolean;}非標準の属性を追加する
Section titled “非標準の属性を追加する”カスタム属性やCSSプロパティの型を定義したい場合があります。.d.tsファイルでastroHTML.JSX名前空間を再宣言することで、デフォルトのJSX定義を拡張し、非標準の属性を追加できます。
declare namespace astroHTML.JSX { interface HTMLAttributes { "data-count"?: number; "data-label"?: string; }
// styleオブジェクトにCSSカスタムプロパティを追加する interface CSSProperties { "--theme-color"?: "black" | "white"; }}astroHTMLは、.astroコンポーネント内にグローバルに注入されます。TypeScriptファイルで使うには、トリプルスラッシュディレクティブを使います。
/// <reference types="astro/astro-jsx" />
type MyAttributes = astroHTML.JSX.ImgHTMLAttributes;インポートを使う
Section titled “インポートを使う”プロジェクト内の他の場所や外部ライブラリで宣言された型を再利用して、グローバル型を拡張したい場合があります。これには、動的インポートを使います。
type Product = { id: string; name: string; price: number;};
declare namespace App { interface Locals { orders: Map<string, Product[]> session: import("./lib/server/session").Session | null; user: import("my-external-library").User; }}.d.tsファイルは、アンビエントモジュールの宣言です。構文はESモジュールに似ていますが、これらのファイルではトップレベルのインポートとエクスポートが許可されていません。TypeScriptがそれらを検出すると、そのファイルはモジュール拡張(module augmentation)とみなされ、グローバル型が壊れてしまいます。
コンポーネントのprops
Section titled “コンポーネントのprops”Astroは、TypeScriptによるコンポーネントのpropsの型付けをサポートしています。有効にするには、コンポーネントのフロントマターにTypeScriptのPropsインターフェースを追加します。export文を使ってもかまいませんが、必須ではありません。AstroのVS Code拡張機能は自動的にPropsインターフェースを探し、そのコンポーネントを別のテンプレート内で使う際に適切なTSサポートを提供します。
---interface Props { name: string; greeting?: string;}
const { greeting = "Hello", name } = Astro.props;---<h2>{greeting}, {name}!</h2>よくあるprop型のパターン
Section titled “よくあるprop型のパターン”- コンポーネントがpropsもスロットコンテンツも受け取らない場合は、
type Props = Record<string, never>を使えます。 - コンポーネントのデフォルトスロットに必ず子要素を渡す必要がある場合は、
type Props = { children: any; };を使ってこれを強制できます。
型ユーティリティ
Section titled “型ユーティリティ”
追加:
astro@1.6.0
Astroには、よくあるprop型のパターン向けに、いくつかの組み込みユーティリティ型が用意されています。これらはastro/typesエントリーポイントから利用できます。
組み込みのHTML属性
Section titled “組み込みのHTML属性”Astroは、マークアップが有効なHTML属性を使っているかをチェックするためのHTMLAttributes型を提供しています。これらの型を使うと、コンポーネントのpropsを構築するのに役立ちます。
たとえば<Link>コンポーネントを作る場合、次のようにすることで、コンポーネントのpropの型に<a>タグのデフォルトのHTML属性を反映できます。
---import type { HTMLAttributes } from "astro/types";
// `type`を使うtype Props = HTMLAttributes<"a">;
// または`interface`で拡張するinterface Props extends HTMLAttributes<"a"> { myProp?: boolean;}
const { href, ...attrs } = Astro.props;---<a href={href} {...attrs}> <slot /></a>ComponentProps型
Section titled “ComponentProps型”
追加:
astro@4.3.0
このエクスポートされた型を使うと、別のコンポーネントが受け取るPropsを、そのコンポーネントがProps型を直接エクスポートしていなくても参照できます。
次の例は、astro/typesのComponentPropsユーティリティを使って、<Button />コンポーネントのProps型を参照する方法を示しています。
---import type { ComponentProps } from "astro/types";import Button from "./Button.astro";
type ButtonProps = ComponentProps<typeof Button>;---ポリモーフィック型
Section titled “ポリモーフィック型”
追加:
astro@2.5.0
Astroには、完全な型安全性を保ちながら、異なるHTML要素としてレンダリングできるコンポーネントを簡単に構築するためのヘルパーが含まれています。これは、渡されたpropsに応じて<a>または<button>のいずれかとしてレンダリングできる<Link>のようなコンポーネントに便利です。
以下の例では、任意のHTML要素としてレンダリングできる、完全に型付けされたポリモーフィックなコンポーネントを実装しています。HTMLTag型を使って、aspropが有効なHTML要素であることを保証しています。
---import type { HTMLTag, Polymorphic } from "astro/types";
type Props<Tag extends HTMLTag> = Polymorphic<{ as: Tag }>;
const { as: Tag, ...props } = Astro.props;---<Tag {...props} />getStaticPaths()の型を推論する
Section titled “getStaticPaths()の型を推論する”
追加:
astro@2.1.0
Astroには、動的ルートのgetStaticPaths() (EN)関数が返す型を扱うためのヘルパーが含まれています。
InferGetStaticParamsTypeでAstro.params (EN)の型を、InferGetStaticPropsTypeでAstro.props (EN)の型を取得できます。また、GetStaticPathsを使えば、両方を一度に推論できます。
---import type { InferGetStaticParamsType, InferGetStaticPropsType, GetStaticPaths,} from "astro";import { getCollection } from "astro:content";
export const getStaticPaths = (async () => { const posts = await getCollection("blog"); return posts.map((post) => { return { params: { id: post.id }, props: { draft: post.data.draft, title: post.data.title }, }; });}) satisfies GetStaticPaths;
type Params = InferGetStaticParamsType<typeof getStaticPaths>;type Props = InferGetStaticPropsType<typeof getStaticPaths>;
const { id } = Astro.params;// ^? { id: string; }
const { title } = Astro.props;// ^? { draft: boolean; title: string; }---エディタで型エラーを確認するには、AstroのVS Code拡張機能がインストールされていることを確認してください。astro startとastro buildコマンドは、esbuildでコードをトランスパイルしますが、型チェックはおこなわないことに注意してください。TypeScriptエラーが含まれている場合にコードのビルドを防ぐには、package.jsonの「build」スクリプトを次のように変更します:
{ "scripts": { "build": "astro build", "build": "astro check && astro build", },}astro checkは、TypeScriptプロジェクトに含まれるすべてのファイルをチェックします。SvelteやVueファイル内の型をチェックするには、それぞれsvelte-checkとvue-tscパッケージを使えます。
.tsファイルのインポート (EN)について、さらに詳しく学べます。
トラブルシューティング
Section titled “トラブルシューティング”複数のJSXフレームワークを同時に型付けする際のエラー
Section titled “複数のJSXフレームワークを同時に型付けする際のエラー”同じプロジェクトで複数のJSXフレームワークを使うと、各フレームワークがtsconfig.json内で異なる、ときには競合する設定を必要とするため、問題が発生することがあります。
解決策: もっともよく使うフレームワークに応じて、jsxImportSource設定をreact(デフォルト)、preact、またはsolid-jsに設定します。そして、その設定と競合する別のフレームワークのファイル内でプラグマコメントを使います。
jsxImportSource: reactというデフォルト設定の場合は、次のように記述します。
// Preactの場合/** @jsxImportSource preact */
// Solidの場合/** @jsxImportSource solid-js */