release: bump version to 0.11.5
Replace interim FUTURE_WORK.md with slim STANDARDS.md and update doc links. Co-authored-by: Cursor <cursoragent@cursor.com>
This commit is contained in:
@@ -31,7 +31,7 @@ creating, grouping, pausing, running, and monitoring scheduled shell commands.
|
||||
- [Changelog](docs/CHANGELOG.md)
|
||||
- [Roadmap](docs/ROADMAP.md)
|
||||
- [Architecture](docs/ARCHITECTURE.md)
|
||||
- [Future Work](docs/FUTURE_WORK.md) — quality standard, maturity checklist, open polish
|
||||
- [Standards](docs/STANDARDS.md) — quality rules and intentional behavior
|
||||
- [Development](docs/DEVELOPMENT.md) — build instructions, project layout, dependencies
|
||||
|
||||
## Storage
|
||||
|
||||
@@ -156,8 +156,7 @@ counted but the timing is skipped.
|
||||
`JobRuntime.Logs` (per-run `RunRecord` entries shown in the History tab) is
|
||||
**session-only**: it is not written to `jobs.json` and is not rebuilt from
|
||||
`.log` files on startup. Log files on disk feed aggregate counters via
|
||||
`SeedStats` only. See [FUTURE_WORK.md](FUTURE_WORK.md) for the intentional
|
||||
trade-off.
|
||||
`SeedStats` only. See [STANDARDS.md](STANDARDS.md).
|
||||
|
||||
### Persisted global pause
|
||||
|
||||
|
||||
@@ -2,6 +2,18 @@
|
||||
|
||||
All notable GoSentry changes are recorded in this file.
|
||||
|
||||
## 0.11.5 - 2026-07-01
|
||||
|
||||
**Quality and documentation polish:**
|
||||
|
||||
- Replaced the interim `docs/FUTURE_WORK.md` with `docs/STANDARDS.md` — a slim,
|
||||
permanent reference for code-quality rules and intentional behavior.
|
||||
- `newMainView` now accepts an injected `*app.Service` for testability;
|
||||
`RunNow` errors are shown in a dialog instead of failing silently.
|
||||
- Empty job lists no longer panic when building the Jobs tab.
|
||||
- Added regression and helper tests for overlap/pause scheduling, UI history
|
||||
helpers, main-view smoke build, and Linux desktop integration.
|
||||
|
||||
## 0.11.4 - 2026-06-30
|
||||
|
||||
**Statistics:**
|
||||
|
||||
@@ -1,112 +0,0 @@
|
||||
# GoSentry — Future Work
|
||||
|
||||
> Временный документ: цель проекта, стандарт качества и открытые задачи.
|
||||
> После завершения шлифовки переименуем (например, в `STANDARDS.md`).
|
||||
|
||||
## Зачем этот документ
|
||||
|
||||
**Образцовый проект** — тот, на который можно сослаться как на эталон: архитектура
|
||||
понятна с первого прочтения, границы пакетов соблюдаются, намеренные компромиссы
|
||||
задокументированы, поведение воспроизводимо тестами, новый контрибьютор знает
|
||||
*как* и *почему* писать код здесь.
|
||||
|
||||
Оценки зрелости ниже — **зеркало**, не KPI. Поднимать балл ради балла не имеет
|
||||
смысла; имеет смысл закрывать пункты чеклиста.
|
||||
|
||||
## Базовая оценка (внутреннее ревью, 2026-06-29)
|
||||
|
||||
| Критерий | Оценка |
|
||||
|----------|--------|
|
||||
| Архитектура | 9/10 |
|
||||
| Сложность vs масштаб | 8/10 |
|
||||
| Качество кода | 8/10 |
|
||||
| Поддерживаемость | 8/10 |
|
||||
| Логические ошибки | 9/10 |
|
||||
|
||||
Ревью проводилось на **0.11.2**; исправления вошли в **0.11.3–0.11.4**.
|
||||
Текущая версия: `src/app/version.go`.
|
||||
|
||||
## Архитектурные сильные стороны
|
||||
|
||||
- Single-writer `app.Service` с явным locking contract
|
||||
- Разделение `domain.Job` (durable) и `domain.JobRuntime` (transient)
|
||||
- Event-driven UI без обратных вызовов в Fyne под lock
|
||||
- Portable storage от `os.Executable()`
|
||||
- Инъекция `runJob` и `scheduler.Clock` в тестах
|
||||
- Подробная документация (`ARCHITECTURE.md`, inline comments)
|
||||
|
||||
## Стандарт качества (обязателен для нового кода)
|
||||
|
||||
- Контракты пакетов — [ARCHITECTURE.md](ARCHITECTURE.md)
|
||||
- User-facing error → `dialog.ShowError` или History event, не silent `return`
|
||||
- Pure helpers → unit-тест в том же пакете
|
||||
- Фикс severity ≥ medium → regression-тест
|
||||
- Намеренное поведение → §«Намеренное поведение» ниже, не backlog-баг
|
||||
- UI view-конструкторы принимают `*app.Service`, не вызывают `app.Open()` внутри
|
||||
|
||||
## Чеклист зрелости
|
||||
|
||||
| # | Критерий | Статус |
|
||||
|---|----------|--------|
|
||||
| 1 | Контракты пакетов задокументированы и соблюдаются | ✓ |
|
||||
| 2 | Намеренные trade-off'ы явно записаны | ✓ |
|
||||
| 3 | Нет silent failures в user-facing путях | ✓ |
|
||||
| 4 | Pure logic вынесена и покрыта unit-тестами | ✓ |
|
||||
| 5 | Regression-тест на серьёзные фиксы ревью | ✓ |
|
||||
| 6 | DI на границе UI↔Service | ✓ |
|
||||
| 7 | Документация = код | ✓ |
|
||||
| 8 | Platform-код тестируется по одному образцу | ✓ |
|
||||
| 9 | Единый стиль ошибок в UI | ✓ |
|
||||
|
||||
## Намеренное поведение (не баги)
|
||||
|
||||
- `RunNow` разрешён при global pause и для disabled jobs
|
||||
- Sequential mode — FIFO по порядку в `jobs.json`
|
||||
- Scheduler tick 1s — sub-second `@every` не поддерживается
|
||||
- Command timeout 30s — глобальный лимит
|
||||
- **History tab — session-only.** `JobRuntime.Logs` живёт только в памяти
|
||||
текущей сессии. Файлы в `logs_dir` используются для aggregate stats
|
||||
(`SeedStats`), не для таблицы History. Подробнее — [ARCHITECTURE.md](ARCHITECTURE.md).
|
||||
|
||||
## Закрытые находки ревью (2026-06-29)
|
||||
|
||||
Историческая справка; не открывать повторно без новых данных.
|
||||
|
||||
| # | Проблема | Серьёзность | Статус |
|
||||
|---|----------|-------------|--------|
|
||||
| 1 | Data race: `store.Paths` в `executeRun` без lock | Высокая | Исправлено |
|
||||
| 2 | Run стартует при ошибке `SaveJobs` | Средняя | Исправлено |
|
||||
| 3 | CRUD эмитит events при failed save | Средняя | Исправлено |
|
||||
| 4 | Overlap queue — только один `Pending` | Средняя | Исправлено (`PendingRuns`) |
|
||||
| 5 | `time.Now()` vs scheduler clock в `startRunLocked` | Низкая | Исправлено |
|
||||
| 6 | Silent log write failures | Низкая | Исправлено |
|
||||
| 7 | Невалидный per-job `overlap_policy` | Низкая | Исправлено |
|
||||
| 8 | Docs drift (YAML, RunNow/pause) | Низкая | Исправлено |
|
||||
| 9 | `StartOnly` игнорировал cancel context | Низкая | Исправлено |
|
||||
| 10 | `SeedStats` коллизия sanitized имён | Низкая | Исправлено (match по `job_id`) |
|
||||
| 11 | `AvgDurationMS` seed vs live расходились | Низкая | Исправлено (`TimedRunCount`) |
|
||||
| 12 | Legacy ticket-ссылки в комментариях | Низкая | Исправлено |
|
||||
|
||||
## Вне scope (осознанные trade-off'ы)
|
||||
|
||||
| Item | Где зафиксировано |
|
||||
|------|-------------------|
|
||||
| History из `.log` | Session-only by design (§выше) |
|
||||
| Per-job command timeout | [ROADMAP.md](ROADMAP.md) |
|
||||
| Window size persistence | [ROADMAP.md](ROADMAP.md) (frozen) |
|
||||
| Column filters в History | [ROADMAP.md](ROADMAP.md) |
|
||||
| CI coverage gate | [ROADMAP.md](ROADMAP.md) (будущее) |
|
||||
|
||||
## Честно про 10/10
|
||||
|
||||
Единые **10/10** по всем критериям — неразумная цель для Fyne desktop: CGO,
|
||||
platform stubs и headless-лимиты GUI объективно добавляют сложность.
|
||||
**Образцовость ≠ идеальный балл.** Целевое состояние: чеклист зрелости ✓,
|
||||
проект как reference implementation layered Go desktop app.
|
||||
|
||||
## Связанные документы
|
||||
|
||||
- [ARCHITECTURE.md](ARCHITECTURE.md) — контракты пакетов
|
||||
- [TESTS.md](TESTS.md) — как и что тестировать
|
||||
- [ROADMAP.md](ROADMAP.md) — крупные фичи и platform blockers
|
||||
- [DEVELOPMENT.md](DEVELOPMENT.md) — сборка и layout
|
||||
@@ -0,0 +1,28 @@
|
||||
# GoSentry — Standards
|
||||
|
||||
Quality rules and intentional behavior for contributors. Package contracts live
|
||||
in [ARCHITECTURE.md](ARCHITECTURE.md); test conventions in [TESTS.md](TESTS.md).
|
||||
|
||||
## Code quality
|
||||
|
||||
- Follow package contracts in [ARCHITECTURE.md](ARCHITECTURE.md).
|
||||
- User-facing errors → `dialog.ShowError` or a History event, never a silent `return`.
|
||||
- Pure helpers → unit test in the same package.
|
||||
- Fixes with severity ≥ medium → regression test.
|
||||
- Documented intentional behavior → section below, not a backlog bug.
|
||||
- UI view constructors accept `*app.Service`; call `app.Open()` only from `run.go`.
|
||||
|
||||
## Intentional behavior (not bugs)
|
||||
|
||||
- `RunNow` is allowed during global pause and for disabled jobs.
|
||||
- Sequential mode runs jobs FIFO by order in `jobs.json`.
|
||||
- Scheduler tick is 1s — sub-second `@every` intervals are not supported.
|
||||
- Command timeout is 30s globally.
|
||||
- **History tab is session-only.** `JobRuntime.Logs` exists only in memory for the
|
||||
current process. Log files on disk feed aggregate statistics via `SeedStats`
|
||||
only. See [ARCHITECTURE.md](ARCHITECTURE.md).
|
||||
|
||||
## Out of scope
|
||||
|
||||
Larger or blocked work is tracked in [ROADMAP.md](ROADMAP.md) (per-job timeout,
|
||||
window size persistence, History column filters, CI coverage gate).
|
||||
+1
-1
@@ -412,5 +412,5 @@ Smoke test for main view construction with an injected `*app.Service`.
|
||||
## Remaining Test Coverage Gaps
|
||||
|
||||
- Full GUI E2E — tab navigation, dialog flows, and native file pickers are not exercised end-to-end
|
||||
- History is session-only by design — `.log` files seed aggregate stats only, not the History table (see [FUTURE_WORK.md](FUTURE_WORK.md))
|
||||
- History is session-only by design — `.log` files seed aggregate stats only, not the History table (see [STANDARDS.md](STANDARDS.md))
|
||||
- `layout.go` custom layouts — optional Fyne `test.NewApp()` coverage when CGO is available in CI
|
||||
|
||||
+1
-1
@@ -3,4 +3,4 @@ package app
|
||||
// Version is the application version shown in the GUI and used by build
|
||||
// scripts in artifact names. It is a var rather than a const so release builds
|
||||
// can override it with Go ldflags when CI tags a build.
|
||||
var Version = "0.11.4"
|
||||
var Version = "0.11.5"
|
||||
|
||||
Reference in New Issue
Block a user