356 lines
13 KiB
Markdown
356 lines
13 KiB
Markdown
# Changelog
|
||
|
||
All notable changes to this project will be documented in this file.
|
||
|
||
The format is based on [Keep a Changelog](https://keepachangelog.com/en/1.0.0/),
|
||
and this project adheres to [Semantic Versioning](https://semver.org/spec/v2.0.0.html).
|
||
|
||
## Versioning Policy
|
||
|
||
This project follows Semantic Versioning (SemVer).
|
||
Breaking changes (removed tools, changed parameters) increment the major version.
|
||
|
||
## [1.4.2] – 2026-04-18
|
||
|
||
### Fixed
|
||
- **`get_tasks` support for secondary circles** — lists in non-primary circles now return tasks correctly
|
||
- Circle is automatically derived from `list_id` format (`taskList/<circleNum>_<listNum>`)
|
||
- Scope parameter passed to `accgetallfamily` call; matches `get_lists` pattern
|
||
- Docstring updated to clarify circle support and list_id format requirement
|
||
|
||
### Notes
|
||
- `_accgetallfamily()` now accepts optional `scope` parameter for secondary circle support
|
||
- No breaking changes; all existing code remains compatible
|
||
|
||
## [1.4.1] – 2026-04-17
|
||
|
||
### Improved
|
||
- **Docstring enhancements** — clearer tool usage guidance for new Claude sessions:
|
||
- `get_wall_posts`: Added note that results include automatic activity entries (task updates, list changes)
|
||
- `get_activities`: Expanded description and added distinction from `get_wall_posts`
|
||
- `like_post`: Extended post_id examples to include `task/` and `taskList/` IDs from activities
|
||
- `get_recipe_categories`: Added usage notes (IDs for create/update, 5 free-tier categories, family-wide scope)
|
||
- `add_meal_note`: Clarified create-only behavior; to update, delete then recreate
|
||
- `clear_list`: Moved risk warning (default deletes all tasks) to opening line for visibility
|
||
- `create_recipe`: Verified IMPORTANT confirmation line present
|
||
|
||
### Notes
|
||
- No breaking changes; docstring improvements only
|
||
- All tools remain backward compatible
|
||
|
||
## [1.4.0] – 2026-04-17
|
||
|
||
### Added
|
||
- **Unit test suite** (`tests/test_unit.py`) — comprehensive tests for core modules
|
||
- `fw_client.py`: Error handling (top-level `ex`/`un`, nested `a00.un.un`/`a00.ex.ex`, successful responses)
|
||
- `recipes.py`: `ingredients_parsed` parser (newline handling, empty lines, headings, commas)
|
||
- `lists.py`: System list name translation (SYS-CAT-SHOPPINGLIST, SYS-CAT-TODOS, unknown names)
|
||
- `server.py`: `_validate_date()` (ISO YYYY-MM-DD validation, format errors)
|
||
- `server.py`: `_err()` helper (JSON response format, Unicode, special characters)
|
||
- All tests use `unittest.mock` (stdlib, no external dependencies)
|
||
- Tests run without API access; all HTTP calls are mocked
|
||
- Framework: pytest with asyncio support
|
||
|
||
### Notes
|
||
- Run tests: `uv run pytest tests/test_unit.py -v`
|
||
- No breaking changes; release is testing infrastructure only
|
||
|
||
## [1.3.1] – 2026-04-17
|
||
|
||
### Fixed
|
||
- **`add_comment` response parser**: corrected response structure from `a00.r.r` with `metaId`
|
||
to nested `a00.r.r.comment.commentId`; response now includes `"created": true` flag
|
||
- **`add_comment` error handling**: now returns error messages directly instead of warnings
|
||
|
||
### Added
|
||
- **`delete_wall_post`** — permanently delete a wall post using the `metadelete` endpoint
|
||
(identical to deleting tasks and recipes)
|
||
|
||
### Notes
|
||
- All wall post tools now complete CRUD operations (Create, Read, Update via like_post, Delete)
|
||
- Test post (wall/16282169_31146617) removed from production after verification
|
||
|
||
## [1.3.0] – 2026-04-17
|
||
|
||
### Added
|
||
- **Wall post reading**: `get_wall_posts` — retrieve recent wall posts with author, text,
|
||
creation date, like count, liked-by-me flag, and comment count
|
||
- **Wall post writing**: `create_wall_post` — publish a new status post to the wall
|
||
- **Comments**: `add_comment` — add a comment to a wall post or activity
|
||
- All three new wall post tools require user confirmation before calling
|
||
|
||
### Notes
|
||
- `get_wall_posts` supersedes the activity-listing functionality of `get_activities`
|
||
(which continues to exist for backward compatibility)
|
||
- `like_post` already supports both wall posts and activities; verified to work
|
||
with metaIds from both `get_wall_posts` and `get_activities`
|
||
- Post IDs are in the format `wall/<familyid>_<postid>`
|
||
|
||
## [1.2.0] – 2026-04-17
|
||
|
||
### Added
|
||
- **Unlike support** for `like_post`: passing `like=False` now removes a STAR reaction via
|
||
`add=$empty, remove.0=STAR` (array dot-notation). New optional `mood` parameter (default `"STAR"`).
|
||
- **Reminder write support** for `create_task` and `update_task`:
|
||
- `reminder_unit`: `"MINUTE"`, `"HOUR"`, or `"DAY"`
|
||
- `reminder_value`: non-negative integer (e.g. `30` for "30 minutes before")
|
||
- `clear_reminder` (update_task only): remove reminder
|
||
- The correct wire format uses **dot-notation** subfields
|
||
(`reminder.reminderUnit`, `reminder.reminderValue`, `reminder.reminderType`,
|
||
`reminder.localId`) — flat top-level keys, JSON-string, and bracket-notation
|
||
are silently ignored by the server.
|
||
|
||
### Fixed
|
||
- `update_task` docstring: removed the "reminders not supported" warning — the
|
||
v1.1.2 write format was flat, which the FiZ encoder silently drops; the
|
||
dot-notation variant works on both Free and Premium accounts.
|
||
|
||
### Investigation notes (2026-04-17)
|
||
- Verified via isolated fuzz test (fresh test task per variant): only dot-notation
|
||
succeeds; every other encoding is accepted with HTTP 200 and `lastAction: UPDATED`
|
||
but the reminder remains at default `{reminderType: NONE, reminderValue: 0}`.
|
||
- `reminder.localId` is optional.
|
||
- Partial block updates (e.g. only `reminder.reminderType=NONE`) return
|
||
`task reminder invalid` — the full inactive block must be sent to clear.
|
||
- Valid `reminderUnit` values: `MINUTE`, `HOUR`, `DAY`. `WEEK` is rejected by the
|
||
API enum decoder.
|
||
- Reminder + recurrency can be set in a single `taskupdate2` call without interference.
|
||
|
||
## [1.1.2] – 2026-04-17
|
||
|
||
### Fixed
|
||
- `update_task`: removed non-functional reminder write parameters (`reminder_unit`,
|
||
`reminder_value`, `clear_reminder`) — exhaustive FW_DEBUG testing (flat params,
|
||
JSON-string, PHP-bracket, all string values, with/without `localId`, alternative
|
||
endpoints) on both Free and Premium accounts confirmed that `taskupdate2` silently
|
||
ignores all reminder fields; historical SNOOZE reminders were set via the mobile
|
||
app's Service Worker which transforms requests in ways not reproducible via direct API
|
||
- `update_task`: docstring now explicitly states reminders are read-only
|
||
- SPEC.md: documented reminder write limitation with investigation findings
|
||
- CLAUDE.md: updated reminder row to reflect read-only status
|
||
|
||
### Investigation notes
|
||
- Tested formats: flat int params, flat string params, JSON-encoded string value,
|
||
PHP-bracket notation (`reminder[reminderUnit]=DAY`), no-`localId` variant
|
||
- Tested endpoints: `tasksetalert`, `taskalertput`, `taskreminderset`, `taskalert`,
|
||
`tasknotification` — all return `"The call X is not registered"`
|
||
- Verified on both test account (Free) and real account (Premium) — same result
|
||
- Recurrency write via flat params is confirmed working (separate from reminder)
|
||
|
||
---
|
||
|
||
## [1.1.1] – 2026-04-17
|
||
|
||
### Fixed
|
||
- `update_task`: recurrency and reminder fields now sent as flat top-level parameters
|
||
instead of nested objects — the FiZ `Ai()` encoder does not support nested objects;
|
||
`recurrencyDescriptor`/`reminder` keys are never sent, fields go directly to top level
|
||
(e.g. `recurrency=WEEKLY`, `reminderUnit=DAY` rather than `recurrencyDescriptor={...}`)
|
||
- SPEC.md and CLAUDE.md corrected to document the flat encoding
|
||
|
||
---
|
||
|
||
## [1.1.0] – 2026-04-17
|
||
|
||
### Added
|
||
- `update_task`: recurrency parameters (`recurrency`, `recurrency_interval`, `rrule`,
|
||
`clear_recurrency`) — set or remove task recurrence rules via `recurrencyDescriptor`
|
||
- `update_task`: reminder parameters (`reminder_unit`, `reminder_value`, `clear_reminder`)
|
||
— set or remove task reminders via `reminder`
|
||
- SPEC.md: documented `recurrencyDescriptor` and `reminder` fields for `taskupdate2`
|
||
(verified via JS-Bundle xb-Encoder / fc-Encoder)
|
||
|
||
---
|
||
|
||
## [1.0.1] – 2026-04-17
|
||
|
||
### Added
|
||
- IMPORTANT confirmation notes in docstrings for write operations (`toggle_task`, `like_post`)
|
||
- `[project.urls]` section in `pyproject.toml` with Gitea repository link
|
||
- Language note in CLAUDE.md explaining German/English split
|
||
- `tests/README.md` documentation for running integration tests
|
||
|
||
### Changed
|
||
- `.gitignore` patterns now recursive (test_*.py without leading slash)
|
||
- CLI help text updated (removed "(read-only)" qualifier)
|
||
- `clear_list()` now logs exception reasons for failed deletions
|
||
- `get_categories()` docstring clarifies custom vs. system category locale behavior
|
||
|
||
### Fixed
|
||
- Exception handling in `clear_list()` with detailed logging
|
||
|
||
---
|
||
|
||
## [1.0.0] – 2026-04-17
|
||
|
||
### Added
|
||
- `tests/` directory with integration tests (moved from root)
|
||
- `LICENSE` (MIT, Marcus van Elst)
|
||
- Date validation (ISO `YYYY-MM-DD`) for all meal-plan tools
|
||
- `_err()` helper — all tools now return `{"error": "..."}` JSON on failure
|
||
|
||
### Changed
|
||
- Version is now a single source of truth in `pyproject.toml`;
|
||
`__init__.py` reads it via `importlib.metadata`
|
||
- `create_server()` exported via `__all__` in `__init__.py`
|
||
- `clear_list` reports partial failures:
|
||
`{"deleted_count": N, "failed_count": M, "failed_ids": [...]}`
|
||
- All tool functions have explicit `-> str` return-type annotations
|
||
- Unified error format: every tool returns `{"error": "message"}` JSON
|
||
|
||
### Removed
|
||
- ~50 debug/probe artefact files (`probe_*.py`, `debug_*.py`, `*.txt` outputs)
|
||
|
||
---
|
||
|
||
## [0.11.x] – Meal Planner write access
|
||
|
||
### [0.11.8]
|
||
- Documented `isRecipe` flag behaviour in `get_recipe_box`
|
||
|
||
### [0.11.7]
|
||
- `get_recipe_box` — returns only real recipes (`isRecipe=true`)
|
||
- Parser fix: `ingredients_parsed` built from free-text, not the API list
|
||
|
||
### [0.11.6]
|
||
- `clear_list` — bulk-delete all tasks in a list within one session
|
||
|
||
### [0.11.5]
|
||
- `add_meal_note` — add note + serving count to a meal plan slot
|
||
|
||
### [0.11.4]
|
||
- `delete_meal_plan_entry` — delete `dish/` and `meal/` entries
|
||
|
||
### [0.11.3]
|
||
- `add_meal_to_meal_plan` — structured output (fixed `a00.r.r` array shape)
|
||
|
||
### [0.11.2]
|
||
- `add_meal_to_meal_plan` — add free-text meal entry
|
||
|
||
### [0.11.1]
|
||
- `add_recipe_to_meal_plan` — structured output after response verified
|
||
|
||
### [0.11.0]
|
||
- `add_recipe_to_meal_plan` — add recipe from recipe box to meal plan
|
||
|
||
---
|
||
|
||
## [0.10.x] – Meal Planner read access
|
||
|
||
### [0.10.3]
|
||
- `get_meal_plan` — `is_from_recipe_box` field via `recipeList[].isRecipe`
|
||
|
||
### [0.10.2]
|
||
- `get_meal_plan` — merges `mealList[]` (free-text notes + servings)
|
||
|
||
### [0.10.1]
|
||
- `get_meal_plan` — structured output after `mplistinterval` response verified
|
||
|
||
### [0.10.0]
|
||
- `get_meal_plan` — read-only, raw JSON (Premium feature)
|
||
|
||
---
|
||
|
||
## [0.9.x] – Task recurrency + reminders
|
||
|
||
### [0.9.1]
|
||
- Fix `reminder` mapping (`reminderUnit`/`reminderValue`; `value=0` is valid)
|
||
|
||
### [0.9.0]
|
||
- `get_tasks` returns `recurrency`, `recurrency_interval`, `rrule`, `reminder`
|
||
|
||
---
|
||
|
||
## [0.8.x] – Recipe categories + misc fixes
|
||
|
||
### [0.8.3]
|
||
- `OTHER` list type documented and supported; `FW_DEBUG=1` logs unknown task fields
|
||
|
||
### [0.8.2]
|
||
- `get_lists()` without scope returns all circles
|
||
|
||
### [0.8.1]
|
||
- Fix recipe category handling
|
||
|
||
### [0.8.0]
|
||
- `get_recipe_categories` — list available recipe categories
|
||
- `create_recipe` / `update_recipe` accept `category_ids`
|
||
|
||
---
|
||
|
||
## [0.7.x] – Circle management
|
||
|
||
### [0.7.5]
|
||
- Primary-circle guard in `update_circle` (`isFirstFamily` check)
|
||
|
||
### [0.7.4]
|
||
- `update_circle` — rename a circle
|
||
|
||
### [0.7.3]
|
||
- `update_list` — rename, change emoji/colour
|
||
|
||
### [0.7.2]
|
||
- `delete_circle`
|
||
|
||
### [0.7.1]
|
||
- `get_lists` scope fix; `create_list` with `circle_id`; `delete_list` scope
|
||
|
||
### [0.7.0]
|
||
- `create_circle`, `add_member_to_circle`
|
||
|
||
---
|
||
|
||
## [0.6.x] – Recipe box
|
||
|
||
### [0.6.1]
|
||
- `update_recipe` + fix newline handling in `create_recipe`
|
||
|
||
### [0.6.0]
|
||
- `get_recipes`, `get_recipe`, `create_recipe`, `delete_recipe`
|
||
|
||
---
|
||
|
||
## [0.5.x] – List management
|
||
|
||
### [0.5.3]
|
||
- Category auto-assign hint in `create_task` docstring
|
||
|
||
### [0.5.2]
|
||
- Quantity convention documented in `create_task` docstring
|
||
|
||
### [0.5.1]
|
||
- `emoji` + `color` in `get_lists` / `create_list`
|
||
|
||
### [0.5.0]
|
||
- `create_list`, `delete_list`
|
||
|
||
---
|
||
|
||
## [0.4.x] – Category management + task fields
|
||
|
||
- `create_category`, `delete_category`
|
||
- `create_task` / `update_task` support `due_date`, `assignee`, `list_id`
|
||
|
||
---
|
||
|
||
## [0.3.x] – Task write access
|
||
|
||
- `create_task`, `update_task`, `toggle_task`, `delete_task`
|
||
|
||
---
|
||
|
||
## [0.2.x] – Activity feed
|
||
|
||
- `get_activities`, `like_post`
|
||
|
||
---
|
||
|
||
## [0.1.0] – Initial release
|
||
|
||
- `get_circles`, `get_members`, `get_lists`, `get_tasks`, `get_categories`
|
||
- Session strategy: login → API calls → logout per tool invocation
|
||
- OS keyring credential storage
|
||
- MCP server via FastMCP
|
||
|
||
[1.0.0]: https://gitea.gecheckt.de/marcus/mcp-familywall/compare/v0.11.8...v1.0.0
|