> ## Documentation Index
> Fetch the complete documentation index at: https://docs.cskn.dev/llms.txt
> Use this file to discover all available pages before exploring further.

# Surfaces

> Where a mini app runs, and how to tell the surfaces apart at runtime.

The same bundle is served in several places. Two questions decide what your app should render: **which page is this**, and **is there a native shell around it**.

## App page vs. user page

| | App page | User page |
| - | - | - |
| Address | `<slug>.cskn.app` | `<username>.cskn.my/<slug>` |
| Who sees it | The signed-in user, using the app | Anyone visiting a creator's profile |
| `isUserPage()` | `false` | `true` |
| `getAppUser()` | `null` | `{ username }` of the profile owner |

The app page is the tool; the user page is the creator's public output from that tool (their blog, their gallery, their CV). Most apps render something quite different on each:

```tsx theme={null}
import { isUserPage } from '@cskn/sdk';

export default function App() {
  return isUserPage() ? <PublicProfileView /> : <Editor />;
}
```

## Shell vs. browser

A native shell (the cskn mobile, desktop or TV app) attaches a message bridge at `window.cskn.bridge`. A plain browser has none.

```tsx theme={null}
import { isAvailable } from '@cskn/sdk';

isAvailable(); // true inside a shell, false in a browser
```

For finer detail, `getPlatform()` / `usePlatform()` return the host kind and the operating system:

| `env` | Host | Bridge |
| - | - | - |
| `mobile` | iOS / Android app (WebView) | yes |
| `desktop` | macOS / Windows / Linux app | yes |
| `tv` | webOS, Tizen or Android TV launcher (iframe) | yes |
| `web` | A plain browser | no |

```tsx theme={null}
import { usePlatform } from '@cskn/sdk';

const platform = usePlatform(); // null until resolved; instant on the web
if (platform?.env === 'desktop') {
  // wide layout
}
```

In a React tree wrapped in `UIProvider`, `useUI()` gives you the same information synchronously, plus `isTV` and the live safe-area insets. See [UIProvider](/ui/provider#useui).

## What changes per surface

<AccordionGroup>
  <Accordion title="Authentication">
    In a shell the user's token arrives over the bridge. In a browser the user is signed in with a cookie on the app's own domain. `useBridgeAuth` handles both. See [Authentication](/concepts/authentication).
  </Accordion>

  <Accordion title="Native features">
    Some bridge calls have a browser fallback (photo capture falls back to a file picker, notification permission falls back to Web Push), some resolve to `not_available`, and a few never resolve without a shell. Check the [availability table](/sdk/native/overview#availability) before calling one from code that also runs in a browser.
  </Accordion>

  <Accordion title="Header and system chrome">
    Mobile and desktop shells draw a native header above your page. In a browser and on TV there is none, so you draw your own. `NativeHeader` from @cskn/ui picks the right one for you.
  </Accordion>

  <Accordion title="Input">
    TV has no touch and no pointer, only a remote. @cskn/ui runs a spatial navigator there so arrow keys move focus between controls. See [TV navigation](/ui/tv-navigation).
  </Accordion>
</AccordionGroup>


This documentation is built and hosted on [Mintlify](https://mintlify.com), a developer documentation platform.