Cómo configurar el uso compartido de archivos

Para ofrecer un archivo de tu app a otra de manera segura, debes configurar tu app para que ofrezca un control seguro del archivo, en forma de URI de contenido. El componente FileProvider de Android genera URI de contenido para archivos según las especificaciones que proporcionas en XML. En esta lección, se muestra cómo agregar la implementación predeterminada de FileProvider a una app y cómo especificar los archivos que deseas ofrecer a otras apps.

Nota: La clase FileProvider es parte de la Biblioteca de compatibilidad v4. Para obtener información sobre cómo incluir esta biblioteca en tu app, consulta Configuración de la biblioteca de compatibilidad.

Cómo especificar el FileProvider

A fin de definir un FileProvider para tu app, se requiere una entrada en el manifiesto que especifique la autoridad que se debe usar en la generación de URI de contenido, así como el nombre de un archivo XML que indique los directorios que la app podrá compartir.

En el siguiente fragmento de código, se muestra cómo agregar al manifiesto el elemento <provider> que especifica la clase FileProvider, la autoridad y el nombre del archivo XML:

    <manifest xmlns:android="http://schemas.android.com/apk/res/android"
        package="com.example.myapp">
        <application
            ...>
            <provider
                android:name="android.support.v4.content.FileProvider"
                android:authorities="com.example.myapp.fileprovider"
                android:grantUriPermissions="true"
                android:exported="false">
                <meta-data
                    android:name="android.support.FILE_PROVIDER_PATHS"
                    android:resource="@xml/filepaths" />
            </provider>
            ...
        </application>
    </manifest>

En este ejemplo, el atributo android:authorities especifica la autoridad del URI que deseas usar para los URI de contenido generados por FileProvider. En el ejemplo, la autoridad es com.example.myapp.fileprovider. Para tu app, especifica una autoridad que incluya el valor de android:package de la app, junto con la string "fileprovider". Para obtener más información sobre el valor de autoridad, consulta el tema URI de contenido y la documentación relacionada con el atributo android:authorities.

El elemento secundario <meta-data> de <provider> apunta a un archivo XML que especifica los directorios que deseas compartir. El atributo android:resource es la ruta de acceso y el nombre del archivo, sin la extensión .xml.En la siguiente sección, se describe el contenido de este archivo.

Cómo especificar directorios para compartir

Una vez que hayas agregado FileProvider al manifiesto de tu app, deberás especificar los directorios que contienen los archivos que deseas compartir. Para ello, primero crea el archivo filepaths.xml en el subdirectorio res/xml/ de tu proyecto. En ese archivo, especifica los directorios agregando un elemento XML para cada uno. En el siguiente fragmento, se muestra un ejemplo del contenido de res/xml/filepaths.xml y se indica cómo compartir un subdirectorio del directorio files/ en el área de almacenamiento interno:

    <paths>
        <files-path path="images/" name="myimages" />
    </paths>

En este ejemplo, la etiqueta <files-path> comparte directorios dentro de files/, en el almacenamiento interno de tu app. El atributo path comparte el subdirectorio images/ de files/. El atributo name le indica a FileProvider que debe agregar el segmento de ruta myimages a los URI de contenido de los archivos del subdirectorio files/images/.

El elemento <paths> puede tener varios elementos secundarios, y uno de estos especifica un directorio diferente para compartir. Además del elemento <files-path>, puedes usar <external-path> para compartir directorios en el almacenamiento externo, así como <cache-path> para compartir directorios en tu directorio de caché interno. Si quieres obtener más información sobre los elementos secundarios que especifican directorios compartidos, consulta la documentación de referencia de FileProvider.

Nota: El archivo XML es la única manera de especificar los directorios que deseas compartir, ya que no es posible agregar un directorio de manera programática.

Ahora tienes una especificación completa de FileProvider que genera URI de contenido para archivos del directorio files/ en el almacenamiento interno de tu app, o para archivos de subdirectorios de files/. Cuando tu app genera un URI de contenido para un archivo, este contiene la autoridad especificada en el elemento <provider> (com.example.myapp.fileprovider), la ruta myimages/ y el nombre del archivo.

Por ejemplo, si defines un FileProvider según los fragmentos de esta lección y solicitas un URI de contenido para el archivo default_image.jpg, FileProvider mostrará el siguiente URI:

    content://com.example.myapp.fileprovider/myimages/default_image.jpg

Para obtener información adicional relacionada, consulta: