我正在Android Studio中创建一个实现自定义ContentProvider
的Android应用。出于某种原因,每当我编译应用程序并在模拟器上测试它时,我收到此错误消息:
11-17 21:12:29.918 1381-1381/com.aiorsoft.encryptic E/AndroidRuntime﹕ FATAL EXCEPTION: main
java.lang.RuntimeException: Unable to get provider com.aiorsoft.encryptic.providers.AccountProvider: java.lang.ClassNotFoundException: Didn't find class "com.aiorsoft.encryptic.providers.AccountProvider" on path: DexPathList[[zip file "/data/app/com.aiorsoft.encryptic-2.apk"],nativeLibraryDirectories=[/data/app-lib/com.aiorsoft.encryptic-2, /system/lib]]
at android.app.ActivityThread.installProvider(ActivityThread.java:4882)
at android.app.ActivityThread.installContentProviders(ActivityThread.java:4485)
at android.app.ActivityThread.handleBindApplication(ActivityThread.java:4425)
at android.app.ActivityThread.access$1300(ActivityThread.java:141)
at android.app.ActivityThread$H.handleMessage(ActivityThread.java:1316)
at android.os.Handler.dispatchMessage(Handler.java:99)
at android.os.Looper.loop(Looper.java:137)
at android.app.ActivityThread.main(ActivityThread.java:5103)
at java.lang.reflect.Method.invokeNative(Native Method)
at java.lang.reflect.Method.invoke(Method.java:525)
at com.android.internal.os.ZygoteInit$MethodAndArgsCaller.run(ZygoteInit.java:737)
at com.android.internal.os.ZygoteInit.main(ZygoteInit.java:553)
at dalvik.system.NativeStart.main(Native Method)
Caused by: java.lang.ClassNotFoundException: Didn't find class "com.aiorsoft.encryptic.providers.AccountProvider" on path: DexPathList[[zip file "/data/app/com.aiorsoft.encryptic-2.apk"],nativeLibraryDirectories=[/data/app-lib/com.aiorsoft.encryptic-2, /system/lib]]
at dalvik.system.BaseDexClassLoader.findClass(BaseDexClassLoader.java:53)
at java.lang.ClassLoader.loadClass(ClassLoader.java:501)
at java.lang.ClassLoader.loadClass(ClassLoader.java:461)
at android.app.ActivityThread.installProvider(ActivityThread.java:4867)
at android.app.ActivityThread.installContentProviders(ActivityThread.java:4485)
at android.app.ActivityThread.handleBindApplication(ActivityThread.java:4425)
at android.app.ActivityThread.access$1300(ActivityThread.java:141)
at android.app.ActivityThread$H.handleMessage(ActivityThread.java:1316)
at android.os.Handler.dispatchMessage(Handler.java:99)
at android.os.Looper.loop(Looper.java:137)
at android.app.ActivityThread.main(ActivityThread.java:5103)
at java.lang.reflect.Method.invokeNative(Native Method)
at java.lang.reflect.Method.invoke(Method.java:525)
at com.android.internal.os.ZygoteInit$MethodAndArgsCaller.run(ZygoteInit.java:737)
at com.android.internal.os.ZygoteInit.main(ZygoteInit.java:553)
at dalvik.system.NativeStart.main(Native Method)
我已经对此进行了一些背景研究,但还没有找到解决我问题的方法。我没有在这个项目中使用ProGuard,因此排除了该服务未保留的任何内容。任何人都可以帮我解决这个问题吗?我可能会遗漏那些显而易见的东西并且正好盯着我,但我找不到它。感谢您的任何帮助!我已经在下面列出了相关文件。
这是我的清单:
<?xml version="1.0" encoding="utf-8"?>
<manifest xmlns:android="http://schemas.android.com/apk/res/android"
package="com.aiorsoft.encryptic"
android:installLocation="preferExternal"
android:versionCode="1"
android:versionName="1.0">
<uses-sdk
android:minSdkVersion="15"
android:targetSdkVersion="18" />
<uses-permission android:name="android.permission.INTERNET" />
<uses-permission android:name="android.permission.ACCESS_NETWORK_STATE" />
<application
android:icon="@drawable/ic_launcher"
android:label="@string/title_app_name"
android:theme="@style/Theme.Encryptic">
<activity android:name=".activities.MainActivity">
<intent-filter>
<action android:name="android.intent.action.MAIN" />
<category android:name="android.intent.category.LAUNCHER" />
</intent-filter>
</activity>
<service android:name=".services.ConnectionService"
android:exported="false" />
<provider
android:name=".providers.AccountProvider"
android:authorities=".providers" />
</application>
</manifest>
提供者本身:
package com.aiorsoft.encryptic.providers;
import android.content.ContentProvider;
import android.content.ContentValues;
import android.content.Context;
import android.content.UriMatcher;
import android.database.Cursor;
import android.database.SQLException;
import android.database.sqlite.SQLiteDatabase;
import android.database.sqlite.SQLiteOpenHelper;
import android.net.Uri;
import android.provider.BaseColumns;
import android.text.TextUtils;
public class AccountProvider extends ContentProvider {
private static final String AUTHORITY = "com.aiorsoft.encryptic.providers";
private static final String DATABASE_NAME = "accounts";
public static final Uri CONTENT_URI = Uri.parse("content://" + AUTHORITY + "/" + DATABASE_NAME);
private static final int DATABASE_VERSION = 1;
private static final String TABLE_ACCOUNTS = "Account";
private static final int ACCOUNTS_ALL = 1;
private static final int ACCOUNTS_SINGLE = 2;
private interface AccountColumns extends BaseColumns {
public static final String _ID = BaseColumns._ID;
public static final String USERNAME = "username";
public static final String EMAIL = "email";
public static final String TOKEN = "token";
}
private static final String[] ALL_COLUMNS = new String[] {
AccountColumns._ID, AccountColumns.USERNAME, AccountColumns.EMAIL, AccountColumns.TOKEN
};
private static final String CREATE_SQL = "CREATE TABLE "
+ TABLE_ACCOUNTS + " ("
+ AccountColumns._ID + " INTEGER PRIMARY KEY AUTOINCREMENT, "
+ AccountColumns.USERNAME + " TEXT NOT NULL, "
+ AccountColumns.EMAIL + " TEXT, "
+ AccountColumns.TOKEN + " TEXT);";
private static final String USERNAME_INDEX_SQL = "CREATE INDEX "
+ AccountColumns.USERNAME + "_idx ON " + TABLE_ACCOUNTS + " ("
+ AccountColumns.USERNAME + " ASC);";
private static UriMatcher uriMatcher;
private DatabaseHelper dbHelper;
static {
uriMatcher = new UriMatcher(UriMatcher.NO_MATCH);
uriMatcher.addURI(AUTHORITY, DATABASE_NAME, ACCOUNTS_ALL);
uriMatcher.addURI(AUTHORITY, DATABASE_NAME + "/#", ACCOUNTS_SINGLE);
}
@Override
public boolean onCreate() {
dbHelper = new DatabaseHelper(getContext());
return true;
}
@Override
public String getType(Uri uri) {
switch (uriMatcher.match(uri)) {
case ACCOUNTS_ALL:
return "vnd.android.cursor.dir/vnd." + AUTHORITY + "." + DATABASE_NAME;
case ACCOUNTS_SINGLE:
return "vdn.android.cursor.item/vnd." + AUTHORITY + "." + DATABASE_NAME;
default:
return null;
}
}
@Override
public Uri insert(Uri uri, ContentValues values) {
Uri result = doInsert(uri, values, dbHelper.getWritableDatabase());
return result;
}
@Override
public int bulkInsert(Uri uri, ContentValues[] values) {
SQLiteDatabase db = dbHelper.getWritableDatabase();
int count = 0;
try {
db.beginTransaction();
for (ContentValues value : values) {
Uri resultUri = doInsert(uri, value, db);
if (resultUri != null) {
count++;
} else {
count = 0;
throw new SQLException("Error in bulk insert");
}
}
db.setTransactionSuccessful();
} finally {
db.endTransaction();
}
db.close();
return count;
}
@Override
public Cursor query(Uri uri, String[] projection, String selection, String[] selectionArgs,
String sortOrder) {
SQLiteDatabase db = dbHelper.getReadableDatabase();
Cursor query;
// Fix the projection
if (projection == null) {
projection = ALL_COLUMNS;
}
// Fix sort order
if (sortOrder == null) {
sortOrder = AccountColumns._ID;
}
switch (uriMatcher.match(uri)) {
case ACCOUNTS_ALL:
query = db.query(TABLE_ACCOUNTS, projection, selection, selectionArgs, null, null, sortOrder);
db.close();
return query;
case ACCOUNTS_SINGLE:
String accountId = uri.getLastPathSegment();
selection = fixSelectionString(selection);
selectionArgs = fixSelectionArgs(selectionArgs, accountId);
query = db.query(TABLE_ACCOUNTS, projection, selection, selectionArgs, null, null, sortOrder);
db.close();
return query;
default:
throw new IllegalArgumentException("Invalid uri: " + uri);
}
}
@Override
public int update(Uri uri, ContentValues values, String selection, String[] selectionArgs) {
getContext().getContentResolver().notifyChange(uri, null);
SQLiteDatabase db = dbHelper.getWritableDatabase();
int rowsAffected;
switch (uriMatcher.match(uri)) {
case ACCOUNTS_ALL:
rowsAffected = db.update(TABLE_ACCOUNTS, values, selection, selectionArgs);
break;
case ACCOUNTS_SINGLE:
String accountId = uri.getLastPathSegment();
selection = fixSelectionString(selection);
selectionArgs = fixSelectionArgs(selectionArgs, accountId);
rowsAffected = db.update(TABLE_ACCOUNTS, values, selection, selectionArgs);
break;
default:
throw new IllegalArgumentException("Illegal URI: " + uri);
}
getContext().getContentResolver().notifyChange(uri, null);
return rowsAffected;
}
@Override
public int delete(Uri uri, String selection, String[] selectionArgs) {
SQLiteDatabase db = dbHelper.getWritableDatabase();
int rowsAffected;
switch (uriMatcher.match(uri)) {
case ACCOUNTS_ALL:
rowsAffected = db.delete(TABLE_ACCOUNTS, selection, selectionArgs);
break;
case ACCOUNTS_SINGLE:
String accountId = uri.getLastPathSegment();
selection = fixSelectionString(selection);
selectionArgs = fixSelectionArgs(selectionArgs, accountId);
rowsAffected = db.delete(TABLE_ACCOUNTS, selection, selectionArgs);
break;
default:
throw new IllegalArgumentException("Illegal URI: " + uri);
}
return rowsAffected;
}
private String[] fixSelectionArgs(String[] selectionArgs, String accountId) {
String[] newSelectionArgs;
if (selectionArgs == null) {
newSelectionArgs = new String[] {accountId};
} else {
newSelectionArgs = new String[selectionArgs.length + 1];
newSelectionArgs[0] = accountId;
System.arraycopy(selectionArgs, 0, newSelectionArgs, 1, selectionArgs.length);
}
return newSelectionArgs;
}
private String fixSelectionString(String selection) {
if (selection == null) {
selection = AccountColumns._ID + " = ?";
} else {
selection = AccountColumns._ID + " = ? AND (" + selection + ")";
}
return selection;
}
private Uri doInsert(Uri uri, ContentValues values, SQLiteDatabase db) {
Uri result = null;
switch (uriMatcher.match(uri)) {
case ACCOUNTS_ALL:
long id = db.insert(TABLE_ACCOUNTS, "", values);
if (id == -1) {
throw new SQLException("Error inserting data");
}
result = Uri.withAppendedPath(uri, String.valueOf(id));
break;
}
db.close();
return result;
}
public class DatabaseHelper extends SQLiteOpenHelper {
public DatabaseHelper(Context context) {
super(context, DATABASE_NAME, null, DATABASE_VERSION);
}
@Override
public void onCreate(SQLiteDatabase db) {
db.execSQL(CREATE_SQL);
db.execSQL(USERNAME_INDEX_SQL);
}
@Override
public void onUpgrade(SQLiteDatabase db, int oldVersion, int newVersion) {
}
}
}
答案 0 :(得分:0)
嗯这是愚蠢的...显然,在Android Studio设置中,我使用的SDK没有找到,所以我不得不修复它。现在一切正常!