Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

NetworkOnMainThreadException while importing data from exported csv file (ArrowOS) #407

Closed
foss- opened this issue Aug 9, 2023 · 11 comments · Fixed by #420
Closed

NetworkOnMainThreadException while importing data from exported csv file (ArrowOS) #407

foss- opened this issue Aug 9, 2023 · 11 comments · Fixed by #420
Labels
bug Something isn't working

Comments

@foss-
Copy link

foss- commented Aug 9, 2023

Reproducer steps

  1. … > Export to File
  2. Import File > Select exported csv file on second device

Actual result
While Plees Tracker shows Import finished successfully the visible sleeps don't change. A few nights were already tracked on the device the import is attempted on, but those never vanish nor is older data added.

Expected behavior
The import should ideally add data to the existing data or if that is not possible remove the current data and replace it with the imported data. In the latter case a warning dialog should ask users how to proceed.

Android 13.1
Plees Tracker 7.6.0 (46)

@vmiklos
Copy link
Owner

vmiklos commented Aug 10, 2023

Just to be clear, the problem only happens when you already have sleeps and you try to import, is that correct?

@vmiklos vmiklos added the needinfo Further information is requested label Aug 10, 2023
@foss-
Copy link
Author

foss- commented Aug 10, 2023

To verify I did the following: with a few entries still there I again tried the import and that did not work. I got the success message but the imported sleeps never showed.

Then I used … > Delete All Sleep, confirmed with Yes, but Import from File still has the same result: success message but no sleeps show. This is persisting after closing and re-opening the app.

@vmiklos
Copy link
Owner

vmiklos commented Aug 11, 2023

Hm, both scenarios work for me on a Pixel 6a, also on Android 13. I'll try to see if perhaps a clean emulator state allows reproducing.

I selected a target file on the phone, not something virtual, provided by an app (since there is a dedicated issue for the nextcloud case).

@foss-
Copy link
Author

foss- commented Aug 11, 2023

This is ArrowOS 13.1(TQ3A.230705.001) on lisa device. Right, my attempt to import in the end was to import form plees-tracker.csv stored on phone storage not nextcloud, to make sure the potential permission problem is not at play.

@vmiklos vmiklos changed the title Import File does not import data from exported csv file ArrowOS: Import File does not import data from exported csv file Aug 18, 2023
@vmiklos
Copy link
Owner

vmiklos commented Aug 18, 2023

adb logcat reports (sanitized):

java.io.FileNotFoundException: Failed to open document for writing plees-tracker.csv
        at android.database.DatabaseUtils.readExceptionWithFileNotFoundExceptionFromParcel(DatabaseUtils.java:151)
        at android.content.ContentProviderProxy.openAssetFile(ContentProviderNative.java:705)
        at android.content.ContentResolver.openAssetFileDescriptor(ContentResolver.java:1860)
        at android.content.ContentResolver.openOutputStream(ContentResolver.java:1562)
        at android.content.ContentResolver.openOutputStream(ContentResolver.java:1537)
        at hu.vmiklos.plees_tracker.DataModel.exportDataToFile(DataModel.kt:290)
        at hu.vmiklos.plees_tracker.DataModel$exportDataToFile$1.invokeSuspend(Unknown Source:18)

Now the question is why openOutputStream() throws an exception even after takePersistableUriPermission(FLAG_GRANT_WRITE_URI_PERMISSION) happily succeeds (i.e. doesn't throw a SecurityException).

The plan is to read some of the k9 mail code which reportedly works fine in this case; and probably need to figure out how to install this ArrowOS in an emulator to be able to reproduce & fix the problem locally.

@foss-
Copy link
Author

foss- commented Aug 19, 2023

Never tried that, quick search turns up https://stackoverflow.com/questions/25985384/run-custom-rom-on-android-emulator

Sounds like it is possible but since roms are device specific you'd need to emulate a device and then pick the corresponding download.

@foss-
Copy link
Author

foss- commented Sep 14, 2023

Importing with blank plees-tracker worked.
Importing with existing past sleeps results in app crash. Logcat sent via email.

@vmiklos
Copy link
Owner

vmiklos commented Sep 15, 2023

Oh, this is interesting:

E AndroidRuntime: android.os.NetworkOnMainThreadException
E AndroidRuntime:       at android.os.Parcel.createExceptionOrNull(Parcel.java:3021)
E AndroidRuntime:       at android.os.Parcel.createException(Parcel.java:2995)
E AndroidRuntime:       at android.os.Parcel.readException(Parcel.java:2978)
E AndroidRuntime:       at android.database.DatabaseUtils.readExceptionFromParcel(DatabaseUtils.java:190)
E AndroidRuntime:       at android.database.DatabaseUtils.readExceptionWithFileNotFoundExceptionFromParcel(DatabaseUtils.java:153)
E AndroidRuntime:       at android.content.ContentProviderProxy.openTypedAssetFile(ContentProviderNative.java:780)
E AndroidRuntime:       at android.content.ContentResolver.openTypedAssetFileDescriptor(ContentResolver.java:2027)
E AndroidRuntime:       at android.content.ContentResolver.openAssetFileDescriptor(ContentResolver.java:1842)
E AndroidRuntime:       at android.content.ContentResolver.openInputStream(ContentResolver.java:1518)
E AndroidRuntime:       at hu.vmiklos.plees_tracker.DataModel.importData(DataModel.kt:163)

I.e. we just work with an input stream, but in case that's backed with some network stuff, Android is unhappy. What is the actual source here, Nextcloud?

@vmiklos vmiklos changed the title ArrowOS: Import File does not import data from exported csv file NetworkOnMainThreadException while importing data from exported csv file (ArrowOS) Sep 15, 2023
@foss-
Copy link
Author

foss- commented Sep 15, 2023

Y, test was done with Import happening from a file located in Nextcloud folder.

@vmiklos
Copy link
Owner

vmiklos commented Sep 15, 2023

Nice, I can reproduce this, thanks.

Edit: possibly all we need is something like this: https://stackoverflow.com/questions/67771324/kotlin-networkonmainthreadexception-error-when-trying-to-run-inetaddress-isreac

@vmiklos vmiklos closed this as completed Sep 15, 2023
@vmiklos vmiklos reopened this Sep 15, 2023
@vmiklos vmiklos added bug Something isn't working and removed needinfo Further information is requested labels Sep 15, 2023
vmiklos added a commit that referenced this issue Oct 13, 2023
Import from file is normally a non-blocking operation, so it can be done
on the UI, except when going via the storage access framework, e.g. when
the file is provided by nextcloud. This resulted in a crash like:

	2023-10-13 22:10:48.342  7896-7896  AndroidRuntime          hu.vmiklos.plees_tracker.debug       E  FATAL EXCEPTION: main
	    at android.database.DatabaseUtils.readExceptionWithFileNotFoundExceptionFromParcel(DatabaseUtils.java:153)
	    at android.content.ContentProviderProxy.openTypedAssetFile(ContentProviderNative.java:814)
	    at android.content.ContentResolver.openTypedAssetFileDescriptor(ContentResolver.java:2043)
	    at android.content.ContentResolver.openAssetFileDescriptor(ContentResolver.java:1858)
	    at android.content.ContentResolver.openInputStream(ContentResolver.java:1528)
	    at hu.vmiklos.plees_tracker.DataModel.importData(DataModel.kt:163)

The NetworkOnMainThreadException is thrown because we actually do
networking on the main thread, but that should be done on a thread to
not block the UI.

Fix the problem by wrapping the IO part of importData() in a
`withContext(Dispatchers.IO)` block, but keep the toast on the main
thread, as UI calls are only allowed on the main thread.

Fixes <#407>.

Change-Id: Ia9d691fd178c343554ede86c39a801134f2aab2e
vmiklos added a commit that referenced this issue Oct 13, 2023
Import from file is normally a non-blocking operation, so it can be done
on the UI, except when going via the storage access framework, e.g. when
the file is provided by nextcloud. This resulted in a crash like:

	2023-10-13 22:10:48.342  7896-7896  AndroidRuntime          hu.vmiklos.plees_tracker.debug       E  FATAL EXCEPTION: main
	    at android.database.DatabaseUtils.readExceptionWithFileNotFoundExceptionFromParcel(DatabaseUtils.java:153)
	    at android.content.ContentProviderProxy.openTypedAssetFile(ContentProviderNative.java:814)
	    at android.content.ContentResolver.openTypedAssetFileDescriptor(ContentResolver.java:2043)
	    at android.content.ContentResolver.openAssetFileDescriptor(ContentResolver.java:1858)
	    at android.content.ContentResolver.openInputStream(ContentResolver.java:1528)
	    at hu.vmiklos.plees_tracker.DataModel.importData(DataModel.kt:163)

The NetworkOnMainThreadException is thrown because we actually do
networking on the main thread, but that should be done on a thread to
not block the UI.

Fix the problem by wrapping the IO part of importData() in a
`withContext(Dispatchers.IO)` block, but keep the toast on the main
thread, as UI calls are only allowed on the main thread.

Fixes <#407>.

Change-Id: Ia9d691fd178c343554ede86c39a801134f2aab2e
@vmiklos
Copy link
Owner

vmiklos commented Oct 13, 2023

Works for me now, will cut a next release in 2-3 weeks.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
bug Something isn't working
Projects
None yet
Development

Successfully merging a pull request may close this issue.

2 participants