Skip to content Skip to main navigation Skip to footer

shell: shell脚本生成xml文件

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

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

具体是这样:

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

具体实现步骤:

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

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

1 #! /bin/bash
2 # filename: create_xml.sh
3 # create_wangxb_20150123
4 #
5 # 从外部传入的第一个参数作为xml的文件名
6 outfile=$1
7 # xml中的缩进位
8 tabs=0
9
10 # ++++++++++++++++++++++++++++
11 # 组装一个节点,输出到文件
12 # 说一说传参数时的这几个区别:假如有下面这个脚本执行的命令
13 # /path/to/scriptname opt1 opt2 opt3 opt4
14 # $0 : 的值是默认是脚本的名字,从$1 -$4 开始就是参数的值
15 # $# :代表后接的参数『个数』
16 # $@ :代表『 " $1 >" " $2 >" " $3 >" " $4 >" 』之意,每个变量是独立的(用双引号括起来);
17 # $* :代表『 " $1c$2c$3c$4 >" 』,其中 c 为分隔字节,默认为空白键, 所以本例中代表『 " $1 $2 $3 $4 >" 』之意。
18 # 在shell中我们可以也可以使用${}包含变量名,来调用变量
19 # ++++++++++++++++++++++++++++
20 put(){
21 echo ' < ' ${*}' > ' >> $outfile
22 }
23
24 # 这里也是输出一个xml的节点,只是比上面的节点有更多的设置
25 # ${@:2 } 的意思:它的值就是由第二个参数开始到最后一个参数,为什么要这样?有时可能你的第二个参数中有空格,shell接受参数是以空格计算的
26 put_tag() {
27 echo ' < ' $1 ' > ' ${@:2 }' </ ' $1 ' > ' >> $outfile
28 }
29 # 同样是一个输出节点函数,但是添加了CDATA,防止特殊字符造成xml解析失败
30 put_tag_cdata() {
31 echo ' < ' $1 ' ><![CDATA[ ' ${@:2 }' ]]></ ' $1 ' > ' >> $outfile
32 }
33
34 put_head(){
35 put ' ? ' ${1 }' ? '
36 }
37 # 这是一个缩进的算法,自行理解
38 out_tabs(){
39 tmp=0
40 tabsstr=">"
41 while [ $tmp -lt $((tabs)) ]
42 do
43 tabsstr=${tabsstr}' t '
44 tmp=$((tmp+1 ))
45 done
46 echo -e -n $tabsstr >> $outfile
47 }
48
49 tag_start(){
50 out_tabs
51 put $1
52 tabs=$((tabs+1 ))
53 }
54
55 tag() {
56 out_tabs
57 if [ " $1 >" == 0 ]
58 then
59 put_tag $2 $(echo ${@:3 })
60 elif [ " $1 >" == 1 ]
61 then
62 put_tag_cdata $2 $(echo ${@:3 })
63 fi
64 }
65
66 tag_end(){
67 tabs=$((tabs-1 ))
68 out_tabs
69 put ' / ' ${1 }
70 }

这里有一些基础知识:

关于参数:

假如有下面这个脚本执行的命令

/path/to/scriptname opt1 opt2 opt3 opt4

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

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

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

1 #!/bin/bash
2 # filename: ts_xml.sh
3 # create_wangxb_20150126
4 #
5
6 PATH=/u01/app/oracle/product/10.2 .0 /db_1/bin:/usr/kerberos/bin:/usr/local/bin:/bin:/usr/bin:/opt/dell/srvadmin/bin:/home/p3s_batch/tools:/home/p3s_batch/bin
7 export PATH
8 # Database account information file
9 source ~/.p3src
10
11 #++++++++++++++++++++++++++++++++++++++++++++++++++++++++
12 # set some variable
13 # XMLSCRIPT: 脚本的绝对路径
14 # MATCHING_RESULT_XML: xml_1的文件名
15 # XML_FUNC_FILE: 生成xml函数文件路径
16 # MATCHING_RESULT_QUERY_DATA: sqlplus 查出数据保存的零时文件
17 # MATCHING_RESULT_QUERY_SQL: sqlplus 查询的sql语句
18 #++++++++++++++++++++++++++++++++++++++++++++++++++++++++
19 # 下面是一些基础的设置
20 export XMLSCRIPT=/usr/p3s/batch/jaaa_match/tmp_xa_wangxb
21 XML_DIR=” $XMLSCRIPT/xmldata >”
22 XML_FUNC_FILE=” xml_func.sh >”
23
24 MATCHING_RESULT_XML=” matching_result_ >” $(date ‘ +%Y%m%d_%H%M%S ‘ )” .xml >”
25 MATCHING_RESULT_QUERY_DATA=” matching_result_query_data.tmp >”
26 MATCHING_RESULT_QUERY_SQL=” matching_result_query.sql >”
27
28 CLIENT_LIST_XML=” client_list_ >” $(date ‘ +%Y%m%d_%H%M%S ‘ )” .xml >”
29 CLIENT_LIST_QUERY_DATA=” client_list_query_data.tmp >”
30 CLIENT_LIST_QUERY_SQL=” client_list_query.sql >”
31
32 # add_wangxb_20150225
33 if [ ! -d ” $XML_DIR >” ];
34 then
35 mkdir $XML_DIR
36 fi
37
38 #+++++++++++++++++++++++++++
39 # modify_wangxb_20150224
40 # check for temporary file
41 #+++++++++++++++++++++++++++
42 if [ -e ” $XML_DIR/$MATCHING_RESULT_XML >” ];
43 then
44 rm -f $XML_DIR/$MATCHING_RESULT_XML
45 fi
46
47 if [ -e ” $XMLSCRIPT/$MATCHING_RESULT_QUERY_DATA >” ];
48 then
49 MATCHING_RESULT_QUERY_DATA=” matching_result_query_data_ >” $(date ‘ +%Y%m%d%H%M%S ‘ )” .tmp >”
50 fi
51 #+++++++++++++++++++++++++++++++++++++++++++++++++
52 # add_wangxb_20150225
53 # check system time , choice query time period
54 # 这是是根据crontab每天执行的时间,取得我们查询数据库时的where条件的时间区间
55 #+++++++++++++++++++++++++++++++++++++++++++++++++
56 sys_datetime=$(date ‘ +%Y%m%d%H ‘ )
57 first_chk_datetime=” $(date ‘+%Y%m%d’)04 >”
58 second_chk_datetime=” $(date ‘+%Y%m%d’)12 >”
59 third_chk_datetime=” $(date ‘+%Y%m%d’)20 >”
60 # 由于服务器crontab是上面的时间,但是执行的shell比较多,在调用我这个shell的时候,不一定就是04:30 ,12 :30 , 20 :30所以,这里的根据系统的时间判断时 范围给的比较宽
61 case $sys_datetime in
62 ” $first_chk_datetime >” |” $(date ‘+%Y%m%d’)05 >” |” $(date ‘+%Y%m%d’)06 >” |” $(date ‘+%Y%m%d’)07 >” )
63 chk_start=$(date ‘ +%Y-%m-%d 21:00:00 ‘ -d ‘ -1 day ‘ )
64 chk_end=$(date ‘ +%Y-%m-%d 04:29:59 ‘ )
65 ;;
66 ” $second_chk_datetime >” |” $(date ‘+%Y%m%d’)13 >” |” $(date ‘+%Y%m%d’)14 >” |” $(date ‘+%Y%m%d’)15 >” )
67 chk_start=$(date ‘ +%Y-%m-%d 04:30:00 ‘ )
68 chk_end=$(date ‘ +%Y-%m-%d 12:29:59 ‘ )
69
70 ;;
71 ” $third_chk_datetime >” |” $(date ‘+%Y%m%d’)21 >” |” $(date ‘+%Y%m%d’)22 >” |” $(date ‘+%Y%m%d’)23 >” )
72 chk_start=$(date ‘ +%Y-%m-%d 12:30:00 ‘ )
73 chk_end=$(date ‘ +%Y-%m-%d 20:59:59 ‘ )
74
75 ;;
76 *)
77 chk_start=$(date ‘ +%Y-%m-%d 00:00:00 ‘ )
78 chk_end=$(date ‘ +%Y-%m-%d 23:59:59 ‘ )
79
80 ;;
81 esac
82
83 # modify_wangxb_20150310
84 # 下面的是做一个oracle数据库连接的测试,如果连接失败,后续代码不再执行,并且写入错误日志
85 $ORACLE_HOME/bin/sqlplus -s $ORAUSER_WEB_PASDB << EOF 86 set echo off 87 set feedback off 88 alter session set nls_date_format=’ YYYY-MM-DD:HH24:MI:SS ‘ ; 89 select sysdate from dual; 90 quit 91 EOF 92 if [ $? -ne 0 ] 93 then 94 echo ” ********** DBへのリンク己窃した ********** >”
95 exit
96 else
97 echo ” ********** DBへのリンクOKです ********** >”
98 fi
99 # sqlplus就是oracle的一个客户端软件,具体使用方法可以问度娘,这里传入要执行的sql和参数,将结果 > 输出到指定文件
100 $ORACLE_HOME/bin/sqlplus -s $ORAUSER_WEB_PASDB @$XMLSCRIPT/$MATCHING_RESULT_QUERY_SQL ” $chk_start >” ” $chk_end >” > $XMLSCRIPT/$MATCHING_RESULT_QUERY_DATA
101
102
103 # create matching result’ s xml file
104 # add_wangxb_20150227
105 # 下面的算法就是将查出的数据进行分析,调用xml函数生成xml文件
106 source ” $XMLSCRIPT/$XML_FUNC_FILE >” ” $XML_DIR/$MATCHING_RESULT_XML >”
107 put_head ‘ xml version=”1.0>” encoding=”utf-8>” ‘
108 tag_start ‘ ROOT ‘
109 if [ -s ” $XMLSCRIPT/$MATCHING_RESULT_QUERY_DATA >” ];
110 then
111 datas=${XMLSCRIPT}/${MATCHING_RESULT_QUERY_DATA}
112 #for res in $datas
113 while read res;
114 do
115 stock_id=$(echo $res | awk ‘ BEGIN {FS=”\^\*\^>”} {print $1} ‘ )
116 seirino=$(echo $res | awk ‘ BEGIN {FS=”\^\*\^>”} {print $2} ‘ )
117 match_flg=$(echo $res | awk ‘ BEGIN {FS=”\^\*\^>”} {print $3} ‘ )
118 unmatch_riyuu=$(echo $res | awk ‘ BEGIN {FS=”\^\*\^>”} {print $4} ‘ )
119 up_date_tmp=$(echo $res | awk ‘ BEGIN {FS=”\^\*\^>”} {print $5} ‘ )
120 up_date=$(echo $up_date_tmp | awk ‘ BEGIN {FS=”@>”} {print $1 ” >” $2} ‘ )
121 tag_start ‘ MATCHING ‘
122 tag 0 ‘ STOCKID ‘ ${stock_id:-“>” }
123 tag 0 ‘ SEIRINO ‘ ${seirino:-“>” }
124 tag 0 ‘ RESULT ‘ ${match_flg:-“>” }
125 tag 1 ‘ REASON ‘ ${unmatch_riyuu:-“>” }
126 tag 0 ‘ UPDATE_DATE ‘ ${up_date:-“>” }
127 tag_end ‘ MATCHING ‘
128 done < $datas 129 fi 130 tag_end ‘ ROOT ‘ 131 rm $XMLSCRIPT/$MATCHING_RESULT_QUERY_DATA 132 133 134 # create client list’ s xml file 135 # add_wangxb_2015027 136 # 下面的是再生成一个xml文件,和上面一样 137 if [ -e ” $XML_DIR/$CLIENT_LIST_XML >” ];
138 then
139 rm -f $XML_DIR/$CLIENT_LIST_XML
140 fi
141
142 if [ -e ” $XMLSCRIPT/$CLIENT_LIST_QUERY_DATA >” ];
143 then
144 CLIENT_LIST_QUERY_DATA=” client_list_query_data_ >” $(date ‘ +%Y%m%d%H%M%S ‘ )” .tmp >”
145 fi
146
147
148 $ORACLE_HOME/bin/sqlplus -s $ORAUSER_MND @$XMLSCRIPT/$CLIENT_LIST_QUERY_SQL > $XMLSCRIPT/$CLIENT_LIST_QUERY_DATA
149
150 source ” $XMLSCRIPT/$XML_FUNC_FILE >” ” $XML_DIR/$CLIENT_LIST_XML >”
151 put_head ‘ xml version=”1.0>” encoding=”utf-8>” ‘
152 tag_start ‘ ROOT ‘
153 if [ -s ” $XMLSCRIPT/$CLIENT_LIST_QUERY_DATA >” ];
154 then
155 datas=${XMLSCRIPT}/${CLIENT_LIST_QUERY_DATA}
156 #for res in $datas
157 while read res;
158 do
159 corporation_id=$(echo $res | awk ‘ BEGIN {FS=”\^\*\^>”} {print $1} ‘ )
160 corporation_name=$(echo $res | awk ‘ BEGIN {FS=”\^\*\^>”} {print $2} ‘ )
161 client_id=$(echo $res | awk ‘ BEGIN {FS=”\^\*\^>”} {print $3} ‘ )
162 client_print_name=$(echo $res | awk ‘ BEGIN {FS=”\^\*\^>”} {print $4} ‘ )
163 tag_start ‘ CLIENT ‘
164 tag 0 ‘ CORPORATION_ID ‘ ${corporation_id:-“>” }
165 tag 1 ‘ CORPORATION_NAME ‘ ${corporation_name:-“>” }
166 tag 0 ‘ CLIENT_ID ‘ ${client_id:-“>” }
167 tag 1 ‘ CLIENT_PRINT_NAME ‘ ${client_print_name:-“>” }
168 tag_end ‘ CLIENT ‘
169 done < $datas 170 fi 171 tag_end ‘ ROOT ‘ 172 rm $XMLSCRIPT/$CLIENT_LIST_QUERY_DATA 173 174 175 # add_wangxb_20150304 176 # Convert xml file encoding 177 # 这是将xml文件进行转码,命令是iconv 178 if [ -e ” $XML_DIR/$MATCHING_RESULT_XML >” ];
179 then
180 echo ” ********** matching_result.xmlファイルコ〖ドを啪垂し、********** >”
181 iconv -f euc-jp -t utf-8 $XML_DIR/$MATCHING_RESULT_XML -o $XML_DIR/$MATCHING_RESULT_XML.utf-8
182 mv $XML_DIR/$MATCHING_RESULT_XML.utf-8 $XML_DIR/$MATCHING_RESULT_XML
183 fi
184 if [ -e ” $XML_DIR/$CLIENT_LIST_XML >” ];
185 then
186 echo ” ********** client_list.xmlフィルコ〖ドを啪垂し、********** >”
187 iconv -f euc-jp -t utf-8 $XML_DIR/$CLIENT_LIST_XML -o $XML_DIR/$CLIENT_LIST_XML.utf-8
188 mv $XML_DIR/$CLIENT_LIST_XML.utf-8 $XML_DIR/$CLIENT_LIST_XML
189 fi
190
191 # add_wangxb_20150304
192 # Send the xml file to the destination server by ftp
193 #ftp_host=” 222.***.***.*** >”
194 #USER=” *** >”
195 #PASS=” *** >”
196 #ftp -i -n $ftp_host << EOF 197 #user $USER $PASS 198 #cd / 199 #lcd $XML_DIR/ 200 #put $MATCHING_RESULT_XML 201 #put $CLIENT_LIST_XML 202 #quit 203 #EOF 204 205 # test ftp 206 # 通过ftp将xml文件放到客户服务器上,ftp_host:客户服务器地址,user登录名,pass密码 207 ftp_host=” ***.***.***.*** >”
208 USER=” *** >”
209 PASS=” *** >”
210 dir =” /upload >”
211 ftp -i -n $ftp_host << EOF 212 user $USER $PASS 213 cd /upload/ 214 lcd $XML_DIR/ 215 put $MATCHING_RESULT_XML 216 put $CLIENT_LIST_XML 217 quit 218 EOF 219 220 221 # Save the program log file 222 YYMM=$(date +’ %Y%m%d%H%M ‘ ) 223 cp /tmp/create_xml.log /usr/p3s/batch/jaaa_match/tmp_xa_wangxb/logs/create_xml.log.$YYMM 224 225 # Send error log files into the Admin mailbox 226 info_to_mail_1=” **@**.co.jp >”
227 info_to_mail_2=” ***@**.co.jp >”
228 # nkf 日文转码的一个命令
229 title=$(echo ” test >” | nkf -j)
230 nkf -j < /tmp/create_xml.log | mail -s $title $info_to_mail_1 $info_to_mail_2
231
232
233 #exit[/code]

关于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文件

1 SET PAGESIZE 0
2 SET FEEDBACK OFF
3 SET VERIFY OFF
4 SET ECHO OFF
5 SET HEADING OFF
6 SET TIMI OFF
7 SET LINESIZE 1000
8 SET WRAP OFF
9
10
11 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 ;
12
13 exit [/code]

1 SET PAGESIZE 0
2 SET FEEDBACK OFF
3 SET VERIFY OFF
4 SET ECHO OFF
5 SET HEADING OFF
6 SET TIMI OFF
7 SET LINESIZE 1000
8 SET WRAP OFF
9
10
11 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 ;
12
13 exit [/code]

三、来看看效果

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

shell: shell脚本生成xml文件
shell: shell脚本生成xml文件

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

题外话:

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

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

原文:http://www.cnblogs.com/wxb0328/p/shellxml.html

0 Comments

There are no comments yet

Leave a comment

Your email address will not be published.