HubDocs

Guides / Access and invitations

Identity in your app

Read the signed-in person's email, name, and role on your server.

View Markdown

Hub signs visitors in before they reach a private or org app. Your server can read these headers when needed:

HeaderValue
X-Hub-EmailEmail
X-Hub-NameName; non-ASCII values are percent-encoded
X-Hub-Roleowner, admin, member, viewer, or guest

Hub replaces visitor-supplied identity headers. Trust them only when your app is served through Hub.

JS
const roles = new Set(['owner', 'admin', 'member', 'viewer', 'guest']);

app.get('/me', (req, res) => {
  try {
    const email = decodeURIComponent(req.get('X-Hub-Email') ?? '');
    const name = decodeURIComponent(req.get('X-Hub-Name') ?? '');
    const role = req.get('X-Hub-Role');
    if (!email.trim() || !roles.has(role)) return res.sendStatus(401);
    return res.json({ email, name, role });
  } catch {
    return res.sendStatus(401);
  }
});

Roles in your app

Hub controls who can open the app. Your server decides what they can do inside it.

Check the role in handlers that need authorization. Reject missing or unknown identity; never default it to member. Decide explicitly what guests and viewers may do. Hiding controls in the browser does not enforce permissions.

Protect your app's writes

Hub apps share the myhub.host site, so SameSite cookies alone do not prevent requests from another app. Protect browser writes with a CSRF token or an origin check, for example:

JS
const ORIGIN = 'https://crm.acme.myhub.host';

function fromOwnPage(req) {
  const site = req.headers['sec-fetch-site'];
  const origin = req.headers.origin;
  if (site !== undefined && site !== 'same-origin') return false;
  if (origin !== undefined && origin !== ORIGIN) return false;
  return site !== undefined || origin !== undefined;
}

Call this check before handling a browser write. Authenticate scripted requests separately; do not accept missing headers as authorization.

For your own session cookies, use the __Host- prefix with Secure, Path=/, and no Domain, so another app cannot set them for your hostname.

Public apps

Public apps receive no Hub identity headers. Use private or org access when your server needs these headers.

On this page