Anki-android: Crash when creating a blank deck if a blank deck already exists

Created on 30 Jun 2020  路  10Comments  路  Source: ankidroid/Anki-Android

  • Create Deck - Press OK
  • Create Deck - Press OK
  • Crash

https://couchdb.ankidroid.org/acralyzer/_design/acralyzer/index.html#/report-details/dd86fc68-bd05-4d67-80ce-b9a191f962f1

2.12alpha20

com.ichi2.anki.exception.ManuallyReportedException: We looked for deck "" and instead got deck "blank".
at com.ichi2.anki.AnkiDroidApp.sendExceptionReport(AnkiDroidApp.java:1)
at com.ichi2.libanki.Decks.byName(Decks.java:5)
at com.ichi2.libanki.Decks.id(Decks.java:7)
at com.ichi2.libanki.Decks.id(Decks.java:2)
at com.ichi2.anki.DeckPicker.createNewDeck(DeckPicker.java:2)
at com.ichi2.anki.DeckPicker.p(DeckPicker.java:2)
at com.ichi2.anki.l0.onClick(lambda)
at com.afollestad.materialdialogs.MaterialDialog.onClick(MaterialDialog.java:7)
at android.view.View.performClick(View.java:5637)
at android.view.View$PerformClick.run(View.java:22429)
at android.os.Handler.handleCallback(Handler.java:751)
at android.os.Handler.dispatchMessage(Handler.java:95)
at androidx.test.espresso.base.Interrogator.a(Interrogator.java:31)
at androidx.test.espresso.base.UiControllerImpl.a(UiControllerImpl.java:130)
at androidx.test.espresso.base.UiControllerImpl.a(UiControllerImpl.java:124)
at androidx.test.espresso.base.UiControllerImpl.a(UiControllerImpl.java:59)
at androidx.test.espresso.action.GeneralSwipeAction.perform(GeneralSwipeAction.java:25)
at androidx.test.espresso.ViewInteraction$SingleExecutionViewAction.perform(ViewInteraction.java:7)
at androidx.test.espresso.ViewInteraction.a(ViewInteraction.java:31)
at androidx.test.espresso.ViewInteraction$1.call(ViewInteraction.java:1)
at java.util.concurrent.FutureTask.run(FutureTask.java:237)
at android.os.Handler.handleCallback(Handler.java:751)
at android.os.Handler.dispatchMessage(Handler.java:95)
at android.os.Looper.loop(Looper.java:154)
at android.app.ActivityThread.main(ActivityThread.java:6121)
at java.lang.reflect.Method.invoke(Native Method)
at com.android.internal.os.ZygoteInit$MethodAndArgsCaller.run(ZygoteInit.java:889)
at com.android.internal.os.ZygoteInit.main(ZygoteInit.java:779)
1   06-29 16:31:19.146 I/AnkiDroid(10382): AnkiActivity::onResume - DeckPicker
2   06-29 16:31:19.172 I/AnkiDroid(10382): Updating deck list UI
3   06-29 16:31:19.208 I/AnkiDroid(10382): AnkiActivity::onStop - MyAccount
4   06-29 16:31:19.210 I/AnkiDroid(10382): AnkiActivity::onDestroy - MyAccount
5   06-29 16:31:19.618 I/AnkiDroid(10382): DeckPicker:: Selected deck with id 1593473467576
6   06-29 16:31:19.628 W/AnkiDroid(10382): AnkiActivity/ Couldn't preload url: https://docs.ankidroid.org/manual.html#gettingStarted
7   06-29 16:31:19.653 I/AnkiDroid(10382): Updating deck list UI
8   06-29 16:31:20.139 I/AnkiDroid(10382): DeckPicker:: Selected deck with id 1593473467576
9   06-29 16:31:20.149 W/AnkiDroid(10382): AnkiActivity/ Couldn't preload url: https://docs.ankidroid.org/manual.html#gettingStarted
10  06-29 16:31:20.176 I/AnkiDroid(10382): Updating deck list UI
11  06-29 16:31:20.690 I/AnkiDroid(10382): AnkiActivity::onPause - DeckPicker
12  06-29 16:31:20.912 I/AnkiDroid(10382): AnkiActivity::onStop - DeckPicker
13  06-29 16:31:20.917 I/AnkiDroid(10382): flush - Saving information to DB...
14  06-29 16:31:21.759 I/AnkiDroid(10382): AnkiActivity::onStart - DeckPicker
15  06-29 16:31:21.801 I/AnkiDroid(10382): AnkiActivity::onResume - DeckPicker
16  06-29 16:31:21.826 I/AnkiDroid(10382): Updating deck list UI
17  06-29 16:31:26.321 I/AnkiDroid(10382): Navigating to feedback
18  06-29 16:31:26.334 I/AnkiDroid(10382): AnkiActivity::onPause - DeckPicker
19  06-29 16:31:26.511 I/AnkiDroid(10382): AnkiActivity::onStop - DeckPicker
20  06-29 16:31:27.293 I/AnkiDroid(10382): AnkiActivity::onStart - DeckPicker
21  06-29 16:31:27.323 I/AnkiDroid(10382): AnkiActivity::onResume - DeckPicker
22  06-29 16:31:27.342 I/AnkiDroid(10382): Updating deck list UI
23  06-29 16:31:29.453 I/AnkiDroid(10382): DeckPicker:: Creating new deck...
2.12.x Bug

All 10 comments

This looks like a robo-test from the on-release autotesting google does with the monkey. Any time I see "espresso" in the traces it's them because we don't currently have espresso integrated.

That means this may not be plausible user behavior, but it also means that I should have video of the issue in their release tools on the play store dashboard. I'll look - the connection to ACRAlyzer to pull device info so I can match it is helpful, as is simply being attentive and fishing this one out of ACRAlyzer, thank you

I have to admit, sometimes the amount of resources available to modern programmers is mind-boggling.

So here's the video captured from the real mobile device google auto-ran testing on as we released 2.12alpha20 that showed the problem, I uploaded it to youtube for an easy link here in our free github space for further diagnosis ;-)

video of issue

https://youtu.be/adPkrC3AnPU

Changed title.

Reproduction steps added to OP

AnkiDesktop (2.1.14 (7b93e985) and AnkiWeb (current as of today) both just silently refuse to allow empty deck names. So I will take the ecosystem rule as "deck names may not be blank for deck creation or rename" and post a PR in a bit

@mikehardy I'm on an old 2.1.28 alpha (Version 2.1.28 (f44597bb))

A deck with a single space is renamed to blank, that may also trigger this behaviour

@Arthur-Milchior - pinging as I believe you've been in this area on Anki Desktop and have a better grip on the intention of this code.

I'm going executive for the moment and saying "if you don't have at least one non-whitespace character in your deck name I'm not creating it". I'll long-toast that it's invalid.

This is indeed an interaction about two distinct PRs I created. I didn't have the first PR in mind when I created the second one, and I can't even tell that I would have thought about this interaction.

My method "byName" uses a cached map from name to deck. Each time a deck is added, renamed, ... the cache is updated.
Since I was not sure of my code, I added a test, and wanted the run to fail if the deck name found is not equal to the deck we were looking for. I actually thought it was removed in the PR before you merged it.

Then, months later, when I thought the first PR were never going to be merged, I ported some upstream code. A deck which contains only whitespace is renamed to "blank" (and if blank already exists, it gets renamed to "blank+", "blank++"...)
Even if you can't create deck with empty name, you can still sync, import a deck with empty name, etc... so that's something that could really occur.
The trouble is that I renamed it using simple json method, instead of using the deck manager. I clearly should have used the deck manager here, otherwise the problem risk to occur again.

If I may, if we had a proper java class for deck instead of a json object, that would not have occured. That was why I created such a class.

By all means go for a more thorough collision or blank fix if you want, I think disallowing user-created blank names is valid standalone and should be sufficient for now

This is a totally valid stand-alone. No doubt here. I am surprised it is not already the case; especially since I pushed a PR upstream recently (it used to forbid empty string, but not " " or " ", this is now corrected)

Was this page helpful?
0 / 5 - 0 ratings

Related issues

SimonePols picture SimonePols  路  3Comments

mashinbaz1 picture mashinbaz1  路  6Comments

sudomain picture sudomain  路  3Comments

infinyte7 picture infinyte7  路  4Comments

david-allison-1 picture david-allison-1  路  4Comments