You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

在通过rebar3 shell运行的Erlang应用中获取隐藏用户输入

Erlang中SSH连接的密码输入与密钥认证方案

1. 实现隐藏式密码输入(交互场景)

你之前尝试的io系列函数默认会回显输入内容,而os:cmd("read -s pass")会启动独立子shell,和Erlang进程的终端环境分离,导致无法捕获输入进而阻塞。正确的做法是直接操作Erlang终端的回显选项:

get_password() ->
    IoDevice = standard_io,
    {ok, OrigOpts} = io:getopts(IoDevice),
    try
        % 关闭终端回显
        ok = io:setopts(IoDevice, [{echo, false}]),
        % 提示用户输入并读取内容
        {ok, Password} = io:get_line(IoDevice, "Enter password: "),
        % 手动输出换行(关闭回显后输入的换行不会显示)
        io:nl(),
        % 去掉输入末尾的换行符
        string:trim(Password)
    after
        % 无论成功失败,都恢复终端原配置,避免影响后续操作
        ok = io:setopts(IoDevice, OrigOpts)
    end.

调用这个函数后,终端会提示输入密码,输入过程中字符不会显示,读取完成后自动恢复终端回显。

2. 使用SSH密钥认证(非交互/更安全场景)

如果你的应用需要避免交互输入(比如后台运行),或者追求更高安全性,推荐使用SSH密钥对认证,完全替代密码输入:

步骤1:生成SSH密钥对

在终端执行以下命令生成密钥对(推荐使用ed25519算法):

ssh-keygen -t ed25519

按提示操作,默认会在~/.ssh目录下生成私钥id_ed25519和公钥id_ed25519.pub。

步骤2:配置服务器授权

将本地生成的公钥内容复制到目标服务器的~/.ssh/authorized_keys文件中,确保文件权限为600,目录~/.ssh权限为700。

步骤3:Erlang代码实现密钥认证

connect_with_ssh_key() ->
    FixedUsername = "your_hardcoded_username",
    TargetHost = "your_target_host",
    SshPort = 22,
    ConnOpts = [
        {user, FixedUsername},
        % 指定SSH配置目录,自动读取私钥文件
        {user_dir, filename:basedir(user_config, ".ssh")},
        % 生产环境建议关闭此选项,手动管理known_hosts文件
        {silently_accept_hosts, true}
    ],
    case ssh:connect(TargetHost, SshPort, ConnOpts) of
        {ok, ConnRef} ->
            io:format("SSH connection established~n"),
            ConnRef;
        {error, Reason} ->
            io:format("Connection failed: ~p~n", [Reason]),
            error(Reason)
    end.

这种方式无需输入密码,Erlang的ssh模块会自动读取私钥完成认证,适合非交互场景的应用。

内容的提问来源于stack exchange,提问作者halfway258

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.08.06 14:20:40