DocumentProvider es una clase abstracta de Android que implementa un proveedor de contenido para acceder a archivos a través de Storage Access Framework. El proveedor se registra en AndroidManifest.xml y proporciona archivos a otras aplicaciones mediante el selector del sistema. Según Android Developers (2026), DocumentsProvider requiere implementar los métodos queryRoots, queryDocument y queryChildDocuments para mostrar la estructura de archivos en el diálogo de selección.
Puntos clave
DocumentsProvider es una clase base de Android que extiende ContentProvider, permitiendo a una aplicación proporcionar sus archivos a otras aplicaciones a través de la interfaz SAF del sistema. El proveedor crea un sistema de archivos virtual que el usuario ve en el diálogo de selección de documentos.
Cada proveedor organiza los archivos en raíces (roots) — puntos de entrada de nivel superior. Por ejemplo, Google Drive tiene las raíces “Mi unidad” y “Compartido conmigo.” Dentro de una raíz, el proveedor devuelve un árbol de documentos, donde cada documento es un archivo o directorio con un tipo MIME, tamaño y fechas específicos.
DocumentProvider forma parte del paquete android.provider y está disponible desde Android 4.4 (API 19). El proveedor es utilizado por servicios en la nube, gestores de contraseñas, aplicaciones de notas y cualquier programa que almacene archivos en su propio formato.
Crear su propio DocumentProvider comienza extendiendo la clase DocumentsProvider e implementando cuatro métodos obligatorios. El proveedor define la estructura de archivos que aparece en el selector SAF del sistema al seleccionar archivos.
El primer método es queryRoots, que devuelve un cursor con las columnas Root.COLUMN_ROOT_ID, Root.COLUMN_TITLE, Root.COLUMN_SUMMARY y Root.COLUMN_FLAGS. Cada raíz puede soportar banderas: FLAG_SUPPORTS_CREATE, FLAG_SUPPORTS_SEARCH y FLAG_SUPPORTS_IS_CHILD.
El segundo método obligatorio es queryChildDocuments, que devuelve los documentos secundarios de un URI especificado. Este método se llama cuando el usuario abre un directorio en el selector. Cada documento contiene las columnas: Document.COLUMN_DOCUMENT_ID, COLUMN_DISPLAY_NAME, COLUMN_MIME_TYPE, COLUMN_SIZE y COLUMN_LAST_MODIFIED.
DocumentsProvider requiere implementar cuatro métodos que forman la estructura de archivos para el selector. Sin ellos, el proveedor no funcionará — el diálogo SAF del sistema no podrá mostrar archivos.
Adicionalmente, se pueden implementar createDocument para crear nuevos archivos, deleteDocument para eliminar y renameDocument para renombrar. Estos métodos requieren la bandera FLAG_SUPPORTS_CREATE en la raíz.
DocumentProvider se registra en AndroidManifest.xml como un ContentProvider normal con un filtro de intent y banderas adicionales. El proveedor debe estar protegido del acceso directo mediante permisos — se recomienda usar android:exported="true" con permiso explícito.
<provider
android:name=".provider.CustomDocumentProvider"
android:authorities="com.example.app.documents"
android:exported="true"
android:grantUriPermissions="true"
android:permission="android.permission.MANAGE_DOCUMENTS">
<intent-filter>
<action
android:name="android.content.action.DOCUMENTS_PROVIDER" />
</intent-filter>
<meta-data
android:name="android.content.documents.roots"
android:resource="@xml/file_paths" />
</provider>
La bandera grantUriPermissions permite que SAF delegue temporalmente los derechos de acceso a la aplicación solicitante. El atributo authorities debe ser único — normalmente se usa el nombre del paquete con el sufijo .documents. También se recomienda especificar metadatos con un recurso XML para configurar las raíces.
Implementar DocumentsProvider requiere devolver un ParcelFileDescriptor desde el método openDocument. Para archivos locales se usa ParcelFileDescriptor.open, para archivos en la nube — ParcelFileDescriptor.open con Pipe para transmisión en flujo. El código debe manejar errores de acceso y archivos faltantes.
class CustomDocumentProvider : DocumentsProvider() {
override fun queryRoots(): Cursor {
val matrix = MatrixCursor(Root.COLUMNS)
matrix.newRow().add(Root.COLUMN_ROOT_ID, "local")
.add(Root.COLUMN_TITLE, "My Files")
.add(Root.COLUMN_SUMMARY, "Local documents")
.add(Root.COLUMN_FLAGS, Root.FLAG_SUPPORTS_CREATE)
return matrix
}
override fun openDocument(
documentId: String, flags: Int, cursor: CancellationSignal?
): ParcelFileDescriptor {
val file = File(context.filesDir, documentId)
val accessMode = ParcelFileDescriptor.parseMode(flags)
return ParcelFileDescriptor.open(file, accessMode)
}
}
DocumentProvider puede devolver archivos virtuales — documentos que no existen como archivos separados en el disco. Por ejemplo, una nota de base de datos puede presentarse como un PDF virtual. Esto usa un tipo MIME con la bandera FLAG_VIRTUAL_DOCUMENT, y openDocument convierte los datos al formato requerido antes de enviarlos.
iOS tiene un mecanismo similar — UIDocumentPickerViewController, que también proporciona una interfaz unificada de selección de archivos. Sin embargo, en iOS el proveedor de documentos se implementa a través de UIDocumentPickerDelegate y Extensiones de Aplicación (App Extensions) con el tipo Document Provider.
A diferencia de Android DocumentsProvider, iOS UIDocumentPickerViewController no requiere crear un proveedor personalizado para archivos locales — el selector del sistema admite iCloud Drive y el almacenamiento local por defecto. Los servicios en la nube de terceros se registran a través de una extensión Document Provider con la clave Info.plist NSExtensionFileProviderDocumentInterface.
La principal diferencia: en Android, DocumentProvider se invoca activamente a través de un Intent SAF y debe implementar la navegación por sí mismo. En iOS, UIDocumentPickerViewController utiliza un navegador de archivos del sistema integrado, y el proveedor de extensión solo es responsable de proporcionar contenido bajo petición.
Preguntas frecuentes
DocumentsProvider es una clase abstracta de Android para crear un proveedor de documentos personalizado. Permite a una aplicación presentar sus archivos a otras aplicaciones a través del diálogo del sistema Storage Access Framework.
Cuatro métodos son obligatorios: queryRoots (raíces de almacenamiento), queryDocument (un documento), queryChildDocuments (contenido de carpeta) y openDocument (abrir archivo). Sin ellos, el proveedor no funcionará.
El proveedor se registra como un <provider> con el nombre de la clase, authorities únicos, un filtro de intent con la acción android.content.action.DOCUMENTS_PROVIDER y grantUriPermissions="true".
FileProvider genera URI de contenido para archivos específicos de su aplicación. DocumentsProvider crea un sistema de archivos completo visible en el selector SAF, con soporte para navegación y búsqueda.
Use la bandera FLAG_VIRTUAL_DOCUMENT en la columna COLUMN_FLAGS y un tipo MIME con el prefijo “vnd.android.document/”. En openDocument, convierta los datos al formato solicitado usando ParcelFileDescriptor con Pipe.
Resumen
Desarrollaremos una aplicación móvil llave en mano
IT Sectr crea aplicaciones para iOS y Android para startups y empresas desde 2017. Le asesoraremos y le propondremos la mejor solución.
Lea también