2010-04-07 38 views

Respuesta

9

El método BeginTrans se puede utilizar como una función que devuelve el nivel de anidamiento de la transacción. Si crea una propiedad para almacenarla, puede verificarla donde sea necesario para ver si es mayor que 0. Cuando confirma o restituye, deberá disminuir la propiedad usted mismo.

Private m_TransLevel As Long 

Public Property Get TransactionLevel() As Long 
    TransactionLevel = m_TransLevel 
End Property 
Public Property Let TransactionLevel(vLevel As Long) 
    m_TransLevel = vLevel 
End Property 

Public Sub SaveMyData() 

    TransactionLevel = adoConnection.BeginTrans() 
    ... 

End Sub 

También puede adaptar el valor de retorno para trabajar dentro de una función que devuelve Verdadero/Falso si el nivel> 1. No me gusta esto así, pero sería algo parecido a esto (y sin control de errores)

Public Function IsConnectionInsideTransaction(ByVal vADOConnection as ADOBD.Connection) As Boolean 
    Dim intLevel As Integer 

    If vADOConnection.State = AdStateOpen Then 
     intLevel = vADOConnection.BeginTrans() 
     IsConnectionInsideTransaction = (intLevel > 1) 
     vADOConnection.RollbackTrans 
    End If 

End Function 
+1

He pensado en las variaciones del primer método, esencialmente envolviendo el ADODB.Connection en un nuevo Clase MyConnection que agregaría esto y otras funcionalidades. Quería minimizar los cambios en el código existente si era posible. La segunda forma responde mi pregunta, supongo, pero parece muy arriesgada para mí, en realidad no quiero interactuar con la base de datos cada vez que reviso ... ¡Gracias por las sugerencias! –

+1

Envolver con su propia clase de conexión podría tener otras ventajas. Si alguna vez necesita actualizar a VB.net, podría ser más fácil si ha envuelto todos los objetos ADO en sus propios objetos. Podría hacer que tengan firmas similares a ADO (para minimizar los cambios al código existente) pero solo exponer el mínimo de funcionalidad, para limitar el alcance del esfuerzo de actualización. Sugiero ponerlos en un proyecto DLL para que el proyecto principal ni siquiera haga referencia a ADO. Divulgación completa: no hemos hecho esto completamente en nuestros propios proyectos, pero desearía haberlo hecho. – MarkJ

+0

¡Si nuestro motor de informes utilizara un contenedor alrededor de 'ADODB.Connection'! He jugado con la idea de minimizar los cambios en el código de extracción de informes existente para que los usuarios puedan ejecutar informes a través de una conexión inalámbrica (que en nuestro caso pasa por un servidor RPC personalizado). –

0

Parece que puede verificar el estado ADO. http://msdn.microsoft.com/en-us/library/ms675068%28v=VS.85%29.aspx

Probablemente ya conozca esta otra parte pero la publicaré de todos modos.

Esto explica cómo funcionan las transacciones con ADO en VB. http://support.microsoft.com/kb/198024

+1

No te creo poder. Este fue el primer lugar que miré, y parece que los valores de estado no tienen nada que decir sobre estar en una transacción o no. Ver: http://msdn.microsoft.com/en-us/library/ms675546%28v=VS.85%29.aspx –

0

No puede hacerlo a menos que lo rastree usted mismo. El objeto de conexión no tiene una propiedad relacionada con el estado de la transacción. Tendrás que hacer que tu proc marque una bandera en otra tabla/área de configuraciones si TIENES que tenerla (lo que puede ser problemático si ocurren errores no controlados y la bandera de estado se "atasca" con un estado no válido, debes subir con un "tiempo de espera" válido o anulación para ignorar/matar/sobrescribir el anterior).

2

Si se conecta a un servidor de Microsoft SQL y puede contar con él para responder lo suficientemente rápido (es decir, no está en el otro lado del planeta) se puede realizar la consulta:

SELECT @@TRANCOUNT 
+0

me gusta esta respuesta! dim rstc, tc conjunto rstc = adoCon.Execute ("SELECT @@ TRANCOUNT") tc = CLng (rstc.Fields (0)) –

Cuestiones relacionadas