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

# webNfcPermissionState

> Reports the Web NFC scan permission for this origin, so the interface can decide whether to offer a scan or point at the browser's site settings.

```ts theme={null}
webNfcPermissionState(
  windowRef?: () => WebNfcWindow | undefined,
): Promise<WebNfcPermissionState>

type WebNfcPermissionState = "granted" | "prompt" | "denied" | "unsupported"
```

Web NFC permission is granted per site, and a denial never re-prompts on its own. Call this before offering a scan so the interface can branch: offer the scan when a prompt is still possible, and route the customer to the browser's site settings once scanning is blocked.

## Example

```ts theme={null}
import { webNfcPermissionState } from "@endstate-sdk/web";

const state = await webNfcPermissionState();
if (state === "unsupported") {
  // No in-page scanner here; rely on the redirect source.
} else if (state === "denied") {
  // Only the browser's site settings can re-enable it.
} else {
  // "granted" or "prompt": offer the scan from a control the user presses.
}
```

## Parameters

<ParamField body="windowRef" type="() => WebNfcWindow | undefined">
  Test seam that supplies the window the check reads `NDEFReader` and the
  permissions API from. Defaults to the page's own `window`. Leave it unset in
  product code.
</ParamField>

## Returns

A `Promise<WebNfcPermissionState>`, one of:

<ResponseField name="granted" type="WebNfcPermissionState">
  Scanning is allowed for this origin. A scan started inside a user gesture
  proceeds without a prompt.
</ResponseField>

<ResponseField name="prompt" type="WebNfcPermissionState">
  Scanning has not been decided. A scan started inside a user gesture asks the
  customer. Also returned as a safe default when the reader exists but the
  permission is not queryable.
</ResponseField>

<ResponseField name="denied" type="WebNfcPermissionState">
  Scanning is blocked for this origin. Only the browser's site settings can
  re-enable it, so present that path rather than retrying the scan.
</ResponseField>

<ResponseField name="unsupported" type="WebNfcPermissionState">
  The device exposes no `NDEFReader`. Web NFC is not available here; rely on the
  redirect source.
</ResponseField>

<Note>
  This reports the origin's permission, not the outcome of a scan. A scan can
  still fail from `"granted"` or `"prompt"` - for example a dismissed prompt or
  an empty-tag read. Handle those through
  [`WebNfcError.reason`](/sdks/web/reference/tap-sources/WebNfcError).
</Note>

## See also

* [`webNfcTapSource`](/sdks/web/reference/tap-sources/webNfcTapSource) - the source this gates.
* [`WebNfcError`](/sdks/web/reference/tap-sources/WebNfcError) - the typed failures a scan rejects with.
