我的问题是如何赋予我的 java 程序“sudo”权限,以便能够写入该文件并保存这些编辑。
我认为简单的答案是你不能。
Sudo 的工作原理是检查文件以查看用户是否允许运行命令,并可选择通过询问他/她的密码来确认他/她的身份。如果这两个都签出,则该sudo
命令以不同的用户身份执行请求的命令;通常root
.
然而,为了做到这一点,“sudo”程序本身被实现为“setuid”程序;即本身以提升的权限运行的程序。没有这个,它不能以“root”身份运行所请求的程序,甚至不能读取“/etc/sudoers”文件。
那么我们可以在 Java 中模拟“sudo”吗?
基本上,没有。为此,您需要将该java
命令设置为“setuid”程序。但是该java
命令可以执行任何人编写的任何 java 程序。因此,“setuid”java
将允许任何人以管理员权限运行任何 java 程序。那将是非常不安全的。
那么有哪些替代方案呢?
您可以使用ProcessBuilder
“执行”sudo
命令作为外部命令。sudo
但是,无法通过其命令行传递密码。因此,您需要:
配置sudoers
文件以允许在没有密码的情况下执行(特定)命令(可能很危险),或者
找出一种使用--askPass
钩子从 Java 安全地请求用户密码的方法,或者
使用--stdin
从标准输入而不是用户终端读取用户密码的选项。
编写自定义“setuid”(或“setgid”)包装器来执行管理命令。注意:“setuid”shell 脚本根本上是不安全的。AC / C++ 包装器可能是最安全的方法......但您需要确保包装器不会通过提供聪明的参数或环境变量而被欺骗做一些危险/讨厌的事情。
不要在Java中这样做。让用户从命令行运行特权命令;例如使用sudo
. 您可以通过提供一个脚本(shell、perl 等)来处理任何复杂的事情、进行完整性检查等,从而使用户更容易使用。
我的建议是方法#3(一般而言)。这是最安全和最透明的方法。(作为管理员/高级用户,我会对一些复杂/不透明的 Java 应用程序要求我的密码来在我的系统上运行命令感到非常不舒服。)sudo
警告
安全可靠地做这种事情需要很好地理解 UNIx / Linux 安全性是如何工作的。您可能会犯许多错误(太多无法列出),这些错误可能会危及安全性,并允许用户以 root 身份运行任意程序或其他危险/破坏性的东西。小心,请一位真正的 UNIX/Linux 专家来审查您实现的机制。