SqlContext 对象
适用范围:SQL Server
调用过程或函数时、在公共语言运行时(CLR)用户定义类型上调用方法或操作触发任何 Microsoft .NET Framework 语言中定义的触发器时,会在服务器中调用托管代码。 由于在用户连接过程中需要执行此代码,因此需要从服务器上运行的代码访问调用方的上下文。 此外,某些数据访问操作只有在调用方的上下文中运行时才有效。 例如,访问触发器操作中使用的插入和删除的伪表只在调用方的上下文中有效。
调用方上下文在 SqlContext 对象中抽象化。 有关 SqlTriggerContext 方法和属性的详细信息,请参阅 .NET Framework SDK 中的 Microsoft.SqlServer.Server.SqlTriggerContext 类参考文档。
SqlContext 提供对以下组件的访问:
SqlPipe:SqlPipe 对象表示结果流向客户端的“管道”。 有关 SqlPipe 对象的详细信息,请参阅 SqlPipe 对象。
SqlTriggerContext: 只能从 CLR 触发器中检索 SqlTriggerContext 对象。 它提供有关导致触发器被激发的操作的信息,以及所更新的列的映射。 有关 SqlTriggerContext 对象的详细信息,请参阅 SqlTriggerContext 对象。
IsAvailable: IsAvailable 属性用于确定上下文可用性。
WindowsIdentity:WindowsIdentity 属性用于检索调用者的 Windows 标识。
确定上下文可用性
查询 SqlContext 类,以查看当前正在执行的代码是否正在进程内运行。 为此,请检查 SqlContext 对象的 IsAvailable 属性。 IsAvailable 属性为只读属性,如果调用代码在 SQL Server 中运行,并且可以访问其他 SqlContext 成员,则返回 True。 如果 IsAvailable 属性返回 False,则所有其他 SqlContext 成员都会引发 InvalidOperationException(如果使用)。 如果 IsAvailable 返回 False,则尝试打开连接字符串中具有“context connection=true”的连接对象失败。
检索 Windows 标识
在 SQL Server 内执行的 CLR 代码始终在进程帐户的上下文中调用。 如果代码应使用调用用户的标识执行某些操作,而不是 SQL Server 进程标识,则应通过 SqlContext 对象的 WindowsIdentity 属性获取模拟令牌。 WindowsIdentity 属性返回一个 WindowsIdentity 实例,该实例表示调用方Microsoft Windows 标识;如果客户端使用 SQL Server 身份验证进行身份验证,则返回 null。 只有标记为 EXTERNAL_ACCESS 或 UNSAFE 权限的程序集才能访问此属性。
获取 WindowsIdentity 对象后,调用方可以模拟客户端帐户并代表其执行操作。
仅当启动执行存储过程或函数的客户端使用 Windows 身份验证连接到服务器的存储过程或函数时,调用方的身份才可通过 SqlContext.WindowsIdentity 使用。 如果改用了 SQL Server 身份验证,则此属性为 null,并且代码无法模拟调用方。
示例
下面的示例说明如何获取调用客户端的 Windows 标识并模拟该客户端。
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
另请参阅
SqlPipe 对象
SqlTriggerContext 对象
CLR 触发器
SQL Server 进程内专用的 ADO.NET 扩展