Skip to content

Commit 3cb7b48

Browse files
committed
more data docs
1 parent aff9797 commit 3cb7b48

23 files changed

+796
-38
lines changed

docs/start/data/actions.md

Lines changed: 138 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,138 @@
1+
---
2+
title: Actions
3+
order: 5
4+
---
5+
6+
# Actions
7+
8+
[MODES: data]
9+
10+
## Defining Actions
11+
12+
Data mutations are done through Route actions defined on the `action` property of a route object. When the action completes, all loader data on the page is revalidated to keep your UI in sync with the data without writing any code to do it.
13+
14+
```tsx
15+
import { createBrowserRouter } from "react-router";
16+
import { someApi } from "./api";
17+
18+
let router = createBrowserRouter([
19+
{
20+
path: "/projects/:projectId",
21+
Component: Project,
22+
action: async ({ request }) => {
23+
let formData = await request.formData();
24+
let title = formData.get("title");
25+
let project = await someApi.updateProject({ title });
26+
return project;
27+
},
28+
},
29+
]);
30+
```
31+
32+
## Calling Actions
33+
34+
Actions are called declaratively through `<Form>` and imperatively through `useSubmit` (or `<fetcher.Form>` and `fetcher.submit`) by referencing the route's path and a "post" method.
35+
36+
### Calling actions with a Form
37+
38+
```tsx
39+
import { Form } from "react-router";
40+
41+
function SomeComponent() {
42+
return (
43+
<Form action="/projects/123" method="post">
44+
<input type="text" name="title" />
45+
<button type="submit">Submit</button>
46+
</Form>
47+
);
48+
}
49+
```
50+
51+
This will cause a navigation and a new entry will be added to the browser history.
52+
53+
### Calling actions with useSubmit
54+
55+
You can submit form data to an action imperatively with `useSubmit`.
56+
57+
```tsx
58+
import { useCallback } from "react";
59+
import { useSubmit } from "react-router";
60+
import { useFakeTimer } from "fake-lib";
61+
62+
function useQuizTimer() {
63+
let submit = useSubmit();
64+
65+
let cb = useCallback(() => {
66+
submit(
67+
{ quizTimedOut: true },
68+
{ action: "/end-quiz", method: "post" }
69+
);
70+
}, []);
71+
72+
let tenMinutes = 10 * 60 * 1000;
73+
useFakeTimer(tenMinutes, cb);
74+
}
75+
```
76+
77+
This will cause a navigation and a new entry will be added to the browser history.
78+
79+
### Calling actions with a fetcher
80+
81+
Fetchers allow you to submit data to actions (and loaders) without causing a navigation (no new entries in the browser history).
82+
83+
```tsx
84+
import { useFetcher } from "react-router";
85+
86+
function Task() {
87+
let fetcher = useFetcher();
88+
let busy = fetcher.state !== "idle";
89+
90+
return (
91+
<fetcher.Form method="post" action="/update-task/123">
92+
<input type="text" name="title" />
93+
<button type="submit">
94+
{busy ? "Saving..." : "Save"}
95+
</button>
96+
</fetcher.Form>
97+
);
98+
}
99+
```
100+
101+
They also have the imperative `submit` method.
102+
103+
```tsx
104+
fetcher.submit(
105+
{ title: "New Title" },
106+
{ action: "/update-task/123", method: "post" }
107+
);
108+
```
109+
110+
See the [Using Fetchers][fetchers] guide for more information.
111+
112+
## Accessing Action Data
113+
114+
Actions can return data available through `useActionData` in the route component or `fetcher.data` when using a fetcher.
115+
116+
```tsx
117+
function Project() {
118+
let actionData = useActionData();
119+
return (
120+
<div>
121+
<h1>Project</h1>
122+
<Form method="post">
123+
<input type="text" name="title" />
124+
<button type="submit">Submit</button>
125+
</Form>
126+
{actionData ? (
127+
<p>{actionData.title} updated</p>
128+
) : null}
129+
</div>
130+
);
131+
}
132+
```
133+
134+
---
135+
136+
Next: [Navigating](./navigating)
137+
138+
[fetchers]: ../../how-to/fetchers

docs/start/data/custom.md

Lines changed: 6 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -1,10 +1,15 @@
11
---
22
title: Custom Framework
3+
order: 8
34
---
45

56
# Custom Framework
67

7-
Instead of using `@react-router/dev`, you can integrate React Router's framework features (like loaders, actions, fetchers, etc.) into your own bundler and server abstractions.
8+
[MODES: data]
9+
10+
## Introduction
11+
12+
Instead of using `@react-router/dev`, you can integrate React Router's framework features (like loaders, actions, fetchers, etc.) into your own bundler and server abstractions with Data Mode..
813

914
## Client Rendering
1015

docs/start/data/data-loading.md

Lines changed: 40 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,40 @@
1+
---
2+
title: Data Loading
3+
order: 4
4+
---
5+
6+
# Data Loading
7+
8+
[MODES: data]
9+
10+
## Providing Data
11+
12+
Data is provided to route components from route loaders:
13+
14+
```tsx
15+
createBrowserRouter([
16+
{
17+
path: "/",
18+
loader: () => {
19+
// return data from here
20+
return { records: await getSomeRecords() };
21+
},
22+
Component: MyRoute,
23+
},
24+
]);
25+
```
26+
27+
## Accessing Data
28+
29+
The data is available in route components with `useLoaderData`.
30+
31+
```tsx
32+
import { useLoaderData } from "react-router";
33+
34+
function MyRoute() {
35+
const { records } = useLoaderData();
36+
return <div>{records.length}</div>;
37+
}
38+
```
39+
40+
As the user navigates between routes, the loaders are called before the route component is rendered.

docs/start/data/installation.md

Lines changed: 55 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,55 @@
1+
---
2+
title: Installation
3+
order: 1
4+
---
5+
6+
# Installation
7+
8+
[MODES: data]
9+
10+
## Bootstrap with a Bundler Template
11+
12+
You can start with a React template from Vite and choose "React", otherwise bootstrap your application however you prefer (Parcel, Webpack, etc).
13+
14+
```shellscript nonumber
15+
npx create-vite@latest
16+
```
17+
18+
## Install React Router
19+
20+
Next install React Router from npm:
21+
22+
```shellscript nonumber
23+
npm i react-router
24+
```
25+
26+
## Create a Router and Render
27+
28+
Create a router and pass it to `RouterProvider`:
29+
30+
```tsx lines=[1-4,9-14,19]
31+
import {
32+
createBrowserRouter,
33+
RouterProvider,
34+
} from "react-router";
35+
36+
import React from "react";
37+
import ReactDOM from "react-dom/client";
38+
39+
const router = createBrowserRouter([
40+
{
41+
path: "/",
42+
element: <div>Hello World</div>,
43+
},
44+
]);
45+
46+
const root = document.getElementById("root");
47+
48+
ReactDOM.createRoot(root).render(
49+
<RouterProvider router={router} />
50+
);
51+
```
52+
53+
---
54+
55+
Next: [Routing](./routing)

docs/start/data/navigating.md

Lines changed: 12 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,12 @@
1+
---
2+
title: Navigating
3+
order: 6
4+
---
5+
6+
# Navigating
7+
8+
Navigating in Data Mode is the same as Framework Mode, please see the [Navigating](../framework/navigating) guide for more information.
9+
10+
---
11+
12+
Next: [Pending UI](./pending-ui)

docs/start/data/pending-ui.md

Lines changed: 12 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,12 @@
1+
---
2+
title: Pending UI
3+
order: 7
4+
---
5+
6+
# Pending UI
7+
8+
Pending UI is the same as Framework Mode, please see the [Pending UI](../framework/pending-ui) guide for more information.
9+
10+
---
11+
12+
Next: [Custom Framework](./custom)

0 commit comments

Comments
 (0)