2012-05-01 11 views
14

Ho solo un semplice sito Web vb.net che deve chiamare un Sub che esegue un'attività molto lunga che funziona con la sincronizzazione di alcune directory nel filesystem (dettagli non importante).Come effettuare una chiamata al metodo asincrono molto semplice in vb.net

Quando chiamo il metodo, alla fine scade sul sito Web in attesa del completamento della routine secondaria. Tuttavia, anche se il sito scade, la routine alla fine completa il suo compito e tutte le directory finiscono come dovrebbero.

Voglio solo impedire il timeout, quindi mi piacerebbe chiamare il Sub in modo asincrono. Non ho bisogno (o nemmeno voglio) e callback/conferma che è stato eseguito correttamente.

Quindi, come posso chiamare il mio metodo in modo asincrono all'interno di un sito Web utilizzando VB.net?

Se avete bisogno di qualche codice:

Protected Sub Page_Load(ByVal sender As Object, ByVal e As System.EventArgs) Handles Me.Load 
    Call DoAsyncWork() 
End Sub 

Protected Sub DoAsyncWork() 
     Dim ID As String = ParentAccountID 
     Dim ParentDirectory As String = ConfigurationManager.AppSettings("AcctDataDirectory") 
     Dim account As New Account() 
     Dim accts As IEnumerable(Of Account) = account.GetAccounts(ID) 

     For Each f As String In My.Computer.FileSystem.GetFiles(ParentDirectory) 
      If f.EndsWith(".txt") Then 
       Dim LastSlashIndex As Integer = f.LastIndexOf("\") 
       Dim newFilePath As String = f.Insert(LastSlashIndex, "\Templates") 
       My.Computer.FileSystem.CopyFile(f, newFilePath) 
      End If 
     Next 

     For Each acct As Account In accts 
      If acct.ID <> ID Then 
       Dim ChildDirectory As String = ConfigurationManager.AppSettings("AcctDataDirectory") & acct.ID 
       If My.Computer.FileSystem.DirectoryExists(ChildDirectory) = False Then 
        IO.Directory.CreateDirectory(ChildDirectory) 
       End If 
       My.Computer.FileSystem.DeleteDirectory(ChildDirectory, FileIO.DeleteDirectoryOption.DeleteAllContents) 
       My.Computer.FileSystem.CopyDirectory(ParentDirectory, ChildDirectory, True) 
      Else 
      End If 
     Next 
End Sub 

risposta

20

Non è consigliabile utilizzare la classe Thread a meno che non sia necessario un maggiore controllo sul thread, poiché la creazione e la riduzione dei thread è costosa. Invece, consiglierei di usare a ThreadPool thread. See this per una buona lettura.

È possibile eseguire il metodo su un thread ThreadPool come questo:

System.Threading.ThreadPool.QueueUserWorkItem(AddressOf DoAsyncWork) 

Avrete anche bisogno di cambiare la vostra firma metodo per ...

Protected Sub DoAsyncWork(state As Object) 'even if you don't use the state object 

Infine, anche essere consapevoli che le eccezioni non gestite in altri thread uccideranno IIS. Vedi this article (vecchio ma ancora rilevante, non sono sicuro delle soluzioni, dal momento che non utilizzo acutamente ASP.NET).

+0

AMORE !!! Grazie! – EdenMachine

+0

Questo ha funzionato alla grande, caricando un file su un server web.Convalidare il file quindi inviarlo via email. Anche se l'utente chiude la pagina web/sito/browser, l'e-mail raggiunge comunque la sua destinazione. – htm11h

7

Si potrebbe fare questo con un semplice filo:

Add:

Imports System.Threading 

E dove vuoi che venga eseguito:

Dim t As New Thread(New ThreadStart(AddressOf DoAsyncWork)) 
t.Priority = Threading.ThreadPriority.Normal 
t.Start() 

La chiamata a t.Start() restituisce immediatamente e il nuovo thread viene eseguito DoAsyncWork in background fino al completamento. Dovresti assicurarti che tutto in quella chiamata fosse sicuro per i thread, ma a prima vista sembra essere già così.

+0

perfettamente risposto così +1, ma mi piace l'idea ThreadPool meglio tenerlo semplice e leggero – EdenMachine

+0

@EdenMachine Sono d'accordo, il ThreadPool è probabilmente il modo migliore per andare. –

0

Inoltre, cercavo informazioni sulla programmazione asincrona in VB. Oltre a questo thread, ho trovato anche quanto segue: a partire da Visual Studio 2012 e .Net Framework 4.5, VB ha ricevuto due nuove parole chiave per rendere un metodo asincrono a destra nella dichiarazione, senza utilizzare Thread o Threadpool. Le nuove parole chiave sono "Async" e "Await". Si può fare riferimento ai seguenti link se lo si desidera:

http://msdn.microsoft.com/library/hh191443%28vs.110%29.aspx

https://msdn.microsoft.com/en-us/library/hh191564%28v=vs.110%29.aspx

Problemi correlati