引言
使用场景:
我所在的smb环境下,只要出现网络异常断开后,再次打开smb共享目录就会出现问题,这个时候就需要在shell下重新设置smb的密码。
标准用法:
使用sudo smbpasswd nferzhuang来设置nferzhuang的smb密码,输入命令后还需要输入一次sudo的密码和两次smbpasswd的密码
[email protected]:~$ sudo smbpasswd nferzhuang [sudo] password for nferzhuang: New SMB password: Retype new SMB password: [email protected]:~$
一句话脚本用法:
passwd=nferzhuang && (echo $passwd;echo $passwd) | sudo -A smbpasswd nferzhuang -s
或
passwd=nferzhuang && printf "${passwd}\n${passwd}\n" | sudo -A smbpasswd nferzhuang -s
上面的脚本分解步骤是:
- 设置一个临时变量passwd,其意义是需要设置smb密码
- 通过echo或printf输出passwd的值两次并通过管道传递给smbpasswd命令。(此处输出两次,是因为在smbpasswd的时候需要输入两次密码来确认)
- 通过sudo -A参数来避免sudo时输入密码
- 通过smbpasswd nferzhuang -s参数来使用上面echo的输出作为smbpasswd的输入
其中临时变量以及echo的操作比较简单,不再赘述。下面分别描述一下sudo -A参数和smbpasswd -s参数。
注:如果你执行上面的一句话脚本失败了,是因为你没有设置SUDO_ASKPASS环境变量,或者SUDO_ASKPASS环境变量指向的文件没有输出有效值,具体见下一章节。
sudo -A参数详解
先看一下sudo的man手册中针对-A参数的说明:
-A Normally, if sudo requires a password, it will read it from the user‘s terminal. If the -A (askpass)
option is specified, a (possibly graphical) helper program is executed to read the user‘s password and
output the password to the standard output. If the SUDO_ASKPASS environment variable is set, it
specifies the path to the helper program.
其大致意思是,在使用sudo命令时,如果有-A参数,则需要通过helper program(如果是UI,则可以通过用户输入)来产生sudo密码,而这个helper program的路径是有SUDO_ASKPASS环境变量来指定的。
在博文《让某一个sudo命令不需要输密码》中提供了一种方法,就是写一个最简单的c程序,通过printf来输出sudo的密码。在这里,如果对于安全没有特殊要求,则可以使用下面的一个简单的shell脚本来输出sudo的密码:
#!/bin/bash echo nferzhuang
注:创建后一定要使用chmod 700 sudo_passwd_helper.sh来设置该文件的读写执行权限完全为当前用户。否则别人直接cat一下就得到你的sudo密码了,这样做坏事就留你名了!!!
创建该脚本后,需要设置SUDO_ASKPASS环境变量来指向该helper program,而为了在每一个ssh窗口都能正常执行,需要将该环境变量设置添加到~/.bashrc文件中:
export SUDO_ASKPASS=~/bin/sudo_passwd_helper.sh
smbpasswd -s参数
同理,先看一下smbpasswd的man手册中针对-s参数的说明:
-s This option causes smbpasswd to be silent (i.e. not issue prompts) and to read its old and new passwords from
standard input, rather than from /dev/tty (like the passwd(1) program does). This option is to aid people
writing scripts to drive smbpasswd
其大致意思是,如果使用-s参数,则smbpasswd会通过标注输入(stdin)来读取需要的密码,而没有该参数时,则通过当前的TTY读取用户输入。因为在之前通过echo或printf已经在stdin产生了两个passwd,并通过"|"管道提供给smbpasswd命令来使用。
总结
本次一句话脚本使用到了以下知识:
- 临时变量的设置和读取
- echo和printf命令来输出变量的值
- &&和;来连接多个命令执行
- sudo命令的-A参数
- 环境变量的设置
- ~/.bashrc文件的作用
- smbpasswd的-s参数
- chmod命令来设置文件的权限