Compartir a través de


Objeto SqlContext

Se invoca código administrado en el servidor cuando se llama a un procedimiento o función, cuando se llama a un método en un tipo definido por el usuario de Common Language Runtime (CLR), o cuando la acción desencadena un desencadenador definido en cualquiera de los lenguajes de Microsoft .NET Framework. Dado que la ejecución de este código se solicita como parte de una conexión de usuario, se requiere el acceso al contexto del autor de la llamada desde el código que se ejecuta en el servidor. Además, ciertas operaciones de acceso a datos solo pueden ser válidas si se ejecutan bajo el contexto del autor de la llamada. Por ejemplo, el acceso a pseudo tablas insertadas y eliminadas utilizadas en operaciones del desencadenador solo es válido bajo el contexto del autor de la llamada.

El contexto del autor de la llamada se resume en un objeto SqlContext. Para obtener más información sobre los métodos y las SqlTriggerContext propiedades, consulte la Microsoft.SqlServer.Server.SqlTriggerContext documentación de referencia de clases en el SDK de .NET Framework.

SqlContext proporciona acceso a los componentes siguientes:

  • SqlPipe: el objeto SqlPipe representa la "canalización" a través de la que los resultados fluyen al cliente. Para obtener más información sobre el SqlPipe objeto, vea Objeto SqlPipe.

  • SqlTriggerContext: el objeto SqlTriggerContext solo se puede recuperar desde un desencadenador CLR. Proporciona información sobre la operación que hizo que se activara el desencadenador y un mapa de las columnas actualizadas. Para obtener más información sobre el SqlTriggerContext objeto , vea Objeto SqlTriggerContext.

  • IsAvailable: la propiedad IsAvailable se utiliza para determinar la disponibilidad de contexto.

  • WindowsIdentity: la propiedad WindowsIdentity se utiliza para recuperar la identidad de Windows del autor de la llamada.

Determinar la disponibilidad del contexto

Consulte la clase SqlContext para ver si el código actualmente en ejecución se ejecuta en proceso. Para ello, compruebe la propiedad IsAvailable del objeto SqlContext. La IsAvailable propiedad es de solo lectura y devuelve True si el código de llamada se ejecuta dentro de SQL Server y si se puede acceder a otros SqlContext miembros. Si la propiedad IsAvailable devuelve False, todos los demás miembros de SqlContext producen una excepción InvalidOperationException, si se utilizan. Si IsAvailable devuelve False, cualquier intento de abrir un objeto de conexión con "context connection=true" en la cadena de conexión genera un error.

Recuperar la identidad de Windows

El código CLR que se ejecuta en SQL Server siempre se invoca en el contexto de la cuenta de proceso. Si el código debe realizar determinadas acciones mediante la identidad del usuario que realiza la llamada, en lugar de la identidad del proceso de SQL Server, se debe obtener un token de suplantación a través de la WindowsIdentity propiedad del SqlContext objeto . La WindowsIdentity propiedad devuelve una WindowsIdentity instancia que representa la identidad de Microsoft Windows del autor de la llamada o null si el cliente se autenticó mediante SQL Server Autenticación. Solo los ensamblados marcados con los permisos EXTERNAL_ACCESS o UNSAFE tienen acceso a esta propiedad.

Después de obtener el objeto WindowsIdentity, los autores de la llamada pueden suplantar la cuenta del cliente y realizar acciones en su nombre.

La identidad del autor de la llamada solo está disponible a través de SqlContext.WindowsIdentity si el cliente que inició la ejecución del procedimiento almacenado o función se conectó al servidor utilizando la autenticación de Windows. Si, por el contrario, se ha utilizado la autenticación de SQL Server, esta propiedad es nula y el código no puede suplantar a la persona que llama.

Ejemplo

En el ejemplo siguiente, se muestra cómo obtener la identidad de Windows del cliente de la llamada y suplantarla.

C#

[Microsoft.SqlServer.Server.SqlProcedure]  
public static void WindowsIDTestProc()  
{  
    WindowsIdentity clientId = null;  
    WindowsImpersonationContext impersonatedUser = null;  
  
    // Get the client ID.  
    clientId = SqlContext.WindowsIdentity;  
  
    // This outer try block is used to thwart exception filter   
    // attacks which would prevent the inner finally   
    // block from executing and resetting the impersonation.  
    try  
    {  
        try  
        {  
            impersonatedUser = clientId.Impersonate();  
            if (impersonatedUser != null)  
            {  
                // Perform some action using impersonation.  
            }  
        }  
        finally  
        {  
            // Undo impersonation.  
            if (impersonatedUser != null)  
                impersonatedUser.Undo();  
        }  
    }  
    catch  
    {  
        throw;  
    }  
}  

Visual Basic

<Microsoft.SqlServer.Server.SqlProcedure()> _  
Public Shared Sub  WindowsIDTestProcVB ()  
    Dim clientId As WindowsIdentity  
    Dim impersonatedUser As WindowsImpersonationContext  
  
    ' Get the client ID.  
    clientId = SqlContext.WindowsIdentity  
  
    ' This outer try block is used to thwart exception filter   
    ' attacks which would prevent the inner finally   
    ' block from executing and resetting the impersonation.  
  
    Try  
        Try  
  
            impersonatedUser = clientId.Impersonate()  
  
            If impersonatedUser IsNot Nothing Then  
                ' Perform some action using impersonation.  
            End If  
  
        Finally  
            ' Undo impersonation.  
            If impersonatedUser IsNot Nothing Then  
                impersonatedUser.Undo()  
            End If  
        End Try  
  
    Catch e As Exception  
  
        Throw e  
  
    End Try  
End Sub  

Consulte también

SqlPipe, objetos
Objeto SqlTriggerContext
Desencadenadores de CLR
Extensiones específicas en proceso de SQL Server a ADO.NET