一介闲人
一介闲人
#!/bin/bash
###########################################################
# 达梦8 数据库全量逻辑备份脚本(麒麟V10 专用)
# 功能:全量导出 → 压缩 → 清理过期备份 → 日志记录 → 异常校验
# 数据库用户:dmdba:dinstall
###########################################################
# ===================== 配置项(请根据实际修改)=====================
export DM_HOME='/home/dmdba/dmdbms'
BAK_DIR='/dmdata/dmbak/backup'
USER='SYSDBA'
PASSWORD='Dm123456'
PORT='5237'
SCHEMA='DM8'
RETENTION_DAYS=7 # 备份保留天数
BACKUP_LOG="${BAK_DIR}/backup_run.log" # 脚本运行日志
# ====================================================================
# 1. 检查是否 root 运行,必须使用 dmdba 用户执行
if [ $(id -u) -eq 0 ]; then
echo "[$(date)] 错误:禁止使用 root 用户执行备份脚本,请切换到 dmdba 用户!" >> ${BACKUP_LOG}
exit 1
fi
# 2. 检查 DM_HOME 是否存在
if [ ! -d "${DM_HOME}" ]; then
echo "[$(date)] 错误:DM_HOME 目录不存在 ${DM_HOME}" >> ${BACKUP_LOG}
exit 1
fi
# 3. 检查 dexp 工具是否存在
if [ ! -f "${DM_HOME}/bin/dexp" ]; then
echo "[$(date)] 错误:dexp 备份工具不存在,请检查达梦安装目录" >> ${BACKUP_LOG}
exit 1
fi
# 4. 创建备份目录(赋权)
mkdir -p ${BAK_DIR}
chmod 755 ${BAK_DIR}
chown -R dmdba:dinstall ${BAK_DIR} >/dev/null 2>&1
# 5. 加载达梦环境变量(必须)
export PATH=${DM_HOME}/bin:${PATH}
export LD_LIBRARY_PATH=${DM_HOME}/bin:${LD_LIBRARY_PATH}
# 6. 生成时间戳文件名
TIMESTAMP=$(date +"%Y%m%d_%H%M%S")
DMP_FILE="${SCHEMA}_${TIMESTAMP}.dmp"
LOG_FILE="${SCHEMA}_${TIMESTAMP}.log"
TAR_FILE="${BAK_DIR}/${SCHEMA}_${TIMESTAMP}.tar.gz"
# 7. 执行 dexp 全量备份(增加校验,失败直接退出)
echo "[$(date)] 开始备份:${DMP_FILE}" >> ${BACKUP_LOG}
${DM_HOME}/bin/dexp USERID=${USER}/${PASSWORD}@localhost:${PORT} \
DIRECTORY=${BAK_DIR} \
FILE=${DMP_FILE} \
LOG=${LOG_FILE} \
SCHEMAS=${SCHEMA} \
COMPRESS=3 \
PARALLEL=4 \ # 多核CPU可开启并行加速(建议=CPU核心数)
BUFFER=102400 \
SILENT=Y
# 校验备份是否成功
if [ $? -ne 0 ]; then
echo "[$(date)] 备份失败:dexp 执行异常,请检查 ${BAK_DIR}/${LOG_FILE}" >> ${BACKUP_LOG}
exit 1
fi
# ===================== 【1/3 校验:dmp 文件是否存在】 =====================
if [ ! -f "${BAK_DIR}/${DMP_FILE}" ]; then
echo "[$(date)] 备份失败:未生成 dmp 文件,终止任务!" >> ${BACKUP_LOG}
exit 1
fi
# ===================== 【2/3 校验:文件大小(非空)】 =====================
MIN_SIZE=1024000 # 最小 1MB
FILE_SIZE=$(du -b "${BAK_DIR}/${DMP_FILE}" | awk '{print $1}')
if [ ${FILE_SIZE} -lt ${MIN_SIZE} ]; then
echo "[$(date)] 备份失败:dmp 文件过小(空文件/损坏),终止任务!" >> ${BACKUP_LOG}
rm -f "${BAK_DIR}/${DMP_FILE}" "${BAK_DIR}/${LOG_FILE}"
exit 1
fi
# ===================== 【3/3 校验:dmp 文件头合法性(达梦独有)】 =====================
echo "[$(date)] 校验备份文件有效性..." >> ${BACKUP_LOG}
FILE_HEAD=$(head -20 "${BAK_DIR}/${DMP_FILE}" | grep -i "DM8" | head -1)
if [ -z "${FILE_HEAD}" ]; then
echo "[$(date)] 备份失败:dmp 文件格式非法,不是有效达梦备份!" >> ${BACKUP_LOG}
rm -f "${BAK_DIR}/${DMP_FILE}" "${BAK_DIR}/${LOG_FILE}"
exit 1
fi
echo "[$(date)] 备份文件校验通过:有效、完整、非空" >> ${BACKUP_LOG}
# 8. 压缩备份文件(压缩后删除原文件)
echo "[$(date)] 开始压缩:${TAR_FILE}" >> ${BACKUP_LOG}
tar -czf ${TAR_FILE} -C ${BAK_DIR} ${DMP_FILE} ${LOG_FILE}
if [ $? -eq 0 ]; then
rm -f ${BAK_DIR}/${DMP_FILE} ${BAK_DIR}/${LOG_FILE}
else
echo "[$(date)] 压缩失败,保留原始备份文件" >> ${BACKUP_LOG}
exit 1
fi
# 9. 清理过期备份(只清理本脚本生成的压缩包,安全)
echo "[$(date)] 清理 ${RETENTION_DAYS} 天前的旧备份" >> ${BACKUP_LOG}
find ${BAK_DIR} -name "${SCHEMA}_*.tar.gz" -mtime +${RETENTION_DAYS} -delete
# 10. 备份成功日志
echo "[$(date)] 备份成功:${TAR_FILE}" >> ${BACKUP_LOG}
echo "================================================================" >> ${BACKUP_LOG}
exit 0
chmod +x 脚本名.sh
chown dmdba:dinstall 脚本名.sh
su - dmdba
cd 脚本目录
./脚本名.sh
crontab -e -u dmdba
编辑:
5 0 * * * /dmdata/dmbak/脚本名.sh
cat /dmdata/dmbak/backup/backup_run.log
#!/bin/bash
###########################################################
# 达梦8 数据恢复脚本(适配上述备份脚本)
# 功能:解压备份 → 校验文件 → 执行恢复 → 日志记录
# 使用:./dm_restore.sh 备份文件名(如 DM8_20260327_100000.tar.gz)
###########################################################
# ===================== 配置项(与备份脚本保持一致)=====================
export DM_HOME='/home/dmdba/dmdbms'
BAK_DIR='/dmdata/dmbak/backup'
USER='SYSDBA'
PASSWORD='Dm123456'
PORT='5237'
SCHEMA='DM8'
RESTORE_LOG="${BAK_DIR}/restore_run.log"
# ====================================================================
# 接收参数:备份压缩包名称
if [ $# -ne 1 ]; then
echo "用法:$0 <备份文件名.tar.gz>"
echo "示例:$0 DM8_20260327_100000.tar.gz"
exit 1
fi
TAR_FILE="$1"
TAR_PATH="${BAK_DIR}/${TAR_FILE}"
# 禁止 root 执行
if [ $(id -u) -eq 0 ]; then
echo "[$(date)] 错误:禁止 root 执行,请切换 dmdba 用户!" >> ${RESTORE_LOG}
exit 1
fi
# 基础校验
if [ ! -d "${DM_HOME}" ]; then
echo "[$(date)] 错误:DM_HOME 不存在 ${DM_HOME}" >> ${RESTORE_LOG}
exit 1
fi
if [ ! -f "${DM_HOME}/bin/dimp" ]; then
echo "[$(date)] 错误:dimp 恢复工具不存在" >> ${RESTORE_LOG}
exit 1
fi
if [ ! -f "${TAR_PATH}" ]; then
echo "[$(date)] 错误:备份文件不存在 ${TAR_PATH}" >> ${RESTORE_LOG}
exit 1
fi
# 加载环境变量
export PATH=${DM_HOME}/bin:$PATH
export LD_LIBRARY_PATH=${DM_HOME}/bin:$LD_LIBRARY_PATH
# 提取时间戳
TIMESTAMP=$(echo ${TAR_FILE} | grep -Eo '[0-9]{8}_[0-9]{6}')
if [ -z "${TIMESTAMP}" ]; then
echo "[$(date)] 错误:无法识别备份文件时间戳" >> ${RESTORE_LOG}
exit 1
fi
DMP_FILE="${SCHEMA}_${TIMESTAMP}.dmp"
LOG_FILE="${SCHEMA}_${TIMESTAMP}_restore.log"
echo "================================================================" >> ${RESTORE_LOG}
echo "[$(date)] 开始恢复:${TAR_FILE}" >> ${RESTORE_LOG}
# 解压备份
echo "[$(date)] 解压备份文件..." >> ${RESTORE_LOG}
tar -zxf "${TAR_PATH}" -C "${BAK_DIR}"
if [ $? -ne 0 ]; then
echo "[$(date)] 解压失败" >> ${RESTORE_LOG}
exit 1
fi
# 检查 dmp
if [ ! -f "${BAK_DIR}/${DMP_FILE}" ]; then
echo "[$(date)] 错误:解压后未找到 dmp 文件" >> ${RESTORE_LOG}
exit 1
fi
# ===================== 开始恢复 =====================
echo "[$(date)] 执行 dimp 恢复..." >> ${RESTORE_LOG}
${DM_HOME}/bin/dimp USERID=${USER}/${PASSWORD}@localhost:${PORT} \
DIRECTORY=${BAK_DIR} \
FILE=${DMP_FILE} \
LOG=${LOG_FILE} \
SCHEMAS=${SCHEMA} \
PARALLEL=4 \
BUFFER=102400 \
SILENT=Y \
TABLE_EXISTS_ACTION=REPLACE
# 校验恢复结果
if [ $? -eq 0 ]; then
echo "[$(date)] 恢复成功!日志:${BAK_DIR}/${LOG_FILE}" >> ${RESTORE_LOG}
else
echo "[$(date)] 恢复失败!请检查:${BAK_DIR}/${LOG_FILE}" >> ${RESTORE_LOG}
exit 1
fi
# 清理临时文件
rm -f "${BAK_DIR}/${DMP_FILE}"
echo "[$(date)] 恢复完成,临时文件已清理" >> ${RESTORE_LOG}
echo "================================================================" >> ${RESTORE_LOG}
exit 0
chmod +x dm_restore.sh
chown dmdba:dinstall dm_restore.sh
su - dmdba
ls /dmdata/dmbak/backup/*.tar.gz
./dm_restore.sh DM8_20260327_100000.tar.gz
cat /dmdata/dmbak/backup/restore_run.log
恢复会覆盖现有表数据TABLE_EXISTS_ACTION=REPLACE意思:表已存在则替换,适合灾难恢复。
恢复必须用 dmdba不能用 root,否则会破坏数据库权限。
恢复前建议
<1>确认业务已停止
<2>确认数据库正常运行
<3>确认磁盘空间充足
评论