monitoring a directory

Tim Golden tim.golden at viacom-outdoor.co.uk
Thu Mar 25 10:07:50 EST 2004


>[Tim Golden <tim.golden at viacom-outdoor.co.uk>]
>
>>The other method, which is a bit more sophisticated, uses the
>
>Hhm, looks like "win32file" expertise is around ;-)
>
>Shameless question plugin: Is there a way to find the realname of a
>file on Windows? In those times of DOS there was a DOS call/interrupt
>"Truename" that would return the real name of a files. This is
>important if you have created additional drives via the "SUBST"
>command.
>
>I'm still looking for a foolproof way to ensure that two files are
>different on windows. There are times where I'd like to avoid deleting
>the last valid copy of a file ...

Well, I must thank you for starting a small voyage of discovery. 
I had started to write a reply saying that I'd previously looked
and that it was impossible (altho' that seemed so unlikely, given
that the O/S itself *must* know whether two files were the same).
So I started to look around a little more, and found that you can
in fact tell if two files are the same using only what's available
in win32file. It's a little involved, but not too much, and nothing 
that a couple of functions can't encapsulate.

In essence, you get a handle to each file and call 
win32file.GetFileInformationByHandle for each. This
returns, among other things, a FileIndexHi/Lo pair
which, coupled with the VolumeSerialNumber also
returned gives you a unique id for a file *while it
is open by a process*. This means that you must have
both handles open to read the info before you close
either.

The following code works ok across drives SUBSTed to the
same path and drives mapped to the same network share.
(And -- naively -- to the same file given twice).

<code>

import os, sys
import win32file

def get_read_handle (filename):
  return win32file.CreateFile (
    filename,
    win32file.GENERIC_READ,
    win32file.FILE_SHARE_READ,
    None,
    win32file.OPEN_EXISTING,
    0,
    None
  )

def get_unique_id (hFile):
  (
    attributes,
    created_at, accessed_at, written_at,
    volume,
    file_hi, file_lo,
    n_links,
    index_hi, index_lo
  ) = win32file.GetFileInformationByHandle (hFile)
  return volume, index_hi, index_lo

def files_are_equal (filename1, filename2):
  hFile1 = get_read_handle (filename1)
  hFile2 = get_read_handle (filename2)
  are_equal = (get_unique_id (hFile1) == get_unique_id (hFile2))
  hFile2.Close ()
  hFile1.Close ()
  return are_equal

</code>

TJG

________________________________________________________________________
This e-mail has been scanned for all viruses by Star Internet. The
service is powered by MessageLabs. For more information on a proactive
anti-virus service working around the clock, around the globe, visit:
http://www.star.net.uk
________________________________________________________________________




More information about the Python-list mailing list