今天把这段时间学习完shell后完成工作上的一个小案件整理了一下,分享给大家!

  说来也巧了,作为一个刚刚毕业半年的菜鸟,进入公司后,听公司的大牛推荐学习linux--”鸟哥的私房菜“,基本上是从去年8月份开始到了今年的1月份,基本上是把基础篇看完了,开始了解shell脚本的相关知识。刚好公司有了一个shell脚本的案件给我了,时间上也没有多紧。然后就一边学习一边开始做,虽然中途客户反映先前的业务逻辑有问题耽搁了两周,但总算是到最后完成了,自己学习的东西能用到很开心,今天闲了,把代码整理了一下,分享给大家

  具体是这样:

  要求是写一个shell脚本,安装要求查询数据,将符合条件的数据按照客户给定的xml样式进行组装,然后加入到crontab中,定时执行通过scp或者ftp放到客户服务器上。

  具体实现步骤:

  一、编写生成xml文档的代码

网上搜索了一篇博客:http://blog.csdn.net/dengzhaoqun/article/details/7262271   拿来学习了一下,感觉好用,自己就根据自己的实际情况修改了一下:

 #! /bin/bash
# filename: create_xml.sh
# create_wangxb_20150123
#
# 从外部传入的第一个参数作为xml的文件名
outfile=$
# xml中的缩进位
tabs= # ++++++++++++++++++++++++++++
# 组装一个节点,输出到文件
# 说一说传参数时的这几个区别:假如有下面这个脚本执行的命令
# /path/to/scriptname opt1 opt2 opt3 opt4
# $: 的值是默认是脚本的名字,从$-$ 开始就是参数的值
# $# :代表后接的参数『个数』
# $@ :代表『 "$1" "$2" "$3" "$4" 』之意,每个变量是独立的(用双引号括起来);
# $* :代表『 "$1c$2c$3c$4" 』,其中 c 为分隔字节,默认为空白键, 所以本例中代表『 "$1 $2 $3 $4" 』之意。
# 在shell中我们可以也可以使用${}包含变量名,来调用变量
# ++++++++++++++++++++++++++++
put(){
echo '<'${*}'>' >> $outfile
} # 这里也是输出一个xml的节点,只是比上面的节点有更多的设置
# ${@:} 的意思:它的值就是由第二个参数开始到最后一个参数,为什么要这样?有时可能你的第二个参数中有空格,shell接受参数是以空格计算的
put_tag() {
echo '<'$'>'${@:}'</'$'>' >> $outfile
}
# 同样是一个输出节点函数,但是添加了CDATA,防止特殊字符造成xml解析失败
put_tag_cdata() {
echo '<'$'><![CDATA['${@:}']]></'$'>' >> $outfile
} put_head(){
put '?'${}'?'
}
# 这是一个缩进的算法,自行理解
out_tabs(){
tmp=
tabsstr=""
while [ $tmp -lt $((tabs)) ]
do
tabsstr=${tabsstr}'\t'
tmp=$((tmp+))
done
echo -e -n $tabsstr >> $outfile
} tag_start(){
out_tabs
put $
tabs=$((tabs+))
} tag() {
out_tabs
if [ "$1" == ]
then
put_tag $ $(echo ${@:})
elif [ "$1" == ]
then
put_tag_cdata $ $(echo ${@:})
fi
} tag_end(){
tabs=$((tabs-))
out_tabs
put '/'${}
}

  这里有一些基础知识: 

  关于参数:

  假如有下面这个脚本执行的命令
     /path/to/scriptname opt1 opt2 opt3 opt4
   

 $: 的值是默认是脚本的名字,从$-$ 开始就是参数的值
$# :代表后接的参数『个数』
$@ :代表『 "$1" "$2" "$3" "$4" 』之意,每个变量是独立的(用双引号括起来);
$* :代表『 "$1c$2c$3c$4" 』,其中 c 为分隔字节,默认为空白键, 所以本例中代表『 "$1 $2 $3 $4" 』之意。
在shell中我们可以也可以使用${}包含变量名,来调用变量

  关于 ${@:2} 这种形式的说明,我转载了一篇博客:http://www.cnblogs.com/wxb0328/p/4276751.html

  二、从数据库查数据利用上面的函数,制作xml文件

 #!/bin/bash
# filename: ts_xml.sh
# create_wangxb_20150126
# PATH=/u01/app/oracle/product/10.2./db_1/bin:/usr/kerberos/bin:/usr/local/bin:/bin:/usr/bin:/opt/dell/srvadmin/bin:/home/p3s_batch/tools:/home/p3s_batch/bin
export PATH
# Database account information file
source ~/.p3src #++++++++++++++++++++++++++++++++++++++++++++++++++++++++
# set some variable
# XMLSCRIPT: 脚本的绝对路径
# MATCHING_RESULT_XML: xml_1的文件名
# XML_FUNC_FILE: 生成xml函数文件路径
# MATCHING_RESULT_QUERY_DATA: sqlplus 查出数据保存的零时文件
# MATCHING_RESULT_QUERY_SQL: sqlplus 查询的sql语句
#++++++++++++++++++++++++++++++++++++++++++++++++++++++++
# 下面是一些基础的设置
export XMLSCRIPT=/usr/p3s/batch/jaaa_match/tmp_xa_wangxb
XML_DIR="$XMLSCRIPT/xmldata"
XML_FUNC_FILE="xml_func.sh" MATCHING_RESULT_XML="matching_result_"$(date '+%Y%m%d_%H%M%S')".xml"
MATCHING_RESULT_QUERY_DATA="matching_result_query_data.tmp"
MATCHING_RESULT_QUERY_SQL="matching_result_query.sql" CLIENT_LIST_XML="client_list_"$(date '+%Y%m%d_%H%M%S')".xml"
CLIENT_LIST_QUERY_DATA="client_list_query_data.tmp"
CLIENT_LIST_QUERY_SQL="client_list_query.sql" # add_wangxb_20150225
if [ ! -d "$XML_DIR" ];
then
mkdir $XML_DIR
fi #+++++++++++++++++++++++++++
# modify_wangxb_20150224
# check for temporary file
#+++++++++++++++++++++++++++
if [ -e "$XML_DIR/$MATCHING_RESULT_XML" ];
then
rm -f $XML_DIR/$MATCHING_RESULT_XML
fi if [ -e "$XMLSCRIPT/$MATCHING_RESULT_QUERY_DATA" ];
then
MATCHING_RESULT_QUERY_DATA="matching_result_query_data_"$(date '+%Y%m%d%H%M%S')".tmp"
fi
#+++++++++++++++++++++++++++++++++++++++++++++++++
# add_wangxb_20150225
# check system time, choice query time period
# 这是是根据crontab每天执行的时间,取得我们查询数据库时的where条件的时间区间
#+++++++++++++++++++++++++++++++++++++++++++++++++
sys_datetime=$(date '+%Y%m%d%H')
first_chk_datetime="$(date '+%Y%m%d')04"
second_chk_datetime="$(date '+%Y%m%d')12"
third_chk_datetime="$(date '+%Y%m%d')20"
# 由于服务器crontab是上面的时间,但是执行的shell比较多,在调用我这个shell的时候,不一定就是04: ,:, :30所以,这里的根据系统的时间判断时 范围给的比较宽
case $sys_datetime in
"$first_chk_datetime"|"$(date '+%Y%m%d')05"|"$(date '+%Y%m%d')06"|"$(date '+%Y%m%d')07")
chk_start=$(date '+%Y-%m-%d 21:00:00' -d '-1 day')
chk_end=$(date '+%Y-%m-%d 04:29:59')
;;
"$second_chk_datetime"|"$(date '+%Y%m%d')13"|"$(date '+%Y%m%d')14"|"$(date '+%Y%m%d')15")
chk_start=$(date '+%Y-%m-%d 04:30:00')
chk_end=$(date '+%Y-%m-%d 12:29:59') ;;
"$third_chk_datetime"|"$(date '+%Y%m%d')21"|"$(date '+%Y%m%d')22"|"$(date '+%Y%m%d')23")
chk_start=$(date '+%Y-%m-%d 12:30:00')
chk_end=$(date '+%Y-%m-%d 20:59:59') ;;
*)
chk_start=$(date '+%Y-%m-%d 00:00:00')
chk_end=$(date '+%Y-%m-%d 23:59:59') ;;
esac # modify_wangxb_20150310
# 下面的是做一个oracle数据库连接的测试,如果连接失败,后续代码不再执行,并且写入错误日志
$ORACLE_HOME/bin/sqlplus -s $ORAUSER_WEB_PASDB << EOF
set echo off
set feedback off
alter session set nls_date_format='YYYY-MM-DD:HH24:MI:SS';
select sysdate from dual;
quit
EOF
if [ $? -ne ]
then
echo "********** DBへのリンク己窃した **********"
exit
else
echo "********** DBへのリンクOKです **********"
fi
# sqlplus就是oracle的一个客户端软件,具体使用方法可以问度娘,这里传入要执行的sql和参数,将结果 > 输出到指定文件
$ORACLE_HOME/bin/sqlplus -s $ORAUSER_WEB_PASDB @$XMLSCRIPT/$MATCHING_RESULT_QUERY_SQL "$chk_start" "$chk_end" > $XMLSCRIPT/$MATCHING_RESULT_QUERY_DATA # create matching result's xml file
# add_wangxb_20150227
# 下面的算法就是将查出的数据进行分析,调用xml函数生成xml文件
source "$XMLSCRIPT/$XML_FUNC_FILE" "$XML_DIR/$MATCHING_RESULT_XML"
put_head 'xml version="1.0" encoding="utf-8"'
tag_start 'ROOT'
if [ -s "$XMLSCRIPT/$MATCHING_RESULT_QUERY_DATA" ];
then
datas=${XMLSCRIPT}/${MATCHING_RESULT_QUERY_DATA}
#for res in $datas
while read res;
do
stock_id=$(echo $res | awk 'BEGIN {FS="\\^\\*\\^"} {print $1}')
seirino=$(echo $res | awk 'BEGIN {FS="\\^\\*\\^"} {print $2}')
match_flg=$(echo $res | awk 'BEGIN {FS="\\^\\*\\^"} {print $3}')
unmatch_riyuu=$(echo $res | awk 'BEGIN {FS="\\^\\*\\^"} {print $4}')
up_date_tmp=$(echo $res | awk 'BEGIN {FS="\\^\\*\\^"} {print $5}')
up_date=$(echo $up_date_tmp | awk 'BEGIN {FS="@"} {print $1 " " $2}')
tag_start 'MATCHING'
tag 'STOCKID' ${stock_id:-""}
tag 'SEIRINO' ${seirino:-""}
tag 'RESULT' ${match_flg:-""}
tag 'REASON' ${unmatch_riyuu:-""}
tag 'UPDATE_DATE' ${up_date:-""}
tag_end 'MATCHING'
done < $datas
fi
tag_end 'ROOT'
rm $XMLSCRIPT/$MATCHING_RESULT_QUERY_DATA # create client list's xml file
# add_wangxb_2015027
# 下面的是再生成一个xml文件,和上面一样
if [ -e "$XML_DIR/$CLIENT_LIST_XML" ];
then
rm -f $XML_DIR/$CLIENT_LIST_XML
fi if [ -e "$XMLSCRIPT/$CLIENT_LIST_QUERY_DATA" ];
then
CLIENT_LIST_QUERY_DATA="client_list_query_data_"$(date '+%Y%m%d%H%M%S')".tmp"
fi $ORACLE_HOME/bin/sqlplus -s $ORAUSER_MND @$XMLSCRIPT/$CLIENT_LIST_QUERY_SQL > $XMLSCRIPT/$CLIENT_LIST_QUERY_DATA source "$XMLSCRIPT/$XML_FUNC_FILE" "$XML_DIR/$CLIENT_LIST_XML"
put_head 'xml version="1.0" encoding="utf-8"'
tag_start 'ROOT'
if [ -s "$XMLSCRIPT/$CLIENT_LIST_QUERY_DATA" ];
then
datas=${XMLSCRIPT}/${CLIENT_LIST_QUERY_DATA}
#for res in $datas
while read res;
do
corporation_id=$(echo $res | awk 'BEGIN {FS="\\^\\*\\^"} {print $1}')
corporation_name=$(echo $res | awk 'BEGIN {FS="\\^\\*\\^"} {print $2}')
client_id=$(echo $res | awk 'BEGIN {FS="\\^\\*\\^"} {print $3}')
client_print_name=$(echo $res | awk 'BEGIN {FS="\\^\\*\\^"} {print $4}')
tag_start 'CLIENT'
tag 'CORPORATION_ID' ${corporation_id:-""}
tag 'CORPORATION_NAME' ${corporation_name:-""}
tag 'CLIENT_ID' ${client_id:-""}
tag 'CLIENT_PRINT_NAME' ${client_print_name:-""}
tag_end 'CLIENT'
done < $datas
fi
tag_end 'ROOT'
rm $XMLSCRIPT/$CLIENT_LIST_QUERY_DATA # add_wangxb_20150304
# Convert xml file encoding
# 这是将xml文件进行转码,命令是iconv
if [ -e "$XML_DIR/$MATCHING_RESULT_XML" ];
then
echo "********** matching_result.xmlファイルコ〖ドを啪垂し、**********"
iconv -f euc-jp -t utf- $XML_DIR/$MATCHING_RESULT_XML -o $XML_DIR/$MATCHING_RESULT_XML.utf-
mv $XML_DIR/$MATCHING_RESULT_XML.utf- $XML_DIR/$MATCHING_RESULT_XML
fi
if [ -e "$XML_DIR/$CLIENT_LIST_XML" ];
then
echo "********** client_list.xmlフィルコ〖ドを啪垂し、**********"
iconv -f euc-jp -t utf- $XML_DIR/$CLIENT_LIST_XML -o $XML_DIR/$CLIENT_LIST_XML.utf-
mv $XML_DIR/$CLIENT_LIST_XML.utf- $XML_DIR/$CLIENT_LIST_XML
fi # add_wangxb_20150304
# Send the xml file to the destination server by ftp
#ftp_host="222.***.***.***"
#USER="***"
#PASS="***"
#ftp -i -n $ftp_host << EOF
#user $USER $PASS
#cd /
#lcd $XML_DIR/
#put $MATCHING_RESULT_XML
#put $CLIENT_LIST_XML
#quit
#EOF # test ftp
# 通过ftp将xml文件放到客户服务器上,ftp_host:客户服务器地址,user登录名,pass密码
ftp_host="***.***.***.***"
USER="***"
PASS="***"
dir="/upload"
ftp -i -n $ftp_host << EOF
user $USER $PASS
cd /upload/
lcd $XML_DIR/
put $MATCHING_RESULT_XML
put $CLIENT_LIST_XML
quit
EOF # Save the program log file
YYMM=$(date +'%Y%m%d%H%M')
cp /tmp/create_xml.log /usr/p3s/batch/jaaa_match/tmp_xa_wangxb/logs/create_xml.log.$YYMM # Send error log files into the Admin mailbox
info_to_mail_1="**@**.co.jp"
info_to_mail_2="***@**.co.jp"
# nkf 日文转码的一个命令
title=$(echo "test" | nkf -j)
nkf -j < /tmp/create_xml.log | mail -s $title $info_to_mail_1 $info_to_mail_2 #exit

  关于nkf 日文转码:http://www.cnblogs.com/wxb0328/p/4333820.html

  本来是用scp传送的,但是后面修改了,这里把自己为scp传送找到的一个,不用密码可立即登入的 ssh 用户

  在鸟哥私房菜的服务器架设篇的第十一章中有介绍:http://vbird.dic.ksu.edu.tw/linux_server/0310telnetssh_2.php#ssh_nopasswd

  下面是执行的两个sql文件

 SET PAGESIZE 0
SET FEEDBACK OFF
SET VERIFY OFF
SET ECHO OFF
SET HEADING OFF
SET TIMI OFF
SET LINESIZE 1000
SET WRAP OFF SELECT s.STOCKID|| '^*^' ||a.SERI_NO|| '^*^' ||a.MATCH_FLG|| '^*^' ||a.UNMATCH_RIYUU|| '^*^' ||to_char(a.UP_DATE,'YYYY-MM-DD@HH24:MI:SS') UP_DATE FROM aaa_stock_db a LEFT JOIN SENDDATAAPPRAISALPROTO s ON a.SERI_NO=s.SEIRINO WHERE a.UP_DATE BETWEEN to_date('&1','yyyy-mm-dd hh24:mi:ss') AND to_date('&2','yyyy-mm-dd hh24:mi:ss') AND a.DEL_FLG=0 ORDER BY a.UP_DATE DESC; exit
 SET PAGESIZE 0
SET FEEDBACK OFF
SET VERIFY OFF
SET ECHO OFF
SET HEADING OFF
SET TIMI OFF
SET LINESIZE 1000
SET WRAP OFF SELECT a.CORPORATION_ID|| '^*^' ||a.CORPORATION_NAME|| '^*^' ||b.CLIENT_ID|| '^*^' ||(select CLIENT_PRINT_NAME from CLIENT_MASTER where CLIENT_ID = b.CLIENT_ID) as CLIENT_PRINT_NAME FROM M_CORPORATION_MASTER a LEFT JOIN M_CORPORATION_GROUP b ON (a.CORPORATION_ID = b.CORPORATION_ID) WHERE a.DEL_FLG=0 AND b.DEL_FLG=0; exit

  

  三、来看看效果

    当然中间出现了许多bug,不过慢慢修改吗,兵来将挡,水来土掩,bug来了自己调么

 

  

  就这样简单的整理一下,可能光这么写不够完整,但是,中间设计的知识也很多,不能展开了说,做个分享,大家有用到的时候也是个思路,具体的某些知识点可以用到了再去找资料了

  题外话:

  这几天打算辞职,想去外面,但是听了在外面找工作的同学说,外面要求的技术很多:“什么优化,缓存,环境搭建啊,高并发,读写分离,负载均衡等等”  。突然就没有了去外面的激情,而且毕竟才毕业半年,工资也不高,毕业前出去旅行也借了5K的钱都没有还,哎、、、本来想着去深圳,怎么也能找个6K+的工作,现在听听,觉得能力不够啊,这是这些能力也不是一天两天能掌握的,很郁闷,如果不出去,要等到什么时候,趁年轻不出去怕以后就没有机会!

  哎、、、这个决定该怎么做,有点烦!如果哪位大牛能够看到小弟这篇博客,希望能提点建设性的意见,不胜感激!!涕泗横流!!!

shell脚本生成xml文件的更多相关文章

  1. Linux Shell脚本读写XML文件

    在Linux下如何用Shell脚本读写XML?现有一个config.xml <?xml version="1.0" encoding="UTF-8"?&g ...

  2. 用shell脚本生成日志文件

    mdate=`date +%R-%d-%m-%Y` LogFile=/root/HDstatusLog.log echo disk is good! $mdate >> $LogFile ...

  3. 利用python和shell脚本生成train.txt的标签文件

    1. 用shell脚本生成带绝对路径的train.txt 例如我要生成如下形式的带标签的文件,如图:(如有两个标签:0 和 1) shell脚本如下: 这样标签0写入了train.txt # /usr ...

  4. Android 解析XML文件和生成XML文件

    解析XML文件 public static void initXML(Context context) { //can't create in /data/media/0 because permis ...

  5. linux下shell脚本执行jar文件

    最近在搞一个shell脚本启动jar文件个关闭jar文件的东东.搞得我都蛋疼了.今天晚上终于弄好了 话说,小弟的linux只是刚入门,经过各方查资料终于搞定了.话不多说,下面开始上小弟写的shell脚 ...

  6. shell 编程生成日期文件;Server虚拟机上进行Web服务器配置

    shell 编程生成日期文件 1. 请编写一个脚本,命名为sh01.sh,其功能是: 键盘输入文件名(要求使用名字全拼作为文件名). 自动创建3个文件. 1个为系统当天日期(CCYYMMDD). 1个 ...

  7. Java生成XML文件

    我们在数据库中的数据可以将其提取出来生成XML文件,方便传输.例如数据库中有Admin这张表: 我们写一个java类表示admin数据: package xmlDom.vo; import java. ...

  8. Android 使用xml序列化器生成xml文件

    在<Android 生成xml文件>一文中使用流的形式写入xml格式文件,但是存在一定的问题,那就是在短信内容中不能出现<>之类的括号,本文使用xml序列化器来解决 xml序列 ...

  9. C# 生成xml文件

    本篇文章旨在.net环境下生成xml文件,以控制台应用程序为例进行说明. 1.在vs中新建控制台应用程序CreateXml 2.CreateXmlFile:主要生成xml的函数 public void ...

随机推荐

  1. 用Keras 和 DDPG play TORCS(1)

    用Keras 和 DDPG play TORCS(环境配置篇) 原作者Using Keras and Deep Deterministic Policy Gradient to play TORCS ...

  2. JVM体系结构之三:方法区之2(jdk1.6,jdk1.7,jdk1.8下的方法区变迁)

    方法区 方法区存储虚拟机加载的类信息,常量,静态变量,即时编译器编译后的代码等数据.HotSpot中也称为永久代(Permanent Generation),(存储的是除了Java应用程序创建的对象之 ...

  3. 十.jQuery源码分析之.map()

    763行:三个参数. elems:待遍历的数组或对象. callback:回调函数,会在数组的每个元素或对象的每个属性上执行.执行时传入两个参数:数组元素,元素下标;或属性名,属性值. arg:仅限于 ...

  4. JVM实例以及内存的分配机制

    JVM:一台用来模拟计算机执行计算指令的虚拟计算机,拥有自己的指令,指令执行环境,虚拟内存等. 下面介绍虚拟机(JVM)--cpu,寄存器,内存,指令 ======================== ...

  5. Selenium Webdriver——Xpath轴定位(preceding)

     1.preceding-sibling 选取当前节点之前的所有同级节点 text=出发之前的同级节点: 2.preceding 选取当前节点开始标签之前的所有节点 text=出发节点标签之前的所有i ...

  6. 串口通信,帧与帧之间的时间间隔问题?9600波特率,帧将各在20ms以上

  7. 跟我学算法- tensorflow 卷积神经网络训练验证码

    使用captcha.image.Image 生成随机验证码,随机生成的验证码为0到9的数字,验证码有4位数字组成,这是一个自己生成验证码,自己不断训练的模型 使用三层卷积层,三层池化层,二层全连接层来 ...

  8. Halcon中二维码解析函数解码率和时长的优化方法

    Halcon中条码解析函数包容多种条码类型且简单强大.现有的‘Data Matrix ECC 200’.‘QR Code’和‘PDF417’等广泛使用的条码均能解析.简单是通过默认参数即可对多种条码进 ...

  9. ajax的post请求方式

    <%@ page language="java" import="java.util.*" pageEncoding="UTF-8"% ...

  10. PC上对限制在微信客户端访问的html页面进行调试

    PC上对微信的html5页面做测试,一般来说需要两个条件:浏览器UA改为微信客户端的UA(打开页面提示请在微信客户端登录就需要修改UA):增加满足html5验证条件的Cookie来进行微信OAUTH验 ...