Skip to content

Instantly share code, notes, and snippets.

Show Gist options
  • Star 0 You must be signed in to star a gist
  • Fork 0 You must be signed in to fork a gist
  • Save ryanflorence/7c8f63e445c5bfb25e4c790ed5b69ad4 to your computer and use it in GitHub Desktop.
Save ryanflorence/7c8f63e445c5bfb25e4c790ed5b69ad4 to your computer and use it in GitHub Desktop.
// src/entry-browser.js
import React from "react";
import { unstable_createRoot as createRoot } from "react-dom";
import Remix from "@remix-run/react/browser";
import App from "./components/App";
// create a custom cache by defining just write/read
const cache = {
// write gets called for each route that matched, so for the "copy"
// operations we just won't call write at all
write({ cache, data, routeModule, location, params, routeId }) {
// create conventions on route modules so they can localize functionality
return routeModule.writeData(cache, data);
},
read({ cache, params, routeModule, location, routeId }) {
return routeModule.readData(cache, params);
},
};
createRoot(document, { hydrate: true }).render(
// pass it in to remix, only need this in the browser because we can use
// the cache.write when we hydrate from the client handoff
<Remix cache={cache}>
<App />
</Remix>
);
///////////////////////////////////
// src/routes/Article.js
import React from "react";
import { normalize, denormalize } from "normalizr";
import { useRouteData } from "@remix-run/react";
import { article } from "../schema";
// app developer normalizes it and assigns to the cache,
// ignoring location.key because they want normalized data for this page.
// any routes that get articles will update the cache for all others,
// so even on back clicks with no refetch the data is fresh (and mutations).
// every write merges into the cache, so the cache is always the combined
// "entities" of every normalize call from every route
export function writeData(cache, data) {
let normalized = normalize(data, article);
Object.assign(cache, normalized.entities);
}
// get it all back denormalized
export function readData(cache, params) {
return denormalize(params.articleId, article, cache);
}
export default function Article() {
// this will get denormalized data that's shared across all locations
let data = useRouteData();
return <ArticlePage data={data} />;
}
// Data from the loader looks like this:
// {
// "id": "123",
// "author": {
// "id": "1",
// "name": "Paul"
// },
// "title": "My awesome blog post",
// "comments": [
// {
// "id": "324",
// "commenter": {
// "id": "2",
// "name": "Nicole"
// }
// }
// ]
// }
// normalizer normalizes it to this and they store `entities` as the cache
// {
// result: "123",
// entities: {
// "articles": {
// "123": {
// id: "123",
// author: "1",
// title: "My awesome blog post",
// comments: [ "324" ]
// }
// },
// "users": {
// "1": { "id": "1", "name": "Paul" },
// "2": { "id": "2", "name": "Nicole" }
// },
// "comments": {
// "324": { id: "324", "commenter": "2" }
// }
// }
// }
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment