2010-11-21 6 views
5

갑자기 내 응용 프로그램이 사용하는 데이터베이스가 손상된 것 같습니다. 데이터베이스의 구조는 변경하지 않았지만 오늘은 장치에 여러 번 응용 프로그램을 다시 배포했습니다.왜 안드로이드 SQLite DB가 갑자기 손상 되었습니까?

다음 예외가 발생합니다.

E/Database(14281): CREATE TABLE android_metadata failed err=26 .. 
E/Database(14281): Failed to setLocale() when constructing, closing the database 
E/Database(14281): android.database.sqlite.SQLiteException: file is encrypted or is not a database 
E/Database(14281): at android.database.sqlite.SQLiteDatabase.native_setLocale(Native Method) 
E/Database(14281): at android.database.sqlite.SQLiteDatabase.setLocale(SQLiteDatabase.java:1848) 
E/Database(14281): at android.database.sqlite.SQLiteDatabase.<init>(SQLiteDatabase.java:1798) 
E/Database(14281): at android.database.sqlite.SQLiteDatabase.openDatabase(SQLiteDatabase.java:798) 
E/Database(14281): at android.database.sqlite.SQLiteDatabase.openOrCreateDatabase(SQLiteDatabase.java:857) 
E/Database(14281): at android.database.sqlite.SQLiteDatabase.openOrCreateDatabase(SQLiteDatabase.java:850) 
E/Database(14281): at android.app.ApplicationContext.openOrCreateDatabase(ApplicationContext.java:539) 
E/Database(14281): at android.content.ContextWrapper.openOrCreateDatabase(ContextWrapper.java:193) 
E/Database(14281): at android.database.sqlite.SQLiteOpenHelper.getWritableDatabase(SQLiteOpenHelper.java:98) 
E/Database(14281): at com.ecs.android.gps.storage.DBAdapter.open(DBAdapter.java:75) 

데이터베이스는 SQLLiteOpenHelper 클래스를 사용하여 초기화됩니다. 나는 기본적으로 개방하고있어

public DBAdapter(Context ctx) 
{ 
    this.context = ctx; 
    DBHelper = new DatabaseHelper(context); 
} 

private static class DatabaseHelper extends SQLiteOpenHelper 
{ 
    DatabaseHelper(Context context) 
    { 
     super(context, DATABASE_NAME, null, DATABASE_VERSION); 
    } 

    @Override 
    public void onCreate(SQLiteDatabase db) 
    { 
     db.execSQL(DATABASE_CREATE); 
    } 

    @Override 
    public void onUpgrade(SQLiteDatabase db, int oldVersion, 
    int newVersion) 
    { 
     Log.w(TAG, "Upgrading database from version " + oldVersion 
       + " to " 
       + newVersion + ", which will destroy all old data"); 
     db.execSQL("DROP TABLE IF EXISTS location_history"); 
     onCreate(db); 
    } 
} 
  • /각 작업에 대한 데이터베이스 및 커서 모두 을 닫는.
  • 일부 기사는이 길을 가야하는 것 표시하지만, 안드로이드 앱 오픈 모든 시간을 데이터베이스 연결을 유지하기 위해 더 의미 을하지 않을까요?
  • 더 많은 리소스를 개봉/닫을 때마다 매번 상상할 수 있습니다.
  • 데이터베이스에 액세스하는 여러 활동 및 서비스가 있습니다. (잠재적으로 동시에)
  • 나는 로그

모든이의 원인이 수 있는지 아이디어, 어떻게에서 복원하는 방법과 미래에이 문제를 방지 할 수있는 예외를 본 적이? 몇 가지 동시성 문제 (데이터베이스를 열거 나 닫거나 읽거나 쓰려고하는 여러 스레드)로 인해 예외가 발생했다는 인상을받습니다. 나는 다중 스레드 액세스, 잠금 등의 경우 SQLite 데이터베이스가 일반적인 데이터베이스 (mysql - oracle)만큼 견고하다는 것을 알지 못합니다 .....

+0

데이터 액티비티를 사용하여 여러 액티비티간에 데이터를 공유 한 적이 있습니까? – Emile

+0

그것은 내가 할 일 목록에 있으며, 내가 이해하는 바에 따르면, 당신에게 많은 배관을 해줄 수있는 옵션이 될 수 있지만, 나는 읽고 쓰는 테이블이 하나 밖에 없다. 데이터를 다른 앱에 공개 할 의도도 없습니다. 난 그냥 어떻게 손상되는지, 그리고 그것을 피할 수있는 방법을 알고 싶습니다 (여전히 표준 SQLiteDatabase 및 SQLiteOpenHelper 클래스를 사용하여) – ddewaele

+0

당신이 이미 그것을 고쳐주지 않으면, 나는 rosstheboss의 대답을 더 조사 할 것입니다. 데이터베이스에 액세스하는 서비스와 활동이 있다고 언급했습니다. 감추어 진 두 가지 활동이 실제로는 결코 활동적이지 않다는 것을 감안하면 안전하다고 생각할 수 있습니다 (r). 그러나 언급 한 서비스는 아마도 활동과 동시에 실행될 것입니다. 나는 java의 전문가는 아니지만, 데이터베이스 잠금에 대한 잠금/확인을 돕는 몇 가지 메소드가 있다고 생각합니다. 나는. 이미 열려 있거나 데이터베이스를 잠 그거나 잠금 해제합니다. 이렇게하면 충돌을 피하고 적어도 오류를 포착 할 수 있습니다. – Emile

답변

0

아마도 데이터베이스를 불법으로 남겨 둡니다. 어떤 식 으로든, 비록 그것이 일반적으로 표시되고 모든 것이 잘 수행되지만.

+0

기본적으로 각 작업에서 데이터베이스와 커서를 열고 닫습니다. 데이터베이스에 액세스하는 여러 활동 및 서비스가 있습니다. 그러나 로그에서 예외를 보지 못했습니다. – ddewaele

+0

큰 문제는 여기서 복구 할 수있는 쉬운 방법이 없다는 것입니다. 기본적으로 응용 프로그램을 제거하고 (데이터베이스를 삭제하도록 함) 응용 프로그램을 다시 설치하여 상황을 차단 해제해야합니다. – ddewaele

+0

시도해 볼 수 있습니다. sdk tools 폴더로 이동하여 쉘 도구 adb를 실행하십시오. 그런 다음 sqlite3을 사용하여 테이블을 탐색하십시오. 그래도 작동하지 않으면 여기에서 로컬 시스템으로 복사하여 다른 도구로 복구 할 수 있습니다. – Emile

0

Ae sql lite DB 파일은 텍스트 형식으로 읽을 수 없습니까? DB 파일을 구문 분석하여 재구성 할 수 없었습니까? 또한 로캘 속성은 안드로이드가 당신을 위해 제시하는 메타 데이터 테이블에 설정되지 않습니다. 그렇다면 테이블을 떨어 뜨리면 수동으로 DB를 복구 할 수 있습니다.

+0

DB 파일을 재구성하는 로직을 구현하는 것은 실제로 여기 구현하는 것 같지 않습니다 :) android_metadata는 실제로 스택 추적에서 판단하여 자동으로 생성되지만 내 느낌은 Android가 이미 DB가 손상되었다고 결정한 것입니다. 그리고 그 시점에서, 그것은 데이터베이스를 삭제하고 그것을 다시 만듭니다 (저는 이것이 표준 Android SQLite 동작이라고 생각합니다). 재창조 중에 실패합니다. 나는 부패에 이르는 잘못된 행동을 알아 내려고 노력하고 있습니다. – ddewaele

+0

그래서 문제를 되풀이 할 수 있습니까? 앱을 다시 설치할 때마다 – Emile

+0

댓글에서 언급 한 재 작성은 DB를 처음 만들 때 (앱 설치시)가 아니라 안드로이드가 손상된 db 파일을 발견했을 때 발생하는 재창조를 의미합니다. 재현하기가 매우 어렵습니다 ... 며칠 동안 앱을 실행할 수 있으며 갑자기 나타납니다. 다음에 몇 시간 후에 팝업이 나타납니다. – ddewaele

관련 문제