chore(openspec): archive add-phone-album-sync and sync main specs
Sync the deltas into phpne...
This commit is contained in:
@@ -0,0 +1,71 @@
|
||||
# Spec Delta
|
||||
|
||||
## MODIFIED Requirements
|
||||
|
||||
### Requirement: Список альбомов
|
||||
|
||||
Приложение SHALL показывать доступные пользователю альбомы одним смешанным списком:
|
||||
серверные альбомы, получаемые из API, а при отсутствии сети — из локального кэша, и
|
||||
альбомы устройства. Элементы SHALL различать источник. Связанная пара «альбом
|
||||
устройства → серверный альбом» SHALL отображаться одной карточкой альбома устройства
|
||||
с указателем связи и меткой режима; связанный серверный альбом SHALL NOT показываться
|
||||
в списке отдельной записью.
|
||||
|
||||
#### Scenario: Онлайн
|
||||
|
||||
- **WHEN** авторизованный пользователь открывает приложение
|
||||
- **THEN** отображается список альбомов с обложками или плейсхолдером
|
||||
|
||||
#### Scenario: Офлайн из кэша
|
||||
|
||||
- **WHEN** сеть недоступна, но кэш существует
|
||||
- **THEN** список альбомов отображается из кэша с признаком офлайн-режима
|
||||
|
||||
#### Scenario: Альбомы устройства
|
||||
|
||||
- **WHEN** у приложения есть доступ к медиа устройства
|
||||
- **THEN** в списке появляются альбомы устройства наряду с серверными и помечены источником
|
||||
|
||||
#### Scenario: Связанная пара
|
||||
|
||||
- **WHEN** альбом устройства синхронизируется с серверным альбомом
|
||||
- **THEN** в списке показывается одна карточка альбома устройства с указателем связи и меткой режима, а связанный серверный альбом отдельной записью не показывается
|
||||
|
||||
## ADDED Requirements
|
||||
|
||||
### Requirement: Экран альбома устройства и настройки синхронизации
|
||||
|
||||
Приложение SHALL открывать альбом устройства с сеткой медиа и SHALL предоставлять
|
||||
настройки синхронизации этого альбома по свайпу вправо. Настройки SHALL содержать
|
||||
только выбор режима синхронизации.
|
||||
|
||||
#### Scenario: Открытие альбома устройства
|
||||
|
||||
- **WHEN** пользователь выбирает альбом устройства в списке
|
||||
- **THEN** открывается сетка медиа этого альбома
|
||||
|
||||
#### Scenario: Настройки по свайпу
|
||||
|
||||
- **WHEN** пользователь свайпает вправо в открытом альбоме устройства
|
||||
- **THEN** открываются настройки синхронизации с выбором режима и только им
|
||||
|
||||
#### Scenario: Метка перенесённого элемента
|
||||
|
||||
- **WHEN** оригинал элемента разгружен на сервер в режиме переноса
|
||||
- **THEN** в сетке на элементе показывается значок облака
|
||||
|
||||
### Requirement: Доступ к альбомам устройства
|
||||
|
||||
Приложение SHALL запрашивать доступ к медиа устройства, нужный для перечисления
|
||||
альбомов и чтения файлов, и SHALL работать без него, не показывая альбомы
|
||||
устройства.
|
||||
|
||||
#### Scenario: Доступ предоставлен
|
||||
|
||||
- **WHEN** пользователь предоставляет доступ к медиа устройства
|
||||
- **THEN** приложение перечисляет альбомы устройства и их содержимое
|
||||
|
||||
#### Scenario: Доступ не предоставлен
|
||||
|
||||
- **WHEN** доступ к медиа устройства не предоставлен
|
||||
- **THEN** приложение продолжает работать с серверными альбомами и не показывает альбомы устройства
|
||||
+242
@@ -0,0 +1,242 @@
|
||||
# Spec Delta
|
||||
|
||||
## Purpose
|
||||
|
||||
Синхронизация альбома устройства с существующим серверным альбомом: режимы A/B/C,
|
||||
отслеживание изменений, идентичность и дедупликация, политика удалений, разгрузка
|
||||
места и провенанс разгруженных превью.
|
||||
|
||||
## ADDED Requirements
|
||||
|
||||
### Requirement: Режимы синхронизации альбома устройства
|
||||
|
||||
Альбом устройства SHALL иметь выбираемый режим синхронизации: выключена (A — только
|
||||
локально), копии оригиналов на сервере (B), перенос оригиналов на сервер (C). Пока
|
||||
режим A, приложение SHALL показывать альбом локально и SHALL NOT обращаться к
|
||||
серверу по этому альбому.
|
||||
|
||||
#### Scenario: Выключенная синхронизация
|
||||
|
||||
- **WHEN** у альбома устройства выбран режим A
|
||||
- **THEN** приложение показывает альбом из локальных файлов и не отправляет запросы на сервер по этому альбому
|
||||
|
||||
#### Scenario: Копии оригиналов
|
||||
|
||||
- **WHEN** у альбома устройства выбран режим B
|
||||
- **THEN** оригиналы остаются на устройстве, а их копии загружаются в целевой серверный альбом
|
||||
|
||||
#### Scenario: Перенос оригиналов
|
||||
|
||||
- **WHEN** у альбома устройства выбран режим C
|
||||
- **THEN** оригиналы загружаются на сервер, а на устройстве вместо них остаются превью
|
||||
|
||||
### Requirement: Выбор целевого серверного альбома
|
||||
|
||||
При включении синхронизации пользователь SHALL выбрать серверный альбом назначения —
|
||||
существующий или созданный на месте, с именем, предзаполненным именем альбома
|
||||
устройства. Несколько альбомов устройства SHALL иметь возможность указывать на один
|
||||
серверный альбом.
|
||||
|
||||
#### Scenario: Выбор цели
|
||||
|
||||
- **WHEN** пользователь включает синхронизацию альбома устройства
|
||||
- **THEN** приложение предлагает выбрать существующий серверный альбом или создать новый с предзаполненным именем и сохраняет выбор
|
||||
|
||||
#### Scenario: Несколько источников в одну цель
|
||||
|
||||
- **WHEN** два альбома устройства указывают на один серверный альбом
|
||||
- **THEN** оба синхронизируются в него, а связь каждого отражается отдельно
|
||||
|
||||
### Requirement: Отслеживание изменений на устройстве
|
||||
|
||||
Приложение SHALL отслеживать изменения содержимого синхронизируемого альбома
|
||||
устройства — добавление, удаление, переименование, перенос между альбомами и
|
||||
изменение содержимого — и SHALL хранить локальный индекс, позволяющий обнаружить
|
||||
удаления, произошедшие вне приложения.
|
||||
|
||||
#### Scenario: Добавление
|
||||
|
||||
- **WHEN** в альбоме устройства появляется новое медиа
|
||||
- **THEN** приложение фиксирует его как новое и ставит в очередь синхронизации
|
||||
|
||||
#### Scenario: Удаление вне приложения
|
||||
|
||||
- **WHEN** медиа удалено из альбома устройства другим приложением или системной галереей
|
||||
- **THEN** приложение обнаруживает отсутствие по локальному индексу
|
||||
|
||||
#### Scenario: Переименование и перенос
|
||||
|
||||
- **WHEN** медиа переименовано или перемещено между альбомами устройства
|
||||
- **THEN** приложение фиксирует изменение имени или принадлежности альбому
|
||||
|
||||
### Requirement: Синхронизация изменений с сервером
|
||||
|
||||
Для каждого отслеженного изменения приложение SHALL применить его к целевому
|
||||
серверному альбому: загрузить новое содержимое, переименовать и перенести через
|
||||
API, а изменение содержимого SHALL трактовать как новую загрузку с удалением
|
||||
устаревшей собственной загрузки.
|
||||
|
||||
#### Scenario: Новое содержимое
|
||||
|
||||
- **WHEN** в альбоме устройства появилось медиа, которого нет на сервере
|
||||
- **THEN** приложение загружает его в целевой серверный альбом
|
||||
|
||||
#### Scenario: Переименование доходит до сервера
|
||||
|
||||
- **WHEN** медиа переименовано на устройстве и уже синхронизировано
|
||||
- **THEN** приложение переименовывает соответствующее серверное фото
|
||||
|
||||
#### Scenario: Изменение содержимого
|
||||
|
||||
- **WHEN** содержимое медиа изменено на устройстве
|
||||
- **THEN** приложение загружает новую версию, а устаревшую собственную загрузку удаляет
|
||||
|
||||
### Requirement: Идентичность по контрольной сумме
|
||||
|
||||
Приложение SHALL сопоставлять локальный ассет с серверным фото по контрольной сумме
|
||||
содержимого и SHALL NOT повторно загружать содержимое, уже присутствующее на
|
||||
сервере.
|
||||
|
||||
#### Scenario: Повторная синхронизация
|
||||
|
||||
- **WHEN** синхронизация запускается повторно без изменений содержимого
|
||||
- **THEN** приложение не создаёт новых загрузок
|
||||
|
||||
#### Scenario: Уже загруженное содержимое
|
||||
|
||||
- **WHEN** содержимое ассета уже присутствует на сервере (в том числе загружено ранее)
|
||||
- **THEN** приложение связывает ассет с существующим серверным фото без загрузки
|
||||
|
||||
### Requirement: Удаление только собственных загрузок
|
||||
|
||||
При удалении содержимого на устройстве приложение SHALL удалять на сервере только
|
||||
фото, загруженные этим клиентом, и SHALL сохранять остальные фото целевого альбома,
|
||||
в том числе загруженные из других источников.
|
||||
|
||||
#### Scenario: Собственная загрузка
|
||||
|
||||
- **WHEN** удалено содержимое, которое загрузил этот клиент, и его контрольная сумма отсутствует во всех локальных альбомах, льющихся в этот серверный
|
||||
- **THEN** приложение удаляет соответствующее серверное фото
|
||||
|
||||
#### Scenario: Чужие фото
|
||||
|
||||
- **WHEN** в целевом серверном альбоме есть фото, загруженные из других источников
|
||||
- **THEN** приложение не удаляет их
|
||||
|
||||
### Requirement: Отражение серверных изменений на устройстве
|
||||
|
||||
Приложение SHALL отражать изменения целевого серверного альбома — новые фото,
|
||||
переименования, теги, подписи и удаления — в локальном представлении, SHALL NOT
|
||||
изменять или удалять оригиналы на устройстве.
|
||||
|
||||
#### Scenario: Новое с другого устройства
|
||||
|
||||
- **WHEN** другое устройство добавляет фото в целевой серверный альбом
|
||||
- **THEN** приложение показывает его в серверном представлении альбома
|
||||
|
||||
#### Scenario: Удалено на сервере
|
||||
|
||||
- **WHEN** серверное фото удалено на сервере
|
||||
- **THEN** приложение убирает его из локального представления, не трогая оригинал на устройстве
|
||||
|
||||
### Requirement: Разгрузка оригиналов в режиме переноса
|
||||
|
||||
В режиме C после успешной загрузки приложение SHALL автоматически заменять оригинал
|
||||
на устройстве превью, без отдельного действия на экране; видео SHALL заменяться
|
||||
постером-кадром. При включении режима C приложение SHALL запрашивать широкий доступ
|
||||
к файлам, чтобы замена выполнялась без системного диалога согласия.
|
||||
|
||||
#### Scenario: Разгрузка фото
|
||||
|
||||
- **WHEN** оригинал фото успешно загружен
|
||||
- **THEN** файл в галерее автоматически заменяется превью с сохранением даты съёмки и места в альбоме
|
||||
|
||||
#### Scenario: Разгрузка видео
|
||||
|
||||
- **WHEN** оригинал видео успешно загружен
|
||||
- **THEN** видео в галерее автоматически заменяется статичным постером-кадром, а элемент в приложении остаётся видео с оригиналом на сервере
|
||||
|
||||
#### Scenario: Доступ к файлам для разгрузки
|
||||
|
||||
- **WHEN** пользователь включает режим переноса
|
||||
- **THEN** приложение запрашивает широкий доступ к файлам, и разгрузка выполняется без системного диалога согласия
|
||||
|
||||
### Requirement: Провенанс разгруженных превью
|
||||
|
||||
Разгруженные превью и постеры видео SHALL содержать метаданные провенанса,
|
||||
достаточные для восстановления связи с серверным альбомом и принадлежности
|
||||
загрузок после переустановки приложения.
|
||||
|
||||
#### Scenario: Восстановление после переустановки
|
||||
|
||||
- **WHEN** приложение переустановлено или его данные очищены, а альбом устройства содержит разгруженные превью
|
||||
- **THEN** приложение восстанавливает связь с серверным альбомом и принадлежность своих загрузок из метаданных превью
|
||||
|
||||
#### Scenario: Метка утрачена
|
||||
|
||||
- **WHEN** метаданные провенанса недоступны (например, файл перезаписан сторонним редактором)
|
||||
- **THEN** элемент считается неопознанным, не удаляется и не загружается повторно
|
||||
|
||||
### Requirement: Возврат оригиналов и отвязка
|
||||
|
||||
При выходе из режима C приложение SHALL предложить вернуть оригиналы на устройство
|
||||
и SHALL предупредить, если пользователь отказывается. Отвязка альбома и выключение
|
||||
синхронизации SHALL NOT удалять фото с сервера.
|
||||
|
||||
#### Scenario: Возврат оригиналов
|
||||
|
||||
- **WHEN** пользователь выходит из режима C и соглашается вернуть оригиналы
|
||||
- **THEN** приложение возвращает оригиналы на устройство вместо превью
|
||||
|
||||
#### Scenario: Отказ от возврата
|
||||
|
||||
- **WHEN** пользователь выходит из режима C и отказывается возвращать оригиналы
|
||||
- **THEN** приложение предупреждает, что на устройстве останутся только превью
|
||||
|
||||
#### Scenario: Отвязка
|
||||
|
||||
- **WHEN** пользователь отвязывает альбом устройства от серверного
|
||||
- **THEN** фото на сервере сохраняются
|
||||
|
||||
#### Scenario: Выключение синхронизации
|
||||
|
||||
- **WHEN** пользователь выключает синхронизацию альбома устройства
|
||||
- **THEN** связь с серверным альбомом снимается, а фото на сервере сохраняются
|
||||
|
||||
### Requirement: Автоматическая фоновая синхронизация
|
||||
|
||||
Синхронизация SHALL выполняться автоматически: при открытом приложении — по
|
||||
событиям изменения, в фоне — периодически, с учётом ограничений сети, выбранных
|
||||
пользователем. В режиме C разгрузка оригиналов SHALL выполняться автоматически
|
||||
после успешной загрузки.
|
||||
|
||||
#### Scenario: Фоновая синхронизация
|
||||
|
||||
- **WHEN** приложение не открыто, а в альбоме устройства появились изменения
|
||||
- **THEN** синхронизация выполняется в фоне при ближайшей возможности
|
||||
|
||||
#### Scenario: Ограничение сети
|
||||
|
||||
- **WHEN** включено ограничение «только Wi-Fi», а доступна только сотовая сеть
|
||||
- **THEN** синхронизация не начинается до появления Wi-Fi
|
||||
|
||||
#### Scenario: Автоматическая разгрузка
|
||||
|
||||
- **WHEN** оригиналы загружены в режиме C
|
||||
- **THEN** замена оригиналов превью выполняется автоматически, без отдельного подтверждения
|
||||
|
||||
### Requirement: Локальные превью
|
||||
|
||||
Приложение SHALL генерировать превью на устройстве и хранить их локально; при
|
||||
просмотре элемента без локального оригинала приложение SHALL подгружать оригинал с
|
||||
сервера.
|
||||
|
||||
#### Scenario: Сетка из превью
|
||||
|
||||
- **WHEN** открыт альбом устройства
|
||||
- **THEN** сетка показывает локальные превью
|
||||
|
||||
#### Scenario: Просмотр без локального оригинала
|
||||
|
||||
- **WHEN** пользователь открывает элемент, чей оригинал разгружен на сервер
|
||||
- **THEN** приложение подгружает оригинал с сервера для полноэкранного просмотра
|
||||
@@ -0,0 +1,24 @@
|
||||
# Spec Delta
|
||||
|
||||
## ADDED Requirements
|
||||
|
||||
### Requirement: Контрольная сумма оригинала
|
||||
|
||||
Данные фото SHALL включать контрольную сумму содержимого оригинала, чтобы клиенты
|
||||
могли сопоставлять локальные файлы с серверными фото и избегать повторной загрузки.
|
||||
Контрольная сумма SHALL быть детерминированной для одного и того же содержимого.
|
||||
|
||||
#### Scenario: Выдача контрольной суммы
|
||||
|
||||
- **WHEN** клиент получает данные фото, у которого зарегистрирован объект-оригинал
|
||||
- **THEN** ответ содержит контрольную сумму оригинала
|
||||
|
||||
#### Scenario: Одинаковое содержимое
|
||||
|
||||
- **WHEN** два фото ссылаются на объекты с одинаковым содержимым
|
||||
- **THEN** их контрольные суммы совпадают
|
||||
|
||||
#### Scenario: Контрольная сумма доступна в списке
|
||||
|
||||
- **WHEN** клиент запрашивает список фото альбома
|
||||
- **THEN** контрольные суммы входят в данные полученных фото
|
||||
Reference in New Issue
Block a user