2015-05-27 4 views
17

Ich habe ein Problem beim Aktualisieren einer App zur Unterstützung von Android Lollipop. Die App implementiert einen SyncAdapter, der über einen Inhaltsanbieter auf eine Datenbank schreibt. Gleichzeitig kann es passieren, dass der Benutzer das Front-End der App durchsucht, wo Loader dieselben Daten aus der Datenbank lesen. Loader hören auch Datenänderungen.Android Lollipop 5.0.1 SQLiteLog POSIX-Fehler 11 SQLite-Fehler: 3850

Nun, wenn ich das Programm auf einem Pre-Lollipop-Gerät ausführen, funktioniert alles ohne Fehler Ausgabe.

Auf Lollipop stattdessen erhalte ich folgende logcat Nachricht:

11:20:59.344 22341-22376/com.example.com E/SQLiteLog﹕ (10) POSIX Error : 11 SQLite Error : 3850 
11:20:59.364 22341-22376/com.example.com E/SQLiteLog﹕ (10) POSIX Error : 11 SQLite Error : 3850 
11:20:59.364 22341-22376/com.example.com E/SQLiteLog﹕ (10) POSIX Error : 11 SQLite Error : 3850 
11:20:59.364 22341-22376/com.example.com E/SQLiteLog﹕ (10) POSIX Error : 11 SQLite Error : 3850 

nun von SQLite-Dokumentation:

(3850) SQLITE_IOERR_LOCK

The SQLITE_IOERR_LOCK error code is an extended error code for SQLITE_IOERR indicating an I/O error in the advisory file locking logic. Usually an SQLITE_IOERR_LOCK error indicates a problem obtaining a PENDING lock. However it can also indicate miscellaneous locking errors on some of the specialized VFSes used on Macs. Everything seems to work properly on a high level (that is both reads and writes are performed)

und:

A PENDING lock means that the process holding the lock wants to write to the database as soon as possible and is just waiting on all current SHARED locks to clear so that it can get an EXCLUSIVE lock. No new SHARED locks are permitted against the database if a PENDING lock is active, though existing SHARED locks are allowed to continue.

Ich weiß, dass die SQLite-Version hat In Lollipop wurden nur wenige Hauptversionen aktualisiert, daher bin ich der Meinung, dass der Fehler auf ein neues Verhalten zurückzuführen ist r von SQLite, die ich nicht isolieren kann.

Aber alles scheint von einem höheren Standpunkt aus gut zu funktionieren (App stürzt nicht ab, sowohl Lese- als auch Schreibvorgänge werden ausgeführt, die Framerate fällt nicht - zumindest für menschliche Augen), aber ich möchte nicht das Problem zu ignorieren, um die App zu veröffentlichen, bis ich sicher bin, dass es keine Datenbeschädigung oder -probleme verursacht.

Vielleicht fehlen mir einige wichtige Änderungen zu Lollipop in Bezug auf Sperren und Multiprozess-Datenbankzugriff, aber ich denke, es ist ein Problem, das auf einer niedrigeren Ebene in Bezug auf die Art/Dalvik-Domäne liegt und so in einem NDK behoben werden muss Kontext.

Gibt es eine Möglichkeit, dies zu beheben, ohne eine app-spezifische Version von SQLite zu verteilen? Gibt es irgendeine Manifest-/SQLite-Option, um den Fehler zu vermeiden?

Vielen Dank im Voraus

Antwort

0

Writer die Datenbank sowohl zum Lesen und Schreiben sperrt. Das bedeutet, es muss warten, bis alle Leser die Sperren abgeschlossen und freigegeben haben, um das Schloss zu erhalten.

Nachdem der Schreiber eine Sperre angefordert hat, müssen neue Lesersperren auf den Schreiber warten, um zuerst die Sperre zu erhalten und sie dann freizugeben.

Dies könnte eine Lösung für Sie sein: WAL mode

aktivieren und WAL-Modus konfigurieren:

Eine SQLite-Datenbank-Verbindung standardmäßig journal_mode = DELETE. Um zu WAL-Modus zu konvertieren, verwenden Sie die folgende Pragma:

PRAGMA journal_mode=WAL; 

WAL nicht blockiert Leser beim Schreiben, was auch bedeutet, dass Schriftsteller nicht zu warten brauchen für aktuelle Lesesperren freigegeben werden.

Mindestens erforderliche SQLite-Version für WAL ist 3.7.0 (2010-07-21). Lollipop 5.0 verwendet SQLite 3.8.4.3 also WAL sollte für Sie verfügbar sein.

Aber WAL existiert nicht in Android-Version weniger als 3.0, obwohl es einige Ausnahmen gibt. Werfen Sie einen Blick auf Version of SQLite used in Android?. Wenn Sie Ihre App nicht unter Android 3.0 verwenden möchten, können Sie WAL verwenden.

Verwandte Themen