Skip to content

Releases: yurydemin/marchi

v0.10.0

Choose a tag to compare

@github-actions github-actions released this 01 Aug 23:32

Добавлено

  • Статистика срабатываний правил — match_count/last_matched_at накапливаются
    батчем в конце каждого прогона синхронизации (не по одной записи на письмо) и видны
    прямо в списке правил («Сработало N раз, последний раз: дата» / «Ещё ни разу»).
    Подключено ко всем трём движкам синхронизации (IMAP, Gmail API, MS Graph), у каждого —
    свои гарантии от повторного учёта одних и тех же совпадений при повторной
    синхронизации после сбоя: для IMAP агрегация безусловна (last_uid продвигается
    по каждому письму атомарно, повторный fetch того же UID невозможен); для Gmail API —
    запись статистики происходит вместе с курсором gmail_history_id, только если весь
    прогон завершился без ошибок (курсор один на весь ящик); для MS Graph — учёт идёт
    отдельно по каждой папке, только если синхронизация именно этой папки прошла успешно
    (у каждой папки свой собственный delta-курсор).
  • POST /api/v1/emails/bulk-delete и POST /api/v1/emails/bulk-folder — массовое
    удаление и перенос между папками для результатов поиска, плюс кнопки «Удалить
    выбранные»/«Переместить выбранные» в Archive UI (переиспользуют чекбоксы, уже
    существовавшие для восстановления). Перенос — только в рамках одного аккаунта (папка
    привязана к account_id); целевая папка ищется по имени и, если её ещё нет,
    создаётся с sync_enabled=false — новый метод FoldersRepo.GetOrCreateManual
    специально не переиспользует UpsertFolder, чтобы перенос в уже существующую,
    активно синхронизируемую папку не сбросил её last_uid и не заставил пересинковать
    её целиком. Перемещённому письму присваивается синтетический UID из отдельного
    диапазона (начиная с 4×10⁹), заведомо выше любого реального IMAP/Gmail/Graph UID, —
    это исключает коллизию с UID, который движок синхронизации назначит той же папке
    позже.
  • date_from/date_to у POST /api/v1/restore/bulk — восстановление всего аккаунта
    или папки теперь можно сузить диапазоном дат письма, не только полным объёмом; два
    новых поля даты в панели «Восстановить весь ящик»/«Восстановить эту папку» в
    Archive UI.
  • Мобильная адаптивная вёрстка Archive UI — результаты поиска на узких экранах (телефон,
    планшет в портретной ориентации) показываются карточками вместо таблицы, а не просто
    горизонтально скроллятся. Заодно исправлена не связанная напрямую, но обнаруженная
    при этой же проверке проблема: верхняя навигация (шапка сайта) не переносилась на
    новую строку на узких экранах и обрезала пункт «Настройки» — теперь переносится.

Исправлено

  • THIRD_PARTY_LICENSES.md — номера версий 17 зависимостей, обновившихся минорными
    Dependabot-патчами с момента последней генерации файла, приведены в соответствие с
    go.mod (классификация лицензий не менялась — только сами версии были устаревшими).
  • README.md и docs/USER_GUIDE.md дополнены описанием возможностей, добавленных за
    несколько предыдущих релизов, но так и не попавших в документацию: импорт
    mbox/Maildir/.eml, экспорт .zip/mbox, уведомления о сбоях (webhook/email),
    аудит-лог, dry-run правил, ручное удаление письма из архива, восстановление целого
    аккаунта/папки. Заодно убран устаревший пример с зафиксированной версией Docker-тега
    (:0.2.0) в пользу :latest.

Полный список изменений: v0.9.0...v0.10.0

v0.9.0

Choose a tag to compare

@github-actions github-actions released this 30 Jul 21:52

Добавлено

  • MS Graph-коннектор — альтернатива IMAP для Microsoft 365/Exchange Online-аккаунтов:
    синхронизация через нативный Microsoft Graph REST API вместо IMAP-протокола. В отличие
    от Gmail-коннектора, у Graph есть настоящие иерархические папки (Inbox, Sent Items,
    Drafts, вложенные пользовательские папки) — каждая синкается как отдельная папка в
    архиве, вложенные разворачиваются в имя вида Родитель/Потомок (тот же формат, что уже
    использует Marchi для IMAP-папок). Дельта-синхронизация — через Graph delta query,
    отдельным курсором на каждую папку (в отличие от единого курсора Gmail на весь ящик):
    первый запрос без токена сразу возвращает и полный список писем, и токен для будущих
    инкрементальных запросов — без отдельного шага вроде Gmail's предварительного снятия
    historyId. Правила архивации работают как обычно: archive_and_mark_read ставит
    isRead=true, archive_and_delete удаляет письмо (Graph переносит его в Deleted Items,
    не стирает). Создать такой аккаунт можно через POST /api/v1/accounts/oauth2 с
    "connector_type": "ms_graph" (нужен OAuth2-токен с scope
    https://graph.microsoft.com/Mail.ReadWrite, не тем же, что используется для IMAP) —
    отдельной формы в Web UI для этого пока нет, как и для Gmail API-коннектора.

Полный список изменений: v0.8.0...v0.9.0

v0.8.0

Choose a tag to compare

@github-actions github-actions released this 29 Jul 22:36

Добавлено

  • Gmail API-коннектор — альтернатива IMAP для Google-аккаунтов: синхронизация через
    нативный Gmail REST API вместо IMAP-протокола, с дельта-синхронизацией по Gmail
    History API (обычный полный обход применяется только на первом запуске или если
    курсор истории устарел). Вся почта (кроме Спама/Корзины) архивируется в единую папку
    «All Mail» — у Gmail нет папок в IMAP-смысле, только метки, а одно письмо может
    одновременно носить несколько меток. Правила архивации работают как обычно:
    archive_and_mark_read снимает метку UNREAD, archive_and_delete перемещает письмо
    в Корзину Gmail (обратимо 30 дней). Создать такой аккаунт можно через
    POST /api/v1/accounts/oauth2 с "connector_type": "gmail_api" (нужен OAuth2-токен
    с scope https://www.googleapis.com/auth/gmail.modify, не тем же, что используется
    для IMAP) — отдельной формы в Web UI для этого пока нет, добавление IMAP-аккаунтов
    через интерфейс не изменилось.

Исправлено

  • OAuth2 IMAP-аккаунты (Google/Microsoft через IMAP, не Gmail API-коннектор выше) не
    синхронизировались вообще: все реальные точки запуска синхронизации (планировщик,
    CLI marchi sync, обе версии «Проверить подключение» — JSON API и Web UI) безусловно
    расшифровывали IMAP-пароль, даже если у аккаунта его никогда не было (OAuth2-аккаунт
    хранит только токен). В результате попытка синхронизации падала на расшифровке до
    реального подключения — internal/account.Manager.ResolveIMAPAuth (резолвинг и, если
    нужно, обновление токена) существовал с Фазы 3, но фактически вызывался только из
    восстановления писем. Теперь все четыре места используют ResolveIMAPAuth, а
    internal/sync.SyncAccount принимает и пароль, и OAuth2 access token, передавая в
    IMAP-клиент то, что реально применимо к аккаунту.

Полный список изменений: v0.7.0...v0.8.0

v0.7.0

Choose a tag to compare

@github-actions github-actions released this 29 Jul 21:08

Добавлено

  • http.trusted_proxies — список IP/подсетей reverse-proxy, чьему X-Forwarded-For
    можно доверять (нужно для корректной работы прогрессивной блокировки /unlock и
    аудит-лога за nginx/Traefik). Подробности — docs/REVERSE_PROXY.md.
  • SECURITY.md — как сообщить об уязвимости.
  • Релизы теперь подписываются keyless-подписью (Sigstore/cosign через GitHub Actions
    OIDC) и сопровождаются SBOM (SPDX) для каждого архива.
  • Dependabot следит за обновлениями Go-модулей и GitHub Actions.
  • Новый раздел «Политика 0.x и совместимость» в USER_GUIDE.md
    что может меняться между минорными версиями, плюс измеренные ориентиры по скорости
    синхронизации/переиндексации и объёму архива на диске.

Изменено

  • Тест на устойчивость к падению (marchi sync, SIGKILL) теперь проверяет три разные
    точки обрыва (в начале/середине/ближе к концу синхронизации), а не одну.

Полный список изменений: v0.6.0...v0.7.0

v0.6.0

Choose a tag to compare

@github-actions github-actions released this 28 Jul 22:07

Добавлено

  • GET /healthz — всегда 200, пока жив процесс, независимо от того, разблокирован ли
    vault — для healthcheck'ов Docker/Kubernetes, которым не нужно перезапускать контейнер
    только из-за запертого vault.
  • Опциональная защита /metrics bearer-токеном (security.metrics_token в config.yaml
    или MARCHI_METRICS_TOKEN) — для тех, кто отдаёт метрики за пределы доверенной сети.
  • Прогрессивная блокировка /unlock после 10 неудачных попыток подряд (блок на
    15 минут) — отдельно от уже существующего общего ограничения по частоте запросов.
  • Аудит-лог: разблокировка через веб-сессию, восстановление писем, ручное удаление письма
    и создание/изменение/удаление правил архивации теперь записываются в новый раздел
    «Аудит-лог» в Settings — кто, когда и что сделал.
  • Экспорт писем в формате mbox (POST /api/v1/export с "format": "mbox") — рядом с уже
    существующим экспортом в .zip, для инструментов, читающих mbox напрямую.

Полный список изменений: v0.5.0...v0.6.0

v0.5.0

Choose a tag to compare

@github-actions github-actions released this 28 Jul 21:00

Добавлено

  • marchi import --type mbox|maildir|eml --path <path> --as-account <email> — импорт уже
    экспортированной почты (mbox-файл, папка Maildir или каталог .eml-файлов) в архив без
    живого IMAP-подключения. Аккаунт для импортированной почты создаётся автоматически.
    Повторный запуск с теми же аргументами безопасен — уже импортированные письма
    распознаются по Message-ID и пропускаются, так что можно как угодно часто дозаписывать
    новые письма в источник и повторно запускать импорт.

Полный список изменений: v0.4.0...v0.5.0

v0.4.0

Choose a tag to compare

@github-actions github-actions released this 28 Jul 01:23

Добавлено

  • Проверка правила архивации на уже заархивированных письмах до его сохранения («Проверить
    на архиве» в Rules UI, POST /api/v1/rules/dry-run) — показывает, сколько писем архива
    совпало бы с условием, и несколько примеров. Особенно полезно перед сохранением правила
    с действием «архивировать и удалить с сервера», где ошибка в условии необратима.
  • Восстановление сразу всего почтового ящика или отдельной папки целиком, без
    предварительного поиска и ручного выбора писем (Archive UI, POST /api/v1/restore/bulk).
    При восстановлении всего ящика структура папок сохраняется — под указанной корневой
    папкой на каждую исходную папку создаётся своя подпапка.

Полный список изменений: v0.3.0...v0.4.0

v0.3.0

Choose a tag to compare

@github-actions github-actions released this 27 Jul 05:38

Добавлено

  • Уведомления о сбоях: webhook (с опциональной HMAC-SHA256 подписью тела) и email через
    отдельный исходящий SMTP-relay. Срабатывают на сбой синхронизации, сбой retention,
    переполнение очереди S3-загрузки и нехватку места на диске; повторные уведомления
    одного типа не чаще раза в час. Настраивается в Settings — там же тестовая отправка по
    каждому каналу отдельно.

Полный список изменений: v0.2.0...v0.3.0

v0.2.0

Choose a tag to compare

@github-actions github-actions released this 26 Jul 17:43

Добавлено

  • marchi backup run <dest-dir> / marchi backup verify <dest-dir> — горячий бэкап базы
    данных (через SQLite Online Backup API, без остановки сервиса), Maildir и ключевого
    материала Master Key, с манифестом контрольных сумм SHA-256 и сверкой целостности.
    Раньше официальный способ бэкапа требовал полной остановки сервиса.
  • Docker-образ теперь публикуется в ghcr.io/yurydemin/marchi при каждом релизе (теги
    :{версия} и :latest) — раньше единственным способом получить образ была сборка из
    исходников. docker-compose.yml по умолчанию использует опубликованный образ.

Полный список изменений: v0.1.2...v0.2.0

v0.1.2

Choose a tag to compare

@github-actions github-actions released this 24 Jul 22:32

Исправлено

  • Восстановление письма из архива обратно в почтовый ящик с последующей синхронизацией
    больше не создаёт дубль в архиве. Причина: APPEND при восстановлении неизбежно
    присваивает письму новый UID, а синхронизация раньше ориентировалась только на UID —
    считала такое письмо новым и архивировала его повторно. Теперь перед архивацией
    проверяется, нет ли в рамках того же аккаунта уже заархивированного письма с таким же
    Message-ID.

Добавлено

  • В Archive UI и REST API (DELETE /api/v1/emails/{id}) появилось ручное удаление одного
    письма из архива — раньше единственным способом что-то удалить была автоматическая
    retention-политика по времени. Удаление каскадно чистит вложения, очередь S3-загрузки,
    историю восстановлений, локальный файл, объект в S3 и запись в поисковом индексе.

Полный список изменений: v0.1.1...v0.1.2