安全 运行管理和通讯策略
组织策略定义的规则是支配应用程序如何安全,如何管理,不同的应用程序组件是如何和另一组件及外部服务进行通讯的。这些策略会影响应用程序或者服务的每一层的设计,如图3.1所示。
图3.1 应用程序设计方面组织策略的影响
策略不仅是在组织层面决定的,而且它们也可能被组织内所决定。在一些情况下,区域的考虑是有益的—如果共享一个策略的子集,所有的应用程序,服务,甚至应用程序各层都是在同一个区域。例如,面向Internet的数据中心,相对于公司基础结构的其余部分,有不同批量的策略,与应用程序其它部分相比,为指定区域定义了紧密的安全约束。因此,相对于内部交互的应用程序和服务,这个数据中心的应用程序和服务是在不同的区域。理解每个组件策略,因此,定义在区域中执行的策略是决定部署组件在哪里的很重要的因素。
本章内容
本章包含以下章节:
l 设计安全策略
l 设计运行管理策略
l 设计通讯策略
设计安全策略
安全策略是和认证,授权,安全通讯,审核,及侧面管理有关的。如图3.2所示。
图3.2 安全策略方面
一般的安全原则
无论是如何设计安全策略,有一些一般的安全原则都需要考虑,考虑以下的指导:
l 无论是那种可能,对于构建自己的自定义解决方案,应该依赖测试,证明系统安全。使用行业证明算法,技术,提供的平台基础结构,已验证的供应商和支持技术。如果决定自定义安全基础结构的开发,在实现它之前和之后,要把使用的方法和技术经过专家和安全评审组织进行验证。
l 永远不相信外部输入。需要验证通过用户或者其它服务提交的所有数据。
l 假设外部系统是非安全的。如果应用程序接受到外部系统的未加密的敏感数据,要假设信息是要危及到安全。
l 应用最小特权原则。不要赋予服务账户比应用程序需要的最低程度的更多的属性。访问具有最低限度权限需求的资源。
l 缩减外界区域。风险伴随着组件的数量和应用程序暴露的数据数量而增加,所以,仅暴露其它人期望使用的功能。
l 默认一个安全模式。不要赋予不直接需要的服务,帐号权利和技术。当部署应用程序在客户端和服务器计算机上,默认配置将会是安全的。
l 不能依赖不明确的安全。加密数据意味着拥有钥匙和证明加密的算法。安全数据存储将防止所有环境下的访问。混淆字符串,存储信息在未意料到的文件路径等等,都是不安全的。
l 遵守STRIDE原则---STRIDE原则是欺骗(Spoofing),Tampering,Repudiability,信息泄漏(Information disclosure),服务拒绝(Denial of service),特权提升(Elevation of privileges)。 一个系统必须依靠这些安全攻击分类来保护自身。有关STRIDE更多的信息,见MSDN上的“Designing for Securability”(http://msdn.microsoft.com/library/default.asp?url=/library/en-us/vsent7/html/vxcondesigningforsecurability.asp。)
l “在关口检查。”在审核用户的第一个地方之外,不要让过程前进的更深。
l 顺着内部和外部锁定系统:内部用户和操作者至少比外部黑客有更大的风险。
认证
认证是作为安全识别来定义的,基本含义是,拥有一个安全识别用户的机制,是适合于应用程序需要的。
认证需要在用户界面层实现,提供授权,审核和个性化能力。这通常包括需要用户输入凭证(如,用户名称和密码)来证明它们的身份。另一个凭证类型包括生态系统读取,智能卡,物理锁,数字证书,等等。
如果应用程序是作为服务暴露,也需要识别某些服务接口,确保参与交换是已知和信任的合作者,其它外部服务不能欺骗应用程序,让它相信正在调用的某些人。
注意:有关更多Microsoft ASP.NET的认证信息,见MSND上的“Authentication in ASP.NET: .NET Security Guidance” (http://msdn.microsoft.com/library/en-us/dnbda/html/authaspdotnet.asp)。
业务逻辑设计的目标是,认证过程是清晰的。例如,在组件方法里有一个额外的参数,仅用于传递用户信息,是个不好的应用。除非业务功能的需要。
身份流转在层之间
某些功能的地方更进一步地说是来源于用户,用户身份逐渐变得不太重要。在基于服务的解决方案中,一些活动甚至不被用户初始化。应该有一个设计目标,减少正在调用的用户的相关性,这个用户来源于很远的用户界面。
遍及应用程序所有层,需要跟踪最原始调用者的身份(用户或者服务)执行授权和审核。这个身份可能是原始调用者(用户或服务)的身份,或者应用程序层的服务账号。跟踪身份,可以使通讯机制跟随安全的上下文环境(例如,在DCOM远程使用Kerveros委托),可以传递标记或者认证票,或者传递用户ID,或者凭证。
考虑以下场景:
l 调用者和被调用的应用程序不能共享平台安全子系统,或者公共的认证机制。在这个场景下,不能够“跟踪”一个已存在的安全上下文环境;需要传递合适的已认证凭证。
l 调用者和被调用的应用程序在Microsoft Windows域中是信任的,或者应用程序执行的是基于Windows身份授权,或者使用Microsoft .NET Enterprise Services角色授权。这样的场景,需要选择一个通讯机制跟踪Kerberos票,或者NTLM票。DCOM-RPC提供这样的能力。使用通道提供的信息,可以基于授权信息重新创建自定义主要的,匹配它的线程。记住,NTLM票仅用于认证的网络上下活动(hop);Kerberos委托计算机,用户和域层面的需要策略。更多的信息,见本章后面的“设计通讯策略”,或者下面的文章:
- “Windows 2000 Kerberos Delegation” (http://www.microsoft.com/technet/treeview/default.asp?url=/TechNet/prodtechnol/windows2000serv/deploy/kerberos.asp)。
- “Impersonating and Reverting” (http://msdn.microsoft.com/library/default.asp?url=/library/en-us/cpguide/html/cpconimpersonatingreverting.asp)。
l 调用者和被调用的应用程序共享一个非Windows认证机制,如单点登录的解决方案,或者认证用户的集中式Web服务。这样的场景,跟踪被认证服务提供的票据。传递这些票据在主区域之外(out-of-band)机制上(不是功能参数),如SOAP头。当介入一个有效的标记时,认证机制应该识别用户;这意味着它认证的标记和原始的计算机没有密切关系。也必须保证没有被Window在第一时间进行充分的认证,特别是长期运行的事务。标记经常产生于用于凭证的哈希(hash)和一个混淆值(a salt value)。混淆值(a salt value)的更多信息,见MSDN得安全术语表(http://msdn.microsoft.com/library/default.asp?url=/library/en-us/security/Security/s_gly.asp)。
l 调用者和被调用的应用程序运行在相同的上下文环境中。这种情况下,Microsoft .NET进行的调用,保存现有的CurrentPrincipal对象在线程中。同一个应用程序域中,所有活动和基于Enterprise Service激活类库的应用程序,都是这样的情形。
其它服务的认证
在一个特定用户的一边,应用程序可能需要调用不同的服务。为一批服务或者数据存储,后端单点登录结构映射一个特定用户的标记或者凭证。例如,一个名叫“Bob”的用户被应用程序认证,且作为“Bobby”登录,访问一个遗留下来的数据存储。设计访问其它数据存储和服务的应用程序或者服务,建议使用服务账号(例如,“SaleApplication”),而不是模拟原始用户;严格的安全要求通过组织的欺骗可以防止这个选择。账户映射特征的开发是个复杂的,特别是需要管理凭证,因此用户账户必须保持同步。然而,一些账户映射机制,如映射客户端凭证到Windows账户,使用IIS,用起来非常有效。
如果在自己的代码中需要模拟用户账户,当前进程需要能够调用登录用户,在Windows 2000中,这需要进程用户账户具有“充当操作系统的一部分“特权。这个是非常有力度的特权,如果进程是危及安全的,会引起严重的风险。对于特别的情况,基于ASP.NET或者Enterprise Service的应用程序的身份,不建议使用这个特权。
自定义认证机制
如果证明不能平衡提供的平台和第三方的认证机制,就需要一个自定义认证机制。使用自定义认证机制,包括能够存储用户账户在某处,有一个算法检查应用的凭证是否是被系统认证过的。当实现自己的用户认证时,考虑以下的指导原则:
l 用一个自定义身份对象中实现用户认证。必须有一个构造器,获得用户凭证和设置内部身份标识(IIdentity.IsAuthentication),这个标识依赖于认证结果。也可以有一个构造器获取一个认证标记。
l 不要存储用户密码。可代替的,存储在数据库中插入混淆值的用户凭证的哈希(hash)。当认证时,应用相同的算法给被用户应用的凭证---如果结果字符串匹配你已存储在数据库中的字符串,用户就可以应用正确的凭证。
l 审计已失败的认证企图。
l 当仅想确保应用程序程序集可以创建和调用身份对象时,给方法增加StrongNameIdentityPermission(强命名身份权限)属性。
l 作为身份对象的一个属性暴露认证标记。身份标记是一个哈希(hash),包括用户名称和其它数据。如果想限制在别处使用,就包括来源数据(如,计算机名称和正在调用的程序集)。限制标记的有效性,是时间的某些片断,可以增加时间戳到哈希值中。哈希的复杂性和加密术将依赖于拥有危机安全标记的风险程度。
表现层的认证
如果应用程序需要执行授权,审核,或者个性化,用户界面组件需要认证用户。更广泛的认证机制是对基于WEB的用户界面是有效的。选择一个正确的场景,见MSDN上的“Authentication In ASP.NET:.NET安全指导原则” (http://msdn.microsoft.com/library/en-us/dnbda/html/authaspdotnet.asp)。基于ASP.NET应用程序在Global.asax的OnAuthenticate事件中设置当前的委托。
基于桌面的用户界面通常也依赖于自定义认证机制(应用程序提交用户名称和密码到这里),或者它们认证它们的Windows登录用户。如果使用一个自定义认证机制,需要实现自己的用户界面,允许用登录,并设置正确的委托到主线程和应用程序创建的每个线程。
用户处理组件不执行认证;他们依赖于上面描述的安全上下文环境(例如,ASP.NET应用程序的OnAuthenticate事件)。
用户处理组件运行在和用户界面一样的用户上下文环境,以便所有的认证任务委托给用户界面,或者展现的基础结构。例如,IIS中,ASP.NET的任何一个ASPX页面请求,都需要认证凭证,或者ASP.NET重导向到认证页面的窗体。对于任何用户处理层,这是个很明确的操作,且没有中断状态流,甚至在一个以认证的会话终止且需要重新恢复。
业务组件的认证
业务组件必须认证调用者,或者委托认证到服务接口。调用者可以是多种类型,如:
l 用户界面组件。
l 用户处理组件
l 业务工作流(例如,Microsoft BizTalk Server XLANG进程)。
l 其它业务处理组件
调用者的身份可能是:
l 参与用户。
l 代表应用程序或者外部系统运行时身份的服务账户。例如,认证一个来自WEB 用户界面层的调用。
l 拥有特定“服务账户”的外部合作者。
如果业务组件认证调用者,需要考虑前面调用者身份如何别认证,和它们是如何影响授权。
数据访问组件的认证
设计的数据访问组件,是被应用程序或者服务的其它组件使用的。它们通常下不打算让脚本或者其它应用程序调用,所以,它们的安全设计依赖于调用者的安全环境(线程的委托(Principal)对象),或者远程策略的认证机制。
数据访问组件可以用两种主要的方法认证数据库:
l 使用服务账号。
l 模拟调用者。
这种情况下,使用一个或者一批有限的服务账户,代表角色或者用户类型。在大多数情况下,仅需要一个服务账户,但是,如果在认证上需要更细致的控制,可以使用多个。例如,在订单处理应用程序中,可以作为“订单应用程序”访问数据库,或者,选择作为“订单处理管理者”或者“订单订购应用程序”登录,这些要依赖于调用者的身份。
在以下情况下,使用服务账号:
l 从原始调用者的扮演者的环境中连接到基本的数据源,是无效时(例如,BizTalk Server)。
l 登录到其它系统的账号有非常小的变化(例如,登录到关系数据库管理系统,该系统是被数据库管理员严格的管理着)。
l 对于应用程序的其它部分,访问的数据存储有不同的认证机制(例如,通过Internet登录到Web服务)。
l 通过大量的账户访问数据存储,不使用连接池,因此,降低性能和可度量性。
在以下情况下,不使用服务账号:
l 没有一个存储的安全方法和维护服务凭证。
l 由于安全策略,使用特定的用户资源访问数据存储(例如,需要访问Microsoft SQL Server中的数据或者对象)。
l 数据存储审核活动,这些审核需要映射到个别用户。
在使用批量帐号映射一个一个的应用程序的用户基础上访问数据存储时,需要模拟调用者。例如,假设,“Joe”登录到应用程序,数据访问组件访问数据库,如果用Joe的凭证登录到数据,就是正在模拟Joe。
在以下情况,需要调用者模拟:
l 数据存储执行的认证时基于登录用户。
l 数据存储需要审核每个个别的终端用户的活动。
一般有两个实现机制用于模拟调用者:
l 平台模拟服务。Windows 2000和后期版本提供用户模拟,通过Kerveros穿过网络。这意味着,如果Joe访问你的Web应用程序,你已经使用Windows认证,就可以模拟Joe穿过网络的所有途径到达你的数据库。
只要你拥有同样的横穿网络所以途径的认证机制,或者一个兼容标准的认证机制(如,Kerberos),模拟化一般都是支持的。
在Windows 2000中,提供横穿多个网络跳转的模拟平台,叫做“委托”。域,计算机,和用户账户需要被赋予给委托的能够委托完全环境。Windows .NET服务提供“约束委托”,增加更多管理的灵活性。
l 后端单点登录方案。后端单点登录机制会提供给你凭证(例如,用户名和密码),这个凭证是用户登录到数据源,你提供给他们已经被其它机制认证过的证据。这个类型的方法构成了一个“弱模拟”,一般,因为它不需要比一次合理的跳转更多的映射。
从分布式应用程序连接到SQL Server的指南,将MSDN上的“.NET Data Access Architecture Guide” (http://msdn.microsoft.com/library/default.asp?url=/library/en-us/dnbda/html/daag.asp)。
注意:在服务代理中实现认证,考虑的是与上面描述的数据访问组件是相似的。
业务实体组件的认证
有时,业务实体组件适合作为SDK自定义开发,或者来源于客户端的脚本或者Microsoft Visual Basic开发系统为应用程序提供的对象模型。
如果业务实体不会被其它应用程序组件或自定义脚本使用,它们不需要介入认证边界。这种情况下,它们要依赖认证的当前安全环境(附着在当前线程的Principal对象)。
如果打算暴露业务实体允许自定义脚本,或者其他应用程序使用,必须提供一个额外的组件帮助客户端从代码中“登录”,通过这些对象设置不依赖于平台机制的安全环境的需要。如果业务实体不需要被模拟的机制调用,不用设计业务实体依赖于参与的用户的Windows安全环境。