Las llamadas de SqlClient que causaron & # 8220; el subproceso se estaba abortando en SNINativeMethodWrapper.SNIPacketGetConnection (paquete IntPtr) & # 8221;

StackOverflow https://stackoverflow.com/questions/424531

Pregunta

Realmente agradecería cualquier sugerencia, sin importar cuán simple o compleja sea, para ayudarme a aislar y resolver este problema.

Tengo un poco de código que genera pequeños archivos de informe. Para cada archivo de la colección, se ejecuta un proceso almacenado para obtener los datos a través del lector XML (es un conjunto de resultados bastante grande). Cuando creé todo esto, y lo pisé, todo está bien. Se generan archivos, sin errores.

Esta biblioteca se llama a través de comunicación remota y se hospeda a través de IIS. Cuando implemento la biblioteca compilada y la llamo, es capaz de generar algunos de los informes, pero luego lanza una excepción de cancelación de subproceso. Si adjunto el depurador al proceso de trabajo asp, y paso por el código, no tengo problemas.

Al ver que esta falla es bastante consistente, busqué similitudes y encontré que la falla ocurre en diferentes informes, pero parece ocurrir aproximadamente en el mismo punto cronológico.

Esto me llevó a pensar que era una configuración de tiempo de espera que el depurador está anulando, hice algunos tiempos aproximados del proceso general (no la única pieza del código que falla) y parece fallar justo después de unos 200 segundos. El tiempo de ejecución de web.config se establece en 600 minutos (lo suficientemente alto). Hay otras partes de esta aplicación de servidor que requieren transacciones COM + (tiempo de espera de 2 minutos), pero esta no es una de ellas. Estoy en una pérdida en cuanto al tiempo de espera que podría estar llegando (en la marca de 200 segundos aproximadamente).

El tiempo de espera de la conexión SQL se deja en forma predeterminada (la conexión se abre con éxito), el tiempo de espera del comando es de 300 segundos (solo se necesitan 12-15 para ejecutar el comando).

  • ¿Hay algún otro tiempo de espera que pueda faltar?

Ejecuté el analizador de SQL, y muestra que el resultado se devuelve correctamente (todas las declaraciones y RPC se completaron, sin errores). La ejecución del código a través de SSMS proporciona resultados perfectos.

Usando el reflector, perforé el SNINativeMethodWrapper, y es una envoltura para el código no administrado y no puedo ver lo que realmente está tratando de hacer. Solo puedo asumir (quizás de manera incorrecta) que el código ha recibido el TDS del servidor SQL y que el contenedor está tratando de obtener la conexión asociada con el paquete y no puede.

  • ¿Alguien sabe qué se supone que debe hacer esta envoltura?
  • ¿Hay alguna forma de rastrear / depurar este código para averiguar qué está causando el error?

Intenté usar diferentes métodos (ExecScalar, DataAdapter), pero todos usan ExecuteReader internamente.

Intenté deshabilitar la agrupación de conexiones y forzando al cliente a usar el mismo tamaño de paquete que el servidor.

  • ¿Alguien tiene alguna idea sobre qué causa esto, o qué puedo hacer para aislar y tratar de corregir el problema?

Este es el código de llamada donde se genera la excepción.

Private Function GetDataAsXmlDoc(ByVal cmd As SqlClient.SqlCommand) As XmlDocument

    Dim _xmlDoc As XmlDocument

    Using _connection As New SqlClient.SqlConnection(GetConnectionString())

        Logging.DebugEvent.Raise(Me.GetType.Namespace, Reflection.MethodBase.GetCurrentMethod().Name, _
                                 "No cached data found or used. Getting data for report from the database using SQL connection.")

        Dim _xmlReader As XmlReader
        'DataAdapter,ExecuteScalar, ExecuteXmlReader all use ExecuteReader internally and suffer the same problem.'
        'If you dont believe me, reflect it or look at one of the blowed up stack traces. '

        '_connection.ConnectionString += ";Pooling=false;"' 'This has no effect on the ThreadAbort.'
        cmd.Connection = _connection
        cmd.CommandTimeout = 300
        _connection.Open()

        Logging.DebugEvent.Log(String.Format("Connection opened, using packet size of {0}.", _connection.PacketSize))

        _xmlReader = cmd.ExecuteXmlReader() 'Thread aborts in here'

        Logging.DebugEvent.Raise(Me.GetType.Namespace, Reflection.MethodBase.GetCurrentMethod().Name, _
                                 "Report data recieved from database")

        _xmlDoc = New XmlDocument()
        _xmlDoc.Load(_xmlReader)

        _xmlReader.Close()

    End Using

  Return _xmlDoc

End Function

Pila

Exception String - System.Threading.ThreadAbortException: Thread was being aborted.
   at SNINativeMethodWrapper.SNIPacketGetConnection(IntPtr packet)
   at System.Data.SqlClient.TdsParserStateObject.ProcessSniPacket(IntPtr packet, UInt32 error)
   at System.Data.SqlClient.TdsParserStateObject.ReadSni(DbAsyncResult asyncResult, TdsParserStateObject stateObj)
   at System.Data.SqlClient.TdsParserStateObject.ReadNetworkPacket()
   at System.Data.SqlClient.TdsParserStateObject.ReadBuffer()
   at System.Data.SqlClient.TdsParserStateObject.ReadByte()
   at System.Data.SqlClient.TdsParser.Run(RunBehavior runBehavior, SqlCommand cmdHandler, SqlDataReader dataStream, BulkCopySimpleResultSet bulkCopyHandler, TdsParserStateObject stateObj)
   at System.Data.SqlClient.SqlDataReader.ConsumeMetaData()
   at System.Data.SqlClient.SqlDataReader.get_MetaData()
   at System.Data.SqlClient.SqlCommand.FinishExecuteReader(SqlDataReader ds, RunBehavior runBehavior, String resetOptionsString)
   at System.Data.SqlClient.SqlCommand.RunExecuteReaderTds(CommandBehavior cmdBehavior, RunBehavior runBehavior, Boolean returnStream, Boolean async)
   at System.Data.SqlClient.SqlCommand.RunExecuteReader(CommandBehavior cmdBehavior, RunBehavior runBehavior, Boolean returnStream, String method, DbAsyncResult result)
   at System.Data.SqlClient.SqlCommand.RunExecuteReader(CommandBehavior cmdBehavior, RunBehavior runBehavior, Boolean returnStream, String method)
   at System.Data.SqlClient.SqlCommand.ExecuteXmlReader()...
¿Fue útil?

Solución

Creo que he resuelto el problema. La línea de código ofensiva en el ejemplo anterior fue la declaración ...

 Logging.DebugEvent.Raise(Me.GetType.Namespace, Reflection.MethodBase.GetCurrentMethod().Name, _
                                 "Report data recieved from database")

Esta es una llamada a un Bloque de aplicaciones (MS enterprise library) para registrar eventos en archivos sin formato (en este caso) o registros de eventos.

Este, entre ExecuteXMLReader () y el uso real del lector en el documento XML, a veces fallaba con dureza, provocando que todo el hilo se abortara. Trasladé la línea después de _xmlReader.Close () y resolví el problema.

Licenciado bajo: CC-BY-SA con atribución
No afiliado a StackOverflow
scroll top