2016-07-28 123 views
2

我正在構建一個bash腳本,該腳本刪除指定目錄中x天以前的日誌文件。正如你所知道的,hadoop fs上沒有「find」,所以我找到了一個在ruby中完成這項工作的簡單方法,並且想知道是否有辦法在bash中實現這一點。刪除hadoop上x天以前的文件

在Ruby:

#!/usr/bin/env ruby 
require "date" 

five_days_ago = Date.parse(Time.now.to_s) - 5 
IO.popen("hadoop fs -lsr /tmp").each_line do |line| 
    permissions,replication,user,group,size,mod_date,mod_time,path = *line.split(/\s+/) 
    if (mod_date) 
    if Date.parse(mod_date.to_s) < five_days_ago 
     puts line 
     if permissions.split('')[0] == 'd' 
     puts "deleting #{path}" 
     `hadoop fs -rmr -skipTrash #{path}` 
     dirname = path 
     next 
     end 
     next if path.start_with? dirname 
     `hadoop fs -rm -skipTrash #{path}` 
    end 
    end 
end 

回答

0

這是我在bash幹什麼用的,你可能會嘗試一下:

例如grep所有8個月的文件。改變grep的正則表達式根據自己的需要:

hadoop fs -ls -R <location> | grep '.*2016-[0-8].*' | awk '{print $8}' 

刪除文件:

hadoop fs -rm -r `hadoop fs -ls -R <location> | grep '.*2016-[0-8].*' | awk '{print $8}'` 
1

我想通了。我知道有些人不推薦使用ls來解決這些問題,但我使用grep -o來創建一個新行(所以我會知道預期的字符串),並且我知道文件名稱模式是什麼所以這會很好地工作。

#!/bin/bash 
IFS=$'\n' 
source_path='/user/' 
current_date=$(date +%Y-%m-%d) 
files_ls=$(hdfs dfs -ls "$source_path" | grep -o " 2[0-9]\{3\}-.*") 

for line in $files_ls; do 
    last_mod=$(echo "$line" | grep -o "[0-9]\{4\}-[0-9]\{2\}-[0-9]\{2\}") 
    file_path=$(echo "$line" | grep -o " /user/.*.log") 
    time_diff="$((($(date --date="$current_date" +%s) - $(date --date="$last_mod" +%s))/(60*60*24)))" 
    if [ "$time_diff" -ge "8" ]; then 
     echo "hdfs dfs -rm -skipTrash$file_path" 
    fi 
done