データフェッチ
.astro
ファイルはビルド時にリモートのデータを取得し、ページの生成に使います。
Astroでのfetch()
すべてのAstroコンポーネントは、そのコンポーネントスクリプトでグローバルなfetch()
functionにアクセスし、APIにHTTPリクエストを行えます。このfetchはビルド時に実行され、そのデータは動的なHTMLを生成するためコンポーネントテンプレートで利用可能になります。
💡 Astroコンポーネントスクリプトの内部で、top-level awaitを利用できます。
💡 取得したデータはAstroとフレームワークの両方のコンポーネントにpropsとして渡されます。
---import Contact from '../components/Contact.jsx';import Location from '../components/Location.astro';
const response = await fetch('https://randomuser.me/api/');const data = await response.json();const randomUser = data.results[0]---<!-- ビルド時に取得したデータでHTMLがレンダリングされます。 --><h1>ユーザー</h1><h2>{randomUser.name.first} {randomUser.name.last}</h2>
<!-- ビルド時に取得したデータがpropsとしてコンポーネントに渡されます。 --><Contact client:load email={randomUser.email} /><Location city={randomUser.location.city} />
GraphQLクエリ
Astroはまた、fetch()
を使用して任意の有効なGraphQLクエリでGraphQLサーバーにクエリを投げられます。
---const response = await fetch("https://graphql-weather-api.herokuapp.com", { method:'POST', headers: {'Content-Type':'application/json'}, body: JSON.stringify({ query: ` query getWeather($name:String!) { getCityByName(name: $name){ name country weather { summary { description } } } } `, variables: { name: "Tokyo", }, }), })
const json = await response.json();const weather = json.data---<h1>天気をビルド時にフェッチします。</h1><h2>{weather.getCityByName.name}, {weather.getCityByName.country}</h2><p>天気: {weather.getCityByName.weather.summary.description}</p>
Astroコンポーネントのすべてのデータは、コンポーネントがレンダリングされるときにフェッチされることを忘れないでください。
デプロイされたAstroサイトは、ビルド時に一度だけデータをfetchします。開発環境では、コンポーネントの更新時にfetchされたデータが表示されます。クライアントサイドで何度もデータを再取得する必要がある場合は、AstroコンポーネントでUIフレームワークまたはクライアントサイドスクリプトを使用します。
UIフレームワークでのfetch()
fetch()
関数は、任意のUI フレームワークからもグローバルに利用できます。
import type { FunctionalComponent } from 'preact';import { h } from 'preact';
const data = await fetch('https://example.com/movies.json').then((response) => response.json());
// ビルド時にレンダリングされるコンポーネントはCLIにもログとして出力されます。// client:*ディレクティブでレンダリングされた場合、ブラウザコンソールにもログが出力されます。console.log(data);
const Movies: FunctionalComponent = () => { // 結果をページに出力する return <div>{JSON.stringify(data)}</div>;};
export default Movies;