Config policies (16 files): alert_routing, architecture_pressure, backlog, cost_weights, data_governance, incident_escalation, incident_intelligence, network_allowlist, nodes_registry, observability_sources, rbac_tools_matrix, release_gate, risk_attribution, risk_policy, slo_policy, tool_limits, tools_rollout Ops (22 files): Caddyfile, calendar compose, grafana voice dashboard, deployments/incidents logs, runbooks for alerts/audit/backlog/incidents/sofiia/voice, cron jobs, scripts (alert_triage, audit_cleanup, migrate_*, governance, schedule), task_registry, voice alerts/ha/latency/policy Docs (30+ files): HUMANIZED_STEPAN v2.7-v3 changelogs and runbooks, NODA1/NODA2 status and setup, audit index and traces, backlog, incident, supervisor, tools, voice, opencode, release, risk, aistalk, spacebot Made-with: Cursor
5.0 KiB
5.0 KiB
Humanized Stepan — CHANGELOG v2.8
Version: v2.8
Date: 2026-02-25
Базується на: v2.7.2 (PII-safe telemetry, recent_topics horizon, invariant tests)
Summary
- Multi-user farm model:
FarmProfileтепер зберігається під ключемfarm_profile:agromatrix:chat:{chat_id}— shared для всіх операторів в одному чаті. - UserProfile залишається per-user (
user_profile:agromatrix:{user_id}) — стиль, recent_topics, interaction_summary окремі для кожного. - Lazy migration: перший запит з
user_idавтоматично мігрує старий legacy-ключfarm_profile:agromatrix:{user_id}у новий chat-ключ (write-through, без ручного втручання). - Conflict policy: якщо chat-profile вже існує і відрізняється від legacy — не перезаписуємо; лише tlog
farm_profile_conflict. - FarmProfile v5: додані нові поля (
farm_name,field_ids,crop_ids,active_integrations,iot_sensors,alert_thresholds,seasonal_context). - Backward-compat:
load_farm_profile(chat_id)безuser_id— не крашить, повертає default.
Key features (деталі)
Нові fact-ключі
| Тип | Ключ | Scope |
|---|---|---|
| UserProfile | user_profile:agromatrix:{user_id} |
per-user (без змін) |
| FarmProfile (v2.8) | farm_profile:agromatrix:chat:{chat_id} |
per-chat (новий) |
| FarmProfile (legacy) | farm_profile:agromatrix:{user_id} |
deprecated, мігрується lazy |
Lazy Migration Flow
load_farm_profile(chat_id, user_id)
│
├── cache hit (chat-key)? → return
├── memory-service chat-key? → return + cache
├── memory-service legacy-key (user_id)?
│ ├── YES → copy to chat-key (write-through) + return migrated profile
│ │ tlog: farm_profile_migrated
│ └── NO → default farm_profile(chat_id)
Conflict Policy
При явній міграції через migrate_farm_profile_legacy_to_chat():
- Якщо chat-profile існує і суттєво відрізняється (crops/field_ids/region/season_state) → NOT overwritten
tlog: farm_profile_conflict reason=legacy_diff- Повертається існуючий chat-profile
Критерій суттєвої відмінності (_farm_profiles_differ): порівнює crops, field_ids, fields, region, season_state, active_integrations.
FarmProfile v5 — нові поля
{
"_version": 5,
"chat_id": "...",
"farm_name": null,
"field_ids": [],
"crop_ids": [],
"active_integrations": [],
"iot_sensors": [],
"alert_thresholds": {},
"seasonal_context": {},
"region": null,
"crops": [],
"fields": [],
"season_state": null
}
Backward Compatibility
| Аспект | Деталі |
|---|---|
load_farm_profile(chat_id) |
Без user_id — не крашить (legacy path пропускається) |
load_farm_profile(chat_id, user_id) |
Новий API; user_id потрібен тільки для lazy migration |
save_farm_profile(chat_id, profile) |
API без змін (тепер під chat-key автоматично) |
| Legacy ключ | Не видаляється, існує в memory-service до явного очищення |
_version FarmProfile |
1 → 5; non-breaking (нові поля, старі залишаються) |
Non-goals / not included
- Немає автоматичного merge при конфлікті.
- Немає видалення legacy ключів (тільки read-migrate).
- Немає зміни light/deep логіки, тональності, банків фраз.
- Немає нових ендпоінтів або інфра-змін.
Tests
Результат: 161/161 зелених (без регресій з v2.7.2)
| Файл | Нових тестів | Опис |
|---|---|---|
tests/test_stepan_v28_farm.py |
24 | Multi-user farm: ключі, міграція, конфлікт, acceptance |
# Тільки v2.8 farm тести
python3 -m pytest tests/test_stepan_v28_farm.py -v
# Всі Stepan тести
python3 -m pytest tests/test_stepan_v28_farm.py tests/test_stepan_telemetry.py \
tests/test_stepan_invariants.py tests/test_stepan_acceptance.py \
tests/test_stepan_light_reply.py tests/test_stepan_memory_followup.py -v
Rollback
git checkout HEAD~1 -- crews/agromatrix_crew/memory_manager.py \
crews/agromatrix_crew/run.py
docker compose -f docker-compose.node1.yml up -d --build dagi-gateway-node1
Після rollback до v2.7.x: farm_profile знову читатиметься зі старого legacy-ключа (якщо є в cache/memory-service). Новий chat-ключ залишиться в memory-service, але не буде використовуватись.