mirror of
https://github.com/jjbrunton/Sauci.git
synced 2026-10-31 18:19:43 +00:00
feat(mobile): finalize XPREM OTA config with real app id and certificate
Server registration is complete: app id 9a66f3c2-fda7-416f-87e2-6db833b32e9d, real code-signing certificate (public half), staging/production channels mapped server-side. Drops the app-id placeholder guard (cert guard stays) and re-includes certificate.pem past the root *.pem ignore rule, which had been silently excluding it. Co-Authored-By: Claude Fable 5 <noreply@anthropic.com>
This commit is contained in:
1 parent
0ada812294
commit
f37673cad7
4 files changed
+45
-35
No files matched your search
@@ -23,11 +23,10 @@ const OTA_SERVER_URL = 'https://ota.apps.jbrunton.co.uk';
|
||||
const OTA_MANIFEST_URL = `${OTA_SERVER_URL}/manifest`;
|
||||
|
||||
/**
|
||||
* XPREM application UUID, shown in the XPREM dashboard under App Info.
|
||||
* PLACEHOLDER until the update server deployment reports the real value.
|
||||
* XPREM application UUID for Sauci, shown in the XPREM dashboard under App
|
||||
* Info. Not a secret; overridable for pointing a build at another app.
|
||||
*/
|
||||
const OTA_APP_ID_PLACEHOLDER = 'REPLACE_WITH_XPREM_APP_ID';
|
||||
const OTA_APP_ID = process.env.XPREM_APP_ID || OTA_APP_ID_PLACEHOLDER;
|
||||
const OTA_APP_ID = process.env.XPREM_APP_ID || '9a66f3c2-fda7-416f-87e2-6db833b32e9d';
|
||||
|
||||
/** Public code-signing certificate downloaded from the XPREM dashboard. */
|
||||
const CODE_SIGNING_CERTIFICATE_PATH = './certs/certificate.pem';
|
||||
@@ -50,14 +49,6 @@ const releaseChannel = process.env.RELEASE_CHANNEL || 'development';
|
||||
const codeSigningDisabled = Boolean(process.env.DISABLE_CODE_SIGNING);
|
||||
|
||||
function assertUpdateConfigIsReal() {
|
||||
if (OTA_APP_ID === OTA_APP_ID_PLACEHOLDER) {
|
||||
throw new Error(
|
||||
`RELEASE_CHANNEL=${releaseChannel} requires a real XPREM app id. ` +
|
||||
'Set XPREM_APP_ID, or replace the placeholder in apps/mobile/app.config.js. ' +
|
||||
'See docs/mobile-ota.md.',
|
||||
);
|
||||
}
|
||||
|
||||
const certificatePath = path.join(__dirname, CODE_SIGNING_CERTIFICATE_PATH);
|
||||
const certificate = fs.existsSync(certificatePath)
|
||||
? fs.readFileSync(certificatePath, 'utf8')
|
||||
|
||||
@@ -1,3 +1,6 @@
|
||||
# The update-signing private key belongs to the XPREM server, never to the app.
|
||||
private-key.pem
|
||||
*.key
|
||||
# The public certificate must be committed despite the root *.pem rule: the
|
||||
# expo-updates plugin embeds it into every build.
|
||||
!certificate.pem
|
||||
@@ -0,0 +1,18 @@
|
||||
-----BEGIN CERTIFICATE-----
|
||||
MIICzTCCAbWgAwIBAgIJAPrPjxnUOGisMA0GCSqGSIb3DQEBCwUAMBAxDjAMBgNV
|
||||
BAMTBVNhdWNpMB4XDTI2MDgzMDE4MTAzMFoXDTM2MDgzMDE4MTAzMFowEDEOMAwG
|
||||
A1UEAxMFU2F1Y2kwggEiMA0GCSqGSIb3DQEBAQUAA4IBDwAwggEKAoIBAQDWiUac
|
||||
8i9bIbNZjv8iunVr6kqlgb9vea98JHz/A83biyszg0+GpmLYsr4zV2F7A6RitiIx
|
||||
SOML+wVedyD0F2quWccBGXinvMAds0TxgIOjQfP+8+VJ/duDjveHvn+OFW4s7XxW
|
||||
SY7TK1ufDcPWo/f5XzfqtBveug49zv3/F3MwfmMUbEY/zvH7nayPGJNuSyf3wISn
|
||||
JIt0BsHNhWykRXCzjaF2fy3nAebOyezbtbapCjUlxPENVtBCzBQ7C9kaQXCBw5mV
|
||||
hxhJlOxHWXpHJgDLHpev8A/CWQRh67tsevjKi6R6SDlf0R0xSbDJTElx8goWOOQW
|
||||
VO9aDqI+oH0KpWfnAgMBAAGjKjAoMA4GA1UdDwEB/wQEAwIHgDAWBgNVHSUBAf8E
|
||||
DDAKBggrBgEFBQcDAzANBgkqhkiG9w0BAQsFAAOCAQEAyUc20bIRCxoBTJg84mPl
|
||||
2nFDWSaAfzgo0K0b6x2T1suuq4LAOUgzBqJISrQAALd0besK1qUZSAMhjQu1wPZT
|
||||
MHuWRMxQHfOkyHMYUfOoPMS4bE+4K0WjzfoVt3y1A+oxhcIAQUUGyNgNmebfEN07
|
||||
JlX0B8UI8aIMjyfpsIDgZx1piHKwittGy/V4MPOLbmT2BBwS9BELcmWE4CwWbfeo
|
||||
JM4lXY0hk3M/GTstRYaUKiwBWEU+z1PdAmWAgrtxpVnXN+oaToWh0WbVkbF1K6r5
|
||||
3oBGFTL7kT+Wogg9GK04XoAREw0jZJ/k77oJx68lGVBNiB+Ue2KqX0H/0cf2CslY
|
||||
Ug==
|
||||
-----END CERTIFICATE-----
|
||||
+21
-23
@@ -12,8 +12,10 @@ already installed build.
|
||||
|
||||
## Status
|
||||
|
||||
The client is wired but not yet live. Two values from the server deployment are
|
||||
still outstanding; see [Pending server values](#pending-server-values).
|
||||
The client is wired with the real server values (app id
|
||||
`9a66f3c2-fda7-416f-87e2-6db833b32e9d` and the Sauci code-signing certificate,
|
||||
SHA-256 fingerprint beginning `DF:C9:17:A9`). What remains is the native
|
||||
prebuild and a store build; see [Server registration](#server-registration).
|
||||
|
||||
## How it works
|
||||
|
||||
@@ -96,9 +98,10 @@ branch surfing, it would strip the header from every poll for the life of the
|
||||
install.
|
||||
|
||||
`RELEASE_CHANNEL` is set per profile in `apps/mobile/eas.json`. The config throws
|
||||
a descriptive error whenever `RELEASE_CHANNEL` is set but the app id or the
|
||||
certificate is still a placeholder, so a misconfigured build fails at config
|
||||
resolution rather than shipping a client that can never validate a manifest.
|
||||
a descriptive error whenever `RELEASE_CHANNEL` is set but the committed
|
||||
certificate is missing or is the placeholder, so a misconfigured build fails at
|
||||
config resolution rather than shipping a client that can never validate a
|
||||
manifest.
|
||||
|
||||
### Local development
|
||||
|
||||
@@ -145,8 +148,8 @@ the request headers, the code-signing metadata, and the certificate contents int
|
||||
these files. Those values embed the real app id and certificate, so the native
|
||||
projects are deliberately left untouched until both land.
|
||||
|
||||
Once the pending values below are in place, regenerate and commit the native
|
||||
projects as a reviewed source change:
|
||||
With the real app id and certificate now committed, regenerate and commit the
|
||||
native projects as a reviewed source change:
|
||||
|
||||
```bash
|
||||
cd apps/mobile
|
||||
@@ -222,24 +225,19 @@ A bad update that prevents the app from starting cannot be fixed over the air on
|
||||
devices that never complete a launch. Keep `fallbackToCacheTimeout` short and
|
||||
treat a startup-path change as store-release risk, not OTA risk.
|
||||
|
||||
## Pending server values
|
||||
## Server registration
|
||||
|
||||
The client wiring is complete apart from two values owned by the XPREM server
|
||||
deployment. Both are non-secret.
|
||||
The Sauci app is registered on the XPREM server; the deployment itself is
|
||||
documented in the homelab repo (`unraid/docs/xprem-ota.md`).
|
||||
|
||||
| Value | Where it goes | How to obtain it |
|
||||
| --- | --- | --- |
|
||||
| XPREM app id (UUID) | `OTA_APP_ID_PLACEHOLDER` in `apps/mobile/app.config.js`, or the `XPREM_APP_ID` env var | XPREM dashboard, App Info page for the Sauci app |
|
||||
| Code-signing certificate (PEM) | Replace the whole of `apps/mobile/certs/certificate.pem` | XPREM dashboard App Info download, or `npx eoas generate-certs` |
|
||||
| Value | State |
|
||||
| --- | --- |
|
||||
| App id | `9a66f3c2-fda7-416f-87e2-6db833b32e9d`, hardcoded in `apps/mobile/app.config.js` (non-secret) |
|
||||
| Code-signing certificate | Committed at `apps/mobile/certs/certificate.pem` (public half; CN=Sauci, valid to 2036, SHA-256 fingerprint `DF:C9:17:A9:85:02:DD:EB:86:06:2B:64:8D:73:D2:8C:A2:AA:29:F0:AC:62:A8:76:62:A1:6B:A2:42:B0:3D:71`) |
|
||||
| Signing private key | Never leaves the server: keys mode `database`, sealed in the server's Postgres under its master key |
|
||||
| Publish token | `XPREM_SAUCI_API_KEY` in the homelab repo `.env`; export as `EOO_TOKEN` when publishing |
|
||||
| Channels | `staging` and `production` created server-side, mapped 1:1 to branches of the same names. `development` intentionally has no server channel — dev clients run with `DISABLE_CODE_SIGNING=1` against the packager |
|
||||
|
||||
Also required, outside this repository:
|
||||
|
||||
- An `EOO_TOKEN` publish token per environment, stored as a secret.
|
||||
- `development`, `staging`, and `production` channels created in the dashboard
|
||||
and mapped to branches of the same names.
|
||||
- The `private-key.pem` counterpart of the certificate installed in the server key
|
||||
store.
|
||||
|
||||
After both values land: replace them, run the prebuild described in
|
||||
Remaining before updates flow: run the prebuild described in
|
||||
[Native projects](#native-projects), commit the native diff, and cut a new store
|
||||
build. Only builds produced after that point can receive updates.
|
||||
Reference in new issue
Block a user