# Hydration and offline mutations

> hydrationOptions() sends the cache to the browser with the client's serializer, and persisted mutations resume with setMutationDefaults.

## Hydration

`hydrationOptions({ client })` returns `{ dehydrate, hydrate }` options that serialize data with the client's [serializer](https://v12.trpc.io/docs/server/serializers.md), so the types it keeps (with danSON: `Date`, `Map`, `Set`, `bigint`, custom types) survive the trip, and that dehydrate pending queries. Their data is serialized once it settles. Without `client` it uses plain JSON; `serializer` overrides both.

```ts
new QueryClient({ defaultOptions: hydrationOptions({ client }) });
```

Use the same options for the server's `QueryClient` and the browser's. In React Server Components, `createTrpcRsc` dehydrates with them on the server, and the browser's `QueryClient` takes them as above ([React Server Components](https://v12.trpc.io/docs/integrations/rsc.md)).

## Offline mutations

A paused mutation that was persisted (with `persistQueryClient`, say) can only resume if the restored client knows its `mutationFn`. `mutationOptions()` returns the key and the function, so register them as defaults:

```ts
const createPost = trpc.post.create.mutationOptions();
queryClient.setMutationDefaults(createPost.mutationKey, createPost);
// after restoring: await queryClient.resumePausedMutations();
```
