java - 支持的、不可欺骗的方式来确定 Java 中的当前用户?
问题描述
由于各种原因,我有一个 Java 应用程序需要能够检测到哪个用户正在运行它。我已经看到了一些解决这个问题的建议,但没有一个是完全令人满意的。
有些人建议使用系统属性user.name
,但这并不可靠,因为它至少可以通过两种方式进行欺骗(更改系统查看的环境变量的值,或者通过-Duser.name
选项使用覆盖值启动程序)。
另一种选择是使用 com.sun.security.auth.module
包中的类,但 Java 规则类非常清楚为什么这不是一个好主意(例如,参见这个网页)。
这似乎是一个足够有价值的功能,应该有一种方法可以在受支持的 Java 中执行此操作,但我一直无法找到它。有什么建议么?
解决方案
由于各种原因,我有一个 Java 应用程序需要能够检测到哪个用户正在运行它。
不幸的是,在现代系统上,尤其是在 unix/posix 系统上,由用户来定义在加载 java 时加载哪些库。这可以包括拦截对检查用户名的 C 运行时 (libc) 的调用的库。
更不用说用户命名空间是多个操作系统的共同特性,它允许任何非特权用户设置任意用户名。这是设计使然。
简而言之:系统是用户的。您不能使用该系统所说的任何内容来针对任何其他系统进行身份验证。这是一个与身份验证系统一样古老的真理:您需要一个信任锚,而在您无法控制的系统上,这样的锚不是您的 - 除非您拥有 TPM 或 FIDO/加密智能卡读卡器之类的东西。
您将不得不找到一种根本不同的安全机制。如果您有任何事情要对他们隐藏,那么您永远无法信任用户的系统。想一想:您的用户很可能会启动一个他们控制一切的虚拟机;他们非常逐字节地复制原始机器的硬盘驱动器,但他们将该VM中的用户名更改为其他人的用户名。为您的系统结束游戏。
我觉得我需要重复一遍:您不能信任用户的系统。如果您的安全性取决于您的软件实际执行预期的操作(例如验证密码或检查其他任何内容,如果成功,则在某处发送数据包),那么简单的调试器可以跳过任何安全措施并执行代码您并不是要在未经身份验证的情况下被处决。作为开发人员,您知道如何使用调试器。任何用户也可以使用调试器。
推荐阅读
- python - 使用 Beautiful Soup for Python 从网格表值中抓取文本问题
- blazor-client-side - Blazor Webassembly,自定义 http 响应标头
- javascript - 可汗学院算法 - 挑战:二分搜索“While 循环运行时间过长。”
- node.js - 快递,猫鼬:我想在一个对象内“req.body”,但我不知道该怎么做
- javascript - 将新数据添加到图形时 chart.js 自动平移
- linux - C# 资源暂时不可用,在 linux 上的 dotnet 核心上阻塞套接字
- c - 使用 Xcode iOS 框架中的 C 库使用不同类型重新定义 Typedef
- r - 在 R 中的 h2o 中跨模型的交叉验证
- regex - 正则表达式在后面几行捕获字符串
- matplotlib - Seaborn 时间序列