需求:统计某个文件或者特定目录下Kafka消息一段时间范围内每个小时消息条数或者每天消息条数。
一行数据行实例:2018-03-28T03:00:02 ...
分析:
参数:1.指定文件的文件绝对路径
2.指定日期或者开始日期和结束日期
3.指定小时或者开始小时和结束小时
4.指定统计维度(小时或者天)
逻辑:1.输出逻辑 -- 文件 + 屏幕打印
2.统计逻辑 -- grep + wc -l
3.按天范围统计逻辑
4.按小时范围统计逻辑
5.按统计维度选择3/4的函数
6.文件分类处理(单个文件或者特定目录下文件)
7.对用户输入的日期进行判断和初始化处理
8.对用户输入的小时进行判断和初始化处理
9.辅助函数,修剪、加前缀0、自定义LOGGER(检查各函数参数)、文件名格式化
扩展:1.增加目录参数,不再限定单一目录。
2.绝对路径和相对路径均适用。
3.对特大文件进行按行拆分处理后再统计。
4.兼容时间戳格式的时间范围。
Shell阶段性总结:
1. Shell脚本调试全局开启,首行声明 #!/bin/bash -xv .
2.获取脚本目录, $( cd "$(dirname $0)" && pwd) .
3.参数选项设置,-o为短参数列表,-l为长参数列表,双引号内不带冒号的为不能带参数值的参数,带冒号的必须带参数值.
OPTS=`getopt -o "s:,e:,dd:,df:,sh:,eh:,dh:,hd,h" -l "start-date:,end-date:,designed-date:,designed-file:,start-hour:,end-hour:,designed-hour:,hour-dimension,help" -- "$@"`
eval set -- "$OPTS"
4.Trim函数在shell中实现,%%为右边最长匹配去除,##为左边最长匹配去除.
trimmed=""
function trim(){
trimmed=$1
trimmed=${trimmed%%\ }
trimmed=${trimmed##\ }
trimmed=${trimmed%%\t}
trimmed=${trimmed##\t}
}
5.数值比较用符号应使用 ((>,>=,<,<=,=)),用字母应该使用[ -eq,-le,-ge,-lt,-gt,-ne ] .
6.字符串比较使用[ -z,-n,=,==,>,<],其中>,<比较字母ASCII顺序.
7.获取距离指定日期后i天的日期,转换成特定格式字符串,$(date +%Y-%m-%d --date="${from_date} + ${i} day") .
8.获取指定日期的时间戳,$(date -d "$to_date" +%s),用于日期比较.
9.函数名变量,$FUNCNAME;函数名调用栈数组 ${FUNCNAME[@]},如 another_func test_func main ;主要用于日志定位.
10.函数中局部变量声明,local designed_date .
11.测试使用全部写在USAGE的Example里面的例子,因此Example要写的较为全面,同时写在Example中便于随时补充。
12.help中USAGE变量填充,<< EOF .. EOF,告诉主shell,后续的输入,是其他命令或者子shell的输入,直到遇到EOF为止,再回到主shell.
read -d '' USAGE << EOF
##填充具体的使用说明
EOF
附Shell脚本:
#!/bin/bash
read -d '' USAGE << EOF
USAGE
$0 [--start-date=yyyy-mm-dd --end-date=yyyy-mm-dd] [--designed-date=yyyy-mm-dd] [--start-hour=HH --end-hour=HH] [--designed-hour=HH] [--designed-file=absulte path] [--hour-dimension] [--help]
DESCRIPTION
This script is for count lines between start-date&start-hour and end-date&end-hour.
Or count lines between designed-date