Trabalhar com o sistema de arquivos é a base de qualquer aplicativo móvel. Cada plataforma oferece seu próprio modelo de acesso: Sandbox no iOS isola os aplicativos em contêineres separados, enquanto o Scoped Storage no Android restringe o acesso direto ao armazenamento compartilhado. De acordo com Google Developer Documentation (2026), a introdução do Scoped Storage com Android 10 exigiu uma revisão completa da arquitetura de armazenamento de dados. Neste guia, abordaremos FileManager, MediaStore API, Storage Access Framework e DocumentProvider para ambas as plataformas.
Principais conclusões
O sistema de arquivos em aplicativos móveis é um conjunto de APIs, regras de segurança e restrições que definem como os dados são armazenados e acessados em dispositivos iOS e Android. Ao contrário dos sistemas operacionais de desktop, as plataformas móveis isolam cada aplicativo para proteger os dados do usuário contra leitura não autorizada por outros programas.
O iOS usa o modelo Sandbox, onde cada aplicativo existe em seu próprio contêiner com permissões estritamente limitadas. Antes da versão 10, o Android fornecia acesso total ao armazenamento externo, mas com a introdução do Scoped Storage, a abordagem se aproximou do iOS. A principal diferença é que o iOS isola completamente o sistema de arquivos, enquanto o Android oferece vários níveis de acesso: um diretório privado, MediaStore público e acesso temporário via SAF.
Os aplicativos móveis usam três tipos de armazenamento de dados. Armazenamento privado — um diretório acessível apenas ao aplicativo para arquivos internos e cache. Armazenamento compartilhado — arquivos de mídia via MediaStore (Android) ou Files App (iOS). Armazenamento na nuvem — iCloud Drive e Google Drive para sincronização entre dispositivos. Cada tipo tem seus próprios limites de tamanho, tempo de vida dos arquivos e condições de acesso.
| Tipo de armazenamento | iOS | Android |
|---|---|---|
| Privado | Documents, Library, Caches | getFilesDir(), getCacheDir() |
| Mídia compartilhada | PHPhotoLibrary via seletor | MediaStore API (ContentResolver) |
| Documentos compartilhados | Files App via UIDocumentPicker | Storage Access Framework (SAF) |
| Nuvem | iCloud Drive (UIDocument) | Google Drive API |
| Cache | Diretório Caches, limpo pelo sistema | getCacheDir(), getExternalCacheDir() |
Sandbox é a arquitetura de segurança do iOS que isola cada aplicativo. Um aplicativo só pode ler e escrever dentro de sua própria sandbox. Para acessar contatos, fotos ou arquivos de outros aplicativos, devem ser usados seletores do sistema: UIImagePickerController ou UIDocumentPickerViewController. O acesso ao Files App é configurado através da flag UIFileSharingEnabled no Info.plist. O sistema de arquivos no desenvolvimento móvel no iOS requer a compreensão da estrutura de diretórios e a escolha do local correto para cada tipo de dado.
A sandbox do iOS consiste em vários diretórios padrão. Documents — para arquivos do usuário, incluído no iCloud Backup. Caches — para dados temporários que o sistema pode excluir quando o armazenamento estiver baixo. Temporary — para arquivos da sessão atual, limpos na reinicialização. Application Support — para dados internos do aplicativo ocultos do usuário. Escolher o diretório errado causa problemas: salvar cache em Documents desperdiça espaço no iCloud e viola as diretrizes da Apple para o sistema de arquivos.
import Foundation
let fileManager = FileManager.default
guard let documentsURL = fileManager.urls(
for: .documentDirectory,
in: .userDomainMask
).first else { return }
let fileURL = documentsURL.appendingPathComponent("notes.txt")
let text = "Содержимое файла"
// Gravação atômica com criptografia
try text.write(
to: fileURL,
atomically: true,
encoding: .utf8
)
A classe FileManager fornece um conjunto completo de métodos para gerenciar arquivos no iOS. FileManager.default é um singleton thread-safe adequado para a maioria das operações. Métodos como fileExists(atPath:), createDirectory(at:withIntermediateDirectories:attributes:), copyItem(at:to:) e removeItem(at:) cobrem cenários básicos. Operações com arquivos maiores que 1 MB devem ser realizadas em uma thread de fundo via DispatchQueue.global(). Para streaming de grandes volumes, use FileHandle em vez de carregar o arquivo inteiro na memória.
func readDocumentsFile(named fileName: String) -> String? {
guard let docsURL = FileManager.default.urls(
for: .documentDirectory,
in: .userDomainMask
).first else { return nil }
let fileURL = docsURL.appendingPathComponent(fileName)
return try? String(contentsOf: fileURL)
}
Com o lançamento do Android 10, o Google introduziu o Scoped Storage — um modelo de acesso restrito ao sistema de arquivos. Um aplicativo pode ler e escrever livremente apenas em seus diretórios privados. Para arquivos de mídia (fotos, vídeos, áudio), o MediaStore API é usado através do ContentResolver. Para documentos arbitrários, o Storage Access Framework é usado via Intent ACTION_OPEN_DOCUMENT. No Android 11+, o acesso direto à raiz do armazenamento externo é completamente proibido, e todos os desenvolvedores devem usar as novas APIs.
MediaStore é um ContentProvider do sistema para acessar arquivos de mídia no dispositivo. Através do ContentResolver, o aplicativo solicita Uri de arquivos em vez de caminhos diretos. MediaStore.Files — para todos os tipos de arquivo, Images — para imagens, Video — para vídeo, Audio — para gravações de áudio. A escrita em diretórios compartilhados é feita via insert() com DISPLAY_NAME, MIME_TYPE e RELATIVE_PATH. Após a inserção, o aplicativo recebe uma Uri através da qual os bytes são escritos. Os tipos MIME desempenham um papel fundamental — um tipo incorreto causará um erro ao abrir o arquivo.
val contentValues = ContentValues().apply {
put(MediaStore.MediaColumns.DISPLAY_NAME, "report.pdf")
put(MediaStore.MediaColumns.MIME_TYPE, "application/pdf")
put(MediaStore.MediaColumns.RELATIVE_PATH, "Documents/Reports")
}
val uri = contentResolver.insert(
MediaStore.Files.getContentUri("external"),
contentValues
)
uri?.let {
contentResolver.openOutputStream(it)?.use { stream ->
stream.write(pdfBytes)
}
}
O SAF fornece uma interface unificada para selecionar e criar arquivos sem permissões de tempo de execução. Intent ACTION_OPEN_DOCUMENT abre o gerenciador de arquivos do sistema no Android. Após a seleção, o aplicativo recebe uma Uri content:// com acesso temporário via FLAG_GRANT_READ_URI_PERMISSION. ACTION_CREATE_DOCUMENT permite salvar arquivos em qualquer local de armazenamento externo escolhido pelo usuário. O SAF funciona no Android 5+ e fornece acesso a arquivos de provedores de nuvem conectados através do DocumentsProvider.
val intent = Intent(Intent.ACTION_OPEN_DOCUMENT).apply {
addCategory(Intent.CATEGORY_OPENABLE)
type = "*/*"
putExtra(Intent.EXTRA_MIME_TYPES, arrayOf(
"application/pdf",
"text/plain"
))
}
startActivityForResult(intent, REQUEST_CODE)
Ambas as plataformas fornecem mecanismos integrados para os usuários selecionarem arquivos. Documentos em aplicativos móveis são passados através de seletores do sistema que concedem acesso temporário a um arquivo sem permissões permanentes. No iOS, isso é UIDocumentPickerViewController; no Android, ACTION_OPEN_DOCUMENT. Documentos em aplicativos móveis podem ser selecionados tanto do armazenamento local quanto de serviços na nuvem. O usuário especifica explicitamente o arquivo, e o aplicativo recebe uma Uri ou URL com um período de validade limitado.
UIDocumentPickerViewController abre o Files App e permite selecionar um ou mais documentos. Modos: importar (copiar para a sandbox) e abrir (acesso via URL com escopo de segurança). Para filtragem de arquivos, uma matriz de tipos UTType é passada — por exemplo, .pdf e .plainText. Após receber a URL, o aplicativo deve chamar startAccessingSecurityScopedResource() antes da leitura e stopAccessingSecurityScopedResource() após terminar. Não chamar stopAccessing causa vazamento de recursos do sistema. Documentos em aplicativos móveis no iOS exigem a liberação obrigatória de permissões temporárias após terminar o trabalho com o arquivo.
let picker = UIDocumentPickerViewController(
forOpeningContentTypes: [.pdf, .plainText]
)
picker.allowsMultipleSelection = true
picker.delegate = self
present(picker, animated: true)
// Liberando acesso no delegado
func documentPicker(
_ controller: UIDocumentPickerViewController,
didPickDocumentsAt urls: [URL]
) {
guard let url = urls.first else { return }
url.startAccessingSecurityScopedResource()
defer { url.stopAccessingSecurityScopedResource() }
}
FileProvider é uma subclasse de ContentProvider para compartilhar arquivos com segurança entre aplicativos. Ele gera Uris content:// temporárias com base em arquivos de diretórios XML especificados. Outros aplicativos obtêm acesso via Intent com FLAG_GRANT_READ_URI_PERMISSION. DocumentProvider, ao contrário do FileProvider, publica arquivos no SAF e permite que outros aplicativos naveguem pelo conteúdo do seu aplicativo como parte do sistema de arquivos. Para implementar DocumentsProvider, você precisa sobrescrever queryRoots(), queryChildDocuments() e openDocument(), depois registrá-lo no AndroidManifest.xml
A sincronização na nuvem dá aos usuários acesso a documentos em todos os seus dispositivos. O sistema de arquivos em aplicativos móveis é complementado por uma camada de nuvem: UIDocument no iOS rastreia automaticamente as alterações e as sincroniza via iCloud. No Android, funcionalidade semelhante é construída através do Google Drive API ou DocumentsProvider com raízes na nuvem. Compreender o sistema de arquivos no desenvolvimento móvel é crítico para construir uma sincronização confiável entre dispositivos.
UIDocument é uma classe abstrata para trabalhar com documentos do iCloud. Ele salva alterações automaticamente, lê dados e notifica o delegado sobre atualizações. Em caso de conflito de gravação, NSFileVersion fornece uma lista de versões disponíveis — o desenvolvedor pode escolher a mais recente ou mostrar ao usuário opções de resolução de conflitos. A configuração do Ubiquity Container nas Capacidades do projeto é obrigatória para o iCloud Drive. NSFileCoordinator e NSFilePresenter previnem condições de corrida durante acesso concorrente de múltiplas threads ou dispositivos.
O iOS inclui automaticamente o diretório Documents no iCloud Backup. O Android funciona com Auto Backup for Apps — o sistema salva dados de getFilesDir(), SharedPreferences e bancos de dados SQLite no Google Drive. Cache e arquivos externos não são incluídos no backup. Ambas as plataformas permitem configurar exclusões: no iOS via NSURLIsExcludedFromBackupKey, no Android via configuração XML de regras de backup. A criptografia de arquivos com dados pessoais é obrigatória — no iOS use NSDataWritingFileProtectionComplete, no Android use EncryptedFile da biblioteca security-crypto.
| Parâmetro | iOS | Android |
|---|---|---|
| Backup padrão | Documents e Library | getFilesDir(), SharedPreferences, BD |
| Exclusão de arquivos | isExcludedFromBackupKey | Regras XML de backup (fullBackupContent) |
| Criptografia | NSDataWritingFileProtectionComplete | EncryptedFile (security-crypto) |
| Sincronização na nuvem | UIDocument + iCloud | Google Drive API + SAF |
| Restauração automática | iCloud Restore após instalação | Auto Backup ao reinstalar |
Perguntas frequentes
Sandbox é um ambiente isolado para cada aplicativo no iOS. O aplicativo não pode acessar arquivos de outros aplicativos sem usar seletores do sistema como UIDocumentPickerViewController.
Scoped Storage é um modelo de acesso restrito ao sistema de arquivos no Android 10+. O aplicativo lê diretamente apenas seus próprios arquivos, usa MediaStore API para mídia e Storage Access Framework para documentos.
Use UIDocumentPickerViewController — o seletor do sistema para escolher documentos do Files App ou iCloud Drive. Após a seleção, você recebe uma URL com escopo de segurança e acesso temporário.
Para arquivos de mídia, use MediaStore API através do ContentResolver especificando o tipo MIME. Para documentos arbitrários, use Storage Access Framework com Intent ACTION_OPEN_DOCUMENT.
FileProvider é uma subclasse de ContentProvider para compartilhar arquivos com segurança entre aplicativos via Uri content:// temporária com FLAG_GRANT_READ_URI_PERMISSION.
Resumo
Vamos desenvolver um aplicativo móvel chave na mão
A IT Sectr cria aplicativos para iOS e Android para startups e empresas desde 2017. Nós vamos aconselhá-lo e propor a melhor solução.