Partager via


Objet SqlContext

S'applique à :SQL Server

Vous appelez du code managé sur le serveur lorsque vous appelez une procédure ou une fonction, lorsque vous appelez une méthode sur un type CLR (Common Language Runtime) défini par l’utilisateur, ou lorsque votre action déclenche un déclencheur défini dans l’un des langages .NET Framework. Comme l'exécution de ce code est demandée dans le cadre d'une connexion utilisateur, l'accès au contexte de l'appelant à partir du code en cours d'exécution dans le serveur est requis. En outre, certaines opérations d’accès aux données peuvent uniquement être valides si elles sont exécutées dans le contexte de l’appelant. Par exemple, l'accès à des pseudo-tables insérées et supprimées utilisées dans les opérations de déclencheur n'est valide que sous le contexte de l'appelant.

Le contexte de l’appelant est abstrait dans un objet SqlContext. Pour plus d’informations, consultez Microsoft.SqlServer.Server.SqlContext.

SqlContext permet d’accéder aux composants suivants.

Composant Description
SqlPipe Cet objet représente le canal à travers lequel les résultats circulent vers le client. Pour plus d’informations, consultez 'objet SqlPipe.
SqlTriggerContext Cet objet ne peut être récupéré qu’à partir d’un déclencheur CLR. Il fournit des informations sur l'opération qui a provoqué l'activation du déclencheur et un mappage des colonnes mises à jour. Pour plus d’informations, consultez 'objet SqlTriggerContext.
IsAvailable Cette propriété est utilisée pour déterminer la disponibilité du contexte.
WindowsIdentity Cette propriété est utilisée pour récupérer l’identité Windows de l’appelant.

Déterminer la disponibilité du contexte

Interrogez la classe SqlContext pour voir si le code en cours d’exécution est en cours d’exécution en vérifiant la propriété IsAvailable de l’objet SqlContext. La propriété IsAvailable est en lecture seule et retourne True si le code appelant s’exécute dans SQL Server et si d’autres membres SqlContext sont accessibles. Si la propriété IsAvailable retourne False, tous les autres membres SqlContext lèvent un InvalidOperationException, s’ils sont utilisés. Si IsAvailable retourne False, toute tentative d’ouverture d’un objet de connexion avec « context connection=true » dans la chaîne de connexion échoue.

Récupérer l’identité Windows

Le code CLR s’exécutant à l’intérieur de SQL Server est toujours appelé dans le contexte du compte de processus. Si le code doit effectuer certaines actions à l’aide de l’identité de l’utilisateur appelant, au lieu de l’identité du processus SQL Server, un jeton d’emprunt d’identité doit être obtenu via la propriété WindowsIdentity de l’objet SqlContext. La propriété WindowsIdentity retourne une instance WindowsIdentity représentant l’identité Windows de l’appelant, ou null si le client a été authentifié à l’aide de l’authentification SQL Server. Seuls les assemblys marqués avec des autorisations EXTERNAL_ACCESS ou UNSAFE peuvent accéder à cette propriété.

Une fois l’objet WindowsIdentity obtenu, les appelants peuvent emprunter l’identité du compte client et effectuer des actions en leur nom.

L’identité de l’appelant est disponible uniquement via SqlContext.WindowsIdentity si le client qui a lancé l’exécution de la procédure stockée ou de la fonction connectée au serveur à l’aide de l’authentification Windows. Si l’authentification SQL Server a été utilisée à la place, cette propriété a la valeur Null et le code ne peut pas emprunter l’identité de l’appelant.

Exemple

L'exemple suivant montre comment obtenir l'identité Windows du client appelant et emprunter l'identité du client.

  • C#
  • Visual Basic .NET
[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;
    }
}