Click here to Skip to main content
15,887,027 members
Please Sign up or sign in to vote.
0.00/5 (No votes)
See more:
1. I have an application that needs to rename folders on a shared network drive.

2. These folders have subfolders and there may be files in the subfolders.

3. One or more of these files may be open in an application on the user's computer or another computer on the network.

When condition #3 is true, the folder rename fails. The user gets an error message, but they are then faced with the problem of what to close on their own machine and, worse, they may have to wander round the office trying to find out who has a file open.

It would be nice to present them with a list of the files that are open.

Below I show the code I have at the moment. It seems to work for files open in some applications but not others. For example, if a file is opened in Notepad or Notepad++, my code does not detect a problem, but Windows clearly is able to detect that Notepad has the file open because it refuses to rename the parent folder.

Is there any way to do this?

What I have tried:

private void TestFunction( string folderPath )
{
    List<string> fileList = Directory.GetFiles( folderPath, "*", SearchOption.AllDirectories ).ToList();
    List<string> filteredFileList = fileList.Where( f => IsFileLocked( f ) ).ToList();
}

private bool IsFileLocked( string filePath )
{
    try
    {
        FileInfo fileInfo = new FileInfo( filePath );
        using( FileStream stream = fileInfo.Open( FileMode.Open, FileAccess.ReadWrite, FileShare.None ) )
        {
            stream.Close();
        }
    }
    catch( IOException )
    {
        return true;
    }
    return false;
}
Posted
Updated 7-Jun-23 0:52am
Comments
Richard Deeming 7-Jun-23 6:37am    
For files opened on the current computer, there's this approach using P/Invoke to the restart manager:
LockFinder/LockFinder.cs at master · TacticalHorse/LockFinder · GitHub[^]
Patrick Skelton 8-Jun-23 3:21am    
Hi, Richard, The code fails at the line res = RmGetList(...), which looks like it should return ERROR_MORE_DATA (234) but returns 5. This is not listed as a return value here: https://learn.microsoft.com/en-us/windows/win32/api/restartmanager/nf-restartmanager-rmgetlist.
Not sure how to proceed with that really. It seems to do no 'better' than the method in my code, in that it fails to spot an application such as Notepad opening a file (the code does not give an error but doesn't spot that Notepad has opened the file, which is no surprise since even Explorer will simply allow it to be renamed without complaint).

Seems like I have over-promised to the client. ://)
Richard Deeming 8-Jun-23 3:23am    
The documentation does mention that it can also return a system error code:
System Error Codes (0-499) (WinError.h) - Win32 apps | Microsoft Learn[^]

5 means ERROR_ACCESS_DENIED; I wonder if your application needs to be running elevated to call these functions?
Patrick Skelton 8-Jun-23 3:44am    
Hi Richard, Just tried it with elevated permission and still get 5. Wonder if it is because the folder is on a network-mapped drive letter. It does seem unlikely it will offer any value on the client's system, since they are not going to let standard users run with elevated permission anyway. I feel a bit of an idiot for blithely assuming this problem would simply be a matter of finding the right chunk of Win32 code.
Richard Deeming 8-Jun-23 3:24am    

1 solution

A better solution might be to not rename folders: instead create a database with the "desired name" and a reference to the new name. That way, users aren't inconvenienced by folder name changes (since the change won't be reflected in MRU lists so they may not know where to go to get it back).

You could even introduce a mixed system where you try to rename the folder, and if it fails record the old and new paths in a DB which gets checked at regular intervals until the rename "takes". The task for that could be scheduled to run hourly on the file server.

That's probably the way I'd go if I was forced by justifiable business rules to rename "active" folders.
 
Share this answer
 
Comments
Patrick Skelton 8-Jun-23 2:37am    
Hi,

Unfortunately (and despite my warnings about the pitfalls) the client made a specific request for the the folders to be renamed. So option #1 won't work.

Option #2 is elegant. I'd like to implement it but will have to wait for fresh work on which I can piggyback it or I'll be doing it for free. :-|

Thank you!

Kind wishes - Patrick
OriginalGriff 8-Jun-23 4:01am    
You're welcome!

This content, along with any associated source code and files, is licensed under The Code Project Open License (CPOL)



CodeProject, 20 Bay Street, 11th Floor Toronto, Ontario, Canada M5J 2N8 +1 (416) 849-8900