SearchOption problem...?

  • (2 Pages)
  • +
  • 1
  • 2

26 Replies - 4544 Views - Last Post: 15 April 2013 - 06:02 AM Rate Topic: -----

#16 andrewsw   User is offline

  • So Smart! S-M-R-T!
  • member icon

Reputation: 6578
  • View blog
  • Posts: 26,715
  • Joined: 12-December 12

Re: SearchOption problem...?

Posted 13 April 2013 - 09:15 AM

View PostIronRazer, on 13 April 2013 - 01:17 AM, said:

You could also use (EndsWith) to check the last directory by changing it to this
                If Not strEntry.ToLower.EndsWith("\appdata") Then


Avoiding the specific use of '\' could be something like:

strEntry.split(Path.DirectorySeparatorChar).Last()

This post has been edited by andrewsw: 13 April 2013 - 09:15 AM

Was This Post Helpful? 1
  • +
  • -

#17 HeBTeMy   User is offline

  • D.I.C Regular

Reputation: 20
  • View blog
  • Posts: 299
  • Joined: 05-October 12

Re: SearchOption problem...?

Posted 13 April 2013 - 11:33 AM

View Postandrewsw, on 13 April 2013 - 09:15 AM, said:

View PostIronRazer, on 13 April 2013 - 01:17 AM, said:

You could also use (EndsWith) to check the last directory by changing it to this
                If Not strEntry.ToLower.EndsWith("\appdata") Then


Avoiding the specific use of '\' could be something like:

strEntry.split(Path.DirectorySeparatorChar).Last()


But the problem isn't that (or at least it doesn't work either)

Let me explain better, it throws this error:

http://prntscr.com/10gp3o

Even with that code excluding appdata and with admin privileges.
Was This Post Helpful? 0
  • +
  • -

#18 andrewsw   User is offline

  • So Smart! S-M-R-T!
  • member icon

Reputation: 6578
  • View blog
  • Posts: 26,715
  • Joined: 12-December 12

Re: SearchOption problem...?

Posted 13 April 2013 - 11:48 AM

Here is some code I found at SO that checks the file-attributes and skips System files, you could do the same for Hidden files:

Dim tempDir As New DirectoryInfo(path)
    Dim FileDetails(4) As String
    Dim iTem As ListViewItem
    Try
        Dim allFiles As FileInfo() = Nothing 
        For Each Directory In tempDir.GetDirectories()
            Try
                If (Directory.Attributes <> FileAttributes.System) Then
                    allFiles = Directory.GetFiles("*.pdf", SearchOption.AllDirectories)
                End If
                Dim oneFIle As FileInfo

                For Each oneFIle In allFiles
                    FileDetails(0) = oneFIle.Name()
                    FileDetails(1) = oneFIle.FullName()
                    FileDetails(2) = oneFIle.Length() / (1024 * 1024)
                    FileDetails(2) = FileDetails(2).Remove(5)
                    iTem = New ListViewItem(FileDetails)
                    ListView1.Items.Add(iTem)                        
                Next
            Catch ex As Exception

            End Try
        Next
    Catch ex As UnauthorizedAccessException

    End Try

Is this application for your own use? If so, then you could disable UAC and change the properties of certain folders. If it is not just for you, and you cannot access C:\Users\Anybody then I don't know how you get around this, sorry (or even if you should attempt to).
Was This Post Helpful? 0
  • +
  • -

#19 HeBTeMy   User is offline

  • D.I.C Regular

Reputation: 20
  • View blog
  • Posts: 299
  • Joined: 05-October 12

Re: SearchOption problem...?

Posted 13 April 2013 - 12:44 PM

View Postandrewsw, on 13 April 2013 - 11:48 AM, said:

Here is some code I found at SO that checks the file-attributes and skips System files, you could do the same for Hidden files:

Dim tempDir As New DirectoryInfo(path)
    Dim FileDetails(4) As String
    Dim iTem As ListViewItem
    Try
        Dim allFiles As FileInfo() = Nothing 
        For Each Directory In tempDir.GetDirectories()
            Try
                If (Directory.Attributes <> FileAttributes.System) Then
                    allFiles = Directory.GetFiles("*.pdf", SearchOption.AllDirectories)
                End If
                Dim oneFIle As FileInfo

                For Each oneFIle In allFiles
                    FileDetails(0) = oneFIle.Name()
                    FileDetails(1) = oneFIle.FullName()
                    FileDetails(2) = oneFIle.Length() / (1024 * 1024)
                    FileDetails(2) = FileDetails(2).Remove(5)
                    iTem = New ListViewItem(FileDetails)
                    ListView1.Items.Add(iTem)                        
                Next
            Catch ex As Exception

            End Try
        Next
    Catch ex As UnauthorizedAccessException

    End Try

Is this application for your own use? If so, then you could disable UAC and change the properties of certain folders. If it is not just for you, and you cannot access C:\Users\Anybody then I don't know how you get around this, sorry (or even if you should attempt to).



Hmm, thanks, i will try to adapt, being for personal use yes, but i'd like to use on other machines as well and i'm not feeling changing that UAC and stuff because it isn't needed, i gave admin privileges and it didn't work, and as i don't want to copy system files i catch the exception and it just loop through the rest, what i don't understand is why it doesn't continue looping when it is going to search AppData wich i don't want but i still come across to and it keeps going there...
Was This Post Helpful? 0
  • +
  • -

#20 andrewsw   User is offline

  • So Smart! S-M-R-T!
  • member icon

Reputation: 6578
  • View blog
  • Posts: 26,715
  • Joined: 12-December 12

Re: SearchOption problem...?

Posted 13 April 2013 - 12:54 PM

As you are looking for AllDirectories then it will also look at sub-folders within AppData, so you need to revise the use of .Last() to .Contains(); I recall there was example code provided in an earlier post.

This post has been edited by andrewsw: 13 April 2013 - 12:55 PM

Was This Post Helpful? 0
  • +
  • -

#21 HeBTeMy   User is offline

  • D.I.C Regular

Reputation: 20
  • View blog
  • Posts: 299
  • Joined: 05-October 12

Re: SearchOption problem...?

Posted 13 April 2013 - 01:22 PM

View Postandrewsw, on 13 April 2013 - 12:54 PM, said:

As you are looking for AllDirectories then it will also look at sub-folders within AppData, so you need to revise the use of .Last() to .Contains(); I recall there was example code provided in an earlier post.


That just make sense... didn't think of that... what an idiot, i though it was excluding the "root" Appdata folder and all it's contents..

I just tested, and it keeps throw me the same error, because it throws me right in the first line "For each strentry..."
and the if comes after and it just doesn't exclude because the error comes before and i can't put the if within the For each block because a value depends of that loop...

Will still try to exclude hidden and system files/folders as stated above.
Was This Post Helpful? 0
  • +
  • -

#22 andrewsw   User is offline

  • So Smart! S-M-R-T!
  • member icon

Reputation: 6578
  • View blog
  • Posts: 26,715
  • Joined: 12-December 12

Re: SearchOption problem...?

Posted 13 April 2013 - 02:07 PM

I tried the following:

        Dim tempDir As New DirectoryInfo("C:\Users\Andrew\")

        Dim dirsExclude = tempDir.GetDirectories("*", SearchOption.AllDirectories) _
                  .Where(Function(x) Not x.ToString.Contains("Application Data") And x.Attributes = FileAttributes.Normal)
        For Each aDir In dirsExclude
            Console.WriteLine(aDir.ToString)
        Next

but, as you've said, as soon as it tries (in my case) to access the folder "Application Data" it bails with UnauthorizedAccessException.

So we need to do this in a more labour intensive way. The following code, which works for me, gathers a list of all those folders containing .mp3 files, and skips pass the annoying Exception.

Module Module1

    Sub Main()
        Dim folderList As New List(Of String)

        GetFolders("C:\Users\Andrew\", folderList)

        'list all folders that contain .mp3 files within 
        'its folder, or any of its sub-folders.
        For Each fold As String In folderList
            Console.WriteLine(fold)
            Debug.Print(fold)
        Next
        Console.ReadKey()

    End Sub

    Sub GetFolders(ByVal pStartPath As String, ByRef pFolderList As List(Of String))
        Try
            Dim dirs() As String = Directory.GetDirectories(pStartPath)

            pFolderList.AddRange(From item In dirs
                                 Select item
                                 Where Directory.GetFiles(item, "*.mp3",
                                                          SearchOption.AllDirectories).Count > 0)

            For Each aDir As String In dirs
                'could exclude a folder here if its parent folder is already in the list
                GetFolders(aDir, pFolderList)
            Next
        Catch ex As System.UnauthorizedAccessException
            'pass, ignore this folder
        Catch ex As Exception
            Throw ex
        End Try

    End Sub
End Module

Was This Post Helpful? 0
  • +
  • -

#23 andrewsw   User is offline

  • So Smart! S-M-R-T!
  • member icon

Reputation: 6578
  • View blog
  • Posts: 26,715
  • Joined: 12-December 12

Re: SearchOption problem...?

Posted 13 April 2013 - 02:19 PM

Erm, but if the error occurs, for you, on the AppData folder, then you've probably still got an issue. I suppose you might have to "bring it up a level" :)

You might modify it to:

Dim dirs() As String = Directory.GetDirectories("C:\Users\", "*Andrew*")

mmm maybe.

Edited: needs two stars *Andrew*

This post has been edited by andrewsw: 13 April 2013 - 02:35 PM

Was This Post Helpful? 0
  • +
  • -

#24 AdamSpeight2008   User is offline

  • MrCupOfT
  • member icon

Reputation: 2298
  • View blog
  • Posts: 9,535
  • Joined: 29-May 08

Re: SearchOption problem...?

Posted 13 April 2013 - 05:55 PM

Using iterators you could write the following function, then use LINQ
 Iterator Function YieldFiles(StartingPath As String) As IEnumerable(Of IO.FileInfo)
    Dim FoldersToLookIn As New Collections.Concurrent.ConcurrentQueue(Of System.IO.DirectoryInfo)({New System.IO.DirectoryInfo(StartingPath)})
    Dim CurrentlyLookingIn As IO.DirectoryInfo = Nothing
    While FoldersToLookIn.Any
      If Not FoldersToLookIn.TryDequeue(CurrentlyLookingIn) Then Continue While
      Try
        If CurrentlyLookingIn.Exists Then
          REM Find Folders
          CurrentlyLookingIn.EnumerateDirectories.
                             AsParallel.
                             ForAll(Sub(ed) FoldersToLookIn.Enqueue(ed))
        End If
      Catch ex As Exception
        Continue While
      End Try
      REM Find Aatching Files
      Dim files = CurrentlyLookingIn.EnumerateFiles.AsParallel
      For Each f In files.AsParallel
        Try
          Yield f
        Catch ex As Exception
          Continue For
        End Try
      Next
    End While
  End Function


Usage Example
    Dim fc=YieldFiles(My.Computer.FileSystem.SpecialDirectories.MyDocuments).
             Where(Function(fi) fi.Extension.
                                   Split("."c).
                                   Any(Function(ext) String.Compare(ext,"mp3",True,Globalization.CultureInfo.InvariantCulture)=0)
           ).count()


The above has the potential to take a long time, locking up the program.

Or create a FileFinder class and utilise events.
  Public Class FileFinder
    Private _BeenToldToStop As Boolean = False
    Public Event FoundFile(ByVal file As IO.FileInfo)
    Public Event Directory(ByVal directory As IO.DirectoryInfo)
    Public Event OnFileException(ByVal File As IO.FileInfo, ByVal ex As Exception)
    Public Event OnDirException(ByVal dir As IO.DirectoryInfo, ByVal ex As Exception)
    Dim tsk As Task
    Private _StoppedInFolder As IO.DirectoryInfo = Nothing
    Public ReadOnly Property StoppedInFolder() As IO.DirectoryInfo
      Get
        Return _StoppedInFolder
      End Get
    End Property
    Public Sub [Stop]()
      _BeenToldToStop = True
    End Sub

    Public Function FindFiles(StartingPath As String, filter As Func(Of IO.FileInfo, Boolean)) As Task
      _BeenToldToStop = False
      tsk = Task.Run(
        Sub()
          Dim FoldersToLookIn As New Collections.Concurrent.ConcurrentQueue(Of System.IO.DirectoryInfo)({New System.IO.DirectoryInfo(StartingPath)})
          Dim CurrentlyLookingIn As IO.DirectoryInfo = Nothing
          While FoldersToLookIn.Any
            If Not FoldersToLookIn.TryDequeue(CurrentlyLookingIn) Then Continue While
            Try
              If CurrentlyLookingIn.Exists Then
                RaiseEvent Directory(CurrentlyLookingIn)
                REM Find Folders
                For Each Folder In CurrentlyLookingIn.EnumerateDirectories.AsParallel
                  If _BeenToldToStop Then _StoppedInFolder = CurrentlyLookingIn : Exit Sub
                  FoldersToLookIn.Enqueue(Folder)
                Next
              End If
            Catch ex As Exception
              RaiseEvent OnDirException(CurrentlyLookingIn, New Exception("Dir?", ex))
              Continue While
            End Try
            REM Find Aatching Files
            Dim files = CurrentlyLookingIn.EnumerateFiles.AsParallel.Where(filter)
            For Each f In files.AsParallel
              Try
                If _BeenToldToStop Then _StoppedInFolder = CurrentlyLookingIn : Exit Sub
                RaiseEvent FoundFile(f)
              Catch ex As Exception
                RaiseEvent OnFileException(f, New Exception("File?", ex))
                Continue For
              End Try
            Next
          End While
        End Sub)
      Return tsk
    End Function

  End Class



 Sub Main()
    Dim c = 0
    
    Dim s As New FileFinder
    AddHandler s.FoundFile, Sub(f)
                              Console.WriteLine(f.FullName)
                              Threading.Interlocked.Increment(c)
                            End Sub
'    AddHandler s.Directory, Sub(d) Console.WriteLine(d.FullName)
    AddHandler s.OnFileException,Sub(f,ex)    Console.WriteLine("FX:  {0}",f.FullName)
    AddHandler s.OnDirException,Sub(d,ex)   Console.WriteLine("DX:   {0}",d.FullName)

    ''My.Computer.FileSystem.SpecialDirectories.MyDocuments
    Dim rt = s.FindFiles("C:\", Function(fi As IO.FileInfo) fi.Extension.
                                          Split("."c).
                                          Any(Function(ext) String.Compare(ext,
                                               "mp3",
                                               True,
                                               Globalization.CultureInfo.InvariantCulture) = 0))
    
    Dim dd = Task.Delay(60000)
    Dim td = Task.WaitAny(dd, rt)
    If td = 0 Then
      s.Stop()
    End If
  End Sub



This post has been edited by AdamSpeight2008: 13 April 2013 - 06:59 PM

Was This Post Helpful? 1
  • +
  • -

#25 HeBTeMy   User is offline

  • D.I.C Regular

Reputation: 20
  • View blog
  • Posts: 299
  • Joined: 05-October 12

Re: SearchOption problem...?

Posted 14 April 2013 - 09:24 AM

That's so much code for me to look through, some of them i'm not yet familiar with, i was looking for an "easy" way of skipping appdata folder...

i tried to put a .where here:
For Each strentry In Directory.GetFiles(sourceDir, "*.png", SearchOption.AllDirectories).Where(strentry.tolower.contains("appdata")



But it doesn't seem to work, i get the "Overload resolution error" that can't be called with these arguments and i understand why, but even if it worked i can't put if not.contains in the midle, because that's what i want...

This post has been edited by HeBTeMy: 14 April 2013 - 09:25 AM

Was This Post Helpful? 0
  • +
  • -

#26 AdamSpeight2008   User is offline

  • MrCupOfT
  • member icon

Reputation: 2298
  • View blog
  • Posts: 9,535
  • Joined: 29-May 08

Re: SearchOption problem...?

Posted 14 April 2013 - 07:57 PM

View PostHeBTeMy, on 14 April 2013 - 05:24 PM, said:

That's so much code for me to look through, some of them i'm not yet familiar with, i was looking for an "easy" way of skipping appdata folder...


It's not that much. It is two different way of doing it, less than 100 Lines.
Print it out and go study it. (This is a good exercise in itself)

Since Directory.GetFiles(sourceDir, "*.png", SearchOption.AllDirectories) has the inbuilt issue of not return only files that the use has enough security rights to access. If it comes across one it can't it access, throws an exception.
You can't do anything about this issue.

So what can you do?
Spoiler

This post has been edited by AdamSpeight2008: 14 April 2013 - 07:58 PM

Was This Post Helpful? 0
  • +
  • -

#27 HeBTeMy   User is offline

  • D.I.C Regular

Reputation: 20
  • View blog
  • Posts: 299
  • Joined: 05-October 12

Re: SearchOption problem...?

Posted 15 April 2013 - 06:02 AM

View PostAdamSpeight2008, on 14 April 2013 - 07:57 PM, said:

View PostHeBTeMy, on 14 April 2013 - 05:24 PM, said:

That's so much code for me to look through, some of them i'm not yet familiar with, i was looking for an "easy" way of skipping appdata folder...


It's not that much. It is two different way of doing it, less than 100 Lines.
Print it out and go study it. (This is a good exercise in itself)

Since Directory.GetFiles(sourceDir, "*.png", SearchOption.AllDirectories) has the inbuilt issue of not return only files that the use has enough security rights to access. If it comes across one it can't it access, throws an exception.
You can't do anything about this issue.

So what can you do?
Spoiler


Going to see that later, leaving to work right now... i'll reply with any doubts i have.
Thanks for your time.
Was This Post Helpful? 0
  • +
  • -

  • (2 Pages)
  • +
  • 1
  • 2