title: zabbix5.0創建監控項通過腳本簡單實現監控oracle11g的磁盤組和表空間的使用量
authors: Loong
date: 2025-08-28
使用SQLPLUS配合crontab任務
用來執行sql獲取信息的腳本
/home/oracle/zabbix_oracle_check.sh
#!/bin/bash
#用于zabbix agent被動模式的 非入侵性的檢測
#由oracle用戶crontab進行巡檢 結果存入/tmp下臨時文件
#zabbix 腳本去讀臨時文件
source $HOME/.bash_profile# 查詢語句
#設置sqlplus
#SET PAGESIZE 9999 設置頁大小遠大于結果行數(如 9999),這樣只輸出一次列頭和分割線.
#SET FEEDBACK OFF:不顯示 6 rows selected. 這類信息。
#SET LINESIZE 9999 設置每行字符數 避免輸出中過多的換行
set_sqlplus="
SET PAGESIZE 9999
SET FEEDBACK OFF
SET LINESIZE 9999
"DB_STATUS_QUERY="${set_sqlplus}
select instance_name,a.status,b.open_mode,a.inst_id from gv\$instance a,gv\$database b where a.inst_id=b.inst_id;"TABLESPACE_QUERY="${set_sqlplus}
select * from dba_tablespace_usage_metrics order by used_percent;"asm_diskgroup_query="${set_sqlplus}
select group_number,name,total_mb,free_mb,((total_mb-free_mb)/total_mb*100) USED_PERCENT from v\$asm_diskgroup;"# 執行數據庫狀態檢查查詢并保存結果到臨時文件
DB_STATUS_RESULT_FILE=$(mktemp)
echo "${DB_STATUS_QUERY}" | sqlplus -s / as sysdba > "${DB_STATUS_RESULT_FILE}"
if [ $? -ne 0 ]; thenecho "數據庫狀態檢查查詢失敗"exit 1
fi# 執行表空間狀態檢查查詢并保存結果���臨時文件
TABLESPACE_RESULT_FILE=$(mktemp)
echo "${TABLESPACE_QUERY}" | sqlplus -s / as sysdba > "${TABLESPACE_RESULT_FILE}"
if [ $? -ne 0 ]; thenecho "表空間狀態檢查查詢失敗"exit 1
fi# 執行asm磁盤組狀態檢查查詢并保存結果到臨時文件
asm_diskgroup_RESULT_FILE=$(mktemp)
echo "${asm_diskgroup_query}" | sqlplus -s / as sysdba > "${asm_diskgroup_RESULT_FILE}"
if [ $? -ne 0 ]; thenecho "asm磁盤組狀態檢查查詢失敗"exit 1
fi#處理sed -e '/----/d' -e '/^$/d' -e '/rows selected/d' 刪除分割線、空行、影響行數(SET FEEDBACK OFF其實已經具備這個功能了)
sed -i -e '/----/d' -e '/^$/d' -e '/rows selected/d' ${DB_STATUS_RESULT_FILE}
sed -i -e '/----/d' -e '/^$/d' -e '/rows selected/d' ${TABLESPACE_RESULT_FILE}
sed -i -e '/----/d' -e '/^$/d' -e '/rows selected/d' ${asm_diskgroup_RESULT_FILE}mkdir /tmp/zabbix_oracle_info 2>/dev/null
#處理文本 將多余的空格和制表符替換成一個制表符
awk '{$1=$1}1' OFS='\t' ${TABLESPACE_RESULT_FILE} > /tmp/zabbix_oracle_info/tablespace_result
awk '{$1=$1}1' OFS='\t' ${asm_diskgroup_RESULT_FILE} > /tmp/zabbix_oracle_info/asm_diskgroup_result
awk '{$1=$1}1' OFS='\t' ${DB_STATUS_RESULT_FILE} > /tmp/zabbix_oracle_info/db_status_result# 清理臨時文件
rm "${DB_STATUS_RESULT_FILE}"
rm "${TABLESPACE_RESULT_FILE}"
rm "${asm_diskgroup_RESULT_FILE}"
腳本權限
chown oracle:oinstall /home/oracle/zabbix_oracle_check.sh
chown +x /home/oracle/zabbix_oracle_check.sh
定時任務
su - oracle
crontab -e
#每1分鐘獲取一次信息
* * * * * /home/oracle/zabbix_oracle_check.sh
測試結果
[oracle@oadb1 ~]$ ls /tmp/zabbix_oracle_info/
asm_diskgroup_result db_status_result tablespace_result[oracle@oadb1 ~]$ cat /tmp/zabbix_oracle_info/tablespace_result
TABLESPACE_NAME USED_SPACE TABLESPACE_SIZE USED_PERCENT
USERS 168 4194302 .004005434
UNDOTBS1 11728 4194302 .279617443
UNDOTBS2 11744 4194302 .279998913
TEMP 18816 4194302 .448608612
ECOLOGY 563512 20971510 2.68703589
SYSAUX 304856 4194302 7.2683369
ECOLOGY1 355184 4194302 8.4682505
SYSTEM 19499480 20971510 92.9808106
配置zabbix agent用戶參數信息獲取
測試命令提取
[oracle@oadb1 ~]$ cat /tmp/zabbix_oracle_info/tablespace_result | grep -iw system
SYSTEM 19499480 20971510 92.9808106
[oracle@oadb1 ~]$ cat /tmp/zabbix_oracle_info/tablespace_result | grep -iw system | tail -1 | awk "{print \$NF}"
92.9808106
配置監控項用戶參數
vim /etc/zabbix/zabbix_agentd.d/oracle.conf
#監控項
UserParameter=oracle.tbs.percent[*], grep -iw "$1" /tmp/zabbix_oracle_info/tablespace_result | tail -1 | awk "{print \$NF}"
UserParameter=oracle.asm.percent[*], grep -iw "$1" /tmp/zabbix_oracle_info/asm_diskgroup_result | tail -1 | awk "{print \$NF}"
需要重啟zabbix-agent服務
systemctl restart zabbix-agent
在zabbix server上測試
#zabbix_get -s 客戶端ip -k "oracle.tbs.percent[表空間名]"[lex@zabbix-server ~]$ zabbix_get -s 10.1.240.21 -k "oracle.tbs.percent[system]"
92.9906144#zabbix_get -s 客戶端ip -k "oracle.asm.percent[磁盤組名]"
zabbix_get -s 10.1.240.21 -k "oracle.asm.percent[arc]"
zabbix web界面配置監控項及觸發器
主機-創建監控項
名稱 Oracle tablespace [system] used in %
鍵值 oracle.tbs.percent[system]
信息類型 浮點數
單位 %
更新間隔1分鐘名稱 Oracle asm diskgroup [arc] used in %
鍵值 oracle.asm.percent[arc]
信息類型 浮點數
單位 %
更新間隔1分鐘
添加觸發器
主機-宏
{$ORACLE.ASM.DISKGROUP.AVERAGE} 80
{$ORACLE.ASM.DISKGROUP.HIGH} 90{$ORACLE.TBS.AVERAGE} 90
{$ORACLE.TBS.HIGH} 95創建4個觸發器
#表空間system大于一般嚴重的值80%
名稱 Oracle tablespace [system] usage >{$ORACLE.TBS.AVERAGE}%
嚴重性 一般嚴重
表達式 {Ecology_DB1:oracle.tbs.percent[system].last()}>{$ORACLE.TBS.AVERAGE}
#表空間system大于嚴重的值90%
名稱 Oracle tablespace [system] usage >{$ORACLE.TBS.HIGH}%
嚴重性 嚴重
表達式 {Ecology_DB1:oracle.tbs.percent[system].last()}>{$ORACLE.TBS.HIGH}
#磁盤組arc大于一般嚴重的值90%
Oracle asm diskgroup [arc] usage >{$ORACLE.ASM.DISKGROUP.AVERAGE}%
一般嚴重
{Ecology_DB1:oracle.asm.percent[arc].last()}>{$ORACLE.ASM.DISKGROUP.AVERAGE}
#磁盤組arc大于一般嚴重的值95%
Oracle asm diskgroup [arc] usage >{$ORACLE.ASM.DISKGROUP.HIGH}%
嚴重
{Ecology_DB1:oracle.asm.percent[arc].last()}>{$ORACLE.ASM.DISKGROUP.HIGH}
進階:通過自動發現,對多個表空間或磁盤組進行監控
獲取信息腳本末尾增加額外的處理腳本
#處理文本 將多余的空格和制表符替換成一個制表符
awk '{$1=$1}1' OFS='\t' tablespace_result > tablespace_result.tsv
awk '{$1=$1}1' OFS='\t' asm_diskgroup_result > asm_diskgroup_result.tsv
awk '{$1=$1}1' OFS='\t' db_status_result > db_status_result.tsv
#生成到同名文件的話
cat tablespace_result | awk '{$1=$1}1' OFS='\t' > tablespace_result
cat asm_diskgroup_result | awk '{$1=$1}1' OFS='\t' > asm_diskgroup_result
cat db_status_result | awk '{$1=$1}1' OFS='\t' > db_status_result
awk
命令來將這些文件中所有連續的空白字符(空格和制表符)分隔的字段,規范化為 單個制表符(Tab)分隔 的標準 TSV 格式。
awk
的默認行為是將連續的空白作為分隔符,并重新以單個空格輸出字段。但我們可以通過設置輸出字段分隔符 OFS
為制表符 \t
,來實現 TSV 格式。
命令解釋:
{$1=$1}
:這是一個技巧,強制awk
重新構建整行(觸發字段重賦值)。1
:是awk
的“真值”,表示對每行執行默認操作(打印)。OFS='\t'
:設置輸出字段分隔符為制表符。
按列名去獲取值而不是位置
$ sh get_column_value.sh /tmp/zabbix_oracle_info/tablespace_result TABLESPACE_NAME SYSTEM USED_PERCENT
93.1655565
$ cat get_column_value.sh
#!/bin/bash# 檢查參數
if [ $# -ne 4 ]; thenecho "用法: $0 <文件路徑> <列名1> <匹配值> <列名2>"echo "例如: $0 /tmp/zabbix_oracle_info/tablespace_result TABLESPACE_NAME SYSTEM USED_PERCENT"exit 1
fiCOL1="$2"
VALUE="$3"
COL2="$4"
FILE="$1"# 檢查文件是否存在
if [ ! -f "$FILE" ]; thenecho "錯誤: 文件 $FILE 不存在"exit 1
fi# 使用 awk 提取
awk -F'\t' -v c1="$COL1" -v val="$VALUE" -v c2="$COL2" '
BEGIN {found = 0
}
NR == 1 {# 查找列索引for (i = 1; i <= NF; i++) {if ($i == c1) idx1 = iif ($i == c2) idx2 = i}if (!idx1) {print "錯誤: 未找到列 \"" c1 "\"" > "/dev/stderr"exit 1}if (!idx2) {print "錯誤: 未找到列 \"" c2 "\"" > "/dev/stderr"exit 1}next
}
{if ($idx1 == val) {print $idx2found = 1exit}
}
END {if (!found && val != "") {print "" # 未找到匹配項,輸出空}
}
' "$FILE"
按照列名依次獲取值生成zabbix自動發現所需的json
sh zabbix_oracle_discovery.sh tablespace_result TABLESPACE_NAME
{"data": [{"{#TABLESPACE_NAME}": "USERS"},{"{#TABLESPACE_NAME}": "TEMP"},{"{#TABLESPACE_NAME}": "UNDOTBS2"},{"{#TABLESPACE_NAME}": "UNDOTBS1"},{"{#TABLESPACE_NAME}": "ECOLOGY"},{"{#TABLESPACE_NAME}": "SYSAUX"},{"{#TABLESPACE_NAME}": "ECOLOGY1"},{"{#TABLESPACE_NAME}": "SYSTEM"}]
}
cat zabbix_oracle_discovery.sh
#!/bin/bashINPUT_FILE="$1"
COLUMN_NAME="$2"if [ $# -lt 2 ]; thenecho "用法: $0 <文件名> <列名>"exit 1
fiif [ ! -f "$INPUT_FILE" ]; thenecho "錯誤: 文件 $INPUT_FILE 不存在" >&2# 輸出合法空 JSONecho '{"data": []}'exit 1
fiawk -v col_name="$COLUMN_NAME" '
BEGIN {FS = "[ \t]+"found_col = 0item_count = 0print "{"print " \"data\": ["
}
NR == 1 {# 查找目標列for (i = 1; i <= NF; i++) {gsub(/^[ \t]+|[ \t]+$/, "", $i)if ($i == col_name) {target_col = ifound_col = 1}}if (!found_col) {# 列未找到,輸出空數組并結束print " ]"print "}"exit 0}next
}
{if (!found_col) nextvalue = $target_colgsub(/^[ \t]+|[ \t]+$/, "", value)if (value != "" && value != "N/A" && value != "NULL") {if (item_count > 0) {printf ",\n"}printf " {\"{#%s}\": \"%s\"}", toupper(col_name), valueitem_count++}
}
END {if (found_col) {# 正常結束if (item_count == 0) {# 沒有數據行print ""}print ""print " ]"print "}"}# 如果 !found_col,已在 NR==1 處理
}
' "$INPUT_FILE"
chmod +x /etc/zabbix/zabbix_agentd.d/*.sh
[root@localhost zabbix_agentd.d]# cat oracle.conf
# 自動發現表空間和asm磁盤組
UserParameter=oracle.tbs.discovery,/etc/zabbix/zabbix_agentd.d/zabbix_oracle_discovery.sh /tmp/zabbix_oracle_info/tablespace_result TABLESPACE_NAME
UserParameter=oracle.asm.discovery,/etc/zabbix/zabbix_agentd.d/zabbix_oracle_discovery.sh /tmp/zabbix_oracle_info/asm_diskgroup_result NAME#UserParameter=oracle.tbs.percent[*], grep -iw "$1" /tmp/zabbix_oracle_info/tablespace_result | tail -1 | awk "{print \$NF}"
#UserParameter=oracle.asm.percent[*], grep -iw "$1" /tmp/zabbix_oracle_info/asm_diskgroup_result | tail -1 | awk "{print \$NF}"
UserParameter=oracle.tbs.percent[*], /etc/zabbix/zabbix_agentd.d/get_column_value.sh /tmp/zabbix_oracle_info/tablespace_result TABLESPACE_NAME "$1" USED_PERCENT
UserParameter=oracle.asm.percent[*], /etc/zabbix/zabbix_agentd.d/get_column_value.sh /tmp/zabbix_oracle_info/asm_diskgroup_result NAME "$1" USED_PERCENT
Zabbix Web 前端配置
新建模板
My Template Oracle asm and tablespace usage
在模板中添加宏
{$ORACLE.ASM.DISKGROUP.AVERAGE} 80
{$ORACLE.ASM.DISKGROUP.HIGH} 90
{$ORACLE.TBS.AVERAGE} 90
{$ORACLE.TBS.HIGH} 95
在模板中創建 自動發現規則(Discovery Rule)
- 進入:配置 → 主機 → 你的 Oracle 主機 → 自動發現
- 點擊 創建發現規則
- 下面以配置表空間的自動發現規則為例,配置如下:
字段 | 值 |
---|---|
名稱 | Oracle Tablespace Discovery |
類型 | Zabbix agent |
鍵值 | oracle.tbs.discovery |
更新間隔 | 1h (或 30m ,不需要太頻繁) |
? 保存
創建 發現規則下的監控項原型(Item Prototype)
點擊你剛創建的發現規則 → 監控項原型 → 創建監控項原型
字段 | 值 |
---|---|
名稱 | Oracle Tablespace {#TABLESPACE_NAME} Used % |
類型 | Zabbix agent |
鍵值 | oracle.tbs.percent[{#TABLESPACE_NAME}] |
類型信息 | Numeric (float) ? 必須是 float |
單位 | % |
更新間隔 | 1m |
應用集 | Oracle Tablespace (可創建新應用集) |
? 保存
(可選)創建 觸發器原型(Trigger Prototype)
點擊 觸發器原型 → 創建觸發器原型
字段 | 值 |
---|---|
名稱 | Oracle Tablespace {#TABLESPACE} usage > 90% |
表達式 | {HOSTNAME:oracle.tbs.percent[{#TABLESPACE}].last()} > 90 |
嚴重性 | High |
? 保存
附:完整模板
My Template Oracle asm and tablespace usage.xml
<?xml version="1.0" encoding="UTF-8"?>
<zabbix_export><version>5.0</version><date>2025-08-29T07:33:05Z</date><groups><group><name>Templates/Databases</name></group></groups><templates><template><template>My Template Oracle asm and tablespace usage</template><name>My Template Oracle asm and tablespace usage</name><description>自定義模板 需要配合agent執行腳本</description><groups><group><name>Templates/Databases</name></group></groups><discovery_rules><discovery_rule><name>auto-discovery asm-diskgroup</name><key>oracle.asm.discovery</key><delay>30m</delay><item_prototypes><item_prototype><name>Oracle ASM diskgroup {#NAME} Used %</name><key>oracle.asm.percent[{#NAME}]</key><value_type>FLOAT</value_type><trigger_prototypes><trigger_prototype><expression>{last()}>{$ORACLE.ASM.DISKGROUP.AVERAGE}</expression><name>Oracle asm diskgroup [{#NAME}] usage >{$ORACLE.ASM.DISKGROUP.AVERAGE}%</name><priority>AVERAGE</priority></trigger_prototype><trigger_prototype><expression>{last()}>{$ORACLE.ASM.DISKGROUP.HIGH}</expression><name>Oracle asm diskgroup [{#NAME}] usage >{$ORACLE.ASM.DISKGROUP.HIGH}%</name><priority>HIGH</priority></trigger_prototype></trigger_prototypes></item_prototype></item_prototypes></discovery_rule><discovery_rule><name>auto-discovery tablespace</name><key>oracle.tbs.discovery</key><delay>30m</delay><item_prototypes><item_prototype><name>Oracle Tablespace {#TABLESPACE_NAME} Used %</name><key>oracle.tbs.percent[{#TABLESPACE_NAME}]</key><value_type>FLOAT</value_type><trigger_prototypes><trigger_prototype><expression>{last()}>{$ORACLE.TBS.AVERAGE}</expression><name>Oracle tablespace [{#TABLESPACE_NAME}] usage >{$ORACLE.TBS.AVERAGE}%</name><priority>AVERAGE</priority></trigger_prototype><trigger_prototype><expression>{last()}>{$ORACLE.TBS.HIGH}</expression><name>Oracle tablespace [{#TABLESPACE_NAME}] usage >{$ORACLE.TBS.HIGH}%</name><priority>HIGH</priority></trigger_prototype></trigger_prototypes></item_prototype></item_prototypes></discovery_rule></discovery_rules><macros><macro><macro>{$ORACLE.ASM.DISKGROUP.AVERAGE}</macro><value>80</value></macro><macro><macro>{$ORACLE.ASM.DISKGROUP.HIGH}</macro><value>90</value></macro><macro><macro>{$ORACLE.TBS.AVERAGE}</macro><value>90</value></macro><macro><macro>{$ORACLE.TBS.HIGH}</macro><value>95</value></macro></macros></template></templates>
</zabbix_export>