> For AI agents: the complete Sanity documentation index is available at [https://www.sanity.io/docs/llms.txt](https://www.sanity.io/docs/llms.txt).

# Share your app's context

Read the resource and document the Dashboard has in focus, and publish your own app's context so panels and agents can follow along.

Every app in the Dashboard can say what it currently has in focus: which resource, and which document. Panels, agents, and other apps read that context to follow along, which is how a side panel knows which document you are looking at. Read it with the `applications.context` topic, and publish it with `useApplicationContext`. Both come from `@sanity/sdk-react/dashboard`.

## Read what the user is looking at

**src/FocusedDocument.tsx**

```tsx
import {useTopic} from '@sanity/sdk-react/dashboard'
import {Suspense} from 'react'

function FocusedDocument() {
  const context = useTopic('applications.context')

  if (!context?.document) {
    return <p>No document in focus</p>
  }

  return (
    <p>
      Viewing {context.document.id} in {context.resource.id}, published by {context.appId}
    </p>
  )
}

export function Panel() {
  return (
    <Suspense fallback={<p>Waiting for the Dashboard</p>}>
      <FocusedDocument />
    </Suspense>
  )
}
```

The topic carries the context of the foreground application, or `null` when no app has published one. A value has the shape `{resource: {id, type}, document: {id} | null, appId}`, where `resource.type` is `dataset`, `media-library`, or `canvas`, and `appId` identifies the app that published it. Like the other state topics, it suspends until the first value arrives, so render it inside `Suspense`. To track only which app is in front, read `applications.foreground` instead.

## Publish context from your own app

If your app has its own notion of an open document, publish it so panels and agents can react. `useApplicationContext` sends the value to the Dashboard on the `applications.context.update` event topic for you.

**src/DocumentView.tsx**

```tsx
import {useApplicationContext} from '@sanity/sdk-react/dashboard'
import {useMemo} from 'react'

export function DocumentView({documentId}: {documentId: string | null}) {
  const context = useMemo(
    () =>
      documentId
        ? {
            resource: {id: 'my-project.production', type: 'dataset' as const},
            document: {id: documentId},
          }
        : null,
    [documentId],
  )

  useApplicationContext(context)

  return <article>{/* your app */}</article>
}
```

> [!WARNING]
> Memoize the context value
> The hook compares values by reference. A fresh object literal on every render republishes the context on every render, so wrap it in `useMemo` or hold it in state.

Two more things to know. Pass `null` when nothing is open: the hook publishes on mount, emits `null` before each new value, and clears the context when the component unmounts. And leave `appId` out of what you publish, because the Dashboard fills it in from the message metadata.

## How the two sides meet

- Your app publishes its context whenever the focused document changes. The Studio does this already, so a panel sees Studio documents without any extra work.
- The Dashboard tracks which app is in the foreground and forwards that app's context to everyone listening.
- Panels read `applications.context` and re-render. Agents use the same topic to work out which document you are asking about.

## Next steps

[Read Dashboard state](https://www.sanity.io/docs/dashboard-beta/read-dashboard-state)
Read the organization, signed-in user, color scheme, and other state topics.

[Navigate the Dashboard](https://www.sanity.io/docs/dashboard-beta/navigate-the-dashboard)
Sync your router and link to other apps and Studios.

