Aitor Sánchez - Blog - Oct. 26, 2023, 9:31 a.m.
¿Necesitas cargar una imagen, o un archivo quizás, desde la memoria local del dispositivo y no hay manera de lograrlo?
Mi nombre es Aitor Sánchez, soy desarrollador de apps desde 2014, y con esta información cargarás archivos locales que estén fuera del entorno de la aplicación cómo si fueras el cartero de las películas los 90, con su carrito y todo.
Pero antes de continuar, esta es la Flutter Mafia. Es mi newsletter donde aprenderás desarrollo de apps móviles, aso y monetización junto con otros genietes que ya están dentro. Y si te suscribes te regalo mi ebook "Duplica los ingreso de tus apps en 5 minutos" No es broma, quizás te interese.
Aquí tienes dos maneras de tratar el tema. Si usas Capacitor, o no lo usas.
Si usas capacitor:
...
import { Capacitor } from '@capacitor/core';
...
const savedPhoto = Capacitor.convertFileSrc("<Local path of photo>")
...
Si usas WebView:
...
const image = window.win.Ionic.WebView.convertFileSrc(path);
...
Imagino que con alguno de los dos anteriores ya has dado solución al problema, pero me gustaría darte algunos consejos más por si acaso no ha sido así.
Es un bug que existe en alguna de las versiones del plugin de WebView.
Muchos usuarios de Ionic reportan que se soluciona cambiando de versión, pero aquí le vamos a dar una solución mucho más específica y completa para que te funcione en todas las versiones.
Asegúrate de que las rutas a los recursos locales estén correctas. En aplicaciones móviles, debes usar rutas relativas o específicas del sistema de archivos del dispositivo.
Verifica tu política de seguridad de contenido en el archivo index.html
de tu aplicación. Asegúrate de que esté configurada para permitir la carga de recursos locales.
Por ejemplo, si estás intentando cargar imágenes locales, tu CSP (Content Security Policy) debería incluir algo como img-src 'self' data:;
para permitir imágenes del mismo origen y datos codificados.
La base sería algo así:
<meta http-equiv="Content-Security-Policy" content="default-src 'self' data: gap: https://ssl.gstatic.com 'unsafe-eval'; style-src 'self' 'unsafe-inline'; media-src *; img-src 'self' data: content:;">
En esta política, las directivas son:
default-src
: Define las fuentes de contenido predeterminadas para varios tipos de datos (como script-src
, img-src
, etc.).style-src
: Define fuentes válidas para hojas de estilo.img-src
: Define fuentes válidas para imágenes.
Para solucionar el problema de "not allowed to load local resource", necesitarías ajustar la directiva img-src
(y posiblemente otras directivas si también estás cargando otros tipos de recursos, como hojas de estilo o scripts).
Aquí te muestro cómo permitir imágenes de la misma fuente ('self'
), datos codificados (data:
), y también contenido de la aplicación (content:
):
<meta http-equiv="Content-Security-Policy" content="default-src 'self'; style-src 'self' 'unsafe-inline'; img-src 'self' data: content:;">
Es importante tener en cuenta que tener una CSP demasiado permisiva puede reducir la seguridad de tu aplicación. Así que debes asegurarte de permitir solo lo que tu aplicación necesita para funcionar correctamente.
En Android, las rutas a archivos locales deben usar el file://
schema. Pero debido a las restricciones de seguridad, a menudo no se permite cargar directamente archivos locales usando este esquema. Puedes necesitar cargar los recursos a través de un servidor o utilizando el plugin cordova-plugin-file
.
Si estás utilizando Cordova, puedes necesitar ajustar la configuración en config.xml
. Por ejemplo, puedes añadir una preferencia para permitir el acceso a los recursos:
<allow-navigation href="file://*/*" />
O también, si estás utilizando el plugin cordova-plugin-whitelist
, asegúrate de tener las etiquetas de acceso adecuadas:
<access origin="*" />
<allow-intent href="http://*/*" />
<allow-intent href="https://*/*" />
<allow-intent href="tel:*" />
<allow-intent href="sms:*" />
<allow-intent href="mailto:*" />
<allow-intent href="geo:*" />
Si estás utilizando una versión antigua de Ionic, considera actualizar a Ionic Webview, que maneja mejor la carga de recursos locales y tiene mejor rendimiento.
Para hacerlo correctamente sería ejecutar las dos siguiente líneas:
ionic cordova plugin rm cordova-plugin-ionic-webview ionic cordova plugin add cordova-plugin-ionic-webview
Asegúrate de que las configuraciones de tu AndroidManifest.xml
no estén restringiendo la carga de recursos locales.
Veamos un posible ejemplo de un bien configurado. Solo basándonos en la carga de recursos:
<manifest xmlns:android="http://schemas.android.com/apk/res/android"
package="com.example.myapp">
<!-- Importante el tema de los permisos -->
<uses-permission android:name="android.permission.INTERNET" />
<uses-permission android:name="android.permission.ACCESS_NETWORK_STATE" />
<uses-permission android:name="android.permission.READ_EXTERNAL_STORAGE" />
<application
android:allowBackup="true"
android:icon="@mipmap/ic_launcher"
android:label="@string/app_name"
android:roundIcon="@mipmap/ic_launcher_round"
android:supportsRtl="true"
android:theme="@style/AppTheme"
android:usesCleartextTraffic="true"> <!-- Esta linea también es importante -->
<activity android:name=".MainActivity">
<intent-filter>
<action android:name="android.intent.action.MAIN" />
<category android:name="android.intent.category.LAUNCHER" />
</intent-filter>
</activity>
</application>
</manifest>
Mira, en el momento que tu mejoras el logo de una app que tengas publicada en Google Play, las descargas y los ingresos que esta aplicación genera aumentan. Esto es así. Mejor logo es igual a más dinero.
Basándonos en esto, hemos creado esta herramienta que te permite evaluar, optimizar y mejorar los logos de tus apps para que reciban más descargas. No te quiero espoilear, dentro hay un video explicativo. Entra en el enlace.
Geniete, pues hasta aquí el artículo de hoy. Espero haberte ayudado con tu problema de recursos y nos vemos en el siguiente artículo. Hasta entonces ¡que te vaya bien!