struct spwd { char *sp_namp; /* user login name */ char *sp_pwdp; /* encrypted password */ long int sp_lstchg; /* last password change */ long int sp_min; /* days until change allowed. */ long int sp_max; /* days before change required */ long int sp_warn; /* days warning for expiration */ long int sp_inact; /* days before account inactive */ long int sp_expire; /* date when account expires */ unsigned long int sp_flag; /* reserved for future use */ }
經過查看shadow的手冊,能夠看到上面的代碼解釋,分別對應/etc/shadow 中的各項參數linux
mail:*:15513:0:99999:7:::
參數一: sp_namp 用戶名稱算法
參數二: sp_pwdp 用戶加密後的密碼安全
參數三: sp_lstchg 用戶密碼最近一次修改時間,算法是今天的時間減去jan,1,1970獲得的時間間隔bash
參數四: sp_min 用戶最少多少天后才能改密碼的天數(默認爲0,表示能夠在任什麼時候間修改,有啥意義?有種需求叫密碼永不變= =。)測試
參數五: sp_max 用戶最多多少天后必定要修改密碼的天數,系統會強制用戶修改密碼(默認爲99999,改成1 也能讓密碼改不了)ui
參數六: sp_warn 過時前多少天時間會被警告(改成-1 則永遠不會提示)this
參數七: sp_inact 過時後多少天內帳號變爲inactive狀態,可登錄,但不能操做 加密
參數八: sp_expire 多少天后帳號會過時,沒法登錄spa
參數九: sp_flag 保留參數code
————————————————————————————————————————————————————————
根據上述功能,我考慮了個需求
1. 查看當前全部用戶何時過時的,用日期的表示方法表示出來
首先實現這個功能手動去加減實在不必,linux有個date命令自帶了個轉換功能(實在是人性化,修改days爲sec 能夠獲得相加秒的結果)
[root ]# date -d "1970-01-01 15776 days" +%Y/%m/%d 2013/03/12
而後,就簡單啦~~寫個腳本轉換下,一個awk能夠搞定
再爲了看的整齊點
#! /bin/bash # FILE=/etc/shadow awk -F ':' '{ if ($2 != "*" && $2 != "!!" ) { NAME=$1; MAX_CH=$3+$5; EXPIRE=$3+$8; CMD="echo -e "NAME" \"\t\`date -d \"1970-01-01 "MAX_CH" days\" +%Y/%m\` \t`date -d \"1970-01-01 "EXPIRE" days\" +%Y/%m\`\" " system(CMD); } }' $FILE 2>/dev/null |sort -k 3 | awk '{printf("%-15s%-15s%-15s\n",$1,$2,$3)}'
2.根據密碼安全規則考慮,除了root用戶 全部用戶應該要3個月必須改一下密碼並設置下時間提醒
這個需求涉及到如何修改已有用戶的各項屬性
先來了解個命令
[root@Bridge ~]# chage --help Usage: chage [options] [LOGIN] Options: -d, --lastday LAST_DAY set date of last password change to LAST_DAY -E, --expiredate EXPIRE_DATE set account expiration date to EXPIRE_DATE -h, --help display this help message and exit -I, --inactive INACTIVE set password inactive after expiration to INACTIVE -l, --list show account aging information -m, --mindays MIN_DAYS set minimum number of days before password change to MIN_DAYS -M, --maxdays MAX_DAYS set maximim number of days before password change to MAX_DAYS -W, --warndays WARN_DAYS set expiration warning days to WARN_DAYS
新建一個測試帳號 testlinjq:*****:16772:0:99999:7:::
根據需求chage –M 6 testlinjq ,令該「testlinjq」用戶第七天就要改密碼,測試下warning參數是否會提醒
testlinjq:*******:16772:0:6:7:::
Warning: your password will expire in 6 days Last login: Thu Dec 3 14:57:50 2015 from 10.0.0.120
確實生效了,那麼本次修改的帳號屬性應該有3個。
1. 用戶上一次修改時間,改成今天,即從今天起後3個月要改密碼,對應命令chage –d 16772
2. 用戶最大超時時間,90天 chage –M 89,(有強迫症的同窗能夠給改爲90,測試了確實是從0開始計數)
3. 用戶密碼超時提醒開啓,方便起見,我給設置成99,至關於永遠提醒,只要比MAX的值大就行 chage –W 99
最終造成以下腳本
#! /bin/bash # FILE=/etc/shadow OUTPUT=/tmp/expire-time function PRINTUSERS { awk -F ':' '{ if ($2 != "*" && $2 != "!!" ) { NAME=$1; MAX_CH=$3+$5; EXPIRE=$3+$8; CMD="echo -e "NAME" \"\t\`date -d \"1970-01-01 "MAX_CH" days\" +%Y/%m/%d\` \t`date -d \"1970-01-01 "EXPIRE" days\" +%Y/%m/%d\`\" " system(CMD); } }' $FILE 2>/dev/null |sort -k 3 | awk '{printf("%-15s%-15s%-15s\n",$1,$2,$3)}' 1> $OUTPUT cat $OUTPUT } function UPDATAUSERS { let TODAY=`date +%s`/86400 while read LINE ;do NAME=`echo $LINE | cut -d ' ' -f 1` if [ $NAME == "root" ];then continue; fi chage -d $TODAY -M 89 -W 99 $NAME done < $OUTPUT } case $1 in "--PRINT") PRINTUSERS ;; "--UPDATA") UPDATAUSERS ;; *) echo "command is [--PRINT|--UPDATA] " ;; esac