Skip to content

Commit 03400da

Browse files
committed
docs: tighten local-testing guide after review
- Correct the `rabbitmq.subscribed` log example; it actually includes the routing_key field. - Reuse a single STACK_TOKEN between the Cloudery mock and the trigger curl instead of minting it twice. - Capture the migration id from the trigger response into MIGRATION_ID and thread it into the CouchDB verify step, so the reader no longer has to hand-edit a placeholder. - Link the intro and the env-var list to the existing Development and Configuration docs to avoid content drift. - Note the mock ignores the request body the real Cloudery validates. - Note the CouchDB admin credentials are independent from RabbitMQ so the verify snippet does not look like a typo. - Document STACK_URL_SCHEME in Configuration so local-testing is not the only place it is described.
1 parent 29805d4 commit 03400da

2 files changed

Lines changed: 26 additions & 18 deletions

File tree

docs/configuration.md

Lines changed: 8 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -30,6 +30,14 @@ CLOUDERY_TOKEN="your-cloudery-api-token"
3030

3131
## Optional variables
3232

33+
### `STACK_URL_SCHEME`
34+
35+
URL scheme the consumer uses to reach the Cozy Stack, either `https` or `http`. Defaults to `https`, which is what production always wants. Set to `http` only for local development against a non-TLS Stack (for example `http://cozy.localhost:8080`). Any other value fails fast at startup.
36+
37+
```
38+
STACK_URL_SCHEME="https"
39+
```
40+
3341
### `LOG_LEVEL`
3442

3543
Controls log verbosity. Defaults to `info`.

docs/local-testing.md

Lines changed: 18 additions & 18 deletions
Original file line numberDiff line numberDiff line change
@@ -1,6 +1,6 @@
11
# Local end-to-end testing
22

3-
A step-by-step recipe for running the full migration flow on a single machine against a real Nextcloud, before the Cloudery is wired up. The unit tests in `test/` mock every network call; this guide is for the higher-confidence check that the service actually boots, consumes RabbitMQ messages, asks a Cloudery for a token, and drives the Stack through a real transfer.
3+
A step-by-step recipe for running the full migration flow on a single machine against a real Nextcloud, before the Cloudery is wired up. The [unit tests](development.md#testing) mock every network call; this guide is for the higher-confidence check that the service actually boots, consumes RabbitMQ messages, asks a Cloudery for a token, and drives the Stack through a real transfer. Environment variables referenced below are described in [Configuration](configuration.md).
44

55
## What you need
66

@@ -63,7 +63,7 @@ You should see `['migration']`.
6363

6464
## 3. Mock the Cloudery
6565

66-
The consumer fetches its Stack token from the Cloudery, which is not available locally. A tiny Node HTTP server that returns a pre-minted Stack token on every call is enough. Save this somewhere outside the repo, for example `/tmp/cloudery-mock.js`:
66+
The consumer fetches its Stack token from the Cloudery, which is not available locally. A tiny Node HTTP server that returns a pre-minted Stack token on every call is enough. Unlike the real Cloudery, this mock ignores the request body (the consumer still sends the expected `audience` and `scope` fields; the real endpoint validates them). Save this somewhere outside the repo, for example `/tmp/cloudery-mock.js`:
6767

6868
```js
6969
const http = require('http')
@@ -96,20 +96,20 @@ server.listen(PORT, '127.0.0.1', () => {
9696
})
9797
```
9898

99-
Mint a long-lived CLI token that covers every doctype the consumer touches, and save it to a file:
99+
Mint a long-lived CLI token that covers every doctype the consumer touches. The same token is used for the trigger curl in step 5, so keep it in a variable or a file:
100100

101101
```bash
102-
cozy-stack instances token-cli cozy.localhost:8080 \
102+
export STACK_TOKEN=$(cozy-stack instances token-cli cozy.localhost:8080 \
103103
io.cozy.nextcloud.migrations \
104104
io.cozy.remote.nextcloud.files \
105105
io.cozy.files \
106-
io.cozy.settings > /tmp/stack_token
106+
io.cozy.settings)
107107
```
108108

109-
Start the mock:
109+
Start the mock in a new shell, passing the token through:
110110

111111
```bash
112-
STACK_TOKEN=$(cat /tmp/stack_token) node /tmp/cloudery-mock.js
112+
STACK_TOKEN="$STACK_TOKEN" node /tmp/cloudery-mock.js
113113
```
114114

115115
## 4. Build and run the consumer
@@ -137,48 +137,48 @@ The consumer does not auto-load `.env`. Either pass the variables inline (as abo
137137
When it is up you should see:
138138

139139
```json
140-
{"event":"rabbitmq.subscribed","exchange":"migration","queue":"migration.nextcloud.commands"}
140+
{"event":"rabbitmq.subscribed","exchange":"migration","queue":"migration.nextcloud.commands","routing_key":"nextcloud.migration.requested"}
141141
```
142142

143143
## 5. Trigger a migration
144144

145-
Mint a token for the caller (the Settings UI's scope in production) and POST to the Stack. Replace the URL, login, and password with your real Nextcloud credentials:
145+
POST to the Stack using the same `STACK_TOKEN` from step 3. Its scope is a superset of what the trigger endpoint needs. Replace the URL, login, and password with your real Nextcloud credentials:
146146

147147
```bash
148-
TOKEN=$(cozy-stack instances token-cli cozy.localhost:8080 io.cozy.nextcloud.migrations)
149-
150-
curl -i -X POST http://cozy.localhost:8080/remote/nextcloud/migration \
151-
-H "Authorization: Bearer $TOKEN" \
148+
MIGRATION_ID=$(curl -s -X POST http://cozy.localhost:8080/remote/nextcloud/migration \
149+
-H "Authorization: Bearer $STACK_TOKEN" \
152150
-H "Content-Type: application/json" \
153151
-H "Accept: application/vnd.api+json" \
154152
-d '{
155153
"nextcloud_url": "https://your-nextcloud.example/",
156154
"nextcloud_login": "you@example.org",
157155
"nextcloud_app_password": "xxxxx-xxxxx-xxxxx-xxxxx-xxxxx",
158156
"source_path": "/"
159-
}'
157+
}' | python3 -c "import sys,json; print(json.load(sys.stdin)['data']['id'])")
158+
159+
echo "migration: $MIGRATION_ID"
160160
```
161161

162-
On success the Stack returns `201 Created` with the tracking document id. The consumer receives the RabbitMQ message within a second, calls the mock to get a Stack token, and starts walking the Nextcloud tree.
162+
On success the Stack returns `201 Created` with the tracking document id (captured above). The consumer receives the RabbitMQ message within a second, calls the mock to get a Stack token, and starts walking the Nextcloud tree.
163163

164164
## 6. Verify
165165

166-
Watch the consumer logs for `migration.started`, one `migration.file_transferred` per file, and a final `migration.completed`. The tracking document can also be read straight from CouchDB:
166+
Watch the consumer logs for `migration.started`, one `migration.file_transferred` per file, and a final `migration.completed`. The tracking document can also be read straight from CouchDB, using the `$MIGRATION_ID` captured in step 5. Replace `admin:password` with whatever admin credentials your local CouchDB was installed with; they are independent from the RabbitMQ ones:
167167

168168
```bash
169169
PFX=$(cozy-stack instances show cozy.localhost:8080 \
170170
| python3 -c "import sys,json; print(json.load(sys.stdin)['attributes']['prefix'])")
171171

172172
curl -s -u admin:password \
173-
"http://localhost:5984/${PFX}%2Fio-cozy-nextcloud-migrations/<migration_id>" \
173+
"http://localhost:5984/${PFX}%2Fio-cozy-nextcloud-migrations/${MIGRATION_ID}" \
174174
| python3 -m json.tool
175175
```
176176

177177
Migrated files land under `/Nextcloud/...` in the target Cozy. You can also browse them from the Drive app at `http://cozy.localhost:8080/`.
178178

179179
## Known gotchas
180180

181-
- **Stack CLI tokens do not expire** in cozy-stack's default configuration, so the mock can serve the same static token for an entire session. If you destroy and recreate the instance, re-mint the token and restart the mock.
181+
- **Stack CLI tokens are tied to the instance.** If you destroy and recreate `cozy.localhost:8080`, re-mint `STACK_TOKEN` and restart the mock; the previous token will be rejected by the new instance.
182182
- **The Stack probe failure message is generic.** If the Stack returns `401 nextcloud credentials are invalid` but you know the password is right, the Nextcloud OCS probe endpoint likely returned a non-200 for reasons other than auth. Recent stacks probe OCS Core (`/ocs/v2.php/cloud/user`), which cannot be disabled.
183183
- **Conflict handling is name-only.** If the target Cozy directory already contains a file with the same name as a Nextcloud file, the migration silently keeps the Cozy version, even when the bytes differ. To retry a clean migration, destroy the instance or delete the `/Nextcloud` tree in Drive before firing the next request.
184184
- **Stuck tracking documents.** Only one `pending` or `running` migration is allowed per instance. If the consumer crashes mid-run, mark the stuck doc as `failed` in CouchDB (edit the `status` field) before triggering again, otherwise you will get a `409 Conflict`.

0 commit comments

Comments
 (0)