安卓:加密密码

14

可能是重复问题:
存储密码

我正在使用共享首选项(shared preference)来存储密码。将密码数据直接保存,安全吗?还是说需要在保存前加密它。麻烦提供一些示例代码。

先行致谢,


3
在发布显然基础的问题之前请先使用搜索功能。 - user146043
我认为这个问题并不糟糕。iOS有钥匙串,我想安卓也有类似的东西,这可能是应该在这里使用的。 - Thilo
已经被问了很多次。点击查看相关讨论 - Mudassir
1
@Thilo,Android没有这样的密码或密钥存储库。密码可以存储在应用程序的共享首选项中,通常它们在普通设备上是不可访问的。但是,如果设备已经被root(这在Android上并不罕见)或者是开发者设备,那么共享首选项也是可以访问的。 - Flo
问题不好,已经关闭。真的,请使用搜索功能。它存在的理由就是为了这个。 - user146043
3个回答

26

简短回答:它是相当安全的。

长话短说:如果你正在创建一个允许用户登录到 Web/远程服务的应用程序,你可能需要查看AccountManager。学习API并与之集成有点难,但你可以获得一些不错的优势:

  1. 简单的多账户管理(所有账户都存储在 AccountManager 中)。
  2. 能够添加SyncAdapter(编写它们将会变得相当简化,因为AccountManager会使用正确的帐户调用适配器——你不必手动为每个帐户运行同步操作)。
  3. 您的应用程序将出现在 设置 > 帐户和同步 下。

在文档中查看示例同步适配器——它展示了如何使用AccountManager(如果您不需要同步内容,则可以忽略同步内容)。

现在,让我们来谈谈密码存储的安全性(以下内容适用于将密码存储在SharedPreferencesAccountManager中)。只要你的应用程序所在的设备没有经过 root,就是完全安全的。除了你的应用程序之外,没有其他应用程序可以读取密码。即使你使用 USB 电缆连接手机并使用adb pull尝试获取相应的文件,你也无法读取密码。

但是,如果手机已经被root,任何获得 root 访问权限的应用程序都可以读取密码。而且,adb pull可以正常工作,你可以在几秒钟内获取密码。

因此,建议使用加密技术保护您的网站/云服务/远程服务中的敏感数据。我在最近的项目中使用了SimpleCrypto(与AccountManager一起使用),效果很不错。如果您想知道,我只是使用了一个常量作为“主密码”。为了增强安全性,我还混淆了最终构建版本(查看方法)。


2
请注意,加密也无法防止专业黑客在已经获取 root 权限的设备上攻击,尤其是如果“主密码”在应用程序中存储。 - Thilo
@Thilo 是的,但混淆肯定有帮助。而且,你不能真的要求用户提供他的密码 :)。从网络服务中获取它也是无用的,因为“专业黑客”会找出来。 - Felix
3
完全同意。我只是想强调这里的重要部分是,将明文存储在共享首选项中已经相当安全,你需要付出很大的努力才能在其基础上做出任何显著的改进。如果你真的担心,你需要像OAuth这样去做一些事情。 - Thilo

4

在明文中存储密码永远不安全,还记得索尼最近发生的事情吗?

任何Java加密技术都可以使用。


如果Android提供密码存储的SDK(不确定是否有),我会使用它而不是自己编写。 - Thilo
2
很遗憾,目前还不支持该功能,但已经有相关的功能请求。Android支持javax.crypto包。 - Reno

1

您永远不应该直接保存密码,而是应该保存密码的哈希值。


10
如果您需要向服务器发送密码进行身份验证,仅存储哈希值是不够的。例如,Thunderbird或Firefox需要存储密码而不仅仅是哈希值。 - Thilo
3
Unnikrishnan PV从未说过密码必须发送到服务器。因此,您不能假设未指定的内容。 - Flo
可能需要更详细的解释。 - eshimoniak

网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接