我有一个使用Windows身份验证的ASP.NET MVC5 CRUD应用程序,该站点由Active Directory组保护,该组中的所有成员具有相同的权限。我正在使用Entity Framework 6来访问数据库。
我目前有一个非常基本的User
模型,其中Login
为DOMAIN\username
。我的所有模型都通过CreatedByUserId
属性引用此模型,我省略了与下面其他模型的关系。
public class User
{
[DatabaseGenerated(DatabaseGeneratedOption.Identity)]
public int Id { get; set; }
[Index(IsUnique = true)]
[MaxLength(100)]
public string Login { get; set; }
[DatabaseGenerated(DatabaseGeneratedOption.Computed)]
public DateTime CreatedDatetime { get; set; }
}
我希望能够实现两件事虽然我不确定如何不在所有控制器中重复代码:
CreatedByUserId
会填充Id
执行操作的User
。我相信第一部分可以通过全局AuthorizeAttribute
过滤器实现,如果它们不存在则创建新的User
并在Id
时进行检索,但应该在哪里存储以供将来参考。
我不确定的第二部分,我相信可以在不必根据当前用户查询数据库的情况下执行此操作。可以使用Id
访问网站时检索到的User
通过构造函数设置此值吗?
答案 0 :(得分:0)
自定义Authorize属性听起来不错。您可以验证用户是否已通过身份验证,并检查他们是否是授权组的成员。我建议您不要单独存储他们的ID。他们的身份将在整个申请期间通过
提供 HttpContext.Current.Request.RequestContext.HttpContext.User.Identity.Name
在您的DbContext
中,您可以覆盖SaveChanges()
并访问用户的身份。
这是一个很好的链接,可以帮助您入门Overriding SaveChanges and setting ModifiedDate, but how do I set ModifiedBy?
在您的authorize属性中,您可以执行以下操作:
protected override void OnAuthorization(AuthorizationContext filterContext)
{
// Get user id (create if not exists) using
// filterContext.HttpContext.User.Identity.Name
// Set generic principal using Id
IPrincipal principal = new GenericPrincipal(
new GenericIdentity("myuserid"), new string[] { "myrole" });
HttpContext.Current.User = principal;
}
然后,您可以在旧DOMAIN\Username
值的任何位置访问您的用户ID。
在通过活动目录进行身份验证时要记住的另一点是用户可以并且确实更改了用户名,例如在结婚或离婚时。 AD还有一个唯一的ID(一个Guid)可以用作参考,但是这也可以改变 - 通常在删除和重新创建用户的配置文件时。如果您要维护自己的用户记录,则还应该维护AD ID,并且您的逻辑应该类似于:
按用户名
查询我的用户表按用户名查询AD(将AD ID作为Guid返回)
我的用户存在 - >如果更改,则更新广告ID。返回用户。
我的用户不存在 - >按AD ID
查询我的用户表我的用户存在 - >更新我的用户名。返回用户。
我的用户不存在 - >创建新用户(用户名,广告ID)。返回用户。