Skip to content
  • Categories
  • Recent
  • Tags
  • Popular
  • World
  • Users
  • Groups
Skins
  • Light
  • Cerulean
  • Cosmo
  • Flatly
  • Journal
  • Litera
  • Lumen
  • Lux
  • Materia
  • Minty
  • Morph
  • Pulse
  • Sandstone
  • Simplex
  • Sketchy
  • Spacelab
  • United
  • Yeti
  • Zephyr
  • Dark
  • Cyborg
  • Darkly
  • Quartz
  • Slate
  • Solar
  • Superhero
  • Vapor

  • Default (No Skin)
  • No Skin
Collapse
Code Project
  1. Home
  2. General Programming
  3. Visual Basic
  4. StreamReader constructor fails in FileWatcher event handler

StreamReader constructor fails in FileWatcher event handler

Scheduled Pinned Locked Moved Visual Basic
question
10 Posts 5 Posters 0 Views 1 Watching
  • Oldest to Newest
  • Newest to Oldest
  • Most Votes
Reply
  • Reply as topic
Log in to reply
This topic has been deleted. Only users with topic management privileges can see it.
  • L Offline
    L Offline
    Lost User
    wrote on last edited by
    #1

    I'm trying to do what should be a simple thing: watch a directory, and when a file appears read what's in the file. I'm using a FileWatcher to watch the directory, and that's working fine. What's not working is the StreamReader (actually it works once then starts failing). Here's a code snippet from the handler routine that is set to process file creation events (I'm typing it in, so typos are mine, not in the code): Private Sub processNewFile(Byval source As Object, ByVal e As FileSystemEventArgs) Dim message As String Dim sr As StreamReader Try ' Uncomment the following to make it work ' MsgBox("Be patient") sr = New StreamReader(e.FullPath) message = sr.ReadToEnd() sr.Close() MsgBox("The message is: " & message) Catch ex As Exception MsgBox("Dang...got an exception") End Try End Sub I test this by plopping files into the watched directory. The symptoms are as follows: 1) The first time I create a file in the watched directory it works perfectly. 2) Any subsequent attempt to create a file will cause the "new" statement to fail. The actual exception claims that the file is in use. 3) If I uncomment the commented lines in the code above (which causes a useless message box to appear) or if I add sufficiently long delay at that same point, it works perfectly. By the way, if I take the exact same code and do it somewhere else (i.e. not in a handler for the filewatcher, just fire it off with a button click) it works perfectly, so clearly there's something about the context that's causing this. Any ideas why this shouldn't work?

    M D 2 Replies Last reply
    0
    • L Lost User

      I'm trying to do what should be a simple thing: watch a directory, and when a file appears read what's in the file. I'm using a FileWatcher to watch the directory, and that's working fine. What's not working is the StreamReader (actually it works once then starts failing). Here's a code snippet from the handler routine that is set to process file creation events (I'm typing it in, so typos are mine, not in the code): Private Sub processNewFile(Byval source As Object, ByVal e As FileSystemEventArgs) Dim message As String Dim sr As StreamReader Try ' Uncomment the following to make it work ' MsgBox("Be patient") sr = New StreamReader(e.FullPath) message = sr.ReadToEnd() sr.Close() MsgBox("The message is: " & message) Catch ex As Exception MsgBox("Dang...got an exception") End Try End Sub I test this by plopping files into the watched directory. The symptoms are as follows: 1) The first time I create a file in the watched directory it works perfectly. 2) Any subsequent attempt to create a file will cause the "new" statement to fail. The actual exception claims that the file is in use. 3) If I uncomment the commented lines in the code above (which causes a useless message box to appear) or if I add sufficiently long delay at that same point, it works perfectly. By the way, if I take the exact same code and do it somewhere else (i.e. not in a handler for the filewatcher, just fire it off with a button click) it works perfectly, so clearly there's something about the context that's causing this. Any ideas why this shouldn't work?

      M Offline
      M Offline
      Mitch F
      wrote on last edited by
      #2

      Hello, I have recently had a similar problem with a message box being required to give the process a bit of a "break". You could use a thread to stop the process for a couple of seconds, such as: Edit:

      Dim thread As Threading.Thread = New Threading.Thread(AddressOf TestSub)
      Private Sub processNewFile(Byval source As Object, ByVal e As FileSystemEventArgs)
      Try

          thread.Start()
      

      Catch ex As Exception
      MsgBox("Dang...got an exception")
      End Try
      End Sub

      And then create a new sub such as:

      Sub TestSub()
      'Your code goes here
      End Sub

      To pause your thread, all that you need to do is: thread.Sleep(1000) Programmer2k4 My sig: "The so-called 'Bugs' do not exist, they are merely features hidden by developers with message boxes that say 'An unhandled exception has occurred'." - Programmer2k4 "And it is a professional faux pas to pay someone else to destroy your computer when you are perfectly capable of destroying it yourself." - Roger Wright I now use my CodeProject Blog!

      S 1 Reply Last reply
      0
      • M Mitch F

        Hello, I have recently had a similar problem with a message box being required to give the process a bit of a "break". You could use a thread to stop the process for a couple of seconds, such as: Edit:

        Dim thread As Threading.Thread = New Threading.Thread(AddressOf TestSub)
        Private Sub processNewFile(Byval source As Object, ByVal e As FileSystemEventArgs)
        Try

            thread.Start()
        

        Catch ex As Exception
        MsgBox("Dang...got an exception")
        End Try
        End Sub

        And then create a new sub such as:

        Sub TestSub()
        'Your code goes here
        End Sub

        To pause your thread, all that you need to do is: thread.Sleep(1000) Programmer2k4 My sig: "The so-called 'Bugs' do not exist, they are merely features hidden by developers with message boxes that say 'An unhandled exception has occurred'." - Programmer2k4 "And it is a professional faux pas to pay someone else to destroy your computer when you are perfectly capable of destroying it yourself." - Roger Wright I now use my CodeProject Blog!

        S Offline
        S Offline
        skifanatic
        wrote on last edited by
        #3

        Programmer2k4 wrote: I have recently had a similar problem with a message box being required to give the process a bit of a "break". Yes, but such tricks are symptomatic of not understanding what's going on under the covers. Adding sleeps/waits is dangerous since you need to determine what is the maximum time that you need in order to ensure success. You can't do that without understanding what's going on...and if you understand what's going on you shouldn't need the sleep in the first place! I actually re-wrote the code to just keep trying to do the "new" and to count how many times it takes before it's successful. I then fired off a process on a machine running a real O/S (not this windows piece of ...oh nevermind), to just keep creating the file. The result is that the "new" always succeeds on the first iteration when the program is initially fired up. After that it may take anywhere from 4 to 25 iterations before being successful (usually around 6 or 7). Clearly there's some sort of asynchronous issue going on here, but I can't figure out what the heck it is!

        M 1 Reply Last reply
        0
        • S skifanatic

          Programmer2k4 wrote: I have recently had a similar problem with a message box being required to give the process a bit of a "break". Yes, but such tricks are symptomatic of not understanding what's going on under the covers. Adding sleeps/waits is dangerous since you need to determine what is the maximum time that you need in order to ensure success. You can't do that without understanding what's going on...and if you understand what's going on you shouldn't need the sleep in the first place! I actually re-wrote the code to just keep trying to do the "new" and to count how many times it takes before it's successful. I then fired off a process on a machine running a real O/S (not this windows piece of ...oh nevermind), to just keep creating the file. The result is that the "new" always succeeds on the first iteration when the program is initially fired up. After that it may take anywhere from 4 to 25 iterations before being successful (usually around 6 or 7). Clearly there's some sort of asynchronous issue going on here, but I can't figure out what the heck it is!

          M Offline
          M Offline
          Mitch F
          wrote on last edited by
          #4

          Glen Baker wrote: Adding sleeps/waits is dangerous since you need to determine what is the maximum time that you need in order to ensure success. True, but you could put the thread.sleep(300) inside of the Catch exc as exception. That way, it checks every 300 milliseconds if it is ready, and if not, it sleeps for another 300 milliseconds, until it eventually works. I don't think there is any way to read/write to the file if it is returning a "File is already in use" error in previous tries. Programmer2k4 My sig: "The so-called 'Bugs' do not exist, they are merely features hidden by developers with message boxes that say 'An unhandled exception has occurred'." - Programmer2k4 "And it is a professional faux pas to pay someone else to destroy your computer when you are perfectly capable of destroying it yourself." - Roger Wright I now use my CodeProject Blog!

          S 1 Reply Last reply
          0
          • M Mitch F

            Glen Baker wrote: Adding sleeps/waits is dangerous since you need to determine what is the maximum time that you need in order to ensure success. True, but you could put the thread.sleep(300) inside of the Catch exc as exception. That way, it checks every 300 milliseconds if it is ready, and if not, it sleeps for another 300 milliseconds, until it eventually works. I don't think there is any way to read/write to the file if it is returning a "File is already in use" error in previous tries. Programmer2k4 My sig: "The so-called 'Bugs' do not exist, they are merely features hidden by developers with message boxes that say 'An unhandled exception has occurred'." - Programmer2k4 "And it is a professional faux pas to pay someone else to destroy your computer when you are perfectly capable of destroying it yourself." - Roger Wright I now use my CodeProject Blog!

            S Offline
            S Offline
            skifanatic
            wrote on last edited by
            #5

            Programmer2k4 wrote: I don't think there is any way to read/write to the file if it is returning a "File is already in use" error in previous tries. This is the crux of the whole issue. The file should not be in use! The StreamReader.Close() method has been called, the method has been exited. There should be no resources associated with the file (at least not with any reasonable operating system!). However clearly the O/S is maintaining some sort of handle to the file and something has to be kicked repeatedly in the butt to get the resources freed. Unfortunately I can't for the life of me figure out what is holding onto the file, how to free it up, and why it eventually fixes itself. Very frustrating.

            D 1 Reply Last reply
            0
            • S skifanatic

              Programmer2k4 wrote: I don't think there is any way to read/write to the file if it is returning a "File is already in use" error in previous tries. This is the crux of the whole issue. The file should not be in use! The StreamReader.Close() method has been called, the method has been exited. There should be no resources associated with the file (at least not with any reasonable operating system!). However clearly the O/S is maintaining some sort of handle to the file and something has to be kicked repeatedly in the butt to get the resources freed. Unfortunately I can't for the life of me figure out what is holding onto the file, how to free it up, and why it eventually fixes itself. Very frustrating.

              D Offline
              D Offline
              Dave Kreskowiak
              wrote on last edited by
              #6

              StreamReader? I must be missing something here. The file is being written to disk by another process, your code tries to read the file when the FileSystemWatcher event fires (which will happen when the file is CREATED, not when it's completely written!) Your code attempts to read a file that is still being written and hasn't been flushed to disk and closed, correct? The StreamReader/StreamWriter classes hold onto underlying Win32 file handles. Even though you called close on the Reader/Writer object, it would appear that the underlying, unmanaged, file handle hasn't been closed and released. This won't happen until the the Reader/Writer object is collect, which will call .Dispose() on the object. You can try calling .Dispose() yourself to free the underlying resources that your application holds. RageInTheMachine9532 "...a pungent, ghastly, stinky piece of cheese!" -- The Roaming Gnome

              S 1 Reply Last reply
              0
              • L Lost User

                I'm trying to do what should be a simple thing: watch a directory, and when a file appears read what's in the file. I'm using a FileWatcher to watch the directory, and that's working fine. What's not working is the StreamReader (actually it works once then starts failing). Here's a code snippet from the handler routine that is set to process file creation events (I'm typing it in, so typos are mine, not in the code): Private Sub processNewFile(Byval source As Object, ByVal e As FileSystemEventArgs) Dim message As String Dim sr As StreamReader Try ' Uncomment the following to make it work ' MsgBox("Be patient") sr = New StreamReader(e.FullPath) message = sr.ReadToEnd() sr.Close() MsgBox("The message is: " & message) Catch ex As Exception MsgBox("Dang...got an exception") End Try End Sub I test this by plopping files into the watched directory. The symptoms are as follows: 1) The first time I create a file in the watched directory it works perfectly. 2) Any subsequent attempt to create a file will cause the "new" statement to fail. The actual exception claims that the file is in use. 3) If I uncomment the commented lines in the code above (which causes a useless message box to appear) or if I add sufficiently long delay at that same point, it works perfectly. By the way, if I take the exact same code and do it somewhere else (i.e. not in a handler for the filewatcher, just fire it off with a button click) it works perfectly, so clearly there's something about the context that's causing this. Any ideas why this shouldn't work?

                D Offline
                D Offline
                Dallas Matthews
                wrote on last edited by
                #7

                Perhaps explicitly opening the files as readonly will help. Dim sr As New IO.StreamReader(IO.File.OpenRead(e.FullPath)) message = sr.ReadToEnd() sr.Close() I colleague of mine was having problems with trying to read, then upload, image files to a database. In the end, both the uploaded files and even the source files were getting hammered somehow, even though the code looked good. Opening the source files as readonly fixed the issue. -- Dallas

                1 Reply Last reply
                0
                • D Dave Kreskowiak

                  StreamReader? I must be missing something here. The file is being written to disk by another process, your code tries to read the file when the FileSystemWatcher event fires (which will happen when the file is CREATED, not when it's completely written!) Your code attempts to read a file that is still being written and hasn't been flushed to disk and closed, correct? The StreamReader/StreamWriter classes hold onto underlying Win32 file handles. Even though you called close on the Reader/Writer object, it would appear that the underlying, unmanaged, file handle hasn't been closed and released. This won't happen until the the Reader/Writer object is collect, which will call .Dispose() on the object. You can try calling .Dispose() yourself to free the underlying resources that your application holds. RageInTheMachine9532 "...a pungent, ghastly, stinky piece of cheese!" -- The Roaming Gnome

                  S Offline
                  S Offline
                  skifanatic
                  wrote on last edited by
                  #8

                  Dave Kreskowiak wrote: StreamReader? I must be missing something here. The file is being written to disk by another process, your code tries to read the file when the FileSystemWatcher event fires (which will happen when the file is CREATED, not when it's completely written!) Your code attempts to read a file that is still being written and hasn't been flushed to disk and closed, correct? Ah...this is a plausible explanation! The first time that the handler gets called I notice that the system appears to load a dll (microsoft.visualbasic.dll). Subsequent iterations of the handler do not result in this dll being loaded. It may well be that the process of loading the dll is sufficient to delay things enough for the file write to complete, and therefore cause the StreamReader constructor to work. From then on the dll is not loaded (it's already there), so the StreamReader constructor is called sooner, and as Dave points out the file may not be completely written yet, therefore causing the symptoms that I'm seeing. Interestingly, trying to use read only handle doesn't solve this problem. Hmm...makes me wonder how to properly use the FileWatcher at all. Anyway, thanks Dave for pointing out the obvious. I'll now scratch my growing stubble and see if I can figure out a way to make this sucker work!

                  D 1 Reply Last reply
                  0
                  • S skifanatic

                    Dave Kreskowiak wrote: StreamReader? I must be missing something here. The file is being written to disk by another process, your code tries to read the file when the FileSystemWatcher event fires (which will happen when the file is CREATED, not when it's completely written!) Your code attempts to read a file that is still being written and hasn't been flushed to disk and closed, correct? Ah...this is a plausible explanation! The first time that the handler gets called I notice that the system appears to load a dll (microsoft.visualbasic.dll). Subsequent iterations of the handler do not result in this dll being loaded. It may well be that the process of loading the dll is sufficient to delay things enough for the file write to complete, and therefore cause the StreamReader constructor to work. From then on the dll is not loaded (it's already there), so the StreamReader constructor is called sooner, and as Dave points out the file may not be completely written yet, therefore causing the symptoms that I'm seeing. Interestingly, trying to use read only handle doesn't solve this problem. Hmm...makes me wonder how to properly use the FileWatcher at all. Anyway, thanks Dave for pointing out the obvious. I'll now scratch my growing stubble and see if I can figure out a way to make this sucker work!

                    D Offline
                    D Offline
                    Dave Kreskowiak
                    wrote on last edited by
                    #9

                    skifanatic wrote: Interestingly, trying to use read only handle doesn't solve this problem. That's because the other process has opened the file for write acces with DenyShareAll attributes. No other process on earth can open that file until the write is completed and the file is flushed and closed. RageInTheMachine9532 "...a pungent, ghastly, stinky piece of cheese!" -- The Roaming Gnome

                    S 1 Reply Last reply
                    0
                    • D Dave Kreskowiak

                      skifanatic wrote: Interestingly, trying to use read only handle doesn't solve this problem. That's because the other process has opened the file for write acces with DenyShareAll attributes. No other process on earth can open that file until the write is completed and the file is flushed and closed. RageInTheMachine9532 "...a pungent, ghastly, stinky piece of cheese!" -- The Roaming Gnome

                      S Offline
                      S Offline
                      skifanatic
                      wrote on last edited by
                      #10

                      Dave Kreskowiak wrote: That's because the other process has opened the file for write acces with DenyShareAll attributes. :) The other process is samba (I'm dropping the file onto the Windows machine from my Linux machine...yes, I'm one of those annoying Linux people :)

                      1 Reply Last reply
                      0
                      Reply
                      • Reply as topic
                      Log in to reply
                      • Oldest to Newest
                      • Newest to Oldest
                      • Most Votes


                      • Login

                      • Don't have an account? Register

                      • Login or register to search.
                      • First post
                        Last post
                      0
                      • Categories
                      • Recent
                      • Tags
                      • Popular
                      • World
                      • Users
                      • Groups