fix: save fails with 'App.Document' has no attribute 'Modified'; SSE reconnect loop #13

Closed
opened 2026-02-10 00:40:07 +00:00 by forbes · 0 comments
Owner

Bug 1: Save fails

Every Silo save prints:

Silo save failed: 'App.Document' object has no attribute 'Modified'

Root Cause: silo_origin.py:396 does doc.Modified = False where doc is an App.Document. The Modified property only exists on Gui.Document. App.Document has isModified() (read-only method) but no Modified attribute. The analogous code in silo_commands.py:910-912 does it correctly using gui_doc.Modified.

Bug 2: SSE reconnection loop — server-side investigation needed

After the SSE URL fix (PR #85), the client connects but the server immediately closes the connection:

Silo: SSE connected
Silo: SSE reconnecting (1/10): connection closed

What the client does

  1. GET {api_url}/events with Accept: text/event-stream + auth headers
  2. urlopen() succeeds (HTTP 200) — 'SSE connected' printed
  3. Iterates response lines — iterator immediately exhausts (server closes)
  4. Retries with exponential backoff up to 10 times

What to check on the server

  • Does GET /api/events return Content-Type: text/event-stream and hold the connection open?
  • Is a reverse proxy (nginx/caddy) buffering or timing out the stream?
    • nginx: needs proxy_buffering off and X-Accel-Buffering: no
    • proxy_read_timeout must be high enough
  • Test: curl -N -H 'Accept: text/event-stream' https://silo.kindred.internal/api/events
    • Should hang open and print events; if it returns immediately, server isn't streaming

Client config

  • URL: https://silo.kindred.internal/api/events
  • Timeout: 90s, Max retries: 10, Exponential backoff from 1s
## Bug 1: Save fails Every Silo save prints: ``` Silo save failed: 'App.Document' object has no attribute 'Modified' ``` **Root Cause:** `silo_origin.py:396` does `doc.Modified = False` where `doc` is an `App.Document`. The `Modified` property only exists on `Gui.Document`. `App.Document` has `isModified()` (read-only method) but no `Modified` attribute. The analogous code in `silo_commands.py:910-912` does it correctly using `gui_doc.Modified`. ## Bug 2: SSE reconnection loop — server-side investigation needed After the SSE URL fix (PR #85), the client connects but the server immediately closes the connection: ``` Silo: SSE connected Silo: SSE reconnecting (1/10): connection closed ``` ### What the client does 1. `GET {api_url}/events` with `Accept: text/event-stream` + auth headers 2. `urlopen()` succeeds (HTTP 200) — 'SSE connected' printed 3. Iterates response lines — iterator immediately exhausts (server closes) 4. Retries with exponential backoff up to 10 times ### What to check on the server - Does `GET /api/events` return `Content-Type: text/event-stream` and hold the connection open? - Is a reverse proxy (nginx/caddy) buffering or timing out the stream? - nginx: needs `proxy_buffering off` and `X-Accel-Buffering: no` - `proxy_read_timeout` must be high enough - Test: `curl -N -H 'Accept: text/event-stream' https://silo.kindred.internal/api/events` - Should hang open and print events; if it returns immediately, server isn't streaming ### Client config - URL: `https://silo.kindred.internal/api/events` - Timeout: 90s, Max retries: 10, Exponential backoff from 1s
Sign in to join this conversation.
1 Participants
Notifications
Due Date
No due date set.
Dependencies

No dependencies set.

Reference: kindred/silo-mod#13