PostgreSQL日志解析工具WalMiner

0.先说需求:

原先有一个线上的pg数据库,就叫它pg-1,现在需要需要将其复制到pg-2,复制完之后对pg-1的所有操作需要同步到pg-2(包括线上系统使用时发生的数据变更和手动修改),但对pg-2的操作不要同步到pg-1。
通过调查决定使用日志分析的方式,分析出pg-1的执行过的sql,然后再在pg-2上执行一遍。日志分析工具使用WalMiner

1.安装WalMiner

gitee上有完整的安装步骤,此处不再赘述,需要注意pg版本,WalMiner3.0之后不再支持9.*的pg
安装过程中可能会报头文件找不到的错误,需安装postgresql对应版本的dev包,并加入环境变量

export LD_LIBRARY_PATH=$LD_LIBRARY_PATH:/usr/pgsql-9.6/include

(dev包在centos上可能叫postgresql96-devel, ubuntu上可能叫postgresql-server-dev-9.6)

2.开启pg的wal日志归档功能

修改postgresql.conf配置文件

  • wal_level = logical
    pg10及以后的版本中,待选的值为minimal、replica、logical。
    minimal --不能通过基础备份和wal日志恢复数据库。 replica = 9.6版本以前的
    archive和hot_standby --该级别支持wal归档和复制。
    logical --在replica级别的基础上添加了支持逻辑解码所需的信息。
  • archive_mode = on
    表示打开归档备份,可选的参数为on,off,always 默认值为off,所以要手动打开
  • archive_command = \'test ! -f /home/archivedir/%f && cp %p /home/archivedir/%f\'
    该参数的默认值是一个空字符串,他的值可以是一条shell命令或者一个复杂的shell脚本。在shell脚本或命令中可以用 “%p” 表示将要归档的wal文件包含完整路径的信息的文件名,用“%f” 代表不包含路径信息的wal文件的文件名
  • archive_timeout=600s
    wal日志10分钟切换一次,同时会触发日志归档。因为我们要实现的复制功能需要一定的时效性,10分钟触发一次归档比较合理。

3.同步脚本

#!/bin/bash
set -e
# 检查程序是否正在运行
pid_file="/var/run/transfer.pid"
if [ -e $pid_file  ];then
  pid=`cat $pid_file`
  echo "$pid"
  if [ `ps aux|awk '{print $2}'|grep -w $pid|wc -l` -gt 0 ]; then
    echo "程序正在运行!"
    exit
  fi
fi

echo $$>$pid_file

# 用于存储sql的目录
sqlsdir="/home/TMIP/nas/sqls/"
# 用于解析的目录
archivedir="/home/archivedir/"
# 用于备份的目录
archivedir1="/home/TMIP/nas/archivedir/"
# 备份的wal保留十天
find $archivedir1 -type f -mtime +10 -exec rm -Rf {} \;
# 备份的sql保留十天
find $sqlsdir -type f -mtime +10 -exec rm -Rf {} \;

psql_cmd="psql -U postgres -h 127.0.0.1 -p 54340 -d tmip_c020 -c "
transfer_cmd="psql -U postgres -h 192.168.1.131 -p 54340 -d tmip_c020 -c "

# 记录上次解析的截止时间的文件
last_time_file="/root/last_time"
# 精确解析开始时间
start_time=`cat $last_time_file`
# 精确解析结束时间
end_time=`date --date='20 minute ago' "+%Y-%m-%d %H:%M:%S"`.$((10#`date +%N`/1000000))

btime=$(date "+%Y-%m-%d %H:%M:%S")

# 精确解析
sql="delete from walminer_contents;select walminer_wal_add('$archivedir');select wal2sql('$start_time','$end_time',true);"
#echo $sql
$psql_cmd "$sql"

# 测试连接是否通
$transfer_cmd "select 1;"

sql="update walminer_contents set op_text=op_text||';';select op_text from walminer_contents;"
#echo $sql
set +e
$psql_cmd "$sql"|grep ";"|while read line;do
  echo "执行sql:${line}"
  echo ${line} >> "$sqlsdir$start_time"
  $transfer_cmd "$line"
done

# 计算此次同步花费多少时间
etime=$(date "+%Y-%m-%d %H:%M:%S")
duration=$(($(date +%M -d "${etime}")-$(date +%M -d "${btime}")));
mmin=$((60+$duration))

# 只保留(60分钟+同步花费的时间)之内的,其余的移到备份文件夹
find $archivedir -type f -mmin +$mmin -exec mv {} $archivedir1 \;

echo $end_time>$last_time_file
rm $pid_file

如果需要密码的话需要在脚本内加上

export PGPASSWORD=mypassword

加入定时器,每分钟执行一次

*/10 * * * * bash /home/ll/transfer.sh
暂无评论

发送评论 编辑评论

|´・ω・)ノ
ヾ(≧∇≦*)ゝ
(☆ω☆)
(╯‵□′)╯︵┴─┴
 ̄﹃ ̄
(/ω\)
∠( ᐛ 」∠)_
(๑•̀ㅁ•́ฅ)
→_→
୧(๑•̀⌄•́๑)૭
٩(ˊᗜˋ*)و
(ノ°ο°)ノ
(´இ皿இ`)
⌇●﹏●⌇
(ฅ´ω`ฅ)
(╯°A°)╯︵○○○
φ( ̄∇ ̄o)
ヾ(´・ ・`。)ノ"
( ง ᵒ̌皿ᵒ̌)ง⁼³₌₃
(ó﹏ò。)
Σ(っ °Д °;)っ
( ,,´・ω・)ノ"(´っω・`。)
╮(╯▽╰)╭
o(*////▽////*)q
>﹏<
( ๑´•ω•) "(ㆆᴗㆆ)
😂
😀
😅
😊
🙂
🙃
😌
😍
😘
😜
😝
😏
😒
🙄
😳
😡
😔
😫
😱
😭
💩
👻
🙌
🖕
👍
👫
👬
👭
🌚
🌝
🙈
💊
😶
🙏
🍦
🍉
😣
Source: github.com/k4yt3x/flowerhd
颜文字
Emoji
小恐龙
花!
上一篇
下一篇