2013-04-08 26 views
8

Tôi đang tìm cách tạm ngưng thông báo trên Uri của ContentProvider. Trường hợp sử dụng là:Tắt thông báo trên URI ContentProvider

  1. An Activity được liên kết với CursorAdapter thông qua CursorLoader.
  2. A Service có thể thực hiện rất nhiều đợt, cập nhật hàng đơn trên ContentProvider.
  3. CursorLoader sẽ tải lại nội dung của nó trên mọi cập nhật hàng, vì ContentProvider thông báo cho người nghe theo số ContentResolver#notifyChange.

Vì tôi không thể chỉnh sửa ContentProvider, và tôi không có quyền kiểm soát việc thực hiện các truy vấn hàng loạt, là có một cách để đình chỉ thông báo trên Uri (trong thực hiện Service) cho đến khi tất cả các ContentProvider truy vấn quản lý bởi đã Thực thi? Tôi cần điều này để tránh các nhấp nháy gây ra bởi việc tiếp tục requerying của CursorLoader.

+1

Để có được quyền này: Bạn phải không ảnh hưởng đến các dịch vụ cũng không phải là CP? Nếu mặt khác, Dịch vụ nằm trong tầm kiểm soát của bạn, vui lòng cung cấp thêm một chút chi tiết về loại cập nhật CP nào bạn đang thực hiện. –

+0

Tôi đang thực hiện một loạt các truy vấn "UPDATE hoặc INSERT" bên trong một vòng lặp 'for' đơn giản. Tôi đang sử dụng 'ContentProvider' để thông báo sau mỗi' chèn' hoặc 'cập nhật' nhưng, trong tình huống cụ thể này, tôi muốn có thể tạm dừng tất cả các thông báo cho đến khi tôi cập nhật xong tất cả các thực thể. – frapontillo

+0

Để chi tiết hơn nữa, tôi đang tạo ra 'ContentProvider' của tôi với một trình tạo bởi Nicolas Klein (https: // github.com/foxykeep/ContentProviderCodeGenerator), ở phần cuối của một cập nhật '(Uri uri, ContentValues ​​values, String selection, String [] selectionArgs)' thực hiện một 'getContext(). getContentResolver(). notifyChange (uri, null); '. – frapontillo

Trả lời

3

Bạn không thể tắt cơ chế này trong Dịch vụ của mình. Nhưng bạn nên cố gắng xử lý chúng bằng cách sử dụng ContentProviderOperations.

Tôi đã viết introductory post about ContentProviderOperations và hai bài đăng bổ sung bao gồm các phương pháp withYieldAllowed()withBackReference() tương ứng.

Đặc biệt, cái thứ hai nên được quan tâm đối với những gì bạn đã mô tả ở đây.

Với ContentProviderOperations bạn có thể thực hiện nhiều lần cập nhật và chèn. Nếu sau đó bạn gọi applyBatch() trên đối tượng ContentResolver của mình, ContentProvider sẽ thực hiện tất cả chúng cùng một lúc.

Bây giờ tôi chưa từng sử dụng máy phát điện Nicolas Klein nhưng kể từ khi ông là một nhà phát triển Android rất, rất thành thạo và làm việc tại Google, tôi đặt cược rằng các mã được tạo tận dụng các giao dịch cuộc gọi notifyChange() chỉ một lần cho hoàn chỉnh hàng loạt ở cuối.

Chính xác những gì bạn cần.

+0

Đoạn mã mà chúng ta đang nói đến là [cái này] (https://github.com/foxykeep/ContentProviderCodeGenerator/blob/master/generator/res/provider.txt#L184), và tôi nghĩ Nicolas không đặt bất kỳ thông báo nào trong đó vì không có thông báo 'Uri' ở cấp bảng nào, vì bất kỳ' Operation' đã cho có thể hoạt động trên bất kỳ 'Uri' nào. Tôi có đúng không? – frapontillo

+1

Bạn có thể sử dụng URI chung. Đó là những gì ContactContract và CalendarContract đang làm. Họ thông báo cho bạn vào cuối applyBatch sử dụng [CalendarContract.CONTENT_URI] (http://developer.android.com/reference/android/provider/CalendarContract.html#CONTENT_URI) hoặc [ContactsContract.AUTHORITY_URI] (http: // developer. android.com/reference/android/provider/ContactsContract.html#AUTHORITY_URI) tương ứng. Tôi đề nghị thêm một cái gì đó như thế này vào mã được tạo ra. –

+0

Tôi có thể dễ dàng thông báo các thay đổi bên ngoài 'ContentProvider' nếu tôi có thể áp dụng một loạt các phép toán mô phỏng một' INSERT OR UPDATE'. Bạn có nghĩ rằng việc mở rộng 'ContentProviderOperation' và xây dựng một hoạt động' InsertOrUpdate' tùy chỉnh có thể thực hiện được không? Điều đó sẽ giải quyết nó mà không gây rối với mã được tạo ra. – frapontillo

0

Bạn có thể thay thế trình ContentResolver của riêng mình không?

Bạn có thể thử mở rộng ContentResolver bằng lớp của riêng mình và sau đó bạn có thể ghi đè lên phương thức notifyChange và nhận ra logic của bạn ở đó.

+0

Điều này là tôi không có thông tin về thao tác được thực hiện trong 'notifyChange', vì nó có thể là thông thường cần được thông báo hoặc một" lô "sẽ không được thông báo. – frapontillo

0

Trong lớp nhà cung cấp nội dung của bạn, bên trong query() phương pháp trước khi trở về con trỏ, chỉ cần chú mã mà trông giống như sau

cursor.setNotificationUri(getContext().getContentResolver(), uri); 
+0

Có, nhưng tôi đang tìm một cách để có cùng một kết quả mà không cần sửa đổi mã/trình tạo được tạo ra. – frapontillo

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