Creating Pages in Gatsby
There is more than one way of creating pages in Gatsby. One way is to make React components inside of src/pages
folder. Another way is doing it programmatically using createPages
API provided by the framework.
Creating Pages From React Components
It is very easy to make a new page. Create a React Component inside of src/pages
.
// src/pages/contact.js
import React from 'react';
const Contact = () => {
return <h1>Contact Page</h1>;
};
export default Contact;
Gatsby automatically makes a route for a page using the name of its file. You can access the src/pages/contact.js
component in /contact
route.
Adding pages to a folder creates nested routes. For example, you can reach a page made in src/pages/products/shirts.js
via /products/shirts
route.
You can create an index.js
file inside of the folder to create a page for the root route. Making a component in src/pages/products/index.js
creates a page for the /products
route.
Creating Pages Programmatically
Making pages by hand sometimes is impossible. You might not know what pages you will need. For example, you can get data for your pages at build time from an API. This data can change and you need to create or remove pages accordingly.
You can dynamically create pages using createPages
API inside of gatsby-node.js
file.
-
Open or create the
gatsby-node.js
file in the root directory of your project -
Create a function for your implementation of
createPages
// gatsby-node.js exports.createPages = ({ actions }) => { const { createPage } = actions; }
Gatsby provides an object containing helper functions as the first argument of
createPages
. You can destructure this object to access theactions
object. You then extractcreatePage
function from it, which you use to create new pages. -
Use the
createPage
function with your data to create as many pages as you needconst path = require(`path`); exports.createPages = ({ actions }) => { const { createPage } = actions; const productTemplate = path.resolve(`src/templates/product.js`); const products = [ { name: 'shirt', price: 20, quantity: 3, }, { name: 'pants', price: 40, quantity: 7, }, ]; products.forEach(product => { createPage({ path: `product/${product.name}`, component: productTemplate, context: { ...product, }, }); }); }
As an example I have hard-coded an array of products (line 7). In your project the data can come from many different sources.
The
createPage
function requires apath
you use as the route to access this page in the browser. It also requires acomponent
, which is a path to a React component you want to use for this page.You can pass data to the component’s props via the
context
property. You can use the spread syntax on theproduct
object to pass its properties one by one tocontext
. -
Create a template for the pages
// src/templates/product.js import React from 'react'; const Product = ({ pageContext: { name, price, quantity } }) => { return ( <> <h1>Page for {name}</h1> <p>Price: {price}</p> <p>Available quantity: {quantity}</p> </> ); }; export default Product;
You can access the data you provided to
context
in the previous step viaprops.pageContext
. The product properties get extracted frompageContext
into individual variables using object destructuring.