设计程序集

适用范围:SQL Server

本文介绍在设计程序集时应考虑的以下因素:

  • 打包程序集
  • 管理程序集安全性
  • 对程序集的限制

包程序集

程序集可以包含多个 SQL Server 例程的功能,或在其类和方法中键入。 在大部分时间里,打包在同一程序集中执行相关函数的例程的功能才有意义,如果这些例程共享相互调用方法的类,则尤为如此。 例如,可以将执行公共语言运行时 (CLR) 触发器和 CLR 存储过程的数据项管理任务的类在同一程序集中打包。 这是因为这些类的方法比不太相关的任务的方法更可能相互调用。

将代码打包到程序集时,请考虑:

  • 依赖于 CLR 用户定义函数的 CLR 用户定义类型和索引可以导致持久化数据存在于依赖程序集的数据库中。 当存在依赖于数据库中程序集的持久化数据时,修改程序集的代码通常更为复杂。 因此,最好将持久化数据依赖项依赖的代码(例如使用用户定义的函数的用户定义类型和索引)与没有这些持久化数据依赖项的代码分开。 有关详细信息,请参阅实现程序集ALTER ASSEMBLY (Transact-SQL)。

  • 如果一段托管代码需要更高的权限,最好将该代码与不需要更高权限的代码分开到单独的程序集中。

管理程序集安全性

当程序集运行托管代码时,可以控制程序集访问受 .NET 代码访问安全性保护的资源的程度。 创建或修改程序集时,可以通过指定三个权限集之一来执行此操作:SAFEEXTERNAL_ACCESSUNSAFE

SAFE 权限

SAFE 是默认权限集,是限制最大的权限集。 具有 SAFE 权限的程序集运行的代码无法访问外部系统资源,例如文件、网络、环境变量或注册表。 SAFE 代码可以从本地 SQL Server 数据库访问数据,或者执行不涉及访问本地数据库外部资源的计算和业务逻辑。

大多数程序集执行计算和数据管理任务,而无需访问 SQL Server 外部的资源。 因此,我们建议 SAFE 作为程序集权限集。

EXTERNAL_ACCESS权限

EXTERNAL_ACCESS 允许程序集访问某些外部系统资源,例如文件、网络、Web 服务、环境变量和注册表。 只有具有权限的 EXTERNAL ACCESS SQL Server 登录名才能创建 EXTERNAL_ACCESS 程序集。

SAFE 和 EXTERNAL_ACCESS 程序集只能包含可验证类型安全的代码。 这意味着这些程序集仅可以通过对类型定义有效的具有定义完善的入口点来访问类。 因此,它们不能随意访问代码不拥有的内存缓冲区。 此外,它们无法执行可能对 SQL Server 进程的可靠性产生不利影响的操作。

UNSAFE 权限

UNSAFE 为程序集提供对 SQL Server 内外资源的无限制访问。 从程序集内 UNSAFE 运行的代码可以调用非托管代码。

此外,指定 UNSAFE 允许程序集中的代码执行 CLR 验证程序认为类型不安全的操作。 这些操作可能以不受控制的方式访问 SQL Server 进程空间中的内存缓冲区。 UNSAFE 程序集还可能会颠覆 SQL Server 或公共语言运行时的安全系统。 有经验的开发人员或管理员应仅向高度可信的程序集授予 UNSAFE 权限。 只有 sysadmin 固定服务器角色的成员才能创建UNSAFE程序集。

对程序集的限制

SQL Server 对程序集中的托管代码施加了某些限制,以确保它们能够以可靠且可缩放的方式运行。 这意味着在 SAFE 和 EXTERNAL_ACCESS 程序集中不允许某些可能损害服务器稳定性的操作。

不允许的自定义属性

程序集不能使用以下自定义属性进行批注:

System.ContextStaticAttribute
System.MTAThreadAttribute
System.Runtime.CompilerServices.MethodImplAttribute
System.Runtime.CompilerServices.CompilationRelaxationsAttribute
System.Runtime.Remoting.Contexts.ContextAttribute
System.Runtime.Remoting.Contexts.SynchronizationAttribute
System.Runtime.InteropServices.DllImportAttribute
System.Security.Permissions.CodeAccessSecurityAttribute
System.STAThreadAttribute
System.ThreadStaticAttribute

此外, SAFE EXTERNAL_ACCESS 不能使用以下自定义属性对程序集进行批注:

System.Security.SuppressUnmanagedCodeSecurityAttribute
System.Security.UnverifiableCodeAttribute

禁止的 .NET Framework API

任何使用不允许HostProtectionAttributes的 .NET Framework API 进行批注的 Microsoft .NET Framework API 都无法从SAFE程序集调用。EXTERNAL_ACCESS

eSelfAffectingProcessMgmt
eSelfAffectingThreading
eSynchronization
eSharedState
eExternalProcessMgmt
eExternalThreading
eSecurityInfrastructure
eMayLeakOnAbort
eUI

支持的 .NET Framework 程序集

自定义程序集引用的任何程序集都必须使用 CREATE ASSEMBLY 加载到 SQL Server 中。 以下 .NET Framework 程序集已加载到 SQL Server 中,因此,自定义程序集可以引用,而无需使用 CREATE ASSEMBLY

  • CustomMarshalers.dll
  • Microsoft.VisualBasic.dll
  • Microsoft.VisualC.dll
  • mscorlib.dll
  • System.dll
  • System.Configuration.dll
  • System.Core.dll
  • System.Data.dll
  • System.Data.OracleClient.dll
  • System.Data.SqlXml.dll
  • System.Deployment.dll
  • System.Security.dll
  • System.Transactions.dll
  • System.Web.Services.dll
  • system.Xml.dll
  • System.Xml.Linq.dll