android - 如何在 Android 中的一组应用程序之间共享数据

标签 android sharedpreferences android-contentprovider android-external-storage

考虑以下场景。一家公司发布了许多应用程序。他们希望在所有这些应用程序之间共享一些数据。这些应用程序中的任何一个都可以创建或读取这些数据,就像一个普通的数据库一样。因此,公司决定创建一个用于此目的的 android 库。我搜索了几天,下面给出了我的分析。

  • SharedPreferences - 不推荐且已弃用。它也没有达到目的。所有其他应用程序都需要知道创建数据以创建 PackageContext 的应用程序的包名称。在这里这是不切实际的,因为任何应用程序都可以创建/更新/读取数据,并且无法确定谁是谁。
  • ContentProviders - 这对我不起作用。原因是每个应用程序中都必须存在 ContentProviders。一个设备中不能有 2 个同名的内容提供者。除此之外,ContentProviders 基本上是为一个应用程序创建数据而其他应用程序使用 Content_Uri 订阅它。
  • 网络连接 - 我们不想在任何服务器中存储数据。
  • 外部存储 - 这是剩下的唯一选择。我应该去吗?

  • 有趣的是,数据也必须受到保护,任何存储选项都不支持。

    注意:对于 iOS,我们使用钥匙串(keychain)来实现相同的功能

    最佳答案

    了解 Android 上的问题

    具有讽刺意味的是,由于 iOS 上的密集沙箱,如果需要共享数据的应用程序都由同一个开发人员提供,则有一种直接的方法(应用程序组)可以实现这一点。可能是因为 Android 在安全性方面更加灵活,这实际上最终成为一个更困难的问题。迄今为止,Android 团队认为不适合提供一种方便且安全的方式来专门共享此类数据,因为安全性较低的解决方法。

    也就是说,有很多方法可以在不涉及云的情况下在应用程序之间共享数据。

    共享首选项

    原始问题指出 SharedPreferences 已弃用。据我所知,这不是真的,但是不推荐使用 MODE_WORLD_READABLE 和 MODE_WORLD_WRITABLE 上下文,这使得这种方法在 future 无法工作。不过,自 Android 4.2 (2012) 以来,该模式已被弃用一段时间。当前的 Android 文档中没有任何威胁表明他们实际上正在逐步淘汰它(有时弃用只是意味着“这不是一个好主意”而不是“这将被删除”)。我怀疑在设置级别缺乏更安全的操作系统级别的应用程序数据共享直接替代方案可能是过去 5 年将其保留在弃用状态的原因。

    文件访问

    我所知道的在 Android 上的应用程序之间实现数据共享的最简单和最常见的方法是简单地请求设备上的文件访问权限并在外部存储上为此数据创建一个共享位置。 (不要被“外部存储”的名称所迷惑——这就是 Android 指代共享数据的方式。它不一定指的是 SD 卡。)你给文件一个唯一的名字,然后把它存储在某个地方您的应用程序知道在哪里寻找它。获得该路径的最佳方法是:
    Environment.getExternalStoragePublicDirectory(Environment.DIRECTORY_DOCUMENTS)

    这样做的明显问题是安全性。虽然没有被操作系统弃用,但它引入了与 Android 文档列出的相同问题作为弃用 MODE_WORLD_* 的原因——它本质上是不安全的,并在您的应用程序中打开了潜在的漏洞。

  • 你将你的信息放在一切都可以访问的地方
    它。
  • 您正在请求您的应用程序可能不需要的权限。
  • 您正在阅读无法验证其来源的文件。

  • 如果您的应用程序不处理任何敏感数据,这可能对您来说无关紧要(可能对您的用户而言)。如果您打算从这些文件中读取数据,则应确保在解析之前为该数据提供最大程度的验证。检查文件大小,验证格式等。

    创建您自己的服务

    你总是可以创建一个服务或一个 IntentService。 (两者之间有细微的差别,但 IntentService 是 Service 的一个子类,它运行在一个 Worker 线程中,而 Service 会中断主线程。IntentService 还实现了 Intent 支持,它提供了 Android 上最直接的应用间通信)。

    这个服务有自己的私有(private)存储,它有完全的读/写访问权限,但没有其他功能。然后,该服务提供一个接口(interface)来接收来自其他应用程序的 Intent,并将结果(作为 Intent)返回给这些应用程序。这是一种非常友好的方式来实现应用间数据,同时最大限度地提高数据的隐私性和安全性。如果外围应用程序大多需要从中央应用程序请求非常基本的信息,这是您的入门级选项。

    实现广播接收器

    同样是 BroadcastReceiver 类。根据您打算在应用程序之间共享的数据类型以及这些应用程序对您的特定方法的熟悉程度,这是另一种可能性。同样,您将在一个应用程序的私有(private)存储下管理共享数据。通信由 Intent 完成,因此它类似于 IntentService - 除了应用程序可以通过发出系统范围的事件与 BroadcastReceiver 通信(也就是说,它们不需要与您的应用程序或服务显式通信 - 它们正在大声喊叫世界获取一条信息,并期待答案。)

    创建一个 ContentProvider

    原始帖子似乎误解了 ContentProvider 是什么以及它是如何工作的。您必须像考虑云解决方案一样考虑此类项目 - 即使它在您的设备本地。每个应用程序都不需要 ContentProvider——它们都需要与 ContentProvider 通信,而 ContentProvider 维护、更新和返回数据。

    对于这个特定用例,这可能是最“Android-y”的解决方案,并提供了最大的可扩展性。您实现了一个独立的进程来处理数据存储并响应其他应用程序。然而,这是一个更进化的解决方案——因此可能更具挑战性。如果你需要一个真正的数据库服务,而不是一个相当简单的请求/响应类型的服务,ContentProvider 似乎是最好的选择。

    关于android - 如何在 Android 中的一组应用程序之间共享数据,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/19691171/

    相关文章:

    android - 更改升级时的默认首选项

    android - 共享文件到邮件时更改附件名称

    android - Android 上的异常 'open failed: EACCES (Permission denied)'

    android - 来电时停止和启动音乐

    android从java设置默认首选项

    java - 共享偏好 VS 上下文?

    java - 如何在Android 8.0中查看默认图库的图像?

    Android浏览器历史URI?

    android - 如何将屏幕坐标转换为控件坐标

    android - 我需要带有游标加载器的内容提供程序吗?