Issue with error handling in callback


New member
Feb 4, 2016
Programming Experience
New to asynchronous calls, in this case using a call back. The code below works.
The code is calling a rather rudimentary web service which returns xml. If the service returns xml the code works fine and msresponse is filled with the xml and the funcion "GetWebserviceData" is able to return, to the caller, a parsed msresponse through the function "CreateDT_Implantable_Device". This works without a hitch as long as xml is returned.
If the service does not return any xml there is an error thrown at this line in the respcallback:
" Dim resp As HttpWebResponse = _ CType(req.EndGetResponse(ar), HttpWebResponse)"
The error that is thrown is "400-bad request)"
It seems that if the service fails the thread for the callback does not complete correctly and the entire application locks up at that point. It returns to the form that called "GetWebserviceData" and none of the controls work: the form is frozen.
I have tried putting try catches around all the code in call back function (as seen below), "respcallback" and around all the code in "GetWebserviceData" (not in the code below). as you can see from the try catch in "respcallback" in case of this error I am trying to end the callback thread and fill msResponse so the loop in "GetWebserviceData" that follows is satisfied and will end. Here is the loop.
Do While msResponse.Length = 0 'wait Loop
The complete code follows: Any help would be appreciated. I am trying allow the webservice to fail, let the code continue and put up a messagebox saying the service failed. Obviously my try catch is not working as seen in "respcallback"; the code simply locks up.
[h=2]Code follows. Any help would be appreciated:[/h]Public Function GetWebserviceData(psUDI As String) As DataTable FillGS1Delimeters() miUDI = psUDI ' Create the request object. 'Try Dim wreq As HttpWebRequest = _ CType(WebRequest.Create("" & psUDI), HttpWebRequest)
' Create the state object.
Dim rs As RequestState = New RequestState()

' Put the request into the state so it can be passed around...
rs.Request = wreq

' Issue the async request..
Dim r As IAsyncResult = _
CType(wreq.BeginGetResponse( _
New AsyncCallback(AddressOf RespCallback), rs), IAsyncResult)

' Wait until the ManualResetEvent is set so that the application
' does not exit until after the callback is called.

Do While msResponse.Length = 0

'Catch ex As Exception
'msResponse = "Error"
'MessageBox.Show("an error")

'End Try
Return CreateDT_Implantable_Device(msResponse)
End FunctionPrivate Function CreateDT_Implantable_Device(wsResponse As String) Dim dtDevice As DataTable = New DataTable() Dim dtPI As DataTable = New DataTable() Dim ds As DataSet = New DataSet
ds = StoreXMLAsText(msResponse)
dtPI = FillRecord(dtDevice, ds)
Return dtPI
End FunctionShared Sub RespCallback(ar As IAsyncResult) Try ' Get the RequestState object from the async result. Dim rs As RequestState = CType(ar.AsyncState, RequestState)
' Get the HttpWebRequest from RequestState..
Dim req As HttpWebRequest = rs.Request

' Call EndGetResponse, which returns the HttpWebResponse object
' that came from the request issued above.
Dim resp As HttpWebResponse = _
CType(req.EndGetResponse(ar), HttpWebResponse)

' Start reading data from the respons stream.
Dim ResponseStream As Stream = resp.GetResponseStream()

' Store the reponse stream in RequestState to read
' the stream asynchronously.
rs.ResponseStream = ResponseStream

' Pass rs.BufferRead to BeginRead. Read data into rs.BufferRead.
Dim iarRead As IAsyncResult = _
ResponseStream.BeginRead(rs.BufferRead, 0, BUFFER_SIZE, _
New AsyncCallback(AddressOf ReadCallBack), rs)
Catch ex As Exception
msResponse = "Invalid UDI"
msResponse = "Error"
End Try

End SubShared Sub ReadCallBack(asyncResult As IAsyncResult) ' Get the RequestState object from the AsyncResult. Dim rs As RequestState = CType(asyncResult.AsyncState, RequestState)
' Retrieve the ResponseStream that was set in RespCallback.
Dim responseStream As Stream = rs.ResponseStream

' Read rs.BufferRead to verify that it contains data.
Dim read As Integer = responseStream.EndRead(asyncResult)
If read > 0 Then
' Prepare a Char array buffer for converting to Unicode.
Dim charBuffer(1024) As Char

' Convert byte stream to Char array and then String.
' len contains the number of characters converted to Unicode.
Dim len As Integer = _
rs.StreamDecode.GetChars(rs.BufferRead, 0, read, charBuffer, 0)
Dim str As String = New String(charBuffer, 0, len)

' Append the recently read data to the RequestData stringbuilder
' object contained in RequestState.
rs.RequestData.Append( _
Encoding.ASCII.GetString(rs.BufferRead, 0, read))

' Continue reading data until responseStream.EndRead
' returns ?1.
Dim ar As IAsyncResult = _
responseStream.BeginRead(rs.BufferRead, 0, BUFFER_SIZE, _
New AsyncCallback(AddressOf ReadCallBack), rs)
If rs.RequestData.Length > 1 Then
' Display data to the console.
Dim strContent As String
strContent = rs.RequestData.ToString()
msResponse = strContent
End If

' Close down the response stream.

' Set the ManualResetEvent so the main thread can exit.
End If

End Sub