diff --git a/Report/images/fig_01_start_sync.png b/Report/images/fig_01_start_sync.png index 8379fb5..f76d093 100644 Binary files a/Report/images/fig_01_start_sync.png and b/Report/images/fig_01_start_sync.png differ diff --git a/Report/images/fig_02_vault_lifecycle.png b/Report/images/fig_02_vault_lifecycle.png index 4419895..6a235ef 100644 Binary files a/Report/images/fig_02_vault_lifecycle.png and b/Report/images/fig_02_vault_lifecycle.png differ diff --git a/Report/images/fig_03_navigation_hub.png b/Report/images/fig_03_navigation_hub.png index 6059e0d..a058d2e 100644 Binary files a/Report/images/fig_03_navigation_hub.png and b/Report/images/fig_03_navigation_hub.png differ diff --git a/Report/images/fig_14_context_system.png b/Report/images/fig_14_context_system.png index 6c6dfd8..362cd51 100644 Binary files a/Report/images/fig_14_context_system.png and b/Report/images/fig_14_context_system.png differ diff --git a/Report/images/fig_15_bpmn_vault.png b/Report/images/fig_15_bpmn_vault.png index 763582f..4fd2f31 100644 Binary files a/Report/images/fig_15_bpmn_vault.png and b/Report/images/fig_15_bpmn_vault.png differ diff --git a/Report/images/fig_16_dfd_level0.png b/Report/images/fig_16_dfd_level0.png index d43a4e2..5c78132 100644 Binary files a/Report/images/fig_16_dfd_level0.png and b/Report/images/fig_16_dfd_level0.png differ diff --git a/Report/images/fig_17_use_case.png b/Report/images/fig_17_use_case.png index 8511889..7434e0e 100644 Binary files a/Report/images/fig_17_use_case.png and b/Report/images/fig_17_use_case.png differ diff --git a/Report/images/fig_18_deployment.png b/Report/images/fig_18_deployment.png index 08fae06..9818ecd 100644 Binary files a/Report/images/fig_18_deployment.png and b/Report/images/fig_18_deployment.png differ diff --git a/Report/images/fig_19_clean_architecture.png b/Report/images/fig_19_clean_architecture.png index c699f2e..dfb3b42 100644 Binary files a/Report/images/fig_19_clean_architecture.png and b/Report/images/fig_19_clean_architecture.png differ diff --git a/Report/images/fig_21_encrypt_flow.png b/Report/images/fig_21_encrypt_flow.png index f9069ae..c36a072 100644 Binary files a/Report/images/fig_21_encrypt_flow.png and b/Report/images/fig_21_encrypt_flow.png differ diff --git a/Report/images/fig_22_cjm_vault.png b/Report/images/fig_22_cjm_vault.png index 600b718..4582baa 100644 Binary files a/Report/images/fig_22_cjm_vault.png and b/Report/images/fig_22_cjm_vault.png differ diff --git a/Report/images/fig_35_sync_merge_algorithm.png b/Report/images/fig_35_sync_merge_algorithm.png index df1fd47..1f2df6a 100644 Binary files a/Report/images/fig_35_sync_merge_algorithm.png and b/Report/images/fig_35_sync_merge_algorithm.png differ diff --git a/Report/images/fig_36_ml_on_device.png b/Report/images/fig_36_ml_on_device.png index 1cb32c5..b1d897b 100644 Binary files a/Report/images/fig_36_ml_on_device.png and b/Report/images/fig_36_ml_on_device.png differ diff --git a/Report/puml/fig_01_start_sync.puml b/Report/puml/fig_01_start_sync.puml index ac3ace1..726a8d2 100644 --- a/Report/puml/fig_01_start_sync.puml +++ b/Report/puml/fig_01_start_sync.puml @@ -54,7 +54,8 @@ fork :StorageSyncEngine.syncAllGroups; while (Есть группа синхронизации?) is (да) :Слияние журналов → победитель по пути; - :findSourceStorage → applyEntry\nна отстающие Storage; + :findSourceStorage → applyEntry +на отстающие Storage; endwhile (нет) } end fork diff --git a/Report/puml/fig_02_vault_lifecycle.puml b/Report/puml/fig_02_vault_lifecycle.puml index 16a2252..cd61f35 100644 --- a/Report/puml/fig_02_vault_lifecycle.puml +++ b/Report/puml/fig_02_vault_lifecycle.puml @@ -13,9 +13,9 @@ skinparam state { skinparam noteBackgroundColor #E3F2FD skinparam noteBorderColor #1565C0 -state "(Б) Список storage\n(LocalVault или VaultBrowser)" as List +state "(Б) Список storage (LocalVault / VaultBrowser)" as List -List --> Create : Создать storage\n(FAB) +List --> Create : Создать storage (FAB) Create --> List : Storage создан List --> EncryptDlg : Включить шифрование storage @@ -36,7 +36,7 @@ OpenDlg --> Opened : Ключ верный OpenDlg --> List : Отмена / неверный ключ state Opened { - state "Файлы, секреты, 2FA\n(StorageHome)" as Browse + state "Файлы, секреты, 2FA (StorageHome)" as Browse } Opened --> List : Закрыть / заблокировать storage diff --git a/Report/puml/fig_03_navigation_hub.puml b/Report/puml/fig_03_navigation_hub.puml index b32c597..a61c610 100644 --- a/Report/puml/fig_03_navigation_hub.puml +++ b/Report/puml/fig_03_navigation_hub.puml @@ -14,7 +14,8 @@ skinparam noteBorderColor #C2185B start partition "**Main: нижняя навигация**" { - :(A) Вкладка LocalVault\n(один LocalVault на устройстве); + :(A) Вкладка LocalVault +(один LocalVault на устройстве); note right На экране — список **IStorage**, не список vault @@ -25,9 +26,11 @@ partition "**Main: нижняя навигация**" { backward:Назад с вложенного экрана; switch (Действие?) case (FAB) - :createStorage()\nновый **storage** в LocalVault; + :createStorage() +новый **storage** в LocalVault; case (Выбор storage) - :StorageHome:\nфайлы, 2FA, текстовые секреты; + :StorageHome: +файлы, 2FA, текстовые секреты; case (Вкладка «Удалённые vault») :Список **IVault** (Yandex по OAuth); if (Нужен OAuth?) then (да) diff --git a/Report/puml/fig_14_context_system.puml b/Report/puml/fig_14_context_system.puml index aa6b56d..d43b714 100644 --- a/Report/puml/fig_14_context_system.puml +++ b/Report/puml/fig_14_context_system.puml @@ -4,18 +4,27 @@ title Контекстная диаграмма Wallenc skinparam defaultFontName "DejaVu Sans" actor "Пользователь" as User -rectangle "Wallenc\n(Android)" as App { - component "UI\nCompose" as UI - component "Домен и\nкриптография" as Domain - component "Room\nметаданные" as Room +rectangle "Wallenc (Android)" as App { + component UI [ + UI + Compose + ] + component Domain [ + Домен и + криптография + ] + component Room [ + Room + метаданные + ] } -cloud "Внешний провайдер\n(Яндекс Диск API)" as Cloud +cloud "Внешний провайдер (Яндекс Диск API)" as Cloud -User --> UI : storage, vault,\nOAuth, файлы +User --> UI : storage, vault, OAuth, файлы UI --> Domain Domain --> Room -Domain --> Cloud : ciphertext,\nOAuth, метаданные API +Domain --> Cloud : ciphertext, OAuth, метаданные API note right of Cloud Сервер приложения diff --git a/Report/puml/fig_15_bpmn_vault.puml b/Report/puml/fig_15_bpmn_vault.puml index 76e0c59..06df5fd 100644 --- a/Report/puml/fig_15_bpmn_vault.puml +++ b/Report/puml/fig_15_bpmn_vault.puml @@ -8,7 +8,8 @@ skinparam activity { } start -:Создать **storage** в vault\n(createStorage); +:Создать **storage** в vault +(createStorage); note right Vault (IVault) не шифруется. Шифрование только у **storage** @@ -18,10 +19,13 @@ if (Включить шифрование storage?) then (да) :enableEncryption(storage); else (нет) endif -:openStorage(storage)\nпри необходимости; -:Работа с содержимым storage:\nфайлы, 2FA, секреты; +:openStorage(storage) +при необходимости; +:Работа с содержимым storage: +файлы, 2FA, секреты; if (Storage в группе синхронизации?) then (да) - :StorageSyncEngine\n(журнал ревизий); + :StorageSyncEngine +(журнал ревизий); else (нет) endif :closeStorage / блокировка; diff --git a/Report/puml/fig_16_dfd_level0.puml b/Report/puml/fig_16_dfd_level0.puml index 4ad09a0..92bc88a 100644 --- a/Report/puml/fig_16_dfd_level0.puml +++ b/Report/puml/fig_16_dfd_level0.puml @@ -4,19 +4,23 @@ title DFD уровень 0: Wallenc skinparam defaultFontName "DejaVu Sans" actor User -rectangle "Процесс 0\nWallenc" as P0 { +rectangle "Процесс 0 — Wallenc" as P0 { usecase "UI" as UI usecase "Домен" as Dom usecase "Крипто" as Crypto - usecase "Адаптеры\nхранилищ" as Store + usecase Store [ + Адаптеры + ---- + хранилищ + ] database "Room" as DB } cloud Provider -User --> UI : команды,\nфайлы +User --> UI : команды, файлы UI --> Dom -Dom --> Crypto : ключ,\nданные +Dom --> Crypto : ключ, данные Dom --> Store Dom --> DB : метаданные Store --> Provider : ciphertext diff --git a/Report/puml/fig_17_use_case.puml b/Report/puml/fig_17_use_case.puml index ffcb126..9075043 100644 --- a/Report/puml/fig_17_use_case.puml +++ b/Report/puml/fig_17_use_case.puml @@ -6,12 +6,36 @@ left to right direction actor "Пользователь" as User rectangle "Wallenc" { - usecase "Управление storage\n(локальный vault)" as UC1 - usecase "Шифрование\nи открытие storage" as UC2 - usecase "Работа с\nсодержимым" as UC3 - usecase "OAuth и\nудалённые vault" as UC4 - usecase "Синхронизация\nгрупп" as UC5 - usecase "Фоновые\nзадачи" as UC6 + usecase UC1 [ + Управление storage + ---- + локальный vault + ] + usecase UC2 [ + Шифрование + ---- + и открытие storage + ] + usecase UC3 [ + Работа с + ---- + содержимым + ] + usecase UC4 [ + OAuth и + ---- + удалённые vault + ] + usecase UC5 [ + Синхронизация + ---- + групп + ] + usecase UC6 [ + Фоновые + ---- + задачи + ] } User --> UC1 diff --git a/Report/puml/fig_18_deployment.puml b/Report/puml/fig_18_deployment.puml index f4a22bc..9c4846d 100644 --- a/Report/puml/fig_18_deployment.puml +++ b/Report/puml/fig_18_deployment.puml @@ -5,14 +5,22 @@ skinparam defaultFontName "DejaVu Sans" node "Устройство Android" { artifact "Wallenc.apk" as App - database "Room\n(SQLite)" as DB + database DB [ + Room + ---- + (SQLite) + ] } node "Облако провайдера" { - artifact "REST API\n(Яндекс Диск)" as API + artifact API [ + REST API + ---- + (Яндекс Диск) + ] } App --> DB -App --> API : HTTPS,\nOAuth 2.0 +App --> API : HTTPS, OAuth 2.0 @enduml diff --git a/Report/puml/fig_19_clean_architecture.puml b/Report/puml/fig_19_clean_architecture.puml index 74c6f07..720196b 100644 --- a/Report/puml/fig_19_clean_architecture.puml +++ b/Report/puml/fig_19_clean_architecture.puml @@ -18,7 +18,11 @@ package ":domain" as DOM { } package ":infrastructure-android" as INF { - [Room, OAuth,\nадаптеры] + component INF_BLOCK [ + Room, OAuth, + ---- + адаптеры + ] } package ":app" as APP { diff --git a/Report/puml/fig_21_encrypt_flow.puml b/Report/puml/fig_21_encrypt_flow.puml index df67291..c9e97cd 100644 --- a/Report/puml/fig_21_encrypt_flow.puml +++ b/Report/puml/fig_21_encrypt_flow.puml @@ -10,11 +10,14 @@ skinparam activity { start :Пользователь включает шифрование; :Сформировать EncryptKey; -:Encryptor: шифрование файлов\n**storage** (IStorageAccessor); -:storage.setEncInfo → Room\n(DbStorageMetaInfo); +:Encryptor: шифрование файлов +**storage** (IStorageAccessor); +:storage.setEncInfo → Room +(DbStorageMetaInfo); :checkKey(ключ); if (Ключ верный?) then (да) - :IUnlockManager.open(storage)\nвиртуальное представление; + :IUnlockManager.open(storage) +виртуальное представление; :Доступ к файлам storage; else (нет) :Ошибка, storage не открыт; diff --git a/Report/puml/fig_22_cjm_vault.puml b/Report/puml/fig_22_cjm_vault.puml index ec9255e..102c1eb 100644 --- a/Report/puml/fig_22_cjm_vault.puml +++ b/Report/puml/fig_22_cjm_vault.puml @@ -10,13 +10,13 @@ skinparam defaultFontName "DejaVu Sans" |Лояльность| |Действия| -|Понимает риск\nоблака| -|Создаёт storage,\nвключает шифрование storage| -|Открывает storage,\nработает с файлами| -|Синхронизирует storage\nбез передачи ключей| +|Понимает риск облака| +|Создаёт storage, включает шифрование storage| +|Открывает storage, работает с файлами| +|Синхронизирует storage без передачи ключей| |Ожидания| -|Данные не читаются\nпровайдером| +|Данные не читаются провайдером| |Простой ввод пароля| |Быстрый доступ| |Надёжная синхронизация| diff --git a/Report/puml/fig_35_sync_merge_algorithm.puml b/Report/puml/fig_35_sync_merge_algorithm.puml index 6a6d771..443822d 100644 --- a/Report/puml/fig_35_sync_merge_algorithm.puml +++ b/Report/puml/fig_35_sync_merge_algorithm.puml @@ -13,10 +13,12 @@ start :Группа Storage (≥ 2 UUID из DbStorageSyncGroup); :Захват блокировок sync (lease); -:Параллельно: flush + readSyncJournal\nдля каждого Storage; +:Параллельно: flush + readSyncJournal +для каждого Storage; partition "Слияние (StorageSyncJournalMerge)" { - :Для каждого пути — запись\nс максимальной ревизией; + :Для каждого пути — запись +с максимальной ревизией; note right compare: sequence → actorId → createdAt end note @@ -25,14 +27,18 @@ partition "Слияние (StorageSyncJournalMerge)" { while (Есть необработанный путь?) is (да) :winnerEntry = победитель по пути; :sourceStorage = findSourceStorage(winnerEntry); - if (operation == UPSERT\nи source == null?) then (да) + if (operation == UPSERT +и source == null?) then (да) :пропуск пути; else (нет) while (Есть target Storage?) is (да) if (ревизия target ≥ winner?) then (да) :пропуск target; else (нет) - :applyEntry:\nUPSERT — copy stream\nDELETE/TRASH — на target\n(recordSyncJournal = false); + :applyEntry: +UPSERT — copy stream +DELETE/TRASH — на target +(recordSyncJournal = false); endif endwhile (нет) endif diff --git a/Report/puml/fig_36_ml_on_device.puml b/Report/puml/fig_36_ml_on_device.puml index 6395855..ae5777c 100644 --- a/Report/puml/fig_36_ml_on_device.puml +++ b/Report/puml/fig_36_ml_on_device.puml @@ -7,24 +7,38 @@ skinparam componentStyle rectangle package "Приложение Wallenc" { [UI / use cases] as UI - [Метаданные:\nжурнал sync, имена,\nразмеры] as Meta - [TFLite / ML Kit\n(inference)] as ML - [Зашифрованные\nфайлы storage] as Enc + component Meta [ + Метаданные + ---- + журнал sync, имена, размеры + ] + component ML [ + TFLite / ML Kit + ---- + (inference) + ] + component Enc [ + Зашифрованные + ---- + файлы storage + ] } -cloud "Провайдер\n(недоверенный)" as Cloud { - [Зашифрованные\nобъекты] as Obj +cloud "Провайдер (недоверенный)" as Cloud { + [Зашифрованные объекты] as Obj } UI --> Meta : анализ -Meta --> ML : признаки\nбез plaintext -ML --> UI : решение /\nподсказка +Meta --> ML : признаки без plaintext +ML --> UI : решение / подсказка Enc --> Cloud : только ciphertext -Enc ..> ML : опционально\nлокальные эмбеддинги\nпосле decrypt на устройстве +Enc ..> ML : опционально: эмбеддинги после decrypt на устройстве note bottom of ML - Обучение: офлайн на размеченных\nсинтетических/агрегированных данных; - выгрузка содержимого storage\nна облако для train — не используется + Обучение: офлайн на размеченных + синтетических/агрегированных данных; + выгрузка содержимого storage + на облако для train — не используется end note @enduml