Search code examples
javascripttypescriptgatsbycontentful

Gatsby: How to solve tslint expects component to receive props when it comes from a query into the component itself


I use Gatsby with Typescript to create a blog based on Contentful CMS.

I have FeaturedPost component which I want to put in the main page and this is the code:

FeaturedPost.tsx

interface IProps {
  data: {
    contentfulPost: ContentfulPost;
  };
}

const FeaturedPost: React.FunctionComponent<IProps> = ({ data }) => {
  const { title, description } = data.contentfulPost;
  return (
    <>
      <Header>{title}</Header>;
      <div>{description}</div>
    </>
  );
};

export const query = graphql`
  query featuredPost($slug: String) {
    contentfulPost(slug: { eq: $slug }) {
      title
      slug
      description {
        childMarkdownRemark {
          html
        }
      }
    }
  }
`;

export default FeaturedPost;

This is my index page code:

index.tsx

const IndexPage: React.FunctionComponent<P> = () => {
  return (
    <Layout>
      <SEO
        title="Home"
        keywords={[`gatsby`, `application`, `react`]}
        description="Index for something I can't remember?!"
      />
      <FeaturedPost />
      <h1>Hi people</h1>
      <p>Welcome to your new Gatsby site.</p>
      <p>Now go build something great.</p>
      <div style={{ maxWidth: `300px`, marginBottom: `1.45rem` }} />
    </Layout>
  );
};

export default IndexPage;

Tslint now expects that I pass a prop called data to FeaturedPost component since I implement interface IProps on FeaturedPost, but actually there is no data to get passed.

FeaturedPost itself receives it as a response from the sent query. Do you have any idea what's wrong with this code or how can I satisfy the linter?


Solution

  • In Gatsby v2, graphql queries in non-page components will be ignored. Use StaticQuery instead. Here's a small example:

    import * as React from 'react'
    import { StaticQuery, graphql, Link } from 'gatsby'
    
    type TOCDataType = {
      readonly allSitePage: {
        edges: [
          {
            node: {
              id: string
              path: string
            }
          }
        ]
      }
    }
    
    const TableOfContents: React.FunctionComponent<{}> = () => (
      <StaticQuery
        query={graphql`
          query SitePageQuery {
            allSitePage {
              edges {
                node {
                  id
                  path
                }
              }
            }
          }
        `}
        render={(data: TOCDataType) => (
          <div>
            {data.allSitePage.edges.map(({ node }) => (
              <li key={node.id}>
                <Link to={node.path}>{node.path}</Link>
              </li>
            ))}
          </div>
        )}
      />
    )
    
    export default TableOfContents