3.0 KiB
3.0 KiB
Architecture
The portal is a Linux FastAPI app. It is the enrollment client. Apple devices only download a finished, signed configuration profile.
Flow
- OIDC. The browser is redirected to a generic OpenID Provider (Keycloak, Okta, Authentik, Entra ID, …). Authorization code + PKCE. A small user dict (
sub,username,email,name) is stored in a signed session cookie. Access tokens are not kept. - LDAP. Using the username claim (default
email, thenpreferred_username), the portal binds as a service account and searches Active Directory. It readsobjectSid,userPrincipalName, anddisplayName. An optional group gate usesLDAP_MATCHING_RULE_IN_CHAIN(nested membership). - Key + CSR (memory only). On Download, not at login, the portal generates RSA-2048 (configurable), and a CSR:
- Subject
CN=<UPN> - SAN otherName
1.3.6.1.4.1.311.20.2.3= UPN - SAN URI
tag:microsoft.com,2022-09-14:sid:<SID>(Microsoft strong mapping / KB5014754)
- Subject
- certsrv. NTLM POST to
/certsrv/certfnsh.aspwithCertificateTemplate:<name>. On issued, GET/certsrv/certnew.cer?ReqID=&Enc=b64. Pending or denied is an error; this portal does not wait for manager approval. - Identity PKCS#12. Private key + issued cert (+ optional CA) encrypted with a one-time password. Not written to disk.
- Unsigned plist. A
com.apple.security.pkcs12payload holds the identity P12 and that password. Optional CA payload ifPROFILE_CA_CERT_PATHis set. - Sign. The completed plist is wrapped in attached CMS (not detached), equivalent to
openssl smime -sign -nodetach -outform der, using the profile-signing PKCS#12. - HTTPS download.
Content-Type: application/x-apple-aspen-config.
The CA database requester is the portal NTLM account. The user is bound by SAN (UPN + SID URI), not by Windows impersonation. OIDC does not yield a Kerberos ticket for the end user, so there is no Enrollment Agent / on-behalf-of in this version.
Two PKCS#12 files
| File | Lifetime | Role |
|---|---|---|
| Identity P12 | One download, RAM only | Embedded in the profile as com.apple.security.pkcs12. User cert + private key. |
| Profile-signing P12 | Long-lived file on the server | CMS-signs the .mobileconfig. Must already be trusted on the device. |
Do not reuse the signing P12 as a user identity, and do not save identity P12s.
Why the phone never talks to the CA
SCEP/NDES would have the device generate a key and speak SCEP to NDES. This portal instead returns the cert and key inside the profile. After install, nothing on the phone needs certsrv or NDES reachability.
Code map
| Module | Responsibility |
|---|---|
auth_oidc.py |
OIDC client registration, claim → username |
directory.py |
LDAPS, objectSid decode, group gate |
enrollment.py |
RSA key, CSR SAN, PKCS#12 export |
certsrv.py |
NTLM submit/fetch, HTML disposition parser |
profile.py |
Unsigned plist + CMS sign |
issue.py |
Orchestrates one download |
app.py |
HTTP routes, session, templates |