我有以下腳本:
#!/bin/bash -e
set -e
DATA_DIR=/home/admin/backup_avl_historico/data
DB_HOST=myHost
DB_USER=myPass
#extract table list
logger 'Extracting Table List'
psql -h $DB_HOST -U $DB_USER -c "select table_name from information_schema.tables where table_name like 'avl_historico_%';" -t -o $DATA_DIR/tables.list
array=($(wc -l $DATA_DIR/tables.list))
logger ''$array
total_tables=${array[0]}
logger 'Total tables: '$total_tables
#Get max date
max_date=$(psql -h $DB_HOST -U $DB_USER -t -c "select now() - interval '12 months'")
logger 'Max date: '$max_date
array=($max_date)
date=${array[0]}
logger 'Only date: '$date
#Dump each table
while read table_name
do
logger 'looping...'
if [ ! -z "$table_name" ]; then
logger 'Processing table '$table_name
output=${table_name}_pre_${date}.csv
psql -h $DB_HOST -U $DB_USER -t -F , -c "COPY (select * from reports.$table_name where fecha < '$max_date') TO STDOUT WITH CSV" -o ${DATA_DIR}/$output
if [ -f ${DATA_DIR}/$output ];then
if test -s ${DATA_DIR}/$output
then
logger 'Deleting records'
psql -h $DB_HOST -U $DB_USER -c "delete from reports.$table_name where fecha < '$max_date'"
logger 'Gzipping '$output
pigz ${DATA_DIR}/$output
logger 'Moving to S3'
aws s3 mv ${DATA_DIR}/$output.gz s3://my-bucket/avl_historico/
logger 'Vacuuming table'
psql -h $DB_HOST -U $DB_USER -c "vacuum full analyze reports.$table_name"
else
rm ${DATA_DIR}/$output
fi
fi
fi
done < $DATA_DIR/tables.list
我遇到的問題是,當 PostgreSQL 退出語句時出現以下錯誤:
ERROR: canceling statement due to lock timeout
整個腳本將被中止,並且不會繼續do
循環的下一個迭代。
任何有關如何避免退出條件的想法將不勝感激,因此腳本可以跳過一次迭代,但繼續其餘部分
答案1
如果您希望腳本執行所有命令而不考慮任何失敗,請刪除這兩個-e
標誌。另一方面,如果您仍然想在出現錯誤時終止腳本,但想捕獲特定的一個(在您的情況下是 PostgreSQL),則只保留一個標誌-e
,哪個標誌並不重要,但個人喜好是在腳本上而不是在shebang 上,捕獲錯誤的方法是在||
以非 0 退出的命令末尾添加一個(邏輯或)||
。
psql -h $DB_HOST -U $DB_USER -c "delete from reports.$table_name where fecha < '$max_date'" || true
上面的範例將默默地捕獲psql
非 0 退出程式碼並繼續,您可以將命令替換true
為您喜歡的任何內容(記錄錯誤,等待一段時間等...)只需確保它以0 退出,否則您將以相同的方式結束情況。該true
命令根本不執行任何操作,只是以 0 代碼退出。