commons-app / apps-android-commons

The Wikimedia Commons Android app allows users to upload pictures from their Android phone/tablet to Wikimedia Commons
https://commons-app.github.io/
Apache License 2.0
1.03k stars 1.23k forks source link

The app erroneously shows successfully uploaded images as "Failed" #5280

Open RitikaPahwa4444 opened 1 year ago

RitikaPahwa4444 commented 1 year ago

Summary

The app erroneously shows successfully uploaded images as "Failed". If the user taps on the retry button (or if it is retried automatically by the app), then the image gets uploaded again. The first upload, however, often lacks caption and/or depiction. This happens probably because Wikidata edit is unsuccessful for such uploads.

Related: This commit tried to forbid retries in such cases and showed the upload as successful in the Contributions list. However, the media details fragment became unreliable; it displayed the Coordinates as None Provided, Description as {{en|1=Ikuchijima}} etc.

Steps to reproduce

Hard to reproduce. A deliberate way of reproducing it:

  1. Start an upload
  2. Monitor the logcat continuously until you see the image details shown by the PageContentsCreator
  3. Cut the internet off

Expected behaviour

The app should upload the image reliably without losing data or adding duplicates to the server.

Actual behaviour

The app shows the image as "Failed" and uploads it again.

Device name

Redmi 5A

Android version

8.1.0

Commons app version

master and prodDebug

Device logs

No response

Screen-shots

No response

Would you like to work on the issue?

None

nicolas-raoul commented 11 months ago

I had not experienced this in a long time, but I just got this when testing #5399

https://commons.wikimedia.org/wiki/File:Buildings_around_Nihonbashi_12.jpg

Screenshot_20231212-182657.png

RitikaPahwa4444 commented 11 months ago

This is supposed to be a rare issue; the connectivity going off exactly at that point shouldn't happen frequently. I'll test that branch more to check if there's an increase in the frequency of this problem occurring.

nicolas-raoul commented 11 months ago

I am sure there is nothing wrong with that branch. it is just because I cut the Internet while uploading, for test purposes.

nicolas-raoul commented 8 months ago

I can still reproduce this in main, though it took 200 uploads in total over a few days. When I managed to reproduce this morning, I had uploading in parallel about four 20-pictures multi-uploads. Could be linked to me taking the elevator.

Explanation of the screencast below: One of the many pictures, despite having been uploaded successfully (as proved by the Commons website) and not being special in content nor metadata, is considered by the app as having failed. Retrying does not make the app "realize its mistake".

https://github.com/commons-app/apps-android-commons/assets/99590/d3e7c410-a12f-4d34-9e5d-a2f0cc201e93

nicolas-raoul commented 6 months ago

I just had something similar with a pic uploaded via the Nearby activity. After upload it looked like this (Adidas pic at the top):

Screenshot_20240427-144340.png

Now the same pic shows up as "Queued" then "Failed" every time I start the app.

It is actually uploaded: https://commons.m.wikimedia.org/wiki/File:Adidas_Futsal_Park.jpg and has correct structured data:

Screenshot_20240428-222123.png

It might actually be a different issue?

RitikaPahwa4444 commented 6 months ago

@nicolas-raoul, does it show up in the logcat?

nicolas-raoul commented 6 months ago

I unfortunately rebooted and thus have no logcat of the upload itself, but I can take a logcat of the queued/failed if you think that's useful.

RitikaPahwa4444 commented 6 months ago

As far as I remember, the logcat used to provide significantly useful details everytime the upload failed due to any exception (including retries). So, it might be useful.

nicolas-raoul commented 6 months ago

Here is the logcat when upload fails (with picture actually already present on the server):

04-29 17:47:28.946  9029  9126 E UploadWorker: java.lang.NullPointerException: The supplied value is null
04-29 17:47:28.946  9029  9126 E UploadWorker:  at io.reactivex.internal.operators.observable.ObservableOnErrorReturn$OnErrorReturnObserver.onError(ObservableOnErrorReturn.java:80)
04-29 17:47:28.946  9029  9126 E UploadWorker:  at io.reactivex.internal.observers.BasicFuseableObserver.onError(BasicFuseableObserver.java:100)
04-29 17:47:28.946  9029  9126 E UploadWorker:  at io.reactivex.internal.observers.BasicFuseableObserver.fail(BasicFuseableObserver.java:110)
04-29 17:47:28.946  9029  9126 E UploadWorker:  at io.reactivex.internal.operators.observable.ObservableMap$MapObserver.onNext(ObservableMap.java:59)
04-29 17:47:28.946  9029  9126 E UploadWorker:  at retrofit2.adapter.rxjava2.BodyObservable$BodyObserver.onNext(BodyObservable.java:51)
04-29 17:47:28.946  9029  9126 E UploadWorker:  at retrofit2.adapter.rxjava2.BodyObservable$BodyObserver.onNext(BodyObservable.java:37)
04-29 17:47:28.946  9029  9126 E UploadWorker:  at retrofit2.adapter.rxjava2.CallExecuteObservable.subscribeActual(CallExecuteObservable.java:47)
04-29 17:47:28.946  9029  9126 E UploadWorker:  at io.reactivex.Observable.subscribe(Observable.java:12267)
04-29 17:47:28.946  9029  9126 E UploadWorker:  at retrofit2.adapter.rxjava2.BodyObservable.subscribeActual(BodyObservable.java:34)
04-29 17:47:28.946  9029  9126 E UploadWorker:  at io.reactivex.Observable.subscribe(Observable.java:12267)
04-29 17:47:28.946  9029  9126 E UploadWorker:  at io.reactivex.internal.operators.observable.ObservableMap.subscribeActual(ObservableMap.java:32)
04-29 17:47:28.946  9029  9126 E UploadWorker:  at io.reactivex.Observable.subscribe(Observable.java:12267)
04-29 17:47:28.946  9029  9126 E UploadWorker:  at io.reactivex.internal.operators.observable.ObservableOnErrorReturn.subscribeActual(ObservableOnErrorReturn.java:31)
04-29 17:47:28.946  9029  9126 E UploadWorker:  at io.reactivex.Observable.subscribe(Observable.java:12267)
04-29 17:47:28.946  9029  9126 E UploadWorker:  at io.reactivex.internal.operators.observable.ObservableSingleMaybe.subscribeActual(ObservableSingleMaybe.java:31)
04-29 17:47:28.946  9029  9126 E UploadWorker:  at io.reactivex.Maybe.subscribe(Maybe.java:4290)
04-29 17:47:28.946  9029  9126 E UploadWorker:  at io.reactivex.Maybe.blockingGet(Maybe.java:2320)
04-29 17:47:28.946  9029  9126 E UploadWorker:  at io.reactivex.Observable.blockingSingle(Observable.java:5381)
04-29 17:47:28.946  9029  9126 E UploadWorker:  at fr.free.nrw.commons.upload.worker.UploadWorker.uploadContribution(UploadWorker.kt:360)
04-29 17:47:28.946  9029  9126 E UploadWorker:  at fr.free.nrw.commons.upload.worker.UploadWorker.access$uploadContribution(UploadWorker.kt:52)
04-29 17:47:28.946  9029  9126 E UploadWorker:  at fr.free.nrw.commons.upload.worker.UploadWorker$doWork$2$invokeSuspend$$inlined$map$1$2.emit(Emitters.kt:242)
04-29 17:47:28.946  9029  9126 E UploadWorker:  at kotlinx.coroutines.flow.FlowKt__BuildersKt$asFlow$$inlined$unsafeFlow$3.collect(SafeCollector.common.kt:115)
04-29 17:47:28.946  9029  9126 E UploadWorker:  at fr.free.nrw.commons.upload.worker.UploadWorker$doWork$2$invokeSuspend$$inlined$map$1.collect(SafeCollector.common.kt:113)
04-29 17:47:28.946  9029  9126 E UploadWorker:  at kotlinx.coroutines.flow.FlowKt__CollectKt.collect(Collect.kt:30)
04-29 17:47:28.946  9029  9126 E UploadWorker:  at kotlinx.coroutines.flow.FlowKt.collect(Unknown Source:1)
04-29 17:47:28.946  9029  9126 E UploadWorker:  at fr.free.nrw.commons.upload.worker.UploadWorker$doWork$2.invokeSuspend(UploadWorker.kt:244)
04-29 17:47:28.946  9029  9126 E UploadWorker:  at kotlin.coroutines.jvm.internal.BaseContinuationImpl.resumeWith(ContinuationImpl.kt:33)
04-29 17:47:28.946  9029  9126 E UploadWorker:  at kotlinx.coroutines.DispatchedTask.run(DispatchedTask.kt:106)
04-29 17:47:28.946  9029  9126 E UploadWorker:  at kotlinx.coroutines.internal.LimitedDispatcher.run(LimitedDispatcher.kt:42)
04-29 17:47:28.946  9029  9126 E UploadWorker:  at kotlinx.coroutines.scheduling.TaskImpl.run(Tasks.kt:95)
04-29 17:47:28.946  9029  9126 E UploadWorker:  at kotlinx.coroutines.scheduling.CoroutineScheduler.runSafely(CoroutineScheduler.kt:570)
04-29 17:47:28.946  9029  9126 E UploadWorker:  at kotlinx.coroutines.scheduling.CoroutineScheduler$Worker.executeTask(CoroutineScheduler.kt:750)
04-29 17:47:28.946  9029  9126 E UploadWorker:  at kotlinx.coroutines.scheduling.CoroutineScheduler$Worker.runWorker(CoroutineScheduler.kt:677)
04-29 17:47:28.946  9029  9126 E UploadWorker:  at kotlinx.coroutines.scheduling.CoroutineScheduler$Worker.run(CoroutineScheduler.kt:664)
04-29 17:47:28.946  9029  9126 E UploadWorker: Caused by: java.lang.Exception: uploadstash-file-not-found
04-29 17:47:28.946  9029  9126 E UploadWorker:  at fr.free.nrw.commons.upload.UploadClient$uploadFileFromStash$1.invoke(UploadClient.kt:236)
04-29 17:47:28.946  9029  9126 E UploadWorker:  at fr.free.nrw.commons.upload.UploadClient$uploadFileFromStash$1.invoke(UploadClient.kt:231)
04-29 17:47:28.946  9029  9126 E UploadWorker:  at fr.free.nrw.commons.upload.UploadClient.uploadFileFromStash$lambda$5(UploadClient.kt:231)
04-29 17:47:28.946  9029  9126 E UploadWorker:  at fr.free.nrw.commons.upload.UploadClient.$r8$lambda$DwajYXCSoltsqST39lAgwvLOkeA(Unknown Source:0)
04-29 17:47:28.946  9029  9126 E UploadWorker:  at fr.free.nrw.commons.upload.UploadClient$$ExternalSyntheticLambda4.apply(Unknown Source:2)
04-29 17:47:28.946  9029  9126 E UploadWorker:  at io.reactivex.internal.operators.observable.ObservableMap$MapObserver.onNext(ObservableMap.java:57)
04-29 17:47:28.946  9029  9126 E UploadWorker:  ... 30 more
04-29 17:47:28.946  9029  9126 E UploadWorker: Upload from stash failed for contribution : File:Adidas Futsal Park.jpg