Shell腳本簡介:
Shell腳本是一種特殊的程序,它是用戶與linux系統內核之間的一個接口,shell是一個工具程序,在用戶登錄後系統啓動。它解釋並運行由命令行或腳本文件輸入的命令,從而實現用戶與內核間的交互。
Shell腳本:也就是用各類命令預先放入到一個文件中,方便一次性執行的一個程序文件,主要是方便管理員進行設置或者管理用的,是利用shell的功能所寫的一個程序,這個程序是使用純文本文件,將一些shell的語法與指令寫在裏面,然後用正規表示法,管道命令以及數據流重導向等功能,以達到我們所想要的處理目的
程序:指令+ 數據
程序編程風格:
過程式:以指令爲中心,數據服務於指令
對象式:以數據爲中心,指令服務於數據
shell 程序:提供了編程能力,解釋執行
程序的執行方式:
計算機:運行二進制指令;
編程語言:
低級:彙編
高級:
編譯:高級語言-->編譯器--> 目標代碼
java,C#
解釋:高級語言-->解釋器--> 機器代碼
shell, perl, python
編程邏輯處理方式:
順序執行
循環執行
選擇執行
shell 編程:過程式、解釋執行
編程語言的基本結構:
數據存儲:變量、數組
表達式: a + b
語句:if
shell 腳本是包含一些命令或聲明,並符合一定格式的文
本文件
格式要求:首行shebang 機制
#!/bin/bash
#!/usr/bin/python
#!/usr/bin/perl
shell 腳本的用途有:
自動化常用命令
執行系統管理和故障排除
創建簡單的應用程序
處理文本或文件
創建shell腳本
第一步:使用文本編輯器來創建文本文件
第一行必須包括shell 聲明序列:#!(要頂格寫)
#!/bin/bash
添加註釋
註釋以# 開頭
第二步:運行腳本
給予執行權限,在命令行上指定腳本的絕對或相對路徑
直接運行解釋器,將腳本作爲解釋器程序的參數運行
腳本的調試:
bash -n/path/to/some_script
檢測腳本中的語法錯誤
bash -x /path/to/some_script
調試執行
變量:
變量:命名的內存空間
數據存儲方式:
字符:
數值:整型,浮點型
變量:變量類型
作用:
1 、數據存儲格式
2 、參與的運算
3 、表示的數據範圍
類型:
字符
數值:整型、浮點型
編程程序語言分類:
強類型:定義變量時必須指定類型、參與運算必須符合類型
要求;調用未聲明變量會產生錯誤
如 java,python
弱類型:無須指定類型,默認均爲字符型;參與運算會自動
進行隱式類型轉換;變量無須事先定義可直接調用
如 :bash 不支持浮點數
變量命名法則:
1 、不能使程序中的保留字:例如if, for;
2 、只能使用數字、字母及下劃線,且不能以數字開頭
3 、見名知義
4 、統一命名Shell腳本包括一些命令或聲明,並符合一個格式的文件
Bash中變量的種類
根據變量的生效範圍等標準:
本地變量:生效範圍爲當前shell進程;對當前shell 之外的其它shell 進程,包括當前shell 的子shell 進程均無效
環境變量:生效範圍爲當前shell進程及其子進程
局部變量:生效範圍爲當前shell進程中某代碼片斷( 通常指函數)
位置變量:$1, $2,... 來表示,用於讓腳本在腳本代碼中調用通過命令行傳遞給它的參數
特殊變量:$?, $0,$*, $@, $#
本地變量:
變量賦值:name=‘value’, ,
可以使用引用value:
(1) 可以是直接字串;name=“root"
(2) 變量引用:name="$USER"
(3) 命令引用:name=`COMMAND `, name =$(COMMAND)
變量引用:${name},$name
"" :弱引用,其中的變量引用會被替換爲變量值
'' :強引用,其中的變量引用不會被替換爲變量值,而保
持原字符串
顯示已定義的所有變量:set
刪除變量:unsetname
舉例演示:
1編寫腳本/root/bin/systeminfo.sh.顯示當前主機系統信息,包括主機名,IPv4地址,操作系統版本,內核版本,CPU型號,內存大小,硬盤大小。
腳本:
2、編寫腳本/root/bin/backup.sh,可實現每日將/etc/ 目錄備份到/root/etcYYYY-mm-dd中
腳本:
3、編寫腳本/root/bin/disk.sh,顯示當前硬盤分區中空間利用率最大的值
4、編寫腳本/root/bin/links.sh,顯示正連接本主機的每個遠程主機的IPv4 地址和連接數,並按連接數從大到小排序
腳本:
環境變量:
變量聲明、賦值:
export name=VALUE
declare -x name=VALUE
變量引用:$name,${name}
顯示所有環境變量命令:
export
env
printenv
刪除:unset name
bash 有許多內建的環境變量:PATH, SHELL, USRE,UID,
HISTSIZE, HOME, PWD, OLDPWD, HISTFILE, PS1
只讀
只讀變量:只能聲明,但不能修改和刪除
readonly name
declare -r name
位置變量
位置變量:在腳本代碼中調用通過命令行傳遞給腳本的參數
$1, $2, ... :對應第1 、第2 等參數,shift [n] 換位置
$0: 命令本身
$*: 傳遞給腳本的所有參數,全部參數合爲一個字符串
$@: 傳遞給腳本的所有參數,每個參數爲獨立字符串
$#: 傳遞給腳本的參數的個數
$@ $* 只在被雙引號包起來的時候纔會有差異
示例:判斷給出的文件的行數
linecount="$(wc -l $1| cut -d' ' -f1)"
echo "$1 has $linecount lines."
算術運算
bash 中的算術運算:help let
+, -, *, /, % 取模(取餘), ** (乘方)
實現算術運算:
(1) let var= 算術表達式
(2) var=$[ 算術表達式]
(3) var=$(( 算術表達式))
(4) var=$(expr arg1 arg2 arg3 ...)
(5) declare –i var = 數值
(6) echo ‘算術表達式’ | bc
乘法符號有些場景中需要轉義 ,如 如*
bash 有內建的隨機數生成器:$RANDOM (1-32767))
echo $[$RANDOM%50] :0-49
賦值
增強型賦值:
+=, -=, *=, /=, %=
let varOPERvalue
例如:letcount+=3
自加3 後自賦值
自增,自減:
let var+=1
let var++
let var-=1
let var—
舉例演示:
1 :寫一個腳本/root/bin/sumid.sh,計算/etc/passwd文件中的第10 個用戶和第20 用戶的ID 之和
腳本:
2 :寫一個腳本/root/bin/sumspace.sh,傳遞兩個文件路徑作爲參數給腳本,計算這兩個文件中所有空白行之和
腳本:
3 :寫一個腳本/root/bin/sumfile.sh,統計/etc, /var, /usr目錄共有多少個一極子目錄和文件
腳本:
邏輯運算
true, false
1, 0
與:
1 與 1 = 1
1 與 0 = 0
0 與 1 = 0
0 與 0 = 0
或:
1 或 1 = 1
1 或 0 = 1
0 或 1 = 1
0 或 0 = 0
非:!
! 1 = 0
! 0 = 1
短路運算:
短路與:
第一個爲0 ,結果必定爲0; ;
第一個爲1 ,第二個必須要參與運算;
短路或 :
第一個爲1 ,結果必定爲1; ;
第一個爲0 ,第二個必須要參與運算;
異或:^
異或的兩個值,相同爲假,不同爲真
聚集命令
有兩種聚集命令的方法:
複合式:date; who | wc -l
命令會一個接一個地運行
子shell :(date; who |wc -l ) >>/tmp/trace
所有的輸出都被髮送給單個STDOUT和STDERR
退出狀態
進程使用退出狀態來報告成功或失敗
0 代表成功,1 -255 代表失敗
$? 變量保存最近的命令退出狀態
例如:
$ ping -c1 -W1 hostdown &> /dev/null
$ echo $?
退出狀態碼
bash 自定義退出狀態碼
exit [n] :自定義退出狀態碼;
注意:腳本中一旦遇到exit 命令,腳本會立即終止;終止退出
狀態取決於exit 命令後面的數字
注意:如果未給腳本指定退出狀態碼,整個腳本的退出狀態碼
取決於腳本中執行的最後一條命令的狀態碼
條件測試
判斷某需求是否滿足,需要由測試機制來實現;
專用的測試表達式需要由測試命令輔助完成測試過程;
評估布爾聲明,以便用在條件性執行中
若真,則返回0
若假,則返回1
測試命令:
test EXPRESSIO
[ EXPRESSION ]
` EXPRESSION `
注意:EXPRESSION前後必須有空白字符
條件性的執行操作符
根據退出狀態而定,命令可以有條件地運行
&& 代表條件性的AND THEN
|| 代表條件性的OR ELSE
Bash的測試類型
數值測試:
-gt: 是否大於;
-ge: 是否大於等於;
-eq: 是否等於;
-ne: 是否不等於;
-lt: 是否小於;
-le: 是否小於等於
字符串測試:
== :是否等於;
>: ascii 碼是否大於ascii碼 碼
<: 是否小於
!=: 是否不等於
=~: 左側字符串是否能夠被右側的PATTERN所 所 匹配
注意: 此表達式一般用於` ` 中;
-z "STRING" :字符串是否爲空,空爲真,不空爲假
-n "STRING" :字符串是否不空,不空爲真,空爲假
注意:用於字符串比較時的用到的操作數都應該使用引號
舉例演示:
1 、寫一個腳本/root/bin/argsnum.sh ,接受一個文件路徑作爲參數;如果參數個數小於1 ,則提示用戶“至少應該給一個參數”,並立即退出;如果參數個數不小於1 ,則顯示第一參數所指向的文件中的空白行數
腳本:
2 、寫一個腳本/root/bin/hostping.sh ,接受一個主機的IPv4 地址做爲參數,測試是否可連通。如果能ping 通,則提示用戶“該IP 地址可訪問” ;如果不可ping 通,則提示用戶“該IP 地址不可訪問”
腳本:
文件測試
存在性測試
-a FILE :同-e
-e FILE: 文件存在性測試,存在爲真,否則爲假;
存在性及類別測試
-b FILE :是否存在且爲塊設備文件;
-c FILE :是否存在且爲字符設備文件;
-d FILE :是否存在且爲目錄文件;
-f FILE :是否存在且爲普通文件;
-h FILE 或 或 -L FILE :存在且爲符號鏈接文件;
-p FILE :是否存在且爲命名管道文件;
-S FILE :是否存在且爲套接字文件
文件權限測試:
-r FILE :是否存在且可讀
-w FILE: 是否存在且可寫
-x FILE: 是否存在且可執行
文件特殊權限測試:
-g FILE :是否存在且擁有sgid 權限;
-u FILE :是否存在且擁有suid 權限;
-k FILE :是否存在且擁有sticky 權限
文件大小測試:
-s FILE: 是否存 在 且非空;
文件是否打開:
-t fd: fd 表示文件描述符是否已經打開且與某終端相關
-N FILE :文件自動上一次被讀取之後是否被修改過
-O FILE :當前有效用戶是否爲文件屬主
-G FILE :當前有效用戶是否爲文件屬組
雙目測試:
FILE1 -ef FILE2: FILE1 與FILE2 是否指向同一個設備上的相同inode
FILE1 -nt FILE2: FILE1 是否新於FILE2; ;
FILE1 -ot FILE2: FILE1 是否舊於FILE2;
組合測試條件
第一種方式:
COMMAND1 &&COMMAND2 並且
COMMAND1 || COMMAND2 或者
! COMMAND 非 非
如:[ -e FILE ] && [ -rFILE ]
第二種方式:
EXPRESSION1 -aEXPRESSION2 並且
EXPRESSION1 -oEXPRESSION2 或者
! EXPRESSION
必須使用測試命令進行
舉例演示:
1 、chmod -rw /tmp/file1,編寫腳本/root/bin/per.sh,判斷當前用戶對/tmp/fiile1件文件 是否不可讀且不可寫
腳本:
2 、編寫腳本/root/bin/nologin.sh和login.sh, 實現禁止和允許普通用戶登錄系統
腳本:
禁止登錄:
允許登錄:
使用read 來把輸入值分配給一個或多個shell 變量:
-p 指定要顯示的提示
-t TIMEOUT
read 從標準輸入中讀取值,給每個單詞分配一個變量
所有剩餘單詞都被分配給最後一個變量
read -p “Enter a filename: “ FILE
流程控制
過程式編程語言:
順序執行
選擇執行
循環執行
條件選擇if語句
選擇執行:
注意: :if 語句可 嵌套
單分支
if 判斷條件:then
條件爲真的分支代碼
fi
雙分支
if 判斷條件; then
條件爲真的分支代碼
else
條件爲假的分支代碼
fi
多分支
if CONDITION1 ; then
if-true
elif CONDITION2 ; then
if-ture
elif CONDITION3 ; then
if-ture
...
else
all-false
fi
逐條 件進行判斷,第一次遇爲“真”條件時,執行其分支,而後 結束整個if 語句
條件判斷:case語句
case 變量引用 in
PAT1)
分支1
;;
PAT2)
分支2
;;
...
*)
默認分支
;;
esac
case 支持glob 風格的通配符:
*: 任意長度任意字符
?: 任意單個字符
[] :指定範圍內的任意單個字符
a|b: a或b
舉例演示:
1 、寫一個腳本/root/bin/createuser.sh,實現如下功能:使用一個用戶名做爲參數,如果指定參數的用戶存在,就顯示其存在,否則添加之;顯示添加的用戶的id 號等信息
腳本:
2 、寫一個腳本/root/bin/yesorno.sh,提示用戶輸入yes或或no, 並判斷用戶輸入的是yes 還是no, 或是其它信息
腳本:
3 、寫一個腳本/root/bin/filetype.sh,判斷用戶輸入文件路徑,顯示其文件類型(普通,目錄,鏈接,其它文件類型)
腳本:
4 、寫一個腳本/root/bin/checkint.sh,判斷用戶輸入的參數是否爲正整數
腳本:
5、判斷硬盤的每個分區空間和inode的利用率是否大於80,如果是,發郵件通知root磁盤
滿
腳本:
6、指定文件做爲參數,判斷文件是否爲.sh後綴,如果是,添加x權限
7、計算1+2+3+...+100
腳本: