The way you fetch content from external sources in Remix is by exporting a loader
function from your route files. Inside the React component you can then retrieve that data with a special hook called useLoaderData
:
// app/routes/index.jsximport { useLoaderData } from 'remix';export async function loader() => {return { foo: 'bar' };};export default Homepage(props) {const { foo } = useLoaderData();// ...}
Inside the loader
function, we can use any Node.JS GraphQL client (or HTTP client, really) to fetch content from the Content Delivery API of DatoCMS.
We suggest using lightweight libraries like graphql-request
, unfetch
or tiny-json-http
since they're all you need to get the job done.
First, use the Remix wizard to set up a new project. Read more about your options on the Remix docs.
npx create-remix@latest
Then, enter inside the project directory, install the tiny-json-http
package, and start the development server:
cd my-remix-appnpm i --save tiny-json-httpnpm run dev
Let's create a function that will help us fetch the content from DatoCMS' GraphQL Content Delivery API endpoints. Create a new directory lib
, and inside of it create a file called datocms.js
:
// lib/datocms.jsimport tiny from 'tiny-json-http';export async function load({ query, variables, includeDrafts, excludeInvalid }) {let endpoint = 'https://graphql.datocms.com';const headers = {authorization: `Bearer ${process.env.DATOCMS_READONLY_TOKEN}`,};if (process.env.DATOCMS_ENVIRONMENT) {headers['X-Environment'] = process.env.DATOCMS_ENVIRONMENT;}if (includeDrafts) {headers['X-Include-Drafts'] = 'true';}if (excludeInvalid) {headers['X-Exclude-Invalid = 'true';}const { body } = await tiny.post({url: endpoint,headers,data: { query, variables },});if (body.errors) {console.error('Ouch! The query has some errors!', body.errors);throw body.errors;}return body.data;}
We want to store inside environment variables both the API token and the name of the DatoCMS environment we want to fetch content from to hide them from the code, and so that we'll be able to modify them later without touching the code. Read this tutorial to know more on how to set server environment variables in Remix.
To create an API token for a DatoCMS project, go to Settings > API Tokens
section of your DatoCMS backend. Make sure to only give it permissions to access the (read-only) Content Delivery API.
It's time to use our function in a real page! Open up app/routes/index.jsx
— which is the route that renders the homepage — and define the loader
function and a basic page component:
import { useLoaderData } from "remix";import { load } from "~/lib/datocms";const HOMEPAGE_QUERY = `query HomePage($limit: IntType) {posts: allBlogPosts(first: $limit) {title}}`;export async function loader() => {return load({query: HOMEPAGE_QUERY,variables: { limit: 10 }});};export default function Home() {const { posts } = useLoaderData();return <div>{JSON.stringify(posts, null, 2)}</div>;}
The HOMEPAGE_QUERY
is the GraphQL query, and of course it depends on the models available in your specific DatoCMS project. You can learn everything you need regarding how to build GraphQL queries on our Content Delivery API documentation.
For more information on what to do next, we recommend reading the next sections of this integration guide!