2013-08-27 57 views
7

Tôi đã đọc tất cả mọi thứ ở đây về vấn đề này, không vượt qua điều này.Không thể tìm thấy thông tin nhà cung cấp cho <nhà cung cấp tùy chỉnh>

Tôi có một ứng dụng đơn giản bắt đầu với MainActivity, tôi Content Provider được định nghĩa một cách chính xác trong AndroidManifest.xml, lớp ContentProvider dường như Alrighty ... này đã được thử nghiệm trên một i9250 nexus chạy phiên bản 4.3 và Asus Memo Pad chạy 4.2.1 như cũng như VDevices chạy Jelly Bean. Các ứng dụng chạy trong mọi trường hợp và không sụp đổ, điều duy nhất các LogCat mang lại cho tôi là "Failed to find provider info for de.somename.provider" tại điểm mà một trong những mảnh của tôi cố gắng truy vấn Content Provider và nhận được một con trỏ. Ở đây Code:

AndroidManifest.xml

<?xml version="1.0" encoding="utf-8"?> 

<uses-sdk android:minSdkVersion="14" 
      android:targetSdkVersion="18" /> 

<application android:allowBackup="true" 
      android:icon="@drawable/ic_launcher" 
      android:label="@string/app_name" 
      android:theme="@style/AppTheme" > 
    <activity android:name="de.somename.hvk3.MainActivity" 
       android:label="@string/app_name" > 
       <intent-filter> 
        <action android:name="android.intent.action.MAIN" /> 
        <category android:name="android.intent.category.LAUNCHER" /> 
       </intent-filter></activity> 
    <activity android:name="de.somename.hvk3.UserSettingActivity" 
       android:label="@string/settings" ></activity> 
    <provider android:authorities="de.somename.provider" 
       android:enabled="true" 
       android:multiprocess="true" 
       android:name=".hvkContentProvider" 
       android:exported="true" ></provider> 
</application> 

hvkContentProvider.java

public class hvkContentProvider extends ContentProvider { 

private static final String DATABASE_NAME = "hvkDB"; 
private static final int DATABASE_VERSION = 1; 
public static final String Authority = "de.somename.provider"; 
public static final String ElementPath = "/hv_kontakte"; 
public static final Uri CONTENT_URI = Uri.parse("content://" + Authority + ElementPath); 
private static final int ALLROWS = 1; 
private static final int SINGLE_ROW = 2; 

private static final UriMatcher suriMatcher = new UriMatcher(UriMatcher.NO_MATCH); 
static{ 
    suriMatcher.addURI("de.somename.provider", ElementPath, ALLROWS); 
    suriMatcher.addURI("de.somename.provider", ElementPath + "/#", SINGLE_ROW); 
} 

public static final String KEY_ID = "_id"; 
public static final String KEY_TYPE = "type"; 
public static final String KEY_CLTYP = "cltyp"; 
public static final String KEY_MDT = "mdt"; 
public static final String KEY_OBJ = "obj"; 
public static final String KEY_VTR = "vtr"; 
public static final String KEY_FKZ = "fkz"; 
public static final String KEY_NAME = "name"; 
public static final String KEY_VNAME = "vname"; 
public static final String KEY_TEL = "tel"; 
public static final String KEY_FAX = "fax"; 
public static final String KEY_MOBIL = "mobil"; 
public static final String KEY_EMAIL = "email"; 

private MySQLiteOpenHelper myOpenHelper; 

@Override 
public boolean onCreate() { 

    myOpenHelper = new MySQLiteOpenHelper(getContext(), DATABASE_NAME, null, DATABASE_VERSION); 
    return true; 
} 

@Override 
public Cursor query(Uri uri, String[] projection, String selection, 
     String[] selectionArgs, String sortOrder) { 

    SQLiteDatabase db = myOpenHelper.getReadableDatabase(); 

    String groupBy = null; 
    String having = null; 
    SQLiteQueryBuilder queryBuilder = new SQLiteQueryBuilder(); 
    queryBuilder.setTables(MySQLiteOpenHelper.DATABASE_TABLE); 

    switch(suriMatcher.match(uri)){ 
    case SINGLE_ROW: 
     String rowID = uri.getPathSegments().get(1); 
     queryBuilder.appendWhere(KEY_ID + "=" + rowID); 
    default: break; 
    } 

    Cursor cursor = queryBuilder.query(db, projection, selection, selectionArgs, groupBy, having, sortOrder); 

    return cursor; 
} 

@Override 
public int delete(Uri uri, String selection, String[] selectionArgs) { 
    SQLiteDatabase db = myOpenHelper.getWritableDatabase(); 
    switch(suriMatcher.match(uri)){ 
    case SINGLE_ROW: 
     String rowID = uri.getPathSegments().get(1); 
     selection = KEY_ID + "=" + rowID 
       + (!TextUtils.isEmpty(selection) ? 
       " AND (" + selection + ')' : ""); 
    default: break; 
    } 
    //To return the number of deleted items you must specify a where clause. To delete all rows and return a value pass in "1" 
    if (selection == null) 
     selection = "1"; 

    return db.delete(MySQLiteOpenHelper.DATABASE_TABLE, selection, selectionArgs); 
} 

@Override 
public Uri insert(Uri uri, ContentValues values) { 

    SQLiteDatabase db = myOpenHelper.getWritableDatabase(); 
    String nullColumnHack = null; 
    long id = db.insert(MySQLiteOpenHelper.DATABASE_TABLE, nullColumnHack, values); 

    if(id > -1){ 
     Uri insertedId = ContentUris.withAppendedId(CONTENT_URI, id); 
     getContext().getContentResolver().notifyChange(insertedId, null); 
     return insertedId; 
    } 
    else 
     return null; 
} 

@Override 
public int update(Uri uri, ContentValues values, String selection, 
     String[] selectionArgs) { 

    SQLiteDatabase db = myOpenHelper.getWritableDatabase(); 

    switch(suriMatcher.match(uri)){ 
    case SINGLE_ROW: 
     String rowID = uri.getPathSegments().get(1); 
     selection = KEY_ID + "=" + rowID 
      + (!TextUtils.isEmpty(selection) ? 
      " AND (" + selection + ')' : ""); 
    default: break; 
    } 

    return db.update(MySQLiteOpenHelper.DATABASE_TABLE, values, selection, selectionArgs); 
} 

@Override 
public String getType(Uri uri) { 
    switch(suriMatcher.match(uri)){ 
    case ALLROWS: 
     return "vnd.android.cursor.dir/vnd.somename.contacts"; 
    case SINGLE_ROW: 
     return "vnd.android.cursor.item/vnd.somename.contacts"; 
    default: 
     throw new IllegalArgumentException("Unsupported URI: " + uri); 
    } 
} 

@Override 
public ParcelFileDescriptor openFile(Uri uri, String mode) throws FileNotFoundException { 

    //Find the row ID and use it as a filename 
    String rowID = uri.getPathSegments().get(1); 

    //Create a file object in the applications external files directory 
    String picsDir = Environment.DIRECTORY_PICTURES; 
    File file = new File(getContext().getExternalFilesDir(picsDir), rowID); 

    if(!file.exists()) { 
     try{ 
      file.createNewFile(); 
     } catch (IOException e) { 
      //Log.d(TAG, "File creation failed: " + e.getMessage()); 
     } 
    } 

    //Translate the mode parameter to the corresponding Parcel File Descriptor open mode 
    int fileMode = 0; 
    if(mode.contains("w")) 
     fileMode |= ParcelFileDescriptor.MODE_WRITE_ONLY; 
    if(mode.contains("r")) 
     fileMode |= ParcelFileDescriptor.MODE_READ_ONLY; 
    if(mode.contains("+")) 
     fileMode |= ParcelFileDescriptor.MODE_APPEND; 

    return ParcelFileDescriptor.open(file, fileMode); 
} 

private class MySQLiteOpenHelper extends SQLiteOpenHelper {  //used to be static 

    public static final String DATABASE_TABLE = "hv_kontakte"; 
    private static final String DATABASE_CREATE = 
      "CREATE TABLE " + DATABASE_TABLE + "(" + KEY_ID + " INTEGER PRIMARY KEY AUTOINCREMENT, " + 
        KEY_TYPE + " TEXT, " + KEY_CLTYP + " TEXT, " + KEY_MDT + " INTEGER, " + KEY_OBJ + " INTEGER, " 
        + KEY_VTR + " INTEGER, " + KEY_FKZ + " INTEGER, " + KEY_NAME + " TEXT, " + KEY_VNAME + " TEXT, " 
        + KEY_TEL + " TEXT, " + KEY_FAX + " TEXT, " + KEY_MOBIL + " TEXT, " + KEY_EMAIL + " TEXT)"; 

    public MySQLiteOpenHelper(Context context, String name, SQLiteDatabase.CursorFactory factory, int version){ 
     super(context, DATABASE_NAME, null, DATABASE_VERSION); 
    } 

    @Override 
    public void onCreate(SQLiteDatabase database) { 
     database.execSQL(DATABASE_CREATE); 
     hvkContentProvider.this.insertSomeContacts(); 
    } 

    @Override 
    public void onUpgrade(SQLiteDatabase database, int oldVersion, int newVersion) { 
     database.execSQL("DROP TABLE IF EXISTS" + DATABASE_TABLE); 
     onCreate(database); 
    } 
} 

}

HdwFragment.java

public class HdwFragment extends Fragment{ 

private SimpleCursorAdapter hdwDataAdapter; 
private ListView listview; 
public static final String ARG_SECTION_NUMBER = "section_number"; 
private static final String TAG = "HdwFragment"; 
public HdwFragment(){} 

@Override 
public View onCreateView(LayoutInflater inflater, ViewGroup container,Bundle savedInstanceState){ 

    Context context = getActivity(); 
    View rootView = inflater.inflate(R.layout.fragment_all,container, false); 
    TextView dummyTextView = (TextView) rootView.findViewById(R.id.section_label); 
    dummyTextView.setText("Dienstleister"); 
    //android.support.v4.app.LoaderManager loaderManager = getLoaderManager(); 

    Log.i(TAG, "Before getContentResolver"); 
    ContentResolver cr = context.getContentResolver(); 
    Log.i(TAG, "Before result_columns"); 
    String[] result_columns = new String[] { 
      hvkContentProvider.KEY_ID, 
      hvkContentProvider.KEY_TYPE, 
      hvkContentProvider.KEY_CLTYP, 
      hvkContentProvider.KEY_NAME, 
      hvkContentProvider.KEY_VNAME 
    }; 
    Log.i(TAG, "Before where,whereArgs and order"); 
    String where = null; 
    String whereArgs[] = null; 
    String order = null; 
    Log.i(TAG, "Before resultCursor action"); 
    Log.i(TAG, "hvkContentProvider URI: " + hvkContentProvider.CONTENT_URI); 
    Cursor resultCursor = cr.query(hvkContentProvider.CONTENT_URI, result_columns, where, whereArgs, order); 
    Log.i(TAG, "resultCursor = " + resultCursor); 
    Log.i(TAG, "Before fromColumns"); 
    String[] fromColumns = new String[]{ 
      hvkContentProvider.KEY_TYPE, 
      hvkContentProvider.KEY_CLTYP, 
      hvkContentProvider.KEY_NAME, 
      hvkContentProvider.KEY_VNAME  
    }; 
    Log.i(TAG, "Before toViews"); 
    int[] toViews = new int[]{ 
     R.id.contactType, 
     R.id.contactCltype, 
     R.id.contactName, 
     R.id.contactVname 
    }; 
    Log.i(TAG, "Before Adapter"); 
    hdwDataAdapter = new SimpleCursorAdapter(getActivity(), R.layout.object_list_item, resultCursor, fromColumns, toViews, 0); 
    listview = (ListView) rootView.findViewById(R.id.list_all); 
    listview.setAdapter(hdwDataAdapter); 
    Log.i(TAG, "Before return Layout"); 
    return (LinearLayout) rootView; 
} 

@Override 
public void onActivityCreated(Bundle savedInstanceState){ 
    super.onActivityCreated(savedInstanceState); 

    //Bundle args = null; 
    //loaderManager.initLoader(LOADER_ID, args, loaderCallback); 
} 

}

Phương pháp: insertSomeFunctions() tôi đã bỏ qua vì nó không tạo sự khác biệt ở đây, sẽ đặt một bounty trên cái này càng sớm càng tốt Thực sự cần phải thực hiện điều này.

Trả lời

17
<provider android:authorities="de.somename.provider" 
    android:enabled="true" 
    android:multiprocess="true" 
    android:name=".hvkContentProvider" 
    android:exported="true" ></provider> 

Từ trang tài liệu tham khảo trên <provider>: Link

android: cơ quan chức năng: ...... Để tránh xung đột, tên thẩm quyền nên sử dụng quy ước đặt tên theo kiểu Java (chẳng hạn như com.ex ample.provider.cartoonprovider). Thông thường, đó là tên của lớp con ContentProvider triển khai nhà cung cấp.

Trong trường hợp của bạn, android:authorities phải có giá trị: de.somename.provider.hvkContentProvider.


android: name: ...... Cái tên của lớp mà thực hiện cung cấp nội dung , một lớp con của ContentProvider.Đây phải là đầy đủ tên lớp đủ điều kiện (chẳng hạn như, "com.example.project.TransportationProvider"). Tuy nhiên, dưới dạng ký hiệu là , nếu ký tự đầu tiên của tên là một khoảng thời gian, nó là được thêm vào tên gói được chỉ định trong phần tử.

Vì vậy, nếu bạn đang định package trong thẻ manifest của AndroidManifest.xml, hãy chắc chắn hvkContentProvidertrong gói đó. Khác, thay đổi android:name=".hvkContentProvider" đến android:name="de.somename.hvk3.hvkContentProvider" hoặc your.package.name.hvkContentProvider

+4

Bạn đã đưa tôi đi đúng hướng ... cảm ơn bạn. Đề xuất của bạn đã bắt đầu đưa các lỗi khác mà cuối cùng dẫn tôi đến giải quyết vấn đề của nhà cung cấp nội dung. Bạn đã làm cho tôi di chuyển một lần nữa mặc dù ... –

4

Hãy thử sử dụng đường dẫn đủ điều kiện trong android:authorities do đó thay thế de.somename.provider bằng de.somename.provider.hvkContentProvider để nó trở thành như sau.

<provider android:authorities="de.somename.provider.hvkContentProvider" 
       android:enabled="true" 
       android:multiprocess="true" 
       android:name=".hvkContentProvider" 
       android:exported="true" ></provider> 

Bạn có thể refer this

Các vấn đề liên quan