views:

597

answers:

5

Hi,

I have two folders, for arguments sake /Volumes/A and /Volumes/B. They are mounted network shares from a Windows server containing a load of .bkf files from Backup Exec.

I am looking for a script which will look into both folders and find the most recently modified .bkf file and copy it to another location. There are other files in the folders which must be ignored.

Thanks in advance!!

Shaun

Edit:

I knocked this together:

cp ls -alt /Volumes/E /Volumes/F| grep bkf | head -n 1 | awk '{print $8}' /Volumes/$xservedisk/Windows/

Can anyone think of any reasons why I shouldnt use it?

Thanks again Shaun

+1  A: 
NEWEST=
for f in /Volumes/A/*.bkf /Volumes/B/*.bkf
do
    if [ -z "$NEWEST" ]
    then 
        NEWEST=$f
    elif [ "$f" -nt "$NEWEST" ] 
    then
        NEWEST=$f
    fi
done
Douglas Leeder
ephemient
This was the solution that worked best as I needed the full path of the file.Thanks Douglas!
Shaun Johnson
A: 

Use dir /O /B *.bkf in each directory. The topmost file will be the newest. the '/B' makes the list bare, just filenames. No looping required.

Kelly French
OP tagged the question "bash", not "batch".
ephemient
I noticed that after I submitted my answer. Oops. I guess I could edit/delete it but no harm no foul.
Kelly French
+2  A: 

Finding files is done with: find /Volumes/[AB] -name '*.bkf'

Sorting files by modification time is done with: ls -t

if load of files is not that much, you can simply use:

ls -lrt `find /Volumes/[AB] -name '*.bkf'`

The last displayed file is the most recently modified.

edit

A more robust solution (thanks ephemient) is:

find /Volumes/[AB] -type f -name '*.bkf' -print0 | xargs -0 ls -lrt
mouviciel
Fails on any names containing spaces or other odd characters.
ephemient
This is why I upvoted your answer. Mine may be sufficient for most old-school users.
mouviciel
Well, you could work around the problem by `find -print0 | xargs -0 ls -ldrt` (`-d` in case some idiot made a directory named `*.bkf`), but that still leaves the problem of parsing...
ephemient
I can filter out `*.bkf` directories with `find -type f`. Thanks for your suggestions.
mouviciel
+2  A: 

Goes through some twists just to make sure to handle filenames with odd characters well, which mouviciel's doesn't:

NEWEST=$(find /Volumes/A /Volumes/B -name '*.bkf' -printf '%T@ %p\0' | \
    sort -rnz | xargs -0n1 2>/dev/null | head -n1 | cut -d' ' -f2-)
[[ -n "$NEWEST" ]] && cp -v "$NEWEST" /other-location

Actually, since these files are coming from Windows and are thus pretty much guaranteed not to have odd characters in their names (like embedded newlines),

NEWEST=$(find /Volumes/A /Volumes/B -name '*.bkf' -printf '%T@ %p\n' | \
    sort -rn | head -n1 | cut -d' ' -f2-)
[[ -n "$NEWEST" ]] && cp -v "$NEWEST" /other-location
ephemient
Why do you choose to employ null termination?
Xepoch
Filenames containing embedded newlines would trip up the `sort` otherwise. Of course, if the leading file found did end up with an embedded newline, `head` wouldn't quite do the right thing either.
ephemient
Thanks for the great answers, after opening this question I created this, is there anything wrong with doing it this way:cp `ls -alt /Volumes/E /Volumes/F| grep bkf | head -n 1 | awk '{print $8}'` /Volumes/$xservedisk/Windows/Thanks again
Shaun Johnson
Doesn't handle filenames with spaces or other odd characters.
ephemient
A: 
cp `find /Volumes/[AB] -name '*bkf' -type f -printf "%A@\t%p\n" |sort -nr |head -1 |cut -f2` dst_directory/
Xepoch
Good, but you should be sorting on modification time instead of access time, and it fails if pathnames contain spaces (you almost have it right, though), and `cp` does not work with only one argument.
ephemient
Ah, I see that you fixed the last bit already.
ephemient
In an NFS mount, surely access may be limited, but surely other times should be considered. Yep, cp was my typing error, edited. Filenames can have spaces? j/k Double-quotes should fix that.
Xepoch
...ahh now I see your cut -f2-
Xepoch