2016-12-28 14 views
0

У меня много проблем, чтобы поймать исключение в async DelegateCommand (Prism 5).Обработка исключений в Prism Async DelegateCommand

В конструктор ViewModel:

cmdModificarPedido = New DelegateCommand(Of Object)(AddressOf OnModificarPedido, AddressOf CanModificarPedido) 

В ViewModel:

Private _cmdModificarPedido As DelegateCommand(Of Object) 
Public Property cmdModificarPedido As DelegateCommand(Of Object) 
    Get 
     Return _cmdModificarPedido 
    End Get 
    Private Set(value As DelegateCommand(Of Object)) 
     SetProperty(_cmdModificarPedido, value) 
    End Set 
End Property 
Private Function CanModificarPedido(arg As Object) As Boolean 
    Return True 
End Function 
Private Async Sub OnModificarPedido(arg As Object) 
    Try 
     Await Task.Run(Sub() 
          Throw New Exception("My Exception") 
         End Sub) 
     NotificationRequest.Raise(New Notification() With { 
         .Title = "OK", 
         .Content = "Command OK" 
        }) 

    Catch ex As Exception 
     NotificationRequest.Raise(New Notification() With { 
        .Title = "Error", 
        .Content = ex.Message 
       }) 

    End Try 
End Sub 

Почему Исключение не поймают? Я знаю, что это еще один поток, но он должен быть пойман в любом случае внешним Try ... Catch block (Try Catch outside of: await Task.Run(()).

enter image description here

Примечание: это vb.net код, но # решение C будет тоже хорошо.

UPDATE 2 После того, как я знаю, что была проблема с моей конфигурации отладчика (первый шанс исключений), я пишу более реалистичный пример с той же проблемой:

Private Async Sub OnModificarPedido(arg As Object) 
    Try 
     Await Task.Run(Sub() 
          Try 
           throwMyException() 
          Catch ex As Exception 
           Throw New Exception(ex.Message) 
          End Try 
         End Sub) 
     NotificationRequest.Raise(New Notification() With { 
         .Title = "Pedido Modificado", 
         .Content = "Pedido " + pedido.numero.ToString + " modificado correctamente" 
        }) 

    Catch ex As Exception 
     NotificationRequest.Raise(New Notification() With { 
        .Title = "Error", 
        .Content = ex.Message 
       }) 

    End Try 
End Sub 
Public Async Sub throwMyException() 
    Throw New Exception("My Exception") 
End Sub 

И теперь он не захватывает исключение, когда я нажимаю F5. Он разбивается на «throwMyException()», он не обнаруживает исключения, хотя он вызывается внутри блока Try Catch.

Важно: Если я удалю асинхронное слово в «throwMyException», оно его поймает !!!

Что я делаю сейчас неправильно?

Спасибо

+0

Вы точно знаете, что * этот код * не поймает исключения? –

+0

Я абсолютно уверен, что в моей жизни очень мало вещей, но я вставил и скопировал код, проверил его, и это не исключение. Я хочу обновить вопрос с изображением –

+1

Похоже, у вас есть исключения с первым шансом, включенные в отладчике. Если вы F5 оттуда, это поймает? –

ответ

0

Там не было никаких проблем с оригинальным кодом вас в курсе - отладчик просто поймать исключение, прежде чем ваш код сделал, что совершенно нормально.

С обновленным кодом проблема заключается в использовании Async Sub. Исключения не могут быть напрямую пойманы с помощью методов Async Sub. Вы должны использовать (не Async) Sub или Async Func(of Task). Этот принцип известен как «избегать асинхронной пустоты» в моем MSDN article on async best practices.

+0

Я делаю что-то неправильно, потому что я этого не понимаю. Если я сменил знак на «Частная асинхронная функция OnModificarPedido (arg As Object) как задание», как насчет этого кода в конструкторе «cmdModificarPedido = New DelegateCommand (Of Object) (AddressOf OnModificarPedido, AddressOf CanModificarPedido)» ??? Он показывает это сообщение: «Задача, возвращенная из этой функции Async, будет удалена, а любые исключения в ней будут игнорироваться. Попробуйте изменить ее на Sub Async, чтобы ее исключения распространялись», и исключение тоже не зацепилось. Большое спасибо –

+1

Неправильный метод. Вы должны менять 'throwMyException', а не' OnModificarPedido'. –

+0

Ты гений !!!Это была именно проблема !!! Нет async Sub решил мою проблему (я не смог заставить ее работать с Async Func (из задачи)). спасибо –