Skip to main content

Authorization operations and bootstrap

Use this reference to prepare service identity and diagnose authorization boundaries. Read authorization, Graph setup, and external prerequisites first.

Service keys​

For a separately prepared standalone development environment, run from the backend directory:

node scripts/authorization-runtime.mjs init
node scripts/authorization-runtime.mjs ecas-backend pnpm dev:admin

The unified runtime manages its services through the runtime lifecycle. Do not start this standalone service beside an existing instance.

AdminService defaults to port 3018. GraphPullPoller uses 3013. BFF ADMIN_SERVICE_URL defaults to http://127.0.0.1:3018.

The development launcher keeps separate RSA identities for BFF, backend, onboarding, and search. They reside under ~/.local/share/ecas-authorization/, outside the repository. ECAS_AUTHORIZATION_DIRECTORY selects another location. init preserves existing keys. Provider-secret encryption uses a separate file and binds tenant/provider identity as authenticated additional data.

Production mounts keys from secret storage. Verification keys constrain issuer, audience, and action. Keep previous verification keys while accepted or scheduled work can still reference them.

The development launcher sets ECAS_ENABLE_BOOTSTRAP_ROOT=true. This enables a separate audited bootstrap membership. It does not make every developer root. Production does not enable it by default. Bootstrap is not proof of a Microsoft role.

Client IP policy​

Untrusted X-Forwarded-For cannot establish the client address. The configured ingress removes incoming MailGen proxy headers, then sets X-Ecas-Client-IP and X-Ecas-Proxy-Token. BFF compares the token against ECAS_TRUSTED_PROXY_TOKEN with a timing-safe check. The verified address enters the signed service context.

With active IP rules and no verified address, a new request fails. Deny wins. If an allow list exists, at least one entry must match. A later IP policy does not revoke the original admission of accepted durable work.

External destinations​

ECAS_ENTITLEMENT_ALLOWED_HOSTS permits HTTP-entitlement destinations. ECAS_PROVIDER_ALLOWED_HOSTS permits custom OpenAI-compatible provider destinations. The HTTP client requires HTTPS and a public address. It pins the checked DNS destination, rejects redirects, and bounds response size and duration.

cURL import parses configuration. It does not run a shell or make a request. Model discovery uses provider APIs. Absent metadata remains unknown. Manual and discovered values remain separate.

Storage measurements​

The meter pages through object metadata with ListObjectsV2 and deduplicates keys. It measures current verified tenant namespaces. It does not measure billing, archived versions, or disk capacity.

The admin API offers aggregate sizes, not S3 credentials, object lists, content, or general deletion. A dedicated mailbox-reset workflow has separate authority. Failed measurement preserves the prior successful snapshot and time, rather than storing a false zero.

The interface separately shows application-owned storage without a mapped user. While measurement runs, it reads status every two seconds and stops after completion.

Accepted work​

authorization.admissions protects the exact stored outbox payload::text digest. Payload edits, another tenant/resource, revoked proof, or invalid source binding cause rejection. A later group loss alone does not invalidate accepted work.

Do not legitimize legacy work without a proof through current administrator rights. Work without verified origin needs fresh user acceptance. Inspect an old schedule before recreating it.

Administrative boundaries​

Creating a local app login does not create a Microsoft identity binding or grant application permissions. The creating tenant can manage an unlinked account through audited provenance. After binding, verified identities receive rank protection.

The settings catalog uses the same validation as application settings. Required policy overrides local and optimistic values. Detailed Sync Center access is separate from the minimal mailbox writability read allowed by mail.read.

Membership details show validity, last proof, revocation, expiry, exception, and source errors. Removing an automatic-membership exception can restore access, so it needs the same assignment checks as adding membership. Removing a model grant also needs model-assignment permission.

Provider identity​

A model UUID cannot change its provider/model target. Create a new record for a new target. Display fields, prices, and limits remain editable. A provider referenced by models cannot redirect its protocol or destination.

Changing a destination with a stored key also requires key-management permission. This prevents provider-management access alone from redirecting a secret. DNS and HTTP share a deadline. The connection pins the permitted public IPv4 destination and rejects private targets and redirects.

default reasoning means the provider default when no explicit level is published. It does not invent capability metadata.