之前在写控制台的时候,使用到了项目里面的shell脚本,然后发现我们开发过程中可以使用shell脚本去方便我们的一些业务场景,提高我们的工作效率,减少一些重复性的操作,特写一篇文章分享自己对于shell脚本的一些认识和使用
Shell 和 Shell脚本
Shell 是一个用 C 语言编写的程序,它是用户使用 Linux 的桥梁。Shell 既是一种命令语言,又是一种程序设计语言。
Shell 是指一种应用程序,这个应用程序提供了一个界面,用户通过这个界面访问操作系统内核的服务。
Shell 脚本(shell script),是一种为 shell 编写的脚本程序。
我理解它们之间的关系是这样的
基本结构
一个shel脚本的最基本的结构如下所示
#!/bin/bash
echo "hello world"
exit 0
语句
-
#!/bin/bash 声明shell脚本使用的shell的名称
-
exit 0 是用来返回脚本执行结果的,类似c/c++会在main函数里面用return 0作为返回的结果,在脚本执行完成之后可以用通过 echo $? 返回脚本执行的结果
执行脚本
shell脚本的执行有两种方法,一种是作为可执行的程序执行
chmod +x ./shanshan.sh // 使脚本具有执行权限
./shanshan.sh
其中chmod是控制用户对文件的权限的命令,+x是指赋予文件执行的权限
另外一种是使用shell的解释器,将脚本作为参数执行
/bin/bash ./shanshan.sh
/bin/sh ./shanshan.sh
shell脚本编程的基本语法
变量
常见的变量有两种,一种是shel脚本的定义的变量,如下
#!/bin/bash
name="shanshan"
echo ${name}
exit 0
其中变量赋值时不可以有空格,可通过 $ 引用定义过的变量
另一种是调用脚本传入的参数变量,如下
#!/bin/bash
echo "传入的参数的个数:$#"
echo "传入的参数的是:$@"
echo "执行的文件名:$0"
echo "第一个参数名:$1"
echo "第二个参数名:$2"
exit 0
执行 ./shanshan.sh 1 2 3
可输出如下
还有一些特殊字符可用来处理参数,就不一一举栗子~
数组
shell脚本数组用括号来表示,元素用"空格"符号分割开,语法格式如下
arr=(value0 value1 value2)
-
${arr[index]}可用来获取数组中的元素 -
${arr[*]}或${arr[@]}可用来获取数组中所有的元素 -
${#arr[*]}或${#arr[@]}可用来获取数组的长度
条件语句
- if 的语法格式如下
if [ $1 == 1 ];
then
echo "fisrt param is one"
elif [ $1 == 2 ];
then
echo "fisrt param is two"
else
echo "other"
fi
需要注意的是它的格式,可见 if 和判断条件之间都存在空格,在[]中进行一些条件的判断,以 fi 作为这条语句的结束
- switch 的语法格式如下
case $1 in
1)
echo "fisrt param is one";;
2)
echo "fisrt param is two";;
*)
echo "other";;
esac
其中的*)表示的是他可以匹配任意值,;;表示break,执行结束
- 循环
其中常见的两种循环有while和for循环
while循环的语法格式如下
num=$1
while [ $num != 3 ]
do
echo $num
((num=num+1))
done
echo $num
for循环的语法格式如下
for (( i=1; i<3; i++))
do
echo $i
done
函数
function print() {
echo "parame 1 is $1 2 is $2"
}
print a b
使用函数时在函数名后用空格分开传入参数
日常开发中常见的几种业务的场景
介绍完了上面一些基本的语法,其实就可以写一些基本的脚本了,也可以去读懂一些脚本的语句了,其实我们项目里面就已经有很多的这个脚本了,不知道大家注意没有,我们在一些业务场景上面还是会比较频繁的需要去使用到它们的
使用shell脚本将打包的文件部署到服务器上
在我们没有使用或者搭建Jenkins去部署某一个环境的时候,我们可以自己手动使用这个命令去将我们打包出来的dist包上传到该环境的服务器上面
#!/bin/bash
source="./dist/console"
target="/opt/dtstack/DTConsole/ConsoleFront"
server="172.16.100.168"
echo "Uploading $source to $server:$target"
### 上传文件到指定服务器
scp -P 22 -r $source root@$server:$target
echo "Upload over."
使用shell脚本推包
每次我们往私有仓库推包也是在使用一样的命令,并且registry的地址非常长,可以使用shell脚本将这个命令简化~
#!/bin/bash
registry="http://registry.npm.dtstack.com/"
package=""
while [[ $# > 0 ]];
do
case $1 in
-D)
package=$2;
shift;;
*)
echo "Unknown parameter passed: $1";
exit 1;;
esac;
shift;
done
npm set registry $registry
if [ ! -z $package ];
then
echo "package is ${package}"
npm unpublish $package --registry $registry
echo "Unpublish over."
else
npm publish --registry $registry
echo "Publish over."
fi
可执行./publish.sh推送当前版本的私有仓库的包, ./publish.sh -D dt-common@version删除对应的私有仓库的包
使用shell脚本打tag
在很久之前,我们部门还是需要我们开发自己去基于这个release的分支去执行npm run release打一个tag,其实这个就是去执行了我们项目下的这个shell脚本,其中这个脚本执行了如下的一些语句
#!/bin/bash
while [[ $# > 0 ]];
do
case $1 in
-r|--release)
release="$2";
shift;;
-b|--branch)
branch="$2";
shift;;
*)
echo "Unknown parameter passed: $1";
exit 1;;
esac;
shift;
done
# Default as minor, the argument major, minor or patch:
if [ -z $release ];
then
release="minor";
fi
# Default release branch is master
if [ -z $branch ];
then
branch="master";
fi;
echo "Branch is $branch"
echo "Release as $release"
# Tag prefix
prefix="DTinsight_v"
git pull origin $branch
echo "Current pull origin $branch."
# Auto generate version number and tag
standard-version -r $release --tag-prefix $prefix --infile CHANGELOG.md
git push --follow-tags origin $branch
echo "Release finished."
总结
在我们日常的开发中还是有比较多的地方使用到了shell脚本的,给我们带来了便利,避免一些重复性的操作,了解一些shell脚本的基本的语法对于我们前端开发来说也是很有帮助的,以上是我对于shel脚本的一些浅薄的认识,如果有不对之处欢迎指正~