概要
Next.js/TypeScriptのプロジェクトから、GitHubのGraphQL APIにアクセスする方法を簡単にメモします。Next.jsのapiルートからGraphQL Yogaとgraphql-requestを用い方法になります。
詳細は以下を参照。
GraphQLのエクスプローラ
https://docs.github.com/ja/graphql/overview/explorer にて、GitHubアカウントでサインインした上で、次のクエリを入力します。
query {
viewer {
login
}
}
これで次の結果が得られます。
{
"data": {
"viewer": {
"login": "pitang1965"
}
}
}
今回は次のクエリを用います。
query MyQuery {
viewer {
name
repositories(last: 5) {
nodes {
name
description
}
}
}
}
このクエリを実行すると先ほどの結果に加えて、5つのリポジトリの名前と説明が出力されます。
インストール
npm i @graphql-yoga/node graphql graphql-request
又は
yarn add @graphql-yoga/node graphql graphql-request
又は
pnpm i @graphql-yoga/node graphql graphql-request
環境変数の設定
GitHub APIのトークンは、GitHubのサイトのSettings → Developer settings → Personal access tokensから取得できます。
// .env.local
GITHUB_BEARER_TOKEN=xxxx
src/pages/api/github.ts
Next.jsのapiルートからgraphql-requestを用いてGitHub GraphQL APIにアクセスし、その結果をGraphQLサーバーであるGraphQL Yogaを使って/api/github として提供します。
import { GraphQLClient, gql } from 'graphql-request';
import { createServer } from '@graphql-yoga/node';
// GitHubからデータを取得
const resolvers = {
Query: {
async repositories() {
const githubEndPoint = 'https://api.github.com/graphql';
const query = gql`
{
viewer {
name
repositories(last: 5) {
nodes {
name
description
}
}
}
}
`;
const graphQLClient = new GraphQLClient(githubEndPoint, {
headers: {
authorization: `Bearer ${process.env.GITHUB_BEARER_TOKEN}`,
},
});
const data = await graphQLClient.request(query);
// console.log(JSON.stringify(data.viewer.repositories.nodes, undefined, 2));
return data.viewer.repositories.nodes;
},
},
};
// APIとして値を返す
const typeDefs = /* GraphQL */ `
type Query {
repositories: [Repository!]!
}
type Repository {
name: String
description: String
}
`;
const server = createServer({
schema: {
typeDefs,
resolvers,
},
endpoint: '/api/github',
// graphiql: false // uncomment to disable GraphiQL
});
export default server;
クライアント側のコード
以下はuseSWRを用いて、/api/githubにアクセスし、5つのリポジトリの名前と説明を表示するコードです。
import useSWR from 'swr';
const fetcher = (query: string) =>
fetch('/api/github', {
method: 'POST',
headers: {
'Content-type': 'application/json',
},
body: JSON.stringify({ query }),
})
.then((res) => res.json())
.then((json) => json.data);
export default function Index() {
const { data, error } = useSWR(
`{
repositories {
name
description
}
}
`,
fetcher
);
console.log(data);
if (error) return <div>Failed to load</div>;
if (!data) return <div>Loading...</div>;
const { repositories } = data;
return (
<div>
{repositories.map((repository: any, i: number) => (
<div key={i}>
<h1>{repository.name}</h1>
<p>{repository.description}</p>
</div>
))}
</div>
);
}
出力イメージは次です。
pitang-todo
Vite + React + TypeScipt + Supabase による簡単なtodoアプリ
gudid-search
openFDAを用いて企業名からUDI(機器固有識別子)の一覧を得て表で表示。
git_trainingnext-portfolio
各種APIを用いた自己紹介サイト
qin-team-dev
qinサロンチーム開発