动态设置ContentProvider的权限 [英] Dynamically set the authority of a ContentProvider

查看:425
本文介绍了动态设置ContentProvider的权限的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

也许标题有点误导.我的问题是我有一个Android库项目,该项目在两个标准Android项目之间共享:一个用于应用程序的免费版本,另一个用于付费版本.该库当前具有ContentProvider的代码,包括一个带有几个静态String变量的协定类,用于处理诸如URI和列名之类的内容.现在,我希望根据哪个应用程序正在使用库来更改URI的权限".我想到的一种解决方案是将权限存储为字符串资源,并在运行时将该字符串加载到静态最终String变量中.但是,我不确定如何执行此操作,因为contract类具有私有构造函数且没有Context对象才能加载字符串资源.还有什么其他选项可以解决我的问题?

Perhaps the title is a bit misleading. My problem is that I have an Android library project which is shared between two standard Android projects: one for a free version of the app and the other for a paid version. The library currently has the code for a ContentProvider, including a contract class with several static String variables for things such as the URI and column names. Now I want the "authority" for the URI to change depending on which app is using the library. One solution that comes to mind is storing the authority as a string resource and loading that string at run-time into the static final String variable. However, I'm not sure how to do this as the contract class has a private constructor and no Context object in order to load the string resource. What other options are available to solve my problem?

推荐答案

使用不同的免费和付费版本授权可以防止用户尝试安装两个版本. 我为清单中的两个版本定义了不同的权限,如下所示:

Using different authorities for the free and the paid version makes sense in case the user tries to install both versions. I'm defining a different authority for the two versions in the manifest like so:

<provider
    android:name="MyApp.MyProvider"
    android:authorities="MyApp.MyProvider.free"
    android:grantUriPermissions="true"/>

然后,我在xml文件中配置提供程序(我使用特殊的config.xml文件,因为我有更多的配置数据,例如提供程序权限,但是您当然可以使用strings.xml):

Then I configure the provider in an xml file (I use a special config.xml file because I have more configuration data like the provider authority, but you can use strings.xml of course):

<string name="my_provider_authority">MyApp.MyProvider.free</string>

该代码与其他任何字符串资源一样检索提供者权限.要在没有上下文的情况下访问字符串资源,请使用应用程序上下文.我正在使用应用程序类从应用程序中的任何位置访问应用程序上下文(尽管有两个例外):

The code retrieves the provider authority as any other string resource. To access string resources without a context use the application context. I'm using an application class to have access to the application context from anywhere in my app (there are two exceptions though):

public class MyApplication extends Application {
    private static Context sContext;

    @Override
    public void onCreate() {
        super.onCreate();
        sContext = this;
    }

    public static Context getContext() {
        return sContext;
    }
}

当然,您需要在清单中定义MyApplication. 这使您可以从应用程序中的任何位置访问字符串和其他资源. 但是有两个例外:

Of course you need to define MyApplication in your manifest. This allows you to access string and other resources from anywhere in your app. There are two exception though:

  1. ContentProviders. ContentProvider可以在Application启动之前启动,因此您将没有Application上下文.但这没问题,因为ContentProvider通过getContext()获得了自己的上下文.
  2. 静态代码:上下文可能在Android组件(活动,片段,BroadcastReceivers,服务等)的生命周期之外不可用.因此,依赖于应用程序上下文的静态初始化器不是一个好主意.但这也不是真正的问题,因为无论如何都不允许在Android组件生命周期之外使用上下文,并且始终会在该生命周期内调用访问上下文的静态方法.例如.如果一个活动需要知道ContentProvider的权限,它将在您的合同类中调用一个静态方法,并且该调用将来自该活动的onXYZ()方法之一,如onCreate()或onStart(),这将确保上下文已初始化.因此,您需要做的就是懒惰地在合约类中初始化变量,并确保仅在很明显之前已调用Application.onCreate()的情况下,调用方才检索变量.当然,您可以在活动中直接检索字符串资源.当您需要其他类/对象中的资源时,我的方法的真正优势将变得显而易见.这些对象仍将与某些Android组件的生命周期相关联,但您不必将上下文传递给所有这些对象,这是1)非常繁琐,并且2)在泄漏上下文时很容易出错,可能会导致内存使用问题(Android应用程序最常见的问题之一).

这篇关于动态设置ContentProvider的权限的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆