Skip to content

Components · Identity

NoAppAccess

The “you don’t have access to this app” screen: who can fix it, request access, contact an admin and switch workspace.

@rookcom/monarch-react/shellComponent

Every action

You don’t have access to Example Desk

Ask an admin of Acme to give you access to Example Desk.

Back to workspace

Usage examples

Explanation and a way back

Purpose

A person can be a member of a Rook workspace without a grant for every app. NoAppAccess is that screen, built on ErrorPage, with the actions the person can actually take.

Use when

  • In place of the app’s pages when Rook ID says this member has no grant for the app.
  • Inside an embedded page (App Settings) for the same case; it still counts as an answer for the ready handshake.

Avoid when

  • A missing permission inside the app (a page or an action): show an ErrorState or disable the action with a reason.
  • Not signed in, or not a member of the workspace: those are sign-in and workspace flows.

Design principles

  • Say who can fix it: the person cannot grant themselves access, so the text names the admins (and the workspace).
  • Always a way forward: request access, contact an admin, back to the workspace or another workspace.
  • The grant check stays in the app; the screen only shows the outcome and runs the callbacks it is given.
  • Calm, not alarming: a lock and plain words, no error code.

API reference

import { NoAppAccess } from '@rookcom/monarch-react/shell';
ExportKindRenderingRoot class
NoAppAccesscomponentclient.mn-no-app-access

Forwards its ref to the root element (section, or main with fullScreen). Built on ErrorPage (kind="forbidden") from @rookcom/monarch-react.

Generated from the TypeScript declarations of packages/react/src/components/identity/no-app-access.

Properties

With onRequestAccess returning a promise, the button shows pending, then "Access requested"; a rejection shows an alert and allows another try. requestState controls it (e.g. sent when a request is already open).

Switch workspace is onSwitchWorkspace, switchWorkspaceHref, or your own control in workspaceSwitcher (such as WorkspaceSwitcher).

NoAppAccess

The "you don't have access to this app" screen: the person is a member of the workspace but has no grant for this app. It explains who can fix it and offers request access, contact an admin, back to the workspace and switch workspace. Built on ErrorPage (`forbidden`). The grant check stays in the app.

PropTypeDescription
appName requiredstringThe app the person can't open, e.g. "Rook Tickets".
childrenReactNode
classNamestring
contactHrefstring"Contact an admin": a mailto: or a page that lists the admins.
descriptionReactNodeReplaces the default explanation.
focusOnMountbooleanFocus the heading on mount, after a client-side navigation. Default false.
fullScreenbooleanFill the viewport (no app shell). Default false: sits in the shell's content area.
headingLevel"h2" | "h1"Heading level. Default `h1` (the screen replaces the page).
homeHrefstring"Back to workspace": the workspace home in Rook ID or another app.
idstring
linkAsShellLinkComponentRouter link for the internal links. Default `<a>`.
messagesPartial<NoAppAccessMessages>Interface text, for translation.
onRequestAccess(() => unknown)Shows "Request access". A returned promise drives the pending, sent and failed states (unless `requestState` is controlled).
onSwitchWorkspace(() => void)"Switch workspace" as an action…
requestStateAccessRequestStateRequest state (controlled), e.g. `sent` when a request is already open.
switchWorkspaceHrefstring…or a link.
titleReactNodeReplaces the default heading.
workspaceNamestringThe current workspace, named in the explanation.
workspaceSwitcherReactNodeOr your own control (e.g. a WorkspaceSwitcher) in place of the switch button.

Variants

PropValuesDescription
fullScreen'false''true'Inside the app shell (default), or filling the viewport without one.
headingLevel'h1''h2'h1 when the screen replaces the page (default).

States

StateExposed asBehaviour
Idledata-request="idle"Request access is offered.
Pendingdata-request="pending"The button is busy (aria-busy) and ignores further clicks.
Sentdata-request="sent"The button reads "Access requested" and is disabled; a status says what happens next.
Errordata-request="error"An alert says the request failed; the button works again.

Interaction behaviour

  • Request access runs onRequestAccess once per attempt.
  • Back to workspace and switch links render with linkAs (your router link) when given.
  • Contact an admin is a plain link (a mailto: or a page listing the admins).

Keyboard support

KeysAction
TabMoves through the actions and the contact link.
Enter / SpaceActivates the focused action.

Accessibility

Role
region (section labelled by its heading), or main with fullScreen
Accessible name
The heading, "You don’t have access to <app>".
  • The lock is decorative (aria-hidden), fixing the products’ unhidden icon.
  • The sent message is in a status region, and a failure is an alert, so both are announced.
  • focusOnMount moves focus to the heading after a client-side navigation.
  • Security: the screen shows no data from the app and does not decide access; render it only after the app’s own grant check, and enforce access on the server too.

Responsive behaviour

  • Centred column; the actions wrap onto several lines at 320px.

Theme support

  • ErrorPage tokens; the status uses the success text colour and the error the danger text colour.

Do and don't

Do

  • Name the app the way the rail and Rook ID do.
  • Offer request access only when the product can actually deliver the request to the admins.
  • Keep the rail on screen so the person can switch apps.

Don't

  • Do not show the app’s data or navigation behind the screen.
  • Do not use it for a missing permission inside the app.

Dependencies

KindDepends on
npm packagesreact
Monarch componentsButton, ErrorPage

Testing coverage

  • Heading, explanation with the workspace, forbidden ErrorPage root, decorative lock, no actions by default.
  • Request access: pending, single call, then sent (status) and disabled.
  • A failed request is an alert and can be retried; a synchronous request counts as sent; controlled state.
  • Back to workspace, switch workspace and contact links; switch link, custom switcher slot and router link.
  • Focus on mount, h2, custom text and full screen; translation.
CheckCovered
Axe in jsdomYes
Server renderingYes
Browser suitesVisual baselines: /__gallery/no-app-access; Cross-browser axe: /components/no-app-access

Tests: packages/react/src/components/identity/no-app-access