Comments 11
У меня был такой же кейс, я его решил намного проще через StorageAccessFramework доступный вроде бы с 4.4 версии. Он даже разрешения на запись не требует и работает как обычный файлпикер в десктопах. Пользователь сам сможет выбрать папку и название файла.
https://developer.android.com/training/data-storage/shared/documents-files#create-file
Спасибо за совет. Обязательно посмотрю и проверю этот способ записи файлов.
там тоже не все гладко
On Android 11 (API level 30) and higher, you cannot use the ACTION_OPEN_DOCUMENT_TREE
intent action to request access to the following directories:
Для большей ясности о версиях Android можно посмотреть на следующий скриншот:
ух-ты, гугл наконец обновил эту картинку
![](https://habrastorage.org/getpro/habr/upload_files/240/7c9/dcf/2407c9dcf9798252c94b059c5e693f74.png)
Не примите за занудство, но пара советов по коду:
1. Потоки стоит закрывать в finally блоке, иначе привет утечка памяти и дескрипторов файлов. В Java есть удобный механизм try-with-resources. В котлине есть https://www.baeldung.com/kotlin/try-with-resources
2. Логирование ошибок лучше сделать централизовано через библиотеку логирования. Возможно для отслеживания ошибок прикрутить Sentry. Писать e.printStackTrace() уже давно моветон. И в принципе, ошибки стоит отлавливать на том уровне, где вы можете принять решение, что делать дальше - откатиться или показать ошибку пользователю.
3. Для поддержания чистой архитектуры тут напрашивается шаблон Мост. Выделить интерфейс для работы с папкой Download и для разных версий Андроид использовать свою реализацию этого интерфейса.
Спасибо, учту. Я еще новичок в мобильной разработке. Буду этот блок программы дорабатывать.
Что библиотека логирования? Можете дать ссылку? Почему "e.printStackTrace() " - моветон?
Можно вас также попросить подробнее пояснить про шаблон "Мост"?
https://refactoring.guru/ru/design-patterns/bridge
Но на мой взгляд самое лучшее описание именно в первоисточнике - Книга «Банды четырёх» "Шаблоны проектирования"
. Наверное ваше решение самое правильное, но есть и другой вариант, в манифест вписать
android:requestLegacyExternalStorage="true"
В 11 андройде так же все работает :
To help your app work more smoothly with third-party media libraries, Android 11 allows you to use APIs other than the MediaStore API to access media files from shared storage using direct file paths.
Android Studio. Kotlin. Сохранение файла в общедоступной папке Download