Prepare ForgeFlow for public release
This commit is contained in:
@@ -212,8 +212,8 @@ and last exit code. See `STATUS_ENDPOINT.md`.
|
||||
|
||||
## v0.4 services
|
||||
|
||||
- `UpdateService` reads `package.json` at an exact Gitea branch SHA, downloads an
|
||||
authenticated archive and launches the rollback-capable Windows source updater.
|
||||
- `UpdateService` reports `package.json` at an exact Gitea branch SHA, refuses
|
||||
unsigned source replacement and applies only publisher-signed packaged updates.
|
||||
- `SshService` provides pinned-host SSH execution with encrypted password or
|
||||
private-key passphrase storage.
|
||||
- `UnraidDeploymentService` inspects existing application folders and performs
|
||||
|
||||
@@ -0,0 +1,63 @@
|
||||
# Deployment migration example
|
||||
|
||||
This example shows how to bring an existing Git-backed Docker or Unraid application under ForgeFlow control without exposing or overwriting runtime data.
|
||||
|
||||
Use synthetic names and values while testing. Replace them with your own repository, server and paths only in ForgeFlow's local configuration; do not commit credentials or environment-specific diagnostics.
|
||||
|
||||
## 1. Establish the authoritative repository
|
||||
|
||||
Before deploying, verify that the server checkout and Gitea repository represent the same application:
|
||||
|
||||
- compare the complete 40-character commit SHA;
|
||||
- confirm the configured remote belongs to the intended Gitea origin and repository;
|
||||
- preserve the root `.git` directory for exact-SHA verification and rollback;
|
||||
- resolve any remote URL mismatch explicitly instead of silently rewriting it.
|
||||
|
||||
ForgeFlow blocks deployment when the existing origin conflicts with the selected repository unless the user explicitly approves alignment.
|
||||
|
||||
## 2. Protect runtime data
|
||||
|
||||
Typical persistent paths include:
|
||||
|
||||
```text
|
||||
.env
|
||||
appdata/
|
||||
config/
|
||||
data/
|
||||
logs/
|
||||
compose.override.yml
|
||||
```
|
||||
|
||||
Keep those paths outside the tracked deployment payload and add runtime-only directories to `.dockerignore` when they are not build inputs. ForgeFlow uses a controlled Git reset without `git clean`, but the repository's own Compose and ignore rules remain authoritative.
|
||||
|
||||
## 3. Reuse the maintained Compose definition
|
||||
|
||||
Prefer the repository's existing `compose.yml` or `docker-compose.yml` when it already defines ports, volumes, device mappings, labels and health checks. These application-specific settings should be reviewed and versioned with the application rather than regenerated during deployment.
|
||||
|
||||
## 4. Handle nested repositories separately
|
||||
|
||||
A historical checkout such as `source/` may contain another `.git` directory. Treat this as a migration warning:
|
||||
|
||||
1. verify that the root Compose file builds from the intended root;
|
||||
2. back up the application folder;
|
||||
3. stop modifying the nested checkout;
|
||||
4. rename it temporarily;
|
||||
5. rebuild and verify the application from the root checkout;
|
||||
6. remove the legacy copy only after rollback has also been tested.
|
||||
|
||||
ForgeFlow reports nested repositories but does not delete them automatically.
|
||||
|
||||
## 5. Recommended profile
|
||||
|
||||
```text
|
||||
Provider: SSH / Unraid
|
||||
Server folder: example-app
|
||||
Branch: main
|
||||
Compose mode: Repository/server Compose
|
||||
Compose file: compose.yml
|
||||
Clone URL: a Git URL reachable from the server
|
||||
Healthcheck: the application's existing health endpoint
|
||||
Preserve paths: .env, appdata, config, data, logs, compose.override.yml
|
||||
```
|
||||
|
||||
Complete a preflight first, deploy one exact commit, verify both the live SHA and runtime health, and test rollback before treating the migration as production-ready.
|
||||
@@ -1,147 +0,0 @@
|
||||
# LumaOps server versus Gitea audit
|
||||
|
||||
This audit compares the supplied `lumaops_server.zip` and `LumaOps_gitea.zip`.
|
||||
|
||||
## Main result
|
||||
|
||||
The main Unraid working tree and the supplied Gitea checkout point to exactly the same commit:
|
||||
|
||||
```text
|
||||
d42d4a7f08240c478d07466e3fabec654dc71367
|
||||
```
|
||||
|
||||
Latest subject:
|
||||
|
||||
```text
|
||||
Preserve colors across Aura zone updates
|
||||
```
|
||||
|
||||
There is therefore no source-version drift at the root of the live LumaOps folder.
|
||||
|
||||
## Root Git repository
|
||||
|
||||
The root `.git` directory should remain in place. It enables:
|
||||
|
||||
- exact-SHA verification;
|
||||
- controlled fetch and reset;
|
||||
- a reliable previous-version reference;
|
||||
- rollback without copying a second complete source tree.
|
||||
|
||||
The archived server copy showed one root status difference for `scripts/unraid-hardware-setup.sh`: file mode `100755 → 100644`. This is consistent with Unix executable bits being lost during ZIP handling. The file content did not differ. Check the executable bit directly on Unraid before deployment.
|
||||
|
||||
|
||||
## Origin URL mismatch to resolve
|
||||
|
||||
The supplied server root uses:
|
||||
|
||||
```text
|
||||
ssh://git@127.0.0.1:222/NuklearRabbit/LumaOps.git
|
||||
```
|
||||
|
||||
The supplied Gitea checkout uses:
|
||||
|
||||
```text
|
||||
https://gitea.itworx.tech/Jens/LumaOps.git
|
||||
```
|
||||
|
||||
Although both archives currently point to the same commit, these are different
|
||||
repository paths. Before the first ForgeFlow deployment, choose the server-
|
||||
reachable URL for the authoritative `Jens/LumaOps` repository, for example an
|
||||
SSH URL through `127.0.0.1:222` when Gitea runs on the same Unraid host.
|
||||
|
||||
ForgeFlow 0.4 detects this mismatch. Deployment is blocked unless the profile
|
||||
matches the existing origin or **Align an existing server origin to this URL**
|
||||
is explicitly enabled.
|
||||
|
||||
## Runtime and persistent paths
|
||||
|
||||
The server copy contains runtime data that must not be replaced by source updates:
|
||||
|
||||
- `appdata/`
|
||||
- `data/`
|
||||
- `logs/`
|
||||
- `.env` and application-specific configuration
|
||||
|
||||
The repository `.gitignore` already excludes the principal runtime paths. ForgeFlow's SSH strategy uses Git reset without `git clean`, so untracked persistent data remains in place.
|
||||
|
||||
## Compose and Unraid integration
|
||||
|
||||
The root `docker-compose.yml` is already suitable as the authoritative deployment definition. It includes:
|
||||
|
||||
- build context at the project root;
|
||||
- container name `lumaops`;
|
||||
- the Unraid `dockerman` label;
|
||||
- a Web UI label;
|
||||
- an Unraid icon label;
|
||||
- `${WEB_PORT:-1223}:${APP_PORT:-8080}`;
|
||||
- persistent relative volumes;
|
||||
- USB, HID and I²C devices;
|
||||
- a healthcheck.
|
||||
|
||||
ForgeFlow should use this existing Compose file rather than generate a replacement. Ports and complex device mappings belong in the repository's maintained Compose definition.
|
||||
|
||||
The supplied `.dockerignore` already excludes `.git`, so keeping the root Git
|
||||
working tree does **not** copy Git history into the Docker build context. It does
|
||||
not yet explicitly exclude the existing runtime/legacy folders `appdata/`,
|
||||
`data/`, `logs/` and `source/`. Before the first production rebuild, add the
|
||||
paths that are not build inputs:
|
||||
|
||||
```text
|
||||
appdata/
|
||||
data/
|
||||
logs/
|
||||
source/
|
||||
.forgeflow/
|
||||
```
|
||||
|
||||
ForgeFlow 0.4 detects existing preserved paths and nested Git repositories that
|
||||
are missing from `.dockerignore` and reports them as a preflight warning. The
|
||||
tool does not silently edit a source-controlled `.dockerignore`; the correction
|
||||
should be committed to Gitea so every deployment uses the same build context.
|
||||
|
||||
## Nested `source/` repository
|
||||
|
||||
The server archive also contains a nested Git working tree under:
|
||||
|
||||
```text
|
||||
source/
|
||||
```
|
||||
|
||||
Its HEAD is:
|
||||
|
||||
```text
|
||||
b746a52af1613f4291235f5e8165b8197a269a79
|
||||
```
|
||||
|
||||
It was ahead of its own upstream and included rebase metadata in the supplied archive. The root Compose file uses build context `.` and does not reference `source/`. This strongly indicates that `source/` is an abandoned or historical checkout rather than the active deployment source.
|
||||
|
||||
ForgeFlow reports this as a nested-repository warning and does not remove it automatically.
|
||||
|
||||
Recommended migration:
|
||||
|
||||
1. Back up `/mnt/user/appdata/lumaops`.
|
||||
2. Verify on Unraid that `docker compose config` uses the root project.
|
||||
3. Stop changing files in `source/`.
|
||||
4. Rename it temporarily to `source.legacy-backup`.
|
||||
5. Rebuild and test LumaOps from the root.
|
||||
6. Remove the legacy copy only after a successful validation period.
|
||||
|
||||
Do not delete the root `.git` directory. Also do not delete the nested `source/`
|
||||
directory as part of the first ForgeFlow test. Treat its cleanup as a separate,
|
||||
backed-up migration after the root deployment and rollback have both been
|
||||
validated.
|
||||
|
||||
## Recommended ForgeFlow profile
|
||||
|
||||
```text
|
||||
Provider: SSH / Unraid
|
||||
Server folder: lumaops
|
||||
Branch: main
|
||||
Compose mode: Repository/server Compose
|
||||
Compose file: docker-compose.yml
|
||||
Clone URL: the Git URL reachable from Unraid
|
||||
Healthcheck: the existing LumaOps health URL, when exposed
|
||||
Preserve paths: .env, appdata, data, logs, config, compose.override.yml
|
||||
```
|
||||
|
||||
No folder rename is required for LumaOps because `lumaops` already aligns with the repository name.
|
||||
@@ -48,9 +48,9 @@ Deployment profiles support:
|
||||
- runtime-data preservation;
|
||||
- rollback to the previous SHA.
|
||||
|
||||
## LumaOps audit
|
||||
## Deployment migration example
|
||||
|
||||
The supplied server and Gitea roots both match commit `d42d4a7f08240c478d07466e3fabec654dc71367`. The root Git checkout and Compose file should remain. A stale nested `source/` Git checkout is documented for controlled cleanup.
|
||||
The documented migration flow keeps the root Git checkout and maintained Compose file in place, verifies the complete commit SHA and treats a stale nested `source/` checkout as separate, controlled cleanup.
|
||||
|
||||
## Validation
|
||||
|
||||
|
||||
+5
-4
@@ -23,7 +23,7 @@ flexibility.
|
||||
- session-only fallback when OS encryption is unavailable;
|
||||
- token omitted from renderer-visible public state;
|
||||
- encrypted token blob excluded from diagnostic bundles;
|
||||
- blank settings token field preserves the existing token;
|
||||
- a blank settings token field preserves the existing token only when the normalized Gitea origin is unchanged;
|
||||
- atomic config replacement and restrictive permissions where supported;
|
||||
- service URLs reject embedded user credentials;
|
||||
- no token is required by setup/build scripts or documentation.
|
||||
@@ -128,9 +128,10 @@ included model uses:
|
||||
require the exact user-confirmed pinned fingerprint;
|
||||
- remote folders and Compose paths are validated against traversal;
|
||||
- tracked server-side changes block exact-SHA reset;
|
||||
- updater tokens are sent only to the configured Gitea origin;
|
||||
- updater tokens are sent only to the configured Gitea origin, and changing that origin requires a newly entered token;
|
||||
- non-loopback Gitea connections require HTTPS;
|
||||
- packaged updates require a publisher-signed Ed25519 manifest that binds the
|
||||
source commit, artifact identity, byte length and SHA-256 digest;
|
||||
- update archives are checksummed and validated by the full local quality gate;
|
||||
- source backup is restored when an update fails.
|
||||
- packaged update bytes are rehashed immediately before apply;
|
||||
- integrated source replacement is disabled until source archives carry the
|
||||
same independent publisher signature.
|
||||
|
||||
+9
-21
@@ -2,31 +2,19 @@
|
||||
|
||||
ForgeFlow stores credentials, repository mappings, preferences, deployment profiles, diagnostics and operation history outside the source directory.
|
||||
|
||||
## Built-in source update
|
||||
## Source checkouts
|
||||
|
||||
Open **Settings → ForgeFlow updates** and choose:
|
||||
Integrated source replacement is disabled until source archives are covered by the same independent publisher signature as packaged releases. A server-provided commit SHA and a checksum calculated from the downloaded archive do not independently authenticate its publisher, while dependency installation can execute package lifecycle scripts.
|
||||
|
||||
1. **Check now**
|
||||
2. **Download update**
|
||||
3. **Apply & restart**
|
||||
Update a source checkout through Git instead:
|
||||
|
||||
The default update source is the configured Gitea instance, repository `Jens/ForgeFlow`, branch `main`.
|
||||
1. fetch the configured upstream;
|
||||
2. review the exact commit and release notes;
|
||||
3. switch to the intended release commit or tag;
|
||||
4. run `npm ci --ignore-scripts` and review the dependency lifecycle allowlist;
|
||||
5. run `npm run check` before starting ForgeFlow.
|
||||
|
||||
The updater pins the download to the exact remote commit, checks the archive SHA-256, starts an external PowerShell helper and waits for a structured `started` marker. ForgeFlow closes only after that marker exists. The helper then:
|
||||
|
||||
1. waits for the old process to exit;
|
||||
2. backs up the current source;
|
||||
3. extracts and validates the requested semantic version;
|
||||
4. mirrors the incoming source;
|
||||
5. runs `npm ci --no-audit --no-fund` when the published release contains `package-lock.json`, otherwise a pinned direct-dependency `npm install`;
|
||||
6. runs `npm run check`;
|
||||
7. writes the successful installation result before restart;
|
||||
8. launches the installed Electron executable directly;
|
||||
9. persists `success`, `failed` or `rolled-back` state for the next launch.
|
||||
|
||||
A failed validation restores the previous source. A successful installation is not rolled back merely because automatic restart fails; start ForgeFlow manually and the persisted result is shown.
|
||||
|
||||
Update logs and status files are stored beneath ForgeFlow's local user-data `updates` folder and exclude the Gitea token.
|
||||
The in-app updater remains available for signed packaged Windows releases.
|
||||
|
||||
## Packaged Windows updates
|
||||
|
||||
|
||||
Reference in New Issue
Block a user