so I have an existing app that has been on the app store for quite some time, as of 3 days ago I was getting more support enquiries saying my app could not connect to my service.
Now it has finally happened to me on my Android devices - everything works perfectly for iOS, and perfectly for Android on Emulator - but nothing in the real world.
I have looked as far as I can by step-debugging with Cordova and it passes the whitelist test fine. My very first XHR request works fine, but subsequent ones always fail until I completely close the app and re-open.
I am using [email protected]
- I have also tried [email protected]
My Content-Security-Policy
looks like this
<meta http-equiv="Content-Security-Policy" content="default-src * 'self' gap:; img-src http://*.my-site.com.au https://*.my-site.com.au https://*.my-site.com http://*.my-site.com https://*.googleusercontent.com http://*.googleapis.com https://google.com https://*.google.com https://*.googleapis.com https://*.gstatic.com 'self' data:; style-src http://*.googleapis.com https://*.googleapis.com 'self' 'unsafe-inline'; script-src 'self' https://*.googleapis.com http://*.googleapis.com http://maps.google.com http://*.gstatic.com https://*.gstatic.com https://maps.google.com 'unsafe-inline' 'unsafe-eval'">
My Cordova config has
<allow-navigation href="*" />
<allow-navigation href="http://*/*" />
<allow-navigation href="https://*/*" />
I have tried adding/removing/replacing the above/every combination with <access origin="*" />
but no luck.
My XHR response always looks like the following
xhr.responseUrl = "http://my-site.com/?d=12343902i49"
xhr.status = 0
xhr.responseText = ""
I have step-debugged the XHR request as far as I could have in the Cordova Plugin, by step debugging out of the Whitelist.java
but everything returns fine and it makes it successfully to the line
// If we don't need to special-case the request, let the browser load it.
return null;
of function
WebResourceResponse shouldInterceptRequest(WebView view, String url)
in org.apache.cordova.engine.SystemWebViewClient.java
My Android Manifest has the following
<uses-sdk android:minSdkVersion="19" android:targetSdkVersion="28" />
<uses-permission android:name="android.permission.WRITE_EXTERNAL_STORAGE" />
<uses-permission android:name="android.permission.WRITE_INTERNAL_STORAGE" />
<uses-permission android:name="android.permission.ACCESS_COARSE_LOCATION" />
<uses-permission android:name="android.permission.ACCESS_FINE_LOCATION" />
<uses-permission android:name="android.permission.READ_EXTERNAL_STORAGE" />
<uses-feature android:name="android.hardware.location.gps" />
<uses-permission android:name="android.permission.RECORD_AUDIO" />
<uses-permission android:name="android.permission.MODIFY_AUDIO_SETTINGS" />
<uses-permission android:name="android.permission.READ_PHONE_STATE" />
<uses-permission android:name="android.permission.RECORD_VIDEO" />
<uses-permission android:name="android.permission.ACCESS_NETWORK_STATE" />
<uses-permission android:name="android.permission.CAMERA" />
<uses-permission android:name="android.permission.FLASHLIGHT" />
<uses-feature android:name="android.hardware.camera" android:required="true" />
<uses-permission android:name="android.permission.WAKE_LOCK" />
<uses-permission android:name="android.permission.VIBRATE" />
I am using [email protected], Cordova platform [email protected]
I've spent several hours trying to dig deeper, what am I missing here? Any help would be greatly appreciated!
To enable debugging on iOS, In the iOS device, go to Settings → Safari → Advanced → Enable 'Web Inspector' From the Mac, Safari → Preferences → Advanced → Enable 'Show Develop menu in menu bar' Once this is done, start the Cordova application and connect your iOS device with USB cable.
Cordova-Android requires the Android SDK, which can be installed on either macOS, Linux, or Windows. For the base system requirements, see the Android Studio's System Requirements.
First tap 7 times on the Build Number (is the last option too), then a message that "You're a developer now will appear". Followed, go back to the settings and you will see now a new available option in the menu. Tap on this and go to the last option (Debugging : USB Debug mode when usb is connected).
As the problem disappears if you lower the targetSDK, it's probably the usesCleartextTraffic
mentioned by Nidhin Josehp. It only affects Android 8 or newer devices when targeting SDK 28 or greater.
Instead of manually editing the AndroidManifest.xml
as he suggest (you should never manually edit it in Cordova apps) you can add this to the config.xml
<platform name="android">
<edit-config file="app/src/main/AndroidManifest.xml" mode="merge" target="/manifest/application">
<application android:usesCleartextTraffic="true" />
</edit-config>
</platform>
You might need to change your widget tag in config.xml
to look something like this:
<widget id="com.your.app.id" version="1.0.0"
xmlns="http://www.w3.org/ns/widgets"
xmlns:android="http://schemas.android.com/apk/res/android"
xmlns:cdv="http://cordova.apache.org/ns/1.0">
(The addition is the xmlns:android="http://schemas.android.com/apk/res/android"
)
Try adding android:usesCleartextTraffic="true"
to the <application>
in the AndroidManifest.xml
or as below using config.xml
<platform name="android">
<edit-config file="app/src/main/AndroidManifest.xml" mode="merge" target="/manifest/application">
<application android:usesCleartextTraffic="true" />
</edit-config>
</platform>
android:usesCleartextTraffic Indicates whether the app intends to use cleartext network traffic, such as cleartext HTTP. The default value for apps that target API level 27 or lower is "true". Apps that target API level 28 or higher default to "false". More info
Cleartext is any transmitted or stored information that is not encrypted or meant to be encrypted. When an app communicates with servers using a cleartext network traffic, such as HTTP, it could raise a risk of eavesdropping and tampering of content which is why in latest Android devices, it's set to
false
by default.
I'm going to jump I swear.
<uses-sdk android:minSdkVersion="19" android:targetSdkVersion="26" />
Changed targetSdkVersion to 26 from 28. Worked. But this is going to be a nightmare.
Edit: Problem has come back but only for Samsung Galaxy Tablets. I can't replicate this behaviour anywhere else.
Edit2: Things are...fine again?
If you love us? You can donate to us via Paypal or buy me a coffee so we can maintain and grow! Thank you!
Donate Us With