使用 Bash Shell 撰寫 Web CGI 程式

使用系統的 Bash Shell 來寫 CGI,這是以前做嵌入式系統時的一個 Web 應用程式解決方案,構想很酷、很有趣。當時考慮到,如果用 C 語言寫 CGI,程式會既複雜又不易維護﹝研發嵌入式系統時 Cross Compile 和繁瑣的 Debug 可是很討厭的!!﹞;若是讓 Web Server 其支援 PHP、Perl,其程式架構會太過龐大。種種因素讓我決定用 Bash 完成需要的 CGI 網站應用程式,畢竟 Bash 從面市到現在,功能越來越齊全強大了,我想應該能勝任 Web Scripts 的工作!:P

當時我先上網搜尋是否有人試過使用 Bash Shell 開發過 CGI 程式,果然有個老兄寫了一些 Bash Functions 來支援些 Web 上的操作,讓我們可以輕易使用 Bash 來寫 CGI。有興趣的人可以到 bashlib(http://bashlib.sourceforge.net/) 抓回來玩玩看。

如果你看過了這個 Bashlib ,一定發現其實它功能很陽春,只有取得 GET 傳值、表單傳值、轉向、Cookies等幾種功能。嘿嘿,這時候當然要開始惡搞這個 bashlib,我改寫並加入了一些功能,像是 Session 的支援。

自己額外亂搞新增支援 Session 的 Functions:
function init_session {
if [ ! -d /tmp/.xcdmgrsess ]; then
mkdir /tmp/.xcdmgrsess &> /dev/null
fi

SESS_ID=`cookie SESS_ID`
if [ A$SESS_ID = A"" ]; then
SESS_ID=`mkcode 30`
set_cookie SESS_ID $SESS_ID
touch /tmp/.xcdmgrsess/$SESS_ID
else
if [ -f /tmp/.xcdmgrsess/$SESS_ID ]; then
while read SESSLINE; do
eval "export 'SESSION_${SESSLINE}'"
done < /tmp/.xcdmgrsess/$SESS_ID
else
touch /tmp/.xcdmgrsess/$SESS_ID
fi
fi
}

function uninit_session {
SESS_ID=`cookie SESS_ID`
if [ ! A$SESS_ID = A"" ]; then
set_cookie SESS_ID ""
if [ -f /tmp/.xcdmgrsess/$SESS_ID ]; then
rm -f /tmp/.xcdmgrsess/$SESS_ID
fi
fi
}

# session function. Same explanation as param
function session {
local name
local value

SESS_ID=`cookie SESS_ID`
while read SESSLINE; do
eval "export 'SESSION_${SESSLINE}'"
done < /tmp/.xcdmgrsess/$SESS_ID

if [ $# -eq 1 ]; then
name=$1
name=$(echo ${name} | /bin/sed -e 's/SESSION_//')
value=$(/usr/bin/env | /bin/grep "^SESSION_${name}" | /bin/sed -e 's/SESSION_//' | /usr/bin/cut -d= -f2-)
echo ${value}
elif [ $# -gt 1 ]; then
name=$1
shift
eval "export 'SESSION_${name}=$*'"
/usr/bin/env | /bin/grep '^SESSION_' | /bin/sed -e 's/SESSION_//' > /tmp/.xcdmgrsess/$SESS_ID
else
value=$(/usr/bin/env | /bin/grep '^SESSION_' | /bin/sed -e 's/SESSION_//' | /usr/bin/cut -d= -f1)
echo ${value}
fi
unset name
unset value
}


function set_session {
local name=$1
shift
local value=$*

session $name $value &> /dev/null
}


使用方法:
  1. 使用前先呼叫:
    • init_session
  2. 設自訂的 Session 變數:
    • set_session NAME "Fred"
  3. 取得 Session 變數值:
    • SESSION_NAME=`session NAME`


後記:

其實,用 Bash 這種系統 shell 來寫 CGI 本來就不是什麼新構想,因為常在開發 Web Server 的 CGI 支援時,就會用這種 Shell 寫簡單的 CGI 做測試。只是這次瘋狂了點,利用 Bash 達成更多 CGI 的功能。

另外,使用 Bash 當 CGI 的 Scripts Language 要注意的是 Injection 的攻擊,因為每一行都被當成系統命令在執行,所以當用戶透過 Web 執行 Bash CGI 時,就相當於用戶在你的 Console 下執行命令。想要避免這些問題,需要詳細了解 Bash 雙引號和單引號的使用和差別。

這個網誌中的熱門文章

Web 技術中的 Session 是什麼?

淺談 USB 通訊架構之定義(一)

淺談 USB 通訊架構之定義(二)

JavaScript 好用的 async 異步函數!

上手使用 JavaScript 的 Map、Reduce 吧!