如何从claimprincipal中删除claimidentity

本文关键字:删除 claimidentity claimprincipal | 更新日期: 2023-09-27 18:12:36

我有一个内置在ASP的HR web应用程序。Net MVC拆分为多个区域,例如Manager, Employee。这些区域表示系统中能够执行不同任务的不同类型的用户。这涉及到一个遗留数据库,每种用户类型的信息存储在不同的表中。此外,为每种用户类型存储的信息类型是不同的,因此将表分开是有意义的。

我希望实现基于声明的身份验证,原因有两个:一,它将更容易在客户端存储每个用户的详细信息,如用户名、角色等。另一个原因是claimprincipal支持多个身份。这一点很重要,因为在某些情况下,一个人可能需要同时以多个身份访问系统。如。管理员需要访问系统来执行管理任务,但是管理员也恰好是雇员,应该能够以雇员身份登录系统。每个区域都是分开处理的,因此,即使用户既是经理又是雇员,他们也必须分别登录到每个区域。

所以我的问题是:通过claimprincipal实现多个身份是可行的吗?还有其他我忽略的技巧吗?如果要使用多个身份,我如何将用户从一个区域注销,但如果他们碰巧同时登录到另一个区域,如何保持他们登录到另一个区域?通常,要注销,代码看起来像这样:

FederatedAuthentication.SessionAuthenticationModule.SignOut();

我的假设是这将使用户退出两个区域。这是正确的吗?假设是这种情况,我认为我可以简单地从claimsprinprincipal中删除特定的Identity,然后重置并写入SessionSecurityToken,但是claimsprinprincipal没有删除方法,只有AddIdentity。所以我想出了下面的伪代码:

注销时:

  • Count claimprincipal中标识的个数
  • 如果count == 1正常退出
  • 如果count> 1,因为我们不能删除一个身份,循环遍历这些身份并创建一个新的claimsprinprincipal,它不包括我们想要注销的身份,然后重置并写入SessionSecurityToken

我讲对了吗?有没有一些如何在claimprincipal中实现多个身份的好例子?我搜索了一下,虽然我找到了关于多重身份的简短提及,但我没有找到实际的例子。

如何从claimprincipal中删除claimidentity

建议:在您的特殊情况下,我们可以使用两个claimprincipal对象来处理两个不同的ClaimsIdentity。

            var claims1 = new List<Claim>
            {
                new Claim(ClaimTypes.Name, "Louise")
               , new Claim(ClaimTypes.Role, "Manager")
            };
            ClaimsIdentity claimsIdentity1 = new ClaimsIdentity(claims1 ,"XYZ");
            ClaimsPrincipal principal1 = new ClaimsPrincipal(claimsIdentity1);
            var claims2 = new List<Claim>
            {
                new Claim(ClaimTypes.Name, "Louise")
               , new Claim(ClaimTypes.Role, "Employee")
            };
            ClaimsIdentity claimsIdentity2 = new ClaimsIdentity(claims2 ,"XYZ");
            ClaimsPrincipal principal2 = new ClaimsPrincipal(claimsIdentity2);

感觉你的问题可能是人为的:

每个区域被单独处理,因此即使用户既是经理又是雇员,他们也必须分别登录到每个区域。

驱动这种分离的需求是什么?这是问题的关键,修复这个问题可能比试图为单个用户提供多个身份的可行解决方案更容易。


回答您的直接问题,不,您不能从主体中删除标识。您只能创建一个新的主体,并用您需要的声明集替换现有的主体。

Thread.CurrentPrincipal = new ClaimsPrincipal(...);

如果您根据现有主体的身份或声明构建主体,则可以过滤掉想要删除的主体。


基于声明的身份验证的基本思想是将身份验证机制与授权机制分开。当您需要知道用户的身份时,您可以验证。当您授权时,您使用与用户关联的声明来执行访问控制决策,例如允许他们进入系统的管理区域。

用户的身份应该是他们在系统上下文中的身份。在大多数系统中,用户将具有单一身份。出于技术原因,拥有多个身份可能是有用的,例如允许用户将单个身份验证与多个可更改的身份相关联的系统,但通常情况下,如果每个用户具有单个身份,则系统最简单,因为现实情况是只有单个用户通常向您提供单个身份。

我只能想到一个用户使用多个身份登录系统的合法原因:用户希望使用多个身份来分离他们的活动,例如工作帐户和个人帐户。

您的系统应该能够使用单个身份验证。如果您的经理需要通过额外的身份验证步骤才能访问管理部分,不要尝试删除他们现有的身份—而是使用提升系统执行身份验证,并将身份添加到他们现有的主体中。用户没有更改,您只是获得了与他们相关的更多声明。