init¶
init performs the one-time bootstrap of {{ product_name }}. It registers the global administrator OIDC resource-server configuration that every later administrator login validates against. This is the first command you run against a fresh deployment, before any host profile or interactive login exists.
Unlike every server-touching admin command, init does not require a prior profile authn login. It runs pre-OIDC: the request is authenticated by a JWT signed with the HMAC HS256 shared initialization secret that matches alpine.services.alpine-admin.initialization.secret in the server alpine.conf. No interactive OIDC login happens here. init only builds the administrator identity-provider validation settings (issuer, audience, discovery, fallbacks, timeouts) and hands them to the one-shot admin-init service.
One-time, shared-secret-gated bootstrap
The admin-init endpoint is gated by the shared HMAC secret and is intended to run once per deployment. Keep the initialization secret (at least 32 bytes) out of shell history; omit --init-secret to be prompted for it interactively. After init succeeds, the administrator authenticates normally through OIDC.
Syntax¶
Required options¶
These identify the administrator OpenID provider and are always required.
| Option | Description |
|---|---|
-i, --oidc-issuer-claim |
OpenID issuer claim expected during administrator token validation |
-a, --oidc-audience-claim |
OpenID audience claim expected during administrator token validation |
The administrator tenant identity (urn:alpine:tenant:admin) is set automatically; you do not pass a tenant option.
Conditionally required options¶
These combinations are enforced in code and fail fast at parse time.
| Condition | Required options |
|---|---|
--no-oidc-use-discovery (discovery disabled) |
--oidc-jwks-url-override |
--oidc-token-mode OIDC_TOKEN_MODE_OPAQUE_INTROSPECT |
--oidc-allow-introspection-fallback |
--oidc-allow-introspection-fallback |
--oidc-introspection-client-id and --oidc-introspection-client-secret |
--oidc-allow-introspection-fallback with discovery disabled |
--oidc-introspection-url-override |
--oidc-allow-user-info-fallback with discovery disabled |
--oidc-user-info-url-override |
Optional options¶
Show optional options
| Option | Default | Description |
|---|---|---|
--oidc-token-mode |
OIDC_TOKEN_MODE_JWT_LOCAL |
Validation mode: OIDC_TOKEN_MODE_JWT_LOCAL, OIDC_TOKEN_MODE_JWT_USERINFO, OIDC_TOKEN_MODE_OPAQUE_INTROSPECT, or OIDC_TOKEN_MODE_AUTO |
--[no-]oidc-use-discovery |
--oidc-use-discovery (enabled) |
Use OIDC discovery to resolve endpoints |
--oidc-discovery-url-override |
none | OpenID discovery URL override |
--oidc-jwks-url-override |
none | OpenID JWKS URL override (required when discovery is disabled) |
--[no-]oidc-allow-user-info-fallback |
--no-oidc-allow-user-info-fallback (disabled) |
Allow OIDC UserInfo fallback |
--oidc-user-info-url-override |
none | OpenID UserInfo URL override |
--[no-]oidc-allow-introspection-fallback |
--no-oidc-allow-introspection-fallback (disabled) |
Allow OIDC token introspection fallback |
--oidc-introspection-url-override |
none | OpenID introspection URL override |
--oidc-introspection-client-id |
none | OpenID introspection client id |
--oidc-introspection-client-secret |
none | OpenID introspection client secret |
--oidc-clock-skew-seconds |
30 |
Clock skew allowance in seconds (minimum 0) |
-O, --oidc-connect-timeout-ms |
1500 |
OIDC connect timeout in milliseconds |
--oidc-read-timeout-ms |
1500 |
OIDC read timeout in milliseconds (minimum 500) |
--init-secret |
interactive prompt | Shared HMAC initialization secret (at least 32 bytes); prompted when omitted |
-f, --out-format |
YAML |
Output format: JSON or YAML |
Validation rules
--oidc-issuer-claimand--oidc-audience-claimare always required.--no-oidc-use-discoveryrequires--oidc-jwks-url-override.--oidc-token-mode OIDC_TOKEN_MODE_OPAQUE_INTROSPECTrequires--oidc-allow-introspection-fallback.--oidc-allow-introspection-fallbackrequires both--oidc-introspection-client-idand--oidc-introspection-client-secret.- When discovery is disabled,
--oidc-allow-introspection-fallbackalso requires--oidc-introspection-url-override. - When discovery is disabled,
--oidc-allow-user-info-fallbackrequires--oidc-user-info-url-override. --init-secretmust match the serveralpine.services.alpine-admin.initialization.secretvalue or the HMAC gate rejects the request.
Standard CLI options are documented in Global options.
Example (discovery-based local JWT validation)¶
bin/admin.sh init \
--oidc-issuer-claim https://login.example.com/realms/alpine \
--oidc-audience-claim alpine-admin \
--init-secret \
-f json
Example (no discovery, explicit JWKS endpoint)¶
bin/admin.sh init \
--oidc-issuer-claim https://login.example.com/realms/alpine \
--oidc-audience-claim alpine-admin \
--no-oidc-use-discovery \
--oidc-jwks-url-override https://login.example.com/realms/alpine/protocol/openid-connect/certs \
--oidc-clock-skew-seconds 60 \
--oidc-connect-timeout-ms 2000 \
--oidc-read-timeout-ms 2000 \
-f yaml
Example (opaque token introspection)¶
bin/admin.sh init \
--oidc-issuer-claim https://login.example.com/realms/alpine \
--oidc-audience-claim alpine-admin \
--oidc-token-mode OIDC_TOKEN_MODE_OPAQUE_INTROSPECT \
--oidc-allow-introspection-fallback \
--oidc-introspection-client-id alpine-admin \
--oidc-introspection-client-secret \
--oidc-introspection-url-override https://login.example.com/realms/alpine/protocol/openid-connect/token/introspect \
--init-secret \
-f json
Next steps¶
After init reports success, the administrator can connect and log in:
- Create a host profile with
profile hosts create. - Authenticate against that profile with
profile authn login.
Host connection profiles — including their embedded OIDC logins (with PIN-sealed tokens) — are stored under ${HOME}/.config/alpinepki/hosts/.
Authorizing the bootstrap administrator¶
init registers only how administrator tokens are validated (issuer, audience, signature, token mode). It does not grant access on its own. Authorization is resolved from claims carried inside the OIDC access token that your identity provider issues to the administrator. For the first administrator to have full control, that token must resolve to the seeded bootstrap administrator role — the global, tenant-less platform-super-admin template role, which holds the complete set of ADMIN-scope permissions.
The administrator's token must therefore carry both of these claims:
| Claim | Required value | Purpose |
|---|---|---|
urn::alpine:tenantId |
urn:alpine:tenant:admin |
Selects the global (tenant-less) administrator authorization domain |
urn::alpine:roles |
a reference to the platform-super-admin role |
Resolves to the bootstrap admin role and its full ADMIN permission set |
The value in urn::alpine:roles is a JSON array of role references. Each reference is matched against the seeded role by template key (platform-super-admin), then role UUID (rol-…), then role name. Use the immutable template key platform-super-admin: it is stable across environments, unlike the generated UUID. Additional group/role references may appear in the same array.
Example administrator token claims (decoded):
{
"iss": "https://login.example.com/realms/alpine",
"aud": "alpine-admin",
"sub": "ops-admin",
"urn::alpine:tenantId": "urn:alpine:tenant:admin",
"urn::alpine:roles": ["platform-super-admin"]
}
At your identity provider, map the bootstrap administrator so the issued token emits urn:alpine:tenant:admin in urn::alpine:tenantId and platform-super-admin in urn::alpine:roles (for example, via a group-to-claim mapping or a protocol/claim mapper).
A token without the bootstrap admin role is locked out
{{ product_name }} fails closed. A token whose urn::alpine:roles does not resolve to an ADMIN role — or that is missing the urn:alpine:tenant:admin tenant claim — still authenticates, but resolves to zero administrator grants, so every ADMIN operation is denied. Configure and verify this claim mapping at your IdP before relying on init, otherwise the first administrator can log in yet be unable to administer the platform.
Related¶
FAQ¶
Do I need to log in before running init?
No. init runs pre-OIDC and is gated by the shared HMAC HS256 secret, so it needs neither a host profile nor a profile authn login. It is the bootstrap step that makes later OIDC logins possible.
Where does the --init-secret value come from?
It must match alpine.services.alpine-admin.initialization.secret in the server alpine.conf. The CLI signs the admin-init request with this shared secret; omit the option to be prompted so it stays out of shell history.
Does init perform an interactive OIDC login?
No. init only registers the global administrator OIDC resource-server validation configuration (issuer, audience, and endpoint settings). The administrator logs in afterward with profile authn login.
What do I run after init succeeds?
Create a host profile with profile hosts create, then authenticate with profile authn login. All subsequent server-touching admin commands use that authenticated profile.
How does the first administrator actually get full access after init?
init only stores token-validation settings; it does not grant anything. The administrator's OIDC token must carry the tenant claim urn::alpine:tenantId = urn:alpine:tenant:admin and a urn::alpine:roles claim that resolves to the seeded global platform-super-admin role (matched by template key, UUID, or name). That bootstrap admin role holds the full ADMIN permission set. Without it, the caller authenticates but has zero admin grants and every ADMIN operation is denied.