一、问题

因公司业务的发展,后台架构的变更,导致测试环境(Linux)部署与管理困难成倍增长,duang的一下,增加N倍。进入正题说问题:

问题1.  测试环境包含普通用户环境、开发者用户环境,原来只需2个Wildfly,现需要15*2,30个容器,启动、停止、部署工作量巨大。

    app

    appInterface

    battle

    friend

    gexin

    msg

    online

    passport

    pay

   push

   support

   union

   upload

   webInterface

   webView

注:因公司以及其他原因,本文中的模块名、环境、数量都进行了适当的修改,此处只举例说明。

问题2.  后续模块扩展与容器增减维护工作

问题3.  部署包SVN的自动获取,自动部署  

问题4.  部署完毕邮件通知

二、分析

1. 现状

a. SVN源码无权限,有固定目录取转测模块WAR包,但需要根据转测svn版本号取(最新的不一定是部署时转测的模块)

b. 转测模块不定,也许15个,也许2、3个

c. 15个模块(即15个WAR包),两环境(普通用户、开发者用户),需要30个容器

d. 根据转测模块,只需要停止对应模块所在容器,无须所有模块停止与启动

2. 分析与方案确定

1) 弃用Jenkins

a.无须自动构建:公司其他原因,测试无法获得SVN源码权限进行自动构建,Jenkins的自动化部署。

b.不够灵活:WAR的自动化部署,Jenkins虽可部署,但需要15个Job+,整体转测时用1Job统一部署,如模块转测试则需要按每个模块(每个Job)一一点击
c.工作量未减少:研发转测发布固定目录是以svn版本号发布,在部署时已经可能最新的版本号是另一个转测模块,因此需要取对应的版本号,每次改太麻烦,基本没有减少工作量。

2) 选用Shell脚本

a.脚本实现快速,随时修改

b.容器的操作都是Linux(shell)命令

c.自动化部署也采用shell分发与检测部署

d.邮件发送采用mail命令 

三、解决问题

1.wildfly统一命名规则

普通用户环境:Formal-wildfly-模块名

开发者环境:DEV-wildfly-模块名

Formal-wildfly-app

Formal-wildfly-appInterface

Formal-wildfly-battle

Formal-wildfly-friend

Formal-wildfly-gexin

...
DEV-wildfly-app

DEV-wildfly-appInterface

DEV-wildfly-battle

DEV-wildfly-friend

DEV-wildfly-gexin

...

2.模块名称列表: wildfly.list

app|app

appInterface|ae

battle|b

friend|f

gexin|g

msg|m

online|o

passport|pt

pay|pay

push|ph

support|st

union|un

upload|ud

webInterface|we

webView|ww

注意:

a.第一列为模块名,用于检测wildfly容器,故需要严格注意大小写

b.第二列为启动、停止、检查脚本使用的参数缩写

c.后续扩展增加模块,只需要增加对应的容器,然后修改此文件加入模块名即可,此处解决第2个问题

3.启动Wildfly脚本(run_wildfly.sh)

#!/bin/bash

# Author:findyou

# Email:1968089885@qq.com

cDate=`date +%Y-%m-%d`

cTime=`date +%H:%M`

shellDIR="/root/shell/"

wildfly_rootDir="/data/"

conf_file="wildfly.list"

echo_tips="      "

checkBoolean=0

# 检测wildfly.list文件是否存在,不存在-则退出脚本执行

if [ ! -f ${shellDIR}${conf_file} ]; then

    echo "Not Found : ${shellDIR}${conf_file}"

    exit 1

fi

# 读wildfly.list文件

count_n=0

while read line;

do

    count_n=`expr ${count_n} + 1`                            #统计模块个数

    wildfly[$count_n]=`echo $line|cut -d '|' -f 1`           #获到模块名称

    wildfly_quick[$count_n]=`echo $line|cut -d '|' -f 2`     #获得快捷命令

done < ${shellDIR}${conf_file}

# 脚本帮助提示,并退出脚本

help_tips(){

   echo "eg: $0 [wildflyName|a]"

   echo ""

   echo "wildflyName:"

    for ((i=1; i<=${count_n}; i++));

    do

       echo "${echo_tips}${wildfly[$i]}|${wildfly_quick[$i]}"

       done

   echo ""

   exit 1

}

# 如果检测到没有传入参数,则执行help_tips方法,

if [ ! -n "$1" ] ; then

    help_tips

fi

# 将传入的 模块名称 参数赋值给para_cmd

para_cmd=$1

# 休眠方法,用于启动间隔

sleep_2(){

    #echo "${echo_tips}${echo_tips}Sleep 2 second!"

    sleep 2

}

# 循环启动Wildfly方法

run_wildfly(){

echo "Time : ${cDate} ${cTime}"

# 循环wildfly.list文件中的所有模块,根据传入参数,判断执行相应的启动

for ((i=1; i<=${count_n}; i++));

do 

# 根据脚本传入的参数,启动对应的容器,传为a则启动所有容器。

if [ "${para_cmd}" == "a" -o "${para_cmd}" == "${wildfly[$i]}" -o "${para_cmd}" == "${wildfly_quick[$i]}" ];then

    echo "Start: ${wildfly[$i]}"

    #检查 普通用户 对应容器的进程

    formal_pc=`ps -ef|grep "Formal-wildfly-${wildfly[$i]}/"|grep -v grep|wc -l`

        #容器进程数,如果不为0,则说明已启动。反之则进行容器启动

        if [ $formal_pc -ne 0  ] ; then

            echo "${echo_tips}${echo_tips}Failure: UAT is already running!" 

        else

            echo "${echo_tips}UAT Start...."

            # 进入对应的容器,启动容器

            cd ${wildfly_rootDir}Formal-wildfly-${wildfly[$i]}/bin

            nohup sh standalone.sh >/dev/null 2>&1 &

            echo "${echo_tips}Please Check file: ${wildfly_rootDir}Formal-wildfly-${wildfly[$i]}/standalone/log/server.log"

            sleep_2

        fi

        

    #检查 开发者用户 对应容器的进程

    dev_pc=`ps -ef|grep "Dev-wildfly-${wildfly[$i]}/"|grep -v grep|wc -l`    

        if [ $dev_pc -ne 0 ] ; then

            echo "${echo_tips}${echo_tips}Failure: UAT-DEV is already running!" 

        else

            echo "${echo_tips}UAT-DEV Start...."

            cd ${wildfly_rootDir}Dev-wildfly-${wildfly[$i]}/bin

            nohup sh standalone.sh >/dev/null 2>&1 &

            echo "${echo_tips}Please Check file: ${wildfly_rootDir}Dev-wildfly-${wildfly[$i]}/standalone/log/server.log"

            sleep_2

        fi

    # 记录启动模块数

    checkBoolean=`expr ${checkBoolean} + 1`

fi

done

}

# 执行run_wildfly方法

run_wildfly

# 传入了参数,但是没有找到应的模块进行启动,调help_tips

if [ ${checkBoolean} -eq 0  ];then

    help_tips

fi

说明:

1.wildfly.list须要与run_wildfly.sh放在同一目录,脚本没有采用相对路径,故run_wildfly.sh脚本中需要调整对应的目录参数shellDIR

2.命令使用,如启动app容器: ./run_wildfly.sh app

3.启动所有app容器:./run_wildfly.sh a

4.检查Wildfly是否运行脚本(check_wildfly.sh)

脚本逻辑与启动脚本一致,直接替换掉run_wildfly方法即可,但记得调用修改后的方法

check_wildfly(){
echo "Time : ${cDate} ${cTime}" # 循环wildfly.list文件中的所有模块,根据传入参数,判断执行相应的启动 for ((i=1; i<=${count_n}; i++)); do  # 根据脚本传入的参数,启动对应的容器,传为a则启动所有容器。 if [ "${para_cmd}" == "a" -o "${para_cmd}" == "${wildfly[$i]}" -o "${para_cmd}" == "${wildfly_quick[$i]}" ];then     echo "Check: ${wildfly[$i]}"     #检查 普通用户 对应容器的进程     formal_pc=`ps -ef|grep "Formal-wildfly-${wildfly[$i]}/"|grep -v grep|wc -l`         #容器进程数,如果不为0,则说明已启动。反之则进行容器启动         if [ $formal_pc -eq 0  ] ; then             echo "${echo_tips}${echo_tips}UAT not Found!"         else             echo "${echo_tips}UAT is running!"         fi              #检查 开发者用户 对应容器的进程     dev_pc=`ps -ef|grep "Dev-wildfly-${wildfly[$i]}/"|grep -v grep|wc -l`             if [ $dev_pc -eq 0 ] ; then             echo "${echo_tips}${echo_tips}UAT-DEV not Found!"         else             echo "${echo_tips}UAT-DEV is running!"         fi     # 记录启动模块数     checkBoolean=`expr ${checkBoolean} + 1` fi done } 

说明:

1.检查所有app容器运行状态:./check_wildfly.sh a

5.停止Wildfly脚本(stop_wildfly.sh)

脚本逻辑与启动脚本一致,直接替换掉run_wildfly方法即可,但记得调用修改后的方法

stop_wildfly(){

for ((i=1; i<=${count_n}; i++));

do 

if [ "${para_cmd}" == "a" -o "${para_cmd}" == "${wildfly[$i]}" -o "${para_cmd}" == "${wildfly_quick[$i]}" ];then

    echo "Stop: ${wildfly[$i]}"

    # 检查 普通用户 对应容器的进程,得到进程号

    formal_pc=`ps -ef|grep "Formal-wildfly-${wildfly[$i]}/"|grep -v grep|awk '{print $2}'`

        if [ "$formal_pc" == "" ] ; then

            echo "${echo_tips}${echo_tips}UAT not Found!" 

        else

            # 停止进程

            kill -9 $formal_pc

            sleep_2

            # 再次检测是否已停止进程

            formal_pc1=`ps -ef|grep "Formal-wildfly-${wildfly[$i]}/"|grep -v grep|awk '{print $2}'`

            if [ "$formal_pc1" == "" ] ; then

                echo "${echo_tips}Stop UAT Success!" 

            else

                echo "${echo_tips}${echo_tips}Stop UAT Failure!"

            fi

        fi

    # 检查 开发者用户 对应容器的进程,得到进程号

    dev_pc=`ps -ef|grep "Dev-wildfly-${wildfly[$i]}/"|grep -v grep|awk '{print $2}'`

        if [ "$dev_pc" == "" ] ; then

            echo "${echo_tips}${echo_tips}UAT-DEV not Found!" 

        else

            # 停止进程

            kill -9 $dev_pc

            sleep_2

            # 再次检测是否已停止进程

            dev_pc1=`ps -ef|grep "Dev-wildfly-${wildfly[$i]}/"|grep -v grep|awk '{print $2}'`

            if [ "$dev_pc1" == "" ] ; then

                echo "${echo_tips}Stop UAT-DEV Success!" 

            else

                echo "${echo_tips}${echo_tips}Stop UAT-DEV Failure!"

            fi

        fi

    checkBoolean=`expr ${checkBoolean} + 1`

fi

done

}

说明:

1.停止所有容器:./stop_wildfly.sh a

至此,第1个问题已圆满解决!

结束语:

1.原本考虑与实现相对简单,第一版,把所有的容器路径写到文件里,读取启动与停止即可,但不利于自动化部署、WAR分发等问题处理。

2.这个版本是实际当中优化的第三个版本,相对扩展与维护简单,为自动化部署提供停止与启动脚本,也最适合我们目前的转测流程。

3.本想与自动部署一起写此文,发现所讲的内容与贴出的脚本内容过多,有时间再讲讲解决第三、四个问题,超简单的实现方式shell脚本。

4.Jenkins大多数觉得持续集成用这个很叼,完了其引入除了用发邮件功能、定时任务,其他组件基本用不上。很多人也许只是对Jenkins组件的熟悉,但完全不具备Jenkins转化提升效率的能力,维护成本与效率还不如之前手工操作。

5.思想的支撑尤为重要,可以在有限的资源里发挥出最大的功效,寻找到最优的方案。

切勿舍本求末,忘记初心!

如转载还请保留出处与作者姓名Findyou,谢谢!

Linux 解决数量庞大wildfly容器启动与停止的脚本的更多相关文章

  1. linux 程序启动与停止管理脚本

    公司接了一个第三方的系统,基于linux写的几个程序,一共有9个部件,第三方没有给脚本,每次启动或停止都得一个一个手工去停止或修改.......,这里稍微鄙视下. 没办法,求人还不如自己动手写, 需求 ...

  2. linux系统下apache服务的启动、停止、重启命令

    本文章简单的介绍了关于linux下在利用命令来操作apache的基本操作如启动.停止.重启等操作,对入门者不错的选择.本文假设你的apahce安装目录为 usr local apache2,这些方法适 ...

  3. Linux下安装nginx,以及启动和停止

    1.安装 安装nginx之前,首先确保系统已经安装了依赖:g++.gcc.openssl-devel.pcre-devel和zlib-devel软件 yum install gcc-c++ yum - ...

  4. linux系统下nginx/mysql/php启动、停止、重启命令

    /usr/local/nginx/sbin/nginx /etc/init.d/mysql start /usr/local/php/sbin/php-fpm start   #nginx命令     ...

  5. Atitit. 软件GUI按钮与仪表盘--web服务器区--获取apache配置文件路径 linux and apache的启动、停止、重启

    Atitit.   软件GUI按钮与仪表盘--web服务器区--获取apache配置文件路径 linux and apache的启动.停止.重启 可以通过"netstat -anp" ...

  6. Atitit. 软件GUIbutton与仪表盘--webserver区--获取apache配置文件路径 linux and apache的启动、停止、重新启动

    Atitit.   软件GUIbutton与仪表盘--webserver区--获取apache配置文件路径 linux and apache的启动.停止.重新启动 能够通过"netstat  ...

  7. Dubbo应用启动与停止脚本,超具体解析

    本周刚好研究了一下dubbo的启动脚本,所以在官网的启动脚本和公司内部的启动脚本做了一个整理,弄了一份比較通过的Dubbo应用启动和停止脚本.          以下的脚本仅仅应用于配置分离的应用.什 ...

  8. 一键启动NameNode和DataNode--shell脚本

    使用shell脚本,一键启动hadoop中的NameNode和DataNode.分为普通版和装逼版.装逼版较普通版多了很多判断和信息提示,当然主要还是为了我联系shell脚本而写的. 如果想实现复用, ...

  9. Centos7.3_x86_64通过systemctl控制tomcat8.0.46启动和停止

    Centos7.3_x86_64通过systemctl控制tomcat8..46启动和停止 之前在centos 6上通过脚本控制tomcat 启动和停止的脚本,虽然在centos 7也可以使用,但ce ...

随机推荐

  1. Linux下服务器端开发流程及相关工具介绍(C++)

    去年刚毕业来公司后,做为新人,发现很多东西都没有文档,各种工具和地址都是口口相传的,而且很多时候都是不知道有哪些工具可以使用,所以当时就想把自己接触到的这些东西记录下来,为后来者提供参考,相当于一个路 ...

  2. webpack入门教程之Hello webpack(一)

    webpack入门教程系列为官网Tutorials的个人译文,旨在给予想要学习webpack的小伙伴一个另外的途径.如有不当之处,请大家指出. 看完入门教程系列后,你将会学习到如下内容: 1.如何安装 ...

  3. C#中如何调整图像大小

    在本篇文章中,我将介绍如何在C#中来调整你想要的图像大小.要实现这一目标,我们可以采取以下几个步骤: 1.首先要获取你想要调整大小的图像: string path = Server.MapPath(& ...

  4. 在知乎上看到 Web Socket这篇文章讲得确实挺好,从头看到尾都非常形象生动,一口气看完,没有半点模糊,非常不错

    在知乎上看到这篇文章讲得确实挺好,从头看到尾都非常形象生动,一口气看完,没有半点模糊,非常不错,所以推荐给大家,非常值得一读. 作者:Ovear链接:https://www.zhihu.com/que ...

  5. 如何在Elasticsearch中安装中文分词器(IK+pinyin)

    如果直接使用Elasticsearch的朋友在处理中文内容的搜索时,肯定会遇到很尴尬的问题--中文词语被分成了一个一个的汉字,当用Kibana作图的时候,按照term来分组,结果一个汉字被分成了一组. ...

  6. JavaScript求两个数字之间所有数字的和

    这是在fcc上的中级算法中的第一题,拉出来的原因并不是因为有什么好说的,而是我刚看时以为是求两个数字的和, 很显然错了.我感觉自己的文字理解能力被严重鄙视了- -.故拉出来折腾折腾. 要求: 给你一个 ...

  7. 【从零开始学BPM,Day4】业务集成

    [课程主题] 主题:5天,一起从零开始学习BPM [课程形式] 1.为期5天的短任务学习 2.每天观看一个视频,视频学习时间自由安排. [第四天课程] 1.课程概要 Step 1 软件下载:H3 BP ...

  8. 项目持续集成环境(jenkins + SVN + maven + tomcat)

    整体流程 每次SVN上代码有变动,触发自动构建动作,并部署到服务器的tomcat上,具体流程: 1.SVN上提交代码修改 2.maven执行Goals 3.将web工程打成war包 4.关闭服务器的t ...

  9. Express 教程 01 - 入门教程之经典的Hello World

    目录: 前言 一.Express?纳尼?! 二.开始前的准备工作 三.测试安装之经典的Hello World 四.使用express(1)来生成一个应用程序 五.说明 前言: 本篇文章是建立在Node ...

  10. JavaScript中undefined与null的区别

    通常情况下, 当我们试图访问某个不存在的或者没有赋值的变量时,就会得到一个undefined值.Javascript会自动将声明是没有进行初始化的变量设为undifined. 如果一个变量根本不存在会 ...