網站可靠性與安全性息息相關,仰賴穩固的管理機制。本文介紹三種 Shell 指令碼,分別用於檢查外部連結、Apache 密碼管理和 SFTP 檔案同步,強化網站的日常維運。首先,checkexternal 指令碼能有效檢測外部連結的可用性,從 checklinks 指令碼產生的 rejects 檔案中讀取 URL 列表,並利用 curl 命令驗證每個連結的狀態,及時發現失效連結。接著,apm 指令碼提供網頁介面,簡化 Apache .htpasswd 檔案的管理,讓管理員能輕鬆新增、更新和刪除使用者帳戶,提升管理效率。最後,sftpsync 指令碼則專注於檔案同步,利用時間戳記檔案追蹤本地與遠端伺服器之間的檔案差異,僅上傳新檔案或修改過的檔案,並透過 SFTP 確保檔案傳輸的安全性。
網站與網際網路管理:檢查外部連結的指令碼
在前一篇文章中,我們討論了一個用於檢查網站內部連結的指令碼(checklinks)。現在,我們將進一步探討如何檢查外部連結,以確保它們的有效性。
檢查外部連結的指令碼(checkexternal)
這個指令碼(checkexternal)旨在檢查一個網站或其子目錄中的所有外部連結,以找出可能失效或損壞的連結。為了簡化流程,它假設前一個指令碼(checklinks)已經執行過,因此可以直接使用其產生的 *.rejects 檔案中的URL列表。
指令碼的工作原理
checkexternal 指令碼透過以下步驟來檢查外部連結:
- 讀取外部連結列表:從 *.rejects 檔案中讀取外部連結的列表。
- 檢查每個連結的有效性:使用
curl命令測試每個外部連結的有效性。 - 報告結果:根據測試結果,報告每個連結的狀態(成功或失敗)。
程式碼解析
#!/bin/bash
# checkexternal--測試一個網站上的所有URL,以建立外部參考列表,
# 然後檢查每個參考,以確定哪些可能已經失效或損壞。
listall=0; errors=0; checked=0
if [ "$1" = "-a" ] ; then
listall=1; shift
fi
if [ -z "$1" ] ; then
echo "用法:$(basename $0) [-a] URL" >&2
exit 1
fi
trap "$(which rm) -f traverse*.errors reject*.dat traverse*.dat" 0
outfile="$(echo "$1" | cut -d/ -f3).errors.ext"
URLlist="$(echo $1 | cut -d/ -f3 | sed 's/www\.//').rejects"
rm -f $outfile # 為新的輸出做好準備
if [ ! -e "$URLlist" ] ; then
echo "找不到檔案 $URLlist。請先執行 checklinks。" >&2
exit 1
fi
if [ ! -s "$URLlist" ] ; then
echo "似乎沒有外部連結($URLlist 為空)。" >&2
exit 1
fi
#### 現在,終於可以開始了...
for URL in $(cat $URLlist | sort | uniq)
do
curl -s "$URL" > /dev/null 2>&1; return=$?
if [ $return -eq 0 ] ; then
if [ $listall -eq 1 ] ; then
echo "$URL 是正常的。"
fi
else
echo "$URL 失敗,錯誤程式碼為 $return"
errors=$(( $errors + 1 ))
fi
checked=$(( $checked + 1 ))
done
echo ""
echo "完成。已檢查 $checked 個URL,發現 $errors 個錯誤。"
exit 0
內容解密:
listall、errors和checked變數:用於控制指令碼的行為和跟蹤錯誤數量及已檢查的URL數量。curl命令的使用:-s選項使curl以靜默模式執行,> /dev/null 2>&1將輸出重定向到/dev/null,丟棄所有輸出,而$?取得curl命令的傳回碼,用於判斷URL是否有效。trap命令:在指令碼離開時自動刪除臨時檔案。for迴圈:遍歷外部連結列表,對每個URL進行檢查。
管理 Apache 密碼的安全實踐
Apache 網頁伺服器提供內建的密碼保護目錄功能,即使在共用公用伺服器上也能實作私密、安全的有限存取資訊。不論是經營付費訂閱服務,還是希望確保家庭照片僅供家人檢視,此功能都非常實用。
設定 .htaccess 檔案
標準設定要求在受密碼保護的目錄中管理名為 .htaccess 的檔案。此檔案指定安全區網域名稱,更重要的是,它指向另一個包含帳戶名稱和密碼配對的資料檔案,用於驗證目錄存取許可權。
$ cat .htaccess
AuthUserFile /usr/lib/cgi-bin/.htpasswd
AuthGroupFile /dev/null
AuthName "Members Only Data Area."
AuthType Basic
<Limit GET>
require valid-user
</Limit>
建立 .htpasswd 檔案
另一個名為 .htpasswd 的檔案儲存所有帳戶和密碼配對。如果此檔案尚未存在,需要建立它。執行 touch .htpasswd 並確保 Apache 使用者 ID(可能是 nobody)可寫入該檔案。
Apache 密碼管理指令碼(apm)
為簡化 .htpasswd 檔案的管理,apm 指令碼提供了一個在瀏覽器中以 CGI 指令碼形式執行的密碼管理工具,方便新增帳戶、修改現有帳戶密碼或刪除帳戶。
apm 程式碼解析
#!/bin/bash
# apm--Apache Password Manager allows the administrator to easily
# add, update, or delete accounts and passwords for a subdirectory
# of a typical Apache configuration (where the config file is called
# .htaccess).
echo "Content-type: text/html"
echo ""
echo "<html><title>Apache Password Manager Utility</title><body>"
basedir=$(pwd)
myname="$(basename $0)"
footer="$basedir/apm-footer.html"
htaccess="$basedir/.htaccess"
htpasswd="$(which htpasswd) -b"
內容解密:
- 設定 HTTP 標頭:首先輸出
Content-type: text/html以指示輸出為 HTML 檔案。 - 初始化變數:定義指令碼工作目錄、指令碼名稱、頁尾檔案路徑、
.htaccess路徑以及htpasswd命令的路徑。
if [ ! -r "$htaccess" ] ; then
echo "Error: cannot read $htaccess file."
exit 1
fi
passwdfile="$(grep "AuthUserFile" $htaccess | cut -d\ -f2)"
內容解密:
- 檢查 .htaccess 可讀性:如果無法讀取
.htaccess,輸出錯誤訊息並離開。 - 擷取密碼檔案路徑:從
.htaccess中擷取AuthUserFile的值,即密碼檔案路徑。
action="$(echo $QUERY_STRING | cut -c3)"
user="$(echo $QUERY_STRING|cut -d\& -f2|cut -d= -f2|tr '[:upper:]' '[:lower:]')"
case "$action" in
A ) echo "<h3>Adding New User <u>$user</u></h3>"
if [ ! -z "$(grep -E "^${user}:" $passwdfile)" ] ; then
echo "Error: user <b>$user</b> already appears in the file."
else
pass="$(echo $QUERY_STRING|cut -d\& -f3|cut -d= -f2)"
if [ ! -z "$(echo $pass|tr -d '[[:upper:][:lower:][:digit:]]')" ]; then
echo "Error: passwords can only contain a-z A-Z 0-9 ($pass)"
內容解密:
- 解析查詢字串:根據查詢字串判斷操作型別(新增、更新或刪除)及使用者名稱。
- 新增使用者邏輯:檢查使用者是否已存在,若不存在則繼續檢查密碼是否符合規範(僅包含字母和數字)。
- 錯誤處理:若使用者已存在或密碼不符合規範,輸出對應的錯誤訊息。
安全性和易用性考量
- 安全性:透過限制只有特定使用者(如
admin)才能存取apm,可以提高安全性。 - 易用性:提供根據網頁的介面,讓管理員能夠輕鬆新增、修改或刪除帳戶,提升了管理的便捷性。
Apache 密碼管理指令碼解析與實作
指令碼功能概述
此指令碼主要用於透過網頁介面管理 Apache 的 .htpasswd 檔案,實作新增、更新和刪除使用者的功能。指令碼透過 CGI(Common Gateway Interface)與網頁伺服器互動,接收使用者請求並執行相應的操作。
指令碼結構與流程
1. 前置處理
在主邏輯執行前,指令碼會:
- 從
.htaccess檔案中提取htpasswd檔案的路徑。 - 檢查指令碼是否具有寫入
.htpasswd檔案的許可權。 - 處理可能的錯誤情況,如檔案不可寫或
htpasswd命令不可用。
2. 主邏輯:case 陳述式
指令碼的核心是一個 case 陳述式,根據從 QUERY_STRING 中提取的操作碼(A、U 或 D)執行相應的操作:
- A(新增使用者):檢查使用者名稱和密碼的有效性,若無誤則使用
htpasswd命令新增使用者。 - U(更新使用者密碼):檢查使用者是否存在、密碼是否有效,若無誤則更新使用者密碼。
- D(刪除使用者):檢查使用者是否存在,若使用者不是
admin則刪除該使用者。
case "$action" in
A ) # 新增使用者邏輯
;;
U ) # 更新使用者密碼邏輯
;;
D ) # 刪除使用者邏輯
;;
esac
3. 列出當前使用者
無論執行何種操作,指令碼都會在操作完成後列出 .htpasswd 檔案中的所有使用者,並提供刪除連結。
while read acct pw ; do
echo "<tr><th>$acct</th><td align=center><a href=\"$myname?a=D&u=$acct\">[delete]</a></td></tr>"
done < $passwdfile
4. 輸出 HTML 表尾與操作表單
指令碼會讀取 apm-footer.html 檔案,並替換其中的 --myname-- 和 --options-- 分別為當前指令碼名稱和使用者列表選項,最後輸出完整的 HTML。
程式碼重點解析
QUERY_STRING 處理
指令碼從 QUERY_STRING 環境變數中提取操作碼、使用者名稱和密碼。
action=$(echo $QUERY_STRING | cut -d\& -f1 | cut -d= -f2)
user=$(echo $QUERY_STRING | cut -d\& -f2 | cut -d= -f2)
pass=$(echo $QUERY_STRING | cut -d\& -f3 | cut -d= -f2)
htpasswd 命令呼叫
使用 htpasswd 命令對密碼進行加密並更新 .htpasswd 檔案。
$htpasswd $passwdfile "$user" "$pass"
實作注意事項
- 安全性:確保
.htpasswd檔案存放在安全的位置,避免直接被網頁伺服器存取。 - 許可權控制:指令碼需要適當的執行許可權,以確保能夠讀寫
.htpasswd檔案。 - 錯誤處理:完善的錯誤處理機制對於提升使用者經驗和系統穩定性至關重要。
使用 SFTP 同步檔案:sftpsync 指令碼詳解
在現代網路環境中,檔案傳輸協定(FTP)由於其安全性問題逐漸被更安全的協定如 rsync 和 ssh(安全殼層)所取代。SFTP(SSH 檔案傳輸協定)作為 ssh 的一部分,提供了加密的檔案傳輸功能。本篇文章將介紹如何使用 sftpsync 指令碼透過 SFTP 同步本地與遠端伺服器之間的檔案。
sftpsync 指令碼功能
sftpsync 是一個 Bash 指令碼,用於將本地目錄中的新檔案或已修改檔案上傳至遠端 SFTP 伺服器。該指令碼使用一個名為 .timestamp 的時間戳記檔案來追蹤最後一次同步的時間,從而決定哪些檔案需要被上傳。
程式碼解析
#!/bin/bash
# sftpsync--Given a target directory on an sftp server, makes sure that
# all new or modified files are uploaded to the remote system. Uses
# a timestamp file ingeniously called .timestamp to keep track.
timestamp=".timestamp"
tempfile="/tmp/sftpsync.$$"
count=0
trap "$(which rm) -f $tempfile" 0 1 15 # Zap tempfile on exit
if [ $# -eq 0 ] ; then
echo "Usage: $0 user@host { remotedir }" >&2
exit 1
fi
user="$(echo $1 | cut -d@ -f1)"
server="$(echo $1 | cut -d@ -f2)"
if [ $# -gt 1 ] ; then
echo "cd $2" >> $tempfile
fi
if [ ! -f $timestamp ] ; then
# If no timestamp file, upload all files.
for filename in *
do
if [ -f "$filename" ] ; then
echo "put -P \"$filename\"" >> $tempfile
count=$(( $count + 1 ))
fi
done
else
for filename in $(find . -newer $timestamp -type f -print)
do
echo "put -P \"$filename\"" >> $tempfile
count=$(( $count + 1 ))
done
fi
if [ $count -eq 0 ] ; then
echo "$0: No files require uploading to $server" >&2
exit 1
fi
echo "quit" >> $tempfile
echo "Synchronizing: Found $count files in local folder to upload."
if ! sftp -b $tempfile "$user@$server" ; then
echo "Done. All files synchronized up with $server"
touch $timestamp
fi
exit 0
內容解密:
初始化變數和暫存檔案:指令碼首先設定了時間戳記檔案
.timestamp和一個用於儲存 SFTP 命令的暫存檔案。trap命令確保在指令碼離開時刪除暫存檔案。引數檢查:指令碼檢查是否提供了足夠的引數(使用者名稱@主機名和可選的遠端目錄)。如果沒有提供足夠的引數,則顯示用法並離開。
解析使用者名稱和伺服器位址:從第一個引數中提取使用者名稱和伺服器位址。
建立 SFTP 命令:
- 如果提供了第二個引數(遠端目錄),則在暫存檔案中新增
cd命令以切換到該目錄。 - 如果不存在時間戳記檔案,則上傳所有本地檔案;否則,只上傳比時間戳記檔案新的檔案。
- 將
put命令(帶有-P選項以保留檔案許可權和時間戳記)新增至暫存檔案中,以上傳選定的檔案。
- 如果提供了第二個引數(遠端目錄),則在暫存檔案中新增
執行 SFTP:使用
-b選項將暫存檔案中的命令餵給sftp命令。如果 SFTP 操作成功,則更新時間戳記檔案。錯誤處理和輸出:指令碼根據需要輸出同步結果,並在沒有檔案需要上傳時離開。
如何使用 sftpsync
移動到本地源目錄:確保你位於想要同步的本地目錄中。
執行 sftpsync:執行
sftpsync指令碼,並提供你的使用者名稱、伺服器名稱和遠端目錄作為引數。例如:sftpsync taylor@intuitive.com /wicked/scripts驗證結果:指令碼將顯示正在上傳的檔案,並在完成後報告同步結果。
使用 SFTP 同步檔案的安全考量
在使用 sftpsync 指令碼或任何其他根據 SFTP 的解決方案時,安全性是一個非常重要的考量因素。以下是一些需要特別注意的安全事項:
私鑰與密碼的安全管理
使用 SSH 金鑰認證:相較於使用密碼,使用 SSH 金鑰進行認證更為安全。確保你的私鑰得到妥善保護,不要將其與他人共用或存放在不安全的地方。
密碼的安全性:如果你仍然選擇使用密碼,請確保密碼足夠複雜並定期更換。
SFTP 伺服器的組態
限制 SFTP 使用者的許可權:確保 SFTP 使用者僅擁有必要的許可權,避免過度授權。例如,可以透過 chroot jail 將使用者限制在其主目錄中,防止他們存取系統上的其他檔案。
更新和修補 SSH/SFTP 軟體:保持你的 SSH/SFTP 軟體(例如 OpenSSH)為最新版本,以確保已修補已知的安全漏洞。
日誌記錄和監控
啟用日誌記錄:確保你的 SFTP 伺服器組態了適當的日誌記錄級別,以便能夠監控和分析任何可疑活動。
定期檢查日誌:定期檢查 SFTP 日誌,以及相關的系統日誌,以便及時發現並回應任何潛在的安全威脅。
網路安全
防火牆組態:使用防火牆限制對 SFTP 伺服器的存取,只允許信任的 IP 位址或網路連線到 SFTP 服務。
使用 VPN:對於需要從不安全網路連線的情況,考慮透過 VPN 連線來增加額外的一層保護。