Skip to content

Commit 056a907

Browse files
committed
Nits
1 parent fe42437 commit 056a907

File tree

1 file changed

+92
-95
lines changed

1 file changed

+92
-95
lines changed

src/content/blog/2024/04/01/react-19.md

Lines changed: 92 additions & 95 deletions
Original file line numberDiff line numberDiff line change
@@ -107,13 +107,13 @@ The async transition will immediately set the `isPending` state to true, make th
107107
Actions automatically manage submitting data for you:
108108

109109
- **Pending state**: Actions provide a pending state that starts at the beginning of a request and automatically resets when the final state update is committed.
110-
- **Optimistic updates**: Actions support the new [`useOptimistic`](#new-feature-optimistic-updates) hook to handle optimistically showing the user the final state while requests are submitting.
111-
- **Error Handling**: Actions provide error handling so you can and display Error Boundaries when a request fails, and revert optimistic updates to their original value automatically.
112-
- **Forms**: Actions support new `action` prop for `<form>` elements called [Form Actions](#form-actions). This means form submissions use Actions by default, and reset automatically after submission.
110+
- **Optimistic updates**: Actions support the new [`useOptimistic`](#new-feature-optimistic-updates) hook so you can show users instant feedback while the requests are submitting.
111+
- **Error handling**: Actions provide error handling so you can and display Error Boundaries when a request fails, and revert optimistic updates to their original value automatically.
112+
- **Forms**: Actions integrate with new `action` and `formActions` props as [`<form>` Actions](#form-actions). This means form submissions use Actions by default and reset the form automatically after submission.
113113

114114
</Note>
115115

116-
Async transitions are the raw primitive that power Actions, and you can always drop down to `useTransition`, `useState`, and `useOptimisitc` to create your own custom behavior. We're also introducing the [`useActionState`](#new-hook-useactionstate) and [`useFormStatus`](#new-hook-useformstatus) hooks to support the common cases for Actions and Forms.
116+
Async transitions are the raw primitive that power Actions, and you can always drop down to `useTransition`, `useState`, and `useOptimistic` to create your own custom behavior. We're also introducing the [`useActionState`](#new-hook-useactionstate) and [`useFormStatus`](#new-hook-useformstatus) hooks to support the common cases for Actions and Forms.
117117

118118
For more information, see the docs for [`useTransition`](/reference/react/useTransition) and the next sections.
119119

@@ -123,7 +123,7 @@ To make the common cases easier for Actions, we've added a new hook called `useA
123123

124124
```js {2,9}
125125
const [name, setName] = useState('');
126-
const [submitAction, data, isPending] = useActionState(async () => {
126+
const [error, submitAction, isPending] = useActionState(async () => {
127127
const {error} = await updateName(name);
128128
setName('');
129129

@@ -145,13 +145,13 @@ See [#28491](https://github.com/facebook/react/pull/28491) for more info.
145145

146146
For more information, see the docs for [`useActionState`](/reference/react/useActionState).
147147

148-
### Form Actions {/*form-actions*/}
148+
### `<form>` Actions {/*form-actions*/}
149149

150-
Actions are also integrated with React 19's new Form features. We've added an `action` prop to React DOM `<form>` elements to automatically submit forms with Actions:
150+
Actions are also integrated with React 19's new `<form>` features. We've added `action` and `formAction` props to React DOM `<form>`, `<input>`, and `<button>` elements to automatically submit forms with Actions:
151151

152152
```js {1,3,7-8}
153153
const [submitAction, state, isPending] = useActionState(async (formData) => {
154-
return updateName(formData.get('name'));
154+
return await updateName(formData.get('name'));
155155
})
156156

157157
return (
@@ -164,23 +164,20 @@ return (
164164

165165
When a `<form>` Action succeeds, React will automatically reset the form for uncontrolled components. If you need to reset the `<form>` manually, you can call the new [`requestFormReset`](/todo) React DOM API.
166166

167+
For more information, see the docs for [`<form>`](/reference/react-dom/components/form), [`<input>`](/reference/react-dom/components/input), and [`<button>`](/reference/react-dom/components/button).
168+
167169
### New Hook: `useFormStatus` {/*new-hook-useformstatus*/}
168170

169-
In design systems, it's common to write design components that need access to the nearest Form status, without passing the status down to the component. This can be done via Context, but to make the common case easier, we've added a new hook `useFormStatus`:
171+
In design systems, it's common to write design components that need access to information about the `<form>` they're in, without drilling props down to the component. This can be done via Context, but to make the common case easier, we've added a new hook `useFormStatus`:
170172

171-
```js {2,5-6}
172-
function NameInput() {
173-
const {data, pending} = useFormStatus();
174-
return (
175-
<>
176-
<input type="text" name="name" disabled={pending} />
177-
{!data.sucess && <span>Failed: {data.error}</span>}
178-
</>
179-
)
173+
```js [[1, 2, "pending"], [1, 3, "pending"]]
174+
function DesignButton() {
175+
const {pending} = useFormStatus();
176+
return <button type="submit" disabled={pending} />
180177
}
181178
```
182179

183-
`useFormStatus` works like Context for the nearest `<form>` element, returning its `pending` state, the last submitted form `data`, and the `action`.
180+
`useFormStatus` reads the status of the parent `<form>` as if the form was a Context provider.
184181

185182
For more information, see the docs for [`useFormStatus`](/reference/react-dom/hooks/useFormStatus).
186183

@@ -332,6 +329,76 @@ Todo: This requires the new transform, correct?
332329

333330
For more information, see [Manipulating the DOM with refs](/learn/manipulating-the-dom-with-refs)
334331

332+
### Diffs for Hydration Errors {/*diffs-for-hydration-errors*/}
333+
334+
We also improved error reporting for hydration errors. For example, instead of logging multiple errors in DEV without any information about the mismatch:
335+
336+
<ConsoleBlockMulti>
337+
338+
<ConsoleLogLine level="error">
339+
340+
Warning: Text content did not match. Server: "Server" Client: "Client"
341+
{' '}at span
342+
{' '}at App
343+
344+
</ConsoleLogLine>
345+
346+
<ConsoleLogLine level="error">
347+
348+
Warning: An error occurred during hydration. The server HTML was replaced with client content in \<div\>.
349+
350+
</ConsoleLogLine>
351+
352+
<ConsoleLogLine level="error">
353+
354+
Warning: Text content did not match. Server: "Server" Client: "Client"
355+
{' '}at span
356+
{' '}at App
357+
358+
</ConsoleLogLine>
359+
360+
<ConsoleLogLine level="error">
361+
362+
Warning: An error occurred during hydration. The server HTML was replaced with client content in \<div\>.
363+
364+
</ConsoleLogLine>
365+
366+
<ConsoleLogLine level="error">
367+
368+
Uncaught Error: Text content does not match server-rendered HTML.
369+
{' '}at checkForUnmatchedText
370+
{' '}...
371+
372+
</ConsoleLogLine>
373+
374+
</ConsoleBlockMulti>
375+
376+
We now log a single message with a diff of the mismatch:
377+
378+
379+
<ConsoleBlockMulti>
380+
381+
<ConsoleLogLine level="error">
382+
383+
Uncaught Error: Hydration failed because the server rendered HTML didn't match the client. As a result this tree will be regenerated on the client. This can happen if an SSR-ed Client Component used:{'\n'}
384+
\- A server/client branch `if (typeof window !== 'undefined')`.
385+
\- Variable input such as `Date.now()` or `Math.random()` which changes each time it's called.
386+
\- Date formatting in a user's locale which doesn't match the server.
387+
\- External changing data without sending a snapshot of it along with the HTML.
388+
\- Invalid HTML tag nesting.{'\n'}
389+
It can also happen if the client has a browser extension installed which messes with the HTML before React loaded.{'\n'}
390+
https://react.dev/link/hydration-mismatch {'\n'}
391+
{' '}\<App\>
392+
{' '}\<span\>
393+
{'+ '}Client
394+
{'- '}Server{'\n'}
395+
{' '}at throwOnHydrationMismatch
396+
{' '}...
397+
398+
</ConsoleLogLine>
399+
400+
</ConsoleBlockMulti>
401+
335402
### `<Context>` as a provider {/*context-as-a-provider*/}
336403

337404
In React 19, you can render `<Context>` as a provider instead of `<Context.Provider>`:
@@ -377,7 +444,7 @@ When the component unmounts, React will call the cleanup function returned from
377444

378445
<Note>
379446

380-
Previously, React would call ref functions with `null` when unmounting the component. If your ref returns a cleanup function, React will skip this step.
447+
Previously, React would call ref functions with `null` when unmounting the component. If your ref returns a cleanup function, React will now skip this step.
381448

382449
In future versions, we will deprecate calling the ref with `null` when unmounting components.
383450

@@ -414,11 +481,11 @@ In React 19, we're adding support for rendering document metadata tags in compon
414481
```js {5,6}
415482
function BlogPost({post}) {
416483
return (
417-
<div>
418-
<p>{post.title}</p>
484+
<article>
485+
<h1>{post.title}</h1>
419486
<title>{post.title}</title>
420487
<meta name="keywords" content={post.keywords} />
421-
</div>
488+
</article>
422489
);
423490
}
424491
```
@@ -446,9 +513,9 @@ return (
446513
```
447514
When React renders this component, it will see the `<link>`, `<style>`, and `<script>` tags and hoist them to the `<head>` of the document.
448515
449-
For some resource elements, React will suspend while waiting for the resource to load (such as a `<link>` to a css file). This ensures that styles are available before the components are displayed, preventing flashes of un-styled content. React may also dedupe some elements to ensure duplicate resources are not loaded.
516+
For some resource elements, React will suspend while waiting for the resource to load (such as a `<link>` to a CSS file). This ensures that styles are available before the components are displayed, preventing flashes of un-styled content. React may also dedupe some elements to ensure duplicate resources are not loaded.
450517
451-
To maintain compatibility with HTML and optimize performance, React will dedupe and hoist some but not all elements for all props. For the specific constraints, read the docs for [Resource and Metadata Components](/reference/react-dom/components#resource-and-metadata-components).
518+
To optimize performance, React will dedupe elements if they refer to equivalent resources. For more details, read the docs for [Resource and Metadata Components](/reference/react-dom/components#resource-and-metadata-components).
452519
453520
### Compatability with third-party scripts and extensions {/*compatability-with-third-party-scripts-and-extensions*/}
454521
@@ -526,76 +593,6 @@ Additionally, we've added two new root options to complement `onRecoverableError
526593
527594
For more info and examples, see the docs for [`createRoot`](/reference/react-dom/client/createRoot) and [`hydrateRoot`](/reference/react-dom/client/createRoot).
528595
529-
### Diffs for Hydration Errors {/*diffs-for-hydration-errors*/}
530-
531-
We also improved error reporting for hydration errors. For example, instead of logging multiple errors in DEV without any information about the mismatch:
532-
533-
<ConsoleBlockMulti>
534-
535-
<ConsoleLogLine level="error">
536-
537-
Warning: Text content did not match. Server: "Server" Client: "Client"
538-
{' '}at span
539-
{' '}at App
540-
541-
</ConsoleLogLine>
542-
543-
<ConsoleLogLine level="error">
544-
545-
Warning: An error occurred during hydration. The server HTML was replaced with client content in \<div\>.
546-
547-
</ConsoleLogLine>
548-
549-
<ConsoleLogLine level="error">
550-
551-
Warning: Text content did not match. Server: "Server" Client: "Client"
552-
{' '}at span
553-
{' '}at App
554-
555-
</ConsoleLogLine>
556-
557-
<ConsoleLogLine level="error">
558-
559-
Warning: An error occurred during hydration. The server HTML was replaced with client content in \<div\>.
560-
561-
</ConsoleLogLine>
562-
563-
<ConsoleLogLine level="error">
564-
565-
Uncaught Error: Text content does not match server-rendered HTML.
566-
{' '}at checkForUnmatchedText
567-
{' '}...
568-
569-
</ConsoleLogLine>
570-
571-
</ConsoleBlockMulti>
572-
573-
We now log a single message with a diff of the mismatch:
574-
575-
576-
<ConsoleBlockMulti>
577-
578-
<ConsoleLogLine level="error">
579-
580-
Uncaught Error: Hydration failed because the server rendered HTML didn't match the client. As a result this tree will be regenerated on the client. This can happen if an SSR-ed Client Component used:{'\n'}
581-
\- A server/client branch `if (typeof window !== 'undefined')`.
582-
\- Variable input such as `Date.now()` or `Math.random()` which changes each time it's called.
583-
\- Date formatting in a user's locale which doesn't match the server.
584-
\- External changing data without sending a snapshot of it along with the HTML.
585-
\- Invalid HTML tag nesting.{'\n'}
586-
It can also happen if the client has a browser extension installed which messes with the HTML before React loaded.{'\n'}
587-
https://react.dev/link/hydration-mismatch {'\n'}
588-
{' '}\<App\>
589-
{' '}\<span\>
590-
{'+ '}Client
591-
{'- '}Server{'\n'}
592-
{' '}at throwOnHydrationMismatch
593-
{' '}...
594-
595-
</ConsoleLogLine>
596-
597-
</ConsoleBlockMulti>
598-
599596
### Custom Element Support {/*support-for-web-components*/}
600597
601598
TODO

0 commit comments

Comments
 (0)