Files
email-assistant/openspec/changes/contacts-caldav-server/tasks.md
T

64 lines
4.8 KiB
Markdown
Raw Blame History

This file contains ambiguous Unicode characters
This file contains Unicode characters that might be confused with other characters. If you think that this is intentional, you can safely ignore this warning. Use the Escape button to reveal them.
# Tasks: CardDAV-сервер для синхронизации контактов
## 1. Адресная книга в Radicale
- [ ] 1.1 Создать адресную книгу «Контакты» на ФС:
`mkdir -p /opt/hermes/email-assistant/radicale/data/collections/collection-root/estorozhenko/Контакты`
и проверить, что Radicale видит её как addressbook:
`curl -u estorozhenko:$RADICALE_PASS -X PROPFIND -H 'Depth: 0' http://127.0.0.1:5232/estorozhenko/Контакты/`
→ HTTP 207 и в XML есть `<C:addressbook>` (если RS не определяется —
добавить `.Radicale.props` с addressbook и повторить).
- [ ] 1.2 Положить тестовую vCard (test.vcf) в коллекцию и проверить, что
она отдаётся: `curl ... /estorozhenko/Контакты/test.vcf` → 200 + vCard;
затем удалить тестовую карточку.
## 2. Синк в contacts_extractor.py
- [ ] 2.1 Рефакторинг: вынести генерацию vCard 4.0 из существующей
generate_vcard() в отдельную функцию `contact_to_vcard(contact) -> str`,
чтобы переиспользовать для CardDAV-карточек. Проверка: скрипт
запускается без ошибок, contacts.vcf генерируется как раньше.
- [ ] 2.2 Добавить функцию `sync_contacts_to_caldav(contacts_dir, base_url,
user, password, prune=False)`: читает contacts.json, строит карту
uid→(ETag, href) через PROPFIND Depth:1, PUT создаёт/обновляет vCard,
при `prune=True` DELETE удаляет лишние. Использовать urllib + Basic
Auth. Проверка: юнит-запуск с тестовым Radicale (см. 3.x).
- [ ] 2.3 CLI-флаги: `--sync-caldav`, `--prune-caldav`, `--caldav-url`,
`--caldav-user`, `--caldav-pass` (или env CALDAV_PASS). По умолчанию
синк выключен. Проверка: `python3 scripts/contacts_extractor.py --help`
показывает все флаги; без `--sync-caldav` поведение прежнее.
- [ ] 2.4 ETag-конфликты: при PUT с If-Match и ответе 412 — записать
`caldav-sync.log` (контакт, conflict) и продолжить. Проверка: ручной
тест — изменить vCard на сервере, запустить синк, увидеть conflict
в логе.
## 3. Сквозной тест sync
- [ ] 3.1 Запустить синк с реальной базой:
`python3 scripts/contacts_extractor.py --sync-caldav`
(или отдельный скрипт) → в Radicale появились карточки (счётчик
PROPFIND/cards): `curl ... PROPFIND Depth:1 /estorozhenko/Контакты/`
показывает N карточек ≈ количеству контактов в contacts.json с email.
- [ ] 3.2 Повторный запуск — количество карточек не растёт (идемпотентность).
- [ ] 3.3 Изменить контакт в contacts.json (добавить телефон) → повторный
синк обновляет карточку (TEL появился, ETag изменился).
- [ ] 3.4 `--prune-caldav`: удалить контакт из contacts.json → карточка
удалена с сервера.
## 4. Интеграция в cron и документация
- [ ] 4.1 Обновить `config/contacts-cron.sh`: добавить `--sync-caldav` и
подтянуть пароль из radicale/.env (env CALDAV_PASS). Проверка:
запуск cron-скрипта вручную синкает контакты без ошибок.
- [ ] 4.2 Обновить README/STATUS: раздел «CardDAV (контакты)» — как
подключить на Android (DAVx5, URL http://cal.nixg.ru:5232
или cal.nixg.ru, логин estorozhenko), порты, флаги синка.
- [ ] 4.3 `openspec validate contacts-caldav-server` → valid.
- [ ] 4.4 Git commit и push (gitea.nixg.ru/hermes/email-assistant).
## Verification
- [ ] V1: `curl -X PROPFIND -u estorozhenko:PASS http://127.0.0.1:5232/estorozhenko/Контакты/` → 207 + addressbook
- [ ] V2: после синка количество vCard в адресной книге == числу контактов с email в contacts.json
- [ ] V3: повторный синк → 0 новых карточек
- [ ] V4: `python3 scripts/contacts_extractor.py --sync-caldav` из cron-обёртки завершается кодом 0 и пишет caldav-sync.log