部分批处理小脚本
#技巧 #shell #Linux
控制字符
颠倒文字显示顺序 \&\#8238\;
这个 控制字符的作用就是让文字在显示时顺序颠倒
这个控制字符的作用就是让文字在显示时顺序颠倒
#sync #rsync
利用rsync同步远程内容到本机
#!/bin/bash
# 本机存储位置
local_path=/jpdata/fb/$1
# 如果本机存储位置不存在,则创建该目录并在创建后开始同步;否则直接开始同步
ls $local_path > /dev/null 2>&1
if [ $? -gt 0 ]; then
echo "$local_path 目录不存在,尝试新建该目录"
mkdir -p $local_path
if [ $? -gt 0 ]; then
echo "$local_path 创建失败,请手动创建该目录"
exit
else
echo "目录创建成功,开始同步"
rsync -rtva --password-file=/jpdata/rsync/rsync.password [email protected]::whftpfile/projects/$1 $local_path
fi
else
echo "开始同步"
rsync -rtva --password-file=/jpdata/rsync/rsync.password [email protected]::whftpfile/projects/$1 $local_path
fi
# 显示同步目录下的结果,方便复制完整路径
find $local_path -maxdepth 3 -name "*.*"linux下快速删除空行的几种操作
grep -v '^$' file
sed '/^$/d' file监控指定任务的定时脚本
有时有些命令执行后所需时间比较长,放着容易忘,可以利用 crontab 和邮件功能做一个提醒。
以下定时任务为当 ps 命令过滤没检测到指定关键字时表示命令执行完成或中断,可以通过 [[Linux发送邮件]] 到指定用户邮箱,并注释当前定时任务,具体注释命令可以参考[[Linux命令/sed命令–处理编辑文本文件]]
# 指定注释行数来注释定时任务
* * * * * ps -aux | grep 'str' | grep -v grep || (sed -i "1 s/^/#/" /var/spool/cron/root; echo "邮件正文" | mail -s "邮件标题" [email protected] )
# 根据任务关键字过滤来注释定时任务
* * * * * ps -aux | grep 'str' | grep -v grep || (sed -i -e "/grep/ {s/^/#/}" /var/spool/cron/root; echo "邮件正文" | mail -s "邮件标题" [email protected] )同步并提交到git
#! /bin/bash
# 需求:有新包要发布时,通过脚本 + 发布包的路径自动将要发布的包同步至git2,并自动解压提交到gi2对应的仓库
# 1.同步发布包至git2
# 2.解析出具体的项目名
# 3.解压发布包并同步至git2对应项目的本地仓库
# 4.进行git提交
# 使用示例:./fb.sh jiaoshoujia_pt/3.9.7_1/publish/20210928_2/java # fb.sh为本脚本名称,后面的路径为测试提供的发布包路径(要去掉路径前面的“/projects/”)
# 本机存储位置
LOCAL_PATH=/jpdata/fb/$1
if [ $1 = "" ];then
echo "待同步的目录为空,请输入正确的同步路径"
exit
fi
# 开始从公司服务器同步待发布的包到华为云Git2服务器
# 如果本机存储位置不存在,则创建该目录并在创建后开始同步;否则直接开始同步
ls ${LOCAL_PATH} > /dev/null 2>&1
if [ $? -gt 0 ]; then
echo "本地 ${LOCAL_PATH} 目录不存在,尝试新建该目录"
mkdir -p ${LOCAL_PATH}
if [ $? -gt 0 ]; then
echo -e "\033[31m 本地 ${LOCAL_PATH} 创建失败,请手动创建该目录 \033[0m"
exit
else
echo "#################################################################################"
echo "目录创建成功,开始同步"
rsync -rtva --password-file=/jpdata/rsync/rsync.password [email protected]::whftpfile/projects/$1 ${LOCAL_PATH}
echo "#################################################################################"
fi
else
echo "#################################################################################"
echo "开始同步"
rsync -rtva --password-file=/jpdata/rsync/rsync.password [email protected]::whftpfile/projects/$1 ${LOCAL_PATH}
echo "#################################################################################"
fi
# 显示同步目录下的结果,方便复制完整路径
FILE_LIST=$(find ${LOCAL_PATH} -maxdepth 3 -name "*.*")
# 临时目录
TEMP_DIR=/tmp/git2_temp
# git commit 时间信息
TIMES=$(date +%Y%m%d-%H%M%S)
if [ ${FILE_LIST} = "" ]; then
echo -e "\033[31m 没有可更新的包,请检查同步的路径是否正确 \033[0m"
exit
fi
echo -e "待发布的包已同步至Git2服务器,本次即将更新的包如下:\n${FILE_LIST}"
echo "#################################################################################"
# 解析出具体的项目名和后缀
echo "开始解析出待发布包的项目名和压缩方式,解压后同步、提交至Git2的[GitLab](Git相关/GitLab%20安装记录.md)仓库"
echo "#################################################################################"
for PACKAGE_FULL_NAME in ${FILE_LIST}
do
ls ${TEMP_DIR} > /dev/null 2>&1
if [ $? -gt 0 ]; then
echo -e "临时目录 ${TEMP_DIR} 不存在,将创建该目录" && mkdir -p ${TEMP_DIR} || exit
fi
cd ${TEMP_DIR}
# 过滤出包的后缀 gz zip war
FITL_TYPE=$(echo ${PACKAGE_FULL_NAME} | awk -F '.' '{print $NF}')
echo ${FITL_TYPE} ${PACKAGE_FULL_NAME}
# 根据是否包含update来过滤出发布包中的项目名,因为更新包和全量包命名格式不一样,样本如下:
# jp-jsjxz-web-1_fht_update_7100_7297_202111221051.tar.gz
# jp-jsc-gw-core-1_update_20211122_01.zip
# jp-thd-core-1.war
if [[ ${PACKAGE_FULL_NAME} =~ "update" ]];
then
PROJECT_NAME=$(echo ${PACKAGE_FULL_NAME} | tr 'A-Z' 'a-z' | awk -F '/' '{print $NF}' | awk -F '_' '{print $1}')
else
PROJECT_NAME=$(echo ${PACKAGE_FULL_NAME} | tr 'A-Z' 'a-z' | awk -F '/' '{print $NF}' | awk -F '.' '{print $1}')
fi
# 根据不同的后缀包来进行不同的解压
if [ ${FITL_TYPE} = 'gz' ]
then
echo -e "开始解压 ${PROJECT_NAME} ,压缩方式为 ${FITL_TYPE}"
tar -zxf ${PACKAGE_FULL_NAME}
elif [ ${FITL_TYPE} = 'zip' ]
then
echo -e "开始解压 ${PROJECT_NAME} ,压缩方式为 ${FITL_TYPE}"
unzip -q ${PACKAGE_FULL_NAME}
elif [ ${FITL_TYPE} = 'war' ]
then
echo -e "开始解压 ${PROJECT_NAME} ,压缩方式为 ${FITL_TYPE}"
unzip -q ${PACKAGE_FULL_NAME} -d ${PROJECT_NAME}
fi
rm -rf ./*.txt # 删除打包中带的txt记录文件
# 如果发布包中jp-开头的项目名不带数字则改成带数据版
ls | grep "jp-" | grep [0-9] > /dev/null 2>&1 || mv $(ls | grep "jp-" | grep -v [0-9]) ${PROJECT_NAME}
GIT_DIR=/jpdata/project/shengyijia/${PROJECT_NAME}
ls ${GIT_DIR}
if [ $? -gt 0 ]; then
echo -e "\033[31m ${GIT_DIR}不存在,请手动检出该项目至/jpdata/project/shengyijia/路径 \033[0m"
cd ${TEMP_DIR} && rm -rf ./jp-* && echo 'clear temp dir'
exit
else
echo "#################################################################################"
echo -e "更新 ${PROJECT_NAME} 本地库至最新"
cd ${GIT_DIR}
while true
do
git pull
if [ $? -eq 0 ]; then
echo -e "${PROJECT_NAME} 本地库已更新完成"
echo "#################################################################################"
break;
else
echo -e "重新尝试更新 ${PROJECT_NAME} 本地库~~"
sleep 3
fi
done
echo "#################################################################################"
echo -e "开始同步"
echo "#################################################################################"
# 复制解压后的内容到git2本地仓库目录进行合并、提交
if [[ ${PACKAGE_FULL_NAME} =~ "update" ]]; then
echo "update~~"
rsync -av ${TEMP_DIR}/${PROJECT_NAME} ${GIT_DIR}/
else
echo "new deploy~~"
rsync -a --delete ${TEMP_DIR}/${PROJECT_NAME} ${GIT_DIR}/
fi
echo "#################################################################################"
echo "开始提交至Git2的GitLab仓库"
echo "#################################################################################"
# 以包名做为commit的描述信息
git add . && git commit -m $(echo ${PACKAGE_FULL_NAME} | awk -F '/' '{print $NF}')
# git push origin master && echo "update completed~"
# 因为本地有多个仓库,提交代码切换不同仓库太快时有可能遇到HTTP 403问题,需要重试几次提交
while true
do
git push origin master
if [ $? -eq 0 ]; then
echo -e "\n \033[32m update completed~ \033[0m \n"
break;
else
sleep 3
fi
done
cd ${TEMP_DIR} && rm -rf ./jp-* && echo -e "\n 临时目录已清空~~ \n"
fi
done
echo -e "\n本次更新的包全路径为:\n${FILE_LIST}\n"
echo -e "本次更新的包如下:"
echo -e "\033[32m"
echo -e "${FILE_LIST}" | awk -F '/' '{print $NF}'
echo -e "\033[0m"Windows使用bat脚本显示本机IP
有时给人远程处理问题,需要让对方提供IP信息,对小白用户来说查IP要一步步指导,比较慢,可以将以下内容保存为.bat文件,然后执行,就会在弹出的命令行窗口显示当前的IPv4地址了。
@echo off
echo "Your Computer IP Address is:"
ipconfig | find "IPv4"
echo.
pause>nul
exit网页内嵌PDF绕过下载限制
页面没有下载入口 打开浏览器开发者模式(F12),切换到Network,选项“fetch/XHR”,刷新页面后在新标签页打开Type为“fetch”的链接
[[vim]]快速删除一对括号
例如有如下内容,要删除整个Zstack{}的内容
Vstack{
Zstack{
print("我竟然在互联网搜不到这个问题的解决方案“)
}
}使用vim打开文件,在命令模式下,将光标移到要要删除的括号位置,输入da{,即可删除光标位置{}的所有内容。
删除小括号da(
Shell获取字符串的长度
# echo
a="abcd"
echo ${#a}
# awk后面的引号要用英文单引号
echo $a | awk '{print length($0)}'
# wc命令有两个参数可以实现
echo $a | wc -L
echo -n $a | wc -c[[远程备份同步导入脚本]]
Shell生成UUID
cat /proc/sys/kernel/random/uuid查找Linux/MacOS系统下的相同文件
利用相同文件的hash值相同来进行查找对比
#! /bin/bash
file_type="\(sh\|jpeg\|jpg\|png\|pdf\|psd\|doc\|docx\|xls\|xlsx\|ppt\|pptx\|mp4\|mov\|gz\|zip\|rar\|dmg\|avi\|wmv\|mpeg\|m4v\|asf\|flv\|f4v\|rmvb\gp\|vob\)"
# 对所有符合条件的文件计算hash值并记录到指定文件中
sha224sum $(find / -type f -regex ".*.${file_type}") >> hash_info.txt
# 对hash值相同的文件进行过滤并将相同的文件写入指定文件中
{
for dup in $(awk -F ' ' '{print $1}' hash_info.txt | sort -n |uniq -d)
do grep ${dup} hash_info.txt
echo "------------------------------------------"
done
} >> dup_file.txt
rm -rf hash_info.txt分析慢日志中是否有符合要监控的对应库慢SQL
#! /bin/bash
logfile="db-pro-slow.log-$(date +%Y%m%d)"
yestday=$(date +%F -d '-1 day')
scp [email protected]:/jpdata/data/mysql/${logfile} /tmp/
SendSussesMail ()
{
echo "生产环境MySQL 慢查询日志见附件 $1 " | mail -s "${yestday} 生产环境慢日志" -a /tmp/${yestday}_slow_sql.tar.gz [email protected]
find /tmp/output* /tmp/*.txt /tmp/*.gz /tmp/db-pro-slow.log-* -exec rm -rf {} \;
}
SendFailedMail ()
{
echo "没有匹配库的慢日志,退出脚本" | mail -s "生产环境没有慢日志" [email protected]
find /tmp/output* /tmp/*.txt /tmp/db-pro-slow.log-* -exec rm -rf {} \;
}
if [ -f /tmp/${logfile} ];then
# cp /jpdata/data/mysql/${logfile} /tmp/
cd /tmp/ || exit 1
# 目前只需要mml_syj和mml_jsj两个库的慢日志先判断要分析的库是否有慢日志,如果没有则直接退出
if ! grep -E '^use mml_syj|^use mml_jsj' ${logfile} > /dev/null 2>&1 ; then SendFailedMail ; exit 1; fi
# 先创建一个空文件,用来写第一个
echo > temp
csplit -s -f output ${logfile} '/^use /' '{*}'
for file in output*; do
cat ${file} >> temp
mv temp ${file}
tail -n 3 ${file} > temp
sed -i '$d' ${file}
done
# 用换行符\n做为for的分隔符
IFS=$'\n'
for keys in $(grep "use " ${logfile} | sort | uniq )
do
dbname=$(echo ${keys} | awk '{print $2}' | tr -d ';')
for file in output*; do
if grep -q "${keys}" ${file}; then
# echo -e "写入 ${file} 日志到 ${dbname}.txt"
cat ${file} >> $dbname.txt
# 删除已经写入的文件,避免重复搜索
rm -rf ${file}
fi
done
done
# 清除临时的IFS值
unset IFS
# 目前只分析需要mml_syj和mml_jsj两个库的慢日志
files_with_keyword=""
Abc ()
{
if [ -f "$1" ];then
# if (grep "FROM" $1 | grep -v 'core_logs' > /dev/null 2>&1 );then
if (grep "FROM" $1 | grep -v -E "core_logs|DELETE" > /dev/null 2>&1 );then
files_with_keyword+="$1 "
fi
fi
}
# 目前只分析需要mml_syj和mml_jsj两个库的慢日志
# 判断这两个库的慢日志中除了core_logs查询以外有没有其它的查询
for a in `ls *.txt | grep -E 'mml_syj|mml_jsj'`; do
Abc $a
done
if [ ! -z ${files_with_keyword} ];then
tar czf ${yestday}_slow_sql.tar.gz ${files_with_keyword} && SendSussesMail ${yestday}_slow_sql.tar.gz
else
echo "没有多的sql"
SendFailedMail
fi
else
SendFailedMail
exit 1
fi从全库备份的sql中切割出每个库的部分内容
使用csplit 指定'/^USE /'做为关键字来进行分割,分割后的文件以db开头,依次增加数字编号
csplit -s -f db bak_20230614030001.sql '/^USE /' '{*}'查看每个文件的第一行,判断文件中是哪个库的所有数据
for a in `ls db*`; do head -n 1 $a ; echo $a " --"; done分割指定库的所有表
使用csplit 指定'/^DROP TABLE IF EXISTS /'做为关键字来进行分割,分割后的文件以table开头,依次增加数字编号
csplit -s -f table db19 '/^DROP TABLE IF EXISTS /' '{*}'查看每个文件的第一行,判断文件中是哪个表的所有数据
for a in `ls table*`; do head -n 1 $a ; echo $a " --"; done通过死循环反复执行指定脚本,直到正常执行完成后退出
有时候会有一些脚本或者命令因为不确定的原因会报错导致退出,又不想每镒退出后手动重新执行,可以通过以while循环命令来实现自动重试,直至成功为止
while true; do python3 type.py; if [ $? -ne 0 ]; then sleep 30; else break; fi ; done#!/bin/bash
# 定义替换图像格式的函数
replace_image_format() {
file="$1"
# 定义目标格式的正则表达式(包含"media/Images"的情况)
pattern_with_path='!\[\[media/Images/([^]]+)\]\]'
# 定义目标格式的正则表达式(不包含"media/Images"的情况)
pattern_without_path='!\[\[([^]]+)\]\]'
# 读取文件内容
content=$(cat "$file")
# 检查文件内容是否包含"media/Images",并根据情况替换图像格式
if [[ "$content" == *"media/Images"* ]]; then
new_content=$(echo "$content" | sed -E "s#$pattern_with_path##g")
else
new_content=$(echo "$content" | sed -E "s#$pattern_without_path##g")
fi
# 处理文件名中的宽度内容(如果有),并移除竖线
new_content=$(echo "$new_content" | sed -E 's/\|([0-9]+)//g')
# 将修改后的内容写回文件
echo "$new_content" > "$file"
}
# 要处理的目录
target_directory="/root/fix_md"
# 查找目标目录及其子目录下的所有.md文件,并执行替换图像格式操作
find "$target_directory" -type f -name "*.md" | while read -r file; do
replace_image_format "$file"
done
批量创建用户、加组、生成密钥并给访问指定主机的权限
groudadd dev
#! /bin/bash
for a in user1 user2; do
useradd $a
usermod -aG dev $a
sudo -H -u $a bash -c 'ssh-keygen -q -N "" -t rsa -m PEM -f ~/.ssh/id_rsa'
sudo -H -u $a bash -c "cat ~/.ssh/id_rsa.pub > ~/.ssh/authorized_keys"
sudo -H -u $a bash -c 'ssh-copy-id -i ~/.ssh/id_rsa [email protected]'
sudo -H -u $a bash -c 'cp ~/.ssh/id_rsa /tmp/tag_$(whoami)_id_rsa'
done
chmod 777 /tmp/*id_rsa最后更新于