各位前輩好,
想請問如何用bat或powershell(Windows)及shell script(Linux)寫出
能搜尋資料夾名稱如:用戶名(不固定)\日誌(固定)\ 內最新的檔案,
並含完整路徑轉出成txt,例如
D:\backup\Vicent Li\日誌\下有多個backup 2018-xx-xx xxx.log
D:\backup\Allen Huang\日誌\下有多個backup 2018-xx-xx xxx.log
D:\backup\Chris Wang\日誌\下有多個backup 2018-xx-xx xxx.log
想輸出每個用戶下最近產出的檔名,得到如下
D:\backup\Vicent Li\日誌\backup 2018-08-29 130002.975.log
(表示最近一次備份日為8/29)
D:\backup\Allen Huang\日誌\backup 2018-08-28 100001.100.log
(表示最近一次備份日為8/28)
D:\backup\Chris Wang\日誌\backup 2018-07-28 110001.100.log
(表示最近一次備份日為7/28)
這樣就可知道Chris Wang已經超過一個月沒備份日誌了,需檢查備份排程
感謝幫忙。
文件系統有Windows也有Linux
我的想法是抓出D:\backup\變數\日誌\ 底下最新檔案
只是不知道linux windows 那變數怎麼去抓backup底下資料夾名稱,轉成陣列,一個個執行並輸出
window 可用以下指令進行搜尋: dir /s 複製
謝謝,請問一下,我想把ls找到的資料夾轉成陣列,可以怎麼打?感謝
array=($(ls -d */))
謝謝,目前測試,同一目錄如Vicent Li 中間有空格,會存成2個索引,有無解決法,感謝。
x=($(find . -maxdepth 1 -type d -printf '%f\n'))
感謝你的幫忙,嘗試執行
find . -maxdepth 1 -type d -printf '%f\n' 結果如下
.
Vicent Li
Allen Huang
嘗試寫成bash
x=($(find . -maxdepth 1 -type d -printf '%f\n'))
echo ${x[0]}
echo ${x[1]}
echo ${x[2]}
echo ${x[3]} 來偵錯,輸出如下
.
Vicent
Li
Allen
Vicent與Li被array分開了
powershell
Get-ChildItem 「路徑」 | sort LastWriteTime | select -last 1
謝謝回覆。想請問路徑的問題,怎麼把backup下的資料夾名稱轉成陣列$用戶[名0,名1,名2],然後用powershell 去迴圈執行
Get-ChildItem 用戶[i]\日誌\ | sort LastWriteTime | select -last 1 > test.txt
Get-ChildItem 用戶[i++]\日誌\ | sort LastWriteTime | select -last 1 >> test.txt
powershell 可以用string format啊。
$a = "test {0} test {1}"
$b = @('b', 'c')
write-host($a -f $b)
感謝提供的一些指導,powershell部分寫出來了
Get-ChildItem -Exclude 日誌,歷史版本,log.ps1 | Select-Object Name > d:\user.txt
$User=(Get-Content d:\user.txt)
$UserTrim=$User.Trim()
$len = $UserTrim.Length-3
Clear-Content D:\temp.txt
for($i=3;$i -le $len;$i++){
$path = join-path -path $UserTrim[$i] -childpath 日誌
Get-ChildItem $path | sort LastWriteTime | select -last 1 >> D:\temp.txt
}
Get-Content D:\temp.txt | ? {$_.trim() -ne "" } | set-content D:\log.txt
原本想for裡1行命令就好,但若在路徑裡加上變數,例如改成
Get-ChildItem D:\backup\$UserTrim[$i]\日誌 | sort LastWriteTime | select -last 1 >> D:\temp.txt
會無法執行,不知道怎麼處理只好多加1條,先把整串路徑轉為變數
為何要寫出去user.txt和temp.txt,然後又讀回來?
為何要去掉頭、尾的3個項目?
$subDirs = Get-ChildItem "D:\backup" | ?{ $_.PSIsContainer } | %{ $_.FullName }
$outputFile = "D:\report.txt"
Clear-Content $outputFile
foreach($sub in $subDirs) {
Get-ChildItem $($sub + "\日誌") -filter "*.log" | sort LastWriteTime | select -last 1 -expand FullName >> $outputFile
}
去頭是有三行空白、標頭分隔符不需要帶入,去尾是有三個空白行。其實我是拼拼湊湊爬文出來的,覺得先求有再求好,週五要完成第一版,目前還沒寫好linux的。很感謝你提供較好的寫法,我完全門外漢,只是有一點點寫程式的邏輯
清掉
上面的程式還有2個隱懮,如果那個用戶的[日誌]資料夾不存在或者他沒有log文件,他的資料就不會被記錄下來。因此,程式應該加上相關的檢測,如下:
#列出在"D:\backup"裏全部的子資料夾的全路徑
$subDirs = Get-ChildItem "D:\backup" | ?{ $_.PSIsContainer } | %{ $_.FullName }
$results = @() #陣列變數
foreach($sub in $subDirs) {
$sub += "\日誌"
if (Test-Path $sub) { #資料夾存在嗎?
#列出在$sub裏全部的log文件
$logFiles = Get-ChildItem $sub -filter "*.log"
if ($logFiles.Length -gt 0) { #有log文件嗎?
#找出在$sub裏最新的log文件的全路徑
$results += $logFiles | sort LastWriteTime | select -last 1 -expand FullName
} else {
$results += $sub + " [警告:沒有log文件]"
}
} else {
$results += $sub + " [警告:資料夾不存在]"
}
}
#將結果放進"D:\report.txt"文件裏
Set-Content "D:\report.txt" -value $results
感謝協助,我後來把使用者與日誌輸出分開兩行,讓沒有目錄、或目錄是空的就只顯示使用者名稱,不過沒有你寫得這麼好!謝謝提供參考
#!/bin/bash
WorkDir="/backup"
ReportFile="/tmp/report`date +%Y%m%d_%H%M%S`.txt"
find ${WorkDir} -type d -name "日誌"> /tmp/test.txt
echo "[`date +%Y-%m-%d\ %H:%M:%S`] Process Start">> ${ReportFile}
exec < /tmp/test.txt
while read -r line
do
ls -alht ${line}/*.log|grep -v total|head -n 1 >> ${ReportFile}
done
echo "[`date +%Y-%m-%d\ %H:%M:%S`] Process End">> ${ReportFile}
這樣就可以幫你列出最近的清單