ブログのプレビューのためのHashNodeのAPIの使用


私は最近、HashNodeに私のブログをホストすることに決めました.私はまだプレビューと私のポートフォリオのウェブサイト上で私の最新の記事へのリンクを表示したい.幸運にも、HashNodeは私の最新のポストを得ることができるGrapql APIを提供します.

API


あなたは、APIの遊び場にアクセスすることができますapi.hashnode.com . これは、あなたのクエリを開発し、必要な正確な応答を与えることができます.ドキュメントを読んだ後、私は私のポートフォリオページにプレビューを表示するために必要なすべてを私に与えるためのクエリを構築しました.
{
  user(username: "CodeByCorey") {
    publication {
      posts(page: 0) {
        slug
        title
        brief
        coverImage
        replyCount
        totalReactions
      }
    }
  }
}
  • user(username: "CodeByCorey") : ユーザのクエリ
  • publication : ブログ一覧にもどる
  • posts(page: 0) : 最初のページのすべてのポストを返す
  • slug : だから私はブログ記事へのリンクを作成することができます
  • title : 私のポストのタイトルを表示するには
  • brief : ポストのテキストの小さな断片です
  • coverImage : それで、私はプレビューでカバーイメージを示すことができます
  • replyCount : ポストのコメント数
  • totalReactions : 私のポストの反応の総数
  • クエリの使用


    クエリを持っているので、データを取得するのに時間がかかります.私は次の新しいlibファイルを作成しました.JSアプリposts.ts . 私はフェッチを使用してAPIの呼び出しを行い、リクエストの本文に問い合わせを渡しました.
    const query: string = `
      {
        user(username: "CodeByCorey") {
          publication {
            posts(page: 0) {
              slug
              title
              brief
              coverImage
              replyCount
              totalReactions
            }
          }
        }
      }
    `;
    export const fetchPosts = async () => {
      const resp: Response = await fetch('https://api.hashnode.com', {
        method: 'POST',
        headers: {
          'Content-type': 'application/json',
        },
        body: JSON.stringify({ query }),
      })
      const hashnodeResponse = await resp.json();
      return hashnodeResponse.data.user.publication.posts;
    };
    
    私は、最後の3つのポストだけを示したかったです.私は応答を制限するためにポストをスライスするもう一つの機能を加えました.この
    export const fetchThreeMostRecentPost = async() => {
      const posts = await fetchPosts();
      return posts.slice(0, 3);
    }
    
    私のコンテナコンポーネントの中で、私は次を使いました.jsgetStaticProps 関数は、ポストを取得し、コンポーネントの小道具に渡します.私は、HashNodeの上に新しいポストを作成するとき、私のHTMLを自動的に再生するために再検証セットを加えました.
    export async function getStaticProps() {
    
      const posts = await fetchThreeMostRecentPosts();
      return {
        props: {
          posts
        },
        revalidate: 60
      };
    }
    
    すべてのデータが取得され、小道具に渡された今、私のコンポーネントのスタイルを今すぐ.私は私のポートフォリオのウェブサイトのためのTrewind CSSを使用している.ここではRecentBlogPosts コンポーネント
    export default function RecentBlogPosts({ posts }: Props) {
      return (
        <div className="container mx-auto py-12 text-gray-800">
          <h2 className="text-center text-2xl md:text-4xl pb-6">Recent Blog Posts</h2>
          <div className="flex flex-wrap justify-center">
            {posts.map((post, index) => (
              <a key={index} href={`https://blog.coreyodonnell.tech/${post.slug}`} className="md:w-2/3 lg:w-1/3 px-5 my-2">
                <BlogPreview post={post} />
              </a>
            ))}
          </div>
          <div className="flex flex-wrap justify-center">
            <a
              className="text-green-500 font-semibold hover:text-gray-800 py-4 px-4 rounded"
              href="https://blog.coreyodonnell.tech/"
            >
              View all posts
            </a>
          </div>
        </div>
      );
    }
    
    ブログプレビュー
    export default function BlogPreview({ post }: Props) {
      return (
        <div className="h-full border-2 border-gray-200 rounded-lg flex flex-col justify-between">
          <div className="w-full">
            <img className="lg:h-48 md:h-36 w-full object-cover object-center" src={post.coverImage} alt="blog" />
            <div className="p-6">
              <h1 className="title-font text-lg font-medium text-gray-900 mb-3">{post.title}</h1>
              <p className="leading-relaxed mb-3 text-gray-600">{post.brief}</p>
            </div>
          </div>
          <div className="flex items-center flex-wrap p-6">
            <span className="text-indigo-500 inline-flex items-center md:mb-2 lg:mb-0">
              Learn More
              <svg
                className="w-4 h-4 ml-2"
                viewBox="0 0 24 24"
                stroke="currentColor"
                strokeWidth="2"
                fill="none"
                strokeLinecap="round"
                strokeLinejoin="round"
              >
                <path d="M5 12h14"></path>
                <path d="M12 5l7 7-7 7"></path>
              </svg>
            </span>
            <span className="text-gray-600 mr-3 inline-flex items-center lg:ml-auto md:ml-0 ml-auto leading-none text-sm pr-3 py-1 border-r-2 border-gray-300">
              <svg className="w-4 h-4 mr-1" xmlns="http://www.w3.org/2000/svg" fill="none" viewBox="0 0 24 24" stroke="currentColor">
                <path
                  strokeLinecap="round"
                  strokeLinejoin="round"
                  strokeWidth={2}
                  d="M4.318 6.318a4.5 4.5 0 000 6.364L12 20.364l7.682-7.682a4.5 4.5 0 00-6.364-6.364L12 7.636l-1.318-1.318a4.5 4.5 0 00-6.364 0z"
                />
              </svg>
              {post.totalReactions}
            </span>
            <span className="text-gray-600 inline-flex items-center leading-none text-sm">
              <svg className="w-4 h-4 mr-1" xmlns="http://www.w3.org/2000/svg" fill="none" viewBox="0 0 24 24" stroke="currentColor">
                <path
                  strokeLinecap="round"
                  strokeLinejoin="round"
                  strokeWidth={2}
                  d="M8 10h.01M12 10h.01M16 10h.01M9 16H5a2 2 0 01-2-2V6a2 2 0 012-2h14a2 2 0 012 2v8a2 2 0 01-2 2h-5l-5 5v-5z"
                />
              </svg>
              {post.replyCount}
            </span>
          </div>
        </div>
      );
    }
    
    
    コンポーネントのスタイリング後の結果
  • hashnode APIapi.hashnode.com
  • 次.JSドキュメントhttps://nextjs.org/
  • あなたは私のチェックアウトすることができますportfolio page - Source Code (進行中)
  • 私についての技術についてのランダムな記事については、自宅からの作業.