Sporadic IllegalArgumentException:未知的URL内容://

时间:2017-01-04 22:56:12

标签: android android-contentprovider android-contentresolver

很少得到:

Fatal Exception: java.lang.IllegalArgumentException: Unknown URL content://com.example.provider/info  
    at android.content.ContentResolver.insert(ContentResolver.java:1252)

Fatal Exception: java.lang.IllegalArgumentException: Unknown authority com.example.provider
    at android.content.ContentResolver.applyBatch(ContentResolver.java:1247)

很少强调 。一般工作正常没有问题,所以当局设置得很好,但这种情况每隔一段时间就会出现无缘无故。是否有原因导致ContentResolver无法找到ContentProvider(即如果尚未设置)?

1 个答案:

答案 0 :(得分:4)

当我在自定义IllegalArgumentException对象中执行ContentResolver操作时,我遇到了罕见的Application带有未知URI问题。

例如,我试图在应用onCreate方法中删除内容提供商中的项目,这会非常偶然地崩溃:

public class CustomApplication extends Application {

    @Override
    public void onCreate() {
        //..
        context.getContentResolver().delete(ReminderEntry.getContentURI(), null, null, null, null);
        //.. 
    }
}

有时会导致以下崩溃:

Fatal Exception: java.lang.RuntimeException: Unable to create application com.myapp.CustomApplication: java.lang.IllegalArgumentException: Unknown URL content://com.myapp.db.CustomContentProvider/reminder
   at android.app.ActivityThread.handleBindApplication(ActivityThread.java:6431)
   at android.app.ActivityThread.access$1800(ActivityThread.java:229)
   at android.app.ActivityThread$H.handleMessage(ActivityThread.java:1887)
   at android.os.Handler.dispatchMessage(Handler.java:102)
   at android.os.Looper.loop(Looper.java:148)
   at android.app.ActivityThread.main(ActivityThread.java:7331)
   at java.lang.reflect.Method.invoke(Method.java)
   at com.android.internal.os.ZygoteInit$MethodAndArgsCaller.run(ZygoteInit.java:1230)
   at com.android.internal.os.ZygoteInit.main(ZygoteInit.java:1120)
Caused by java.lang.IllegalArgumentException: Unknown URL content://com.myapp.db.CustomContentProvider/reminder
       at android.content.ContentResolver.delete(ContentResolver.java:1376)
       at com.myapp.ReminderEntryDao.delete(Unknown Source)
       at com.myapp.CustomApplication.onCreate(Unknown Source)
       at android.app.Instrumentation.callApplicationOnCreate(Instrumentation.java:1037)
       at android.app.ActivityThread.handleBindApplication(ActivityThread.java:6428)
       at android.app.ActivityThread.access$1800(ActivityThread.java:229)
       at android.app.ActivityThread$H.handleMessage(ActivityThread.java:1887)
       at android.os.Handler.dispatchMessage(Handler.java:102)
       at android.os.Looper.loop(Looper.java:148)
       at android.app.ActivityThread.main(ActivityThread.java:7331)
       at java.lang.reflect.Method.invoke(Method.java)
       at com.android.internal.os.ZygoteInit$MethodAndArgsCaller.run(ZygoteInit.java:1230)
       at com.android.internal.os.ZygoteInit.main(ZygoteInit.java:1120)

我也看到了BOOT_COMPLETE接收器的类似行为。我有大约70个报告的崩溃,这个例外(大多数是Infinix设备~43%,几乎没有任何三星设备)每月活跃用户约20万。 IllegalArguementException Device Stats

我把它搬到后台预定的工作中,从那以后就没有看到崩溃。我曾经只能在我使用的Nexus设备上重现此问题,但再也没有。

我怀疑某些设备上某些版本的Android上有时 Application / BOOT_COMPLETE Receiver会在ContentProvider完全初始化之前初始化,因此当它试图访问它,它尚未正确设置。

有几个stackoverflow帖子确实说明了首先创建的内容以及操作系统应该的行为:

Is the Application class guaranteed to be instantiated before a defined boot receiver is called

但就像我说的那样,我已经看到了其他情况,并且将操作从类中移出到后台调度程序似乎解决了问题(也许只是因为它需要花费更长的时间来进行设置)。希望我的经验能帮到你。

编辑:如果需要,我使用evernote job dispatcher并将ContentResolver操作延迟到作业。 (但我认为将内容提供程序操作推迟到任何类型的后台处理可能会修复它,因为它有更多的时间来设置 - 这些只是我的怀疑当然)。

class DeleteRemindersJob extends Job {
    @NonNull
    @Override
    protected Result onRunJob(final Params params) {
        cursor = getContext().getContentResolver().delete(ReminderEntry.getContentURI(), null, null, null, null);
        //..
        return Result.SUCCESS;
    }
}